Search This Blog

Friday 26 December 2014

Saturday 11 October 2014

Create First Custom Service In Microsoft Dynamics AX 2012

There is very good blog available for creating the Custom Services in Microsoft Dynamics 2012.

http://sumitsaxfactor.wordpress.com/2012/05/19/create-your-first-custom-service-ax-2012/


One thing I just wanted to mention here that is not given in this blog is:

While consuming your newly created service outside AX in your C# or any other code you need to specify the company name in which your x++ service code will execute.

if just pass the code as mention in above blog post i.e

string[] custIds = servClient.retrieveCustomerNames(new SamCustomAXService.CallContext(), strItem);  

than your code will run in dat company which by default set in AX and it contains no data therefore it will not return any data which you want.

To run your x++ service code in your specified company than you have to create the object of call context and in that object specify your company. You can see the below code for reference.

In my case I have specified the ceu company.

 mzkCustomerService.CallContext context = new mzkCustomerService.CallContext { Company = "ceu" }; 

and than pass this context object in your code as below:

string[] custIds = servClient.retrieveCustomerNames(context, strItem);  
 

This was all related to the Custom Services.

Thanks

Muhammad Zahid.

Friday 26 September 2014

Calling menu item through code with arguments in Microsoft Dynamics AX 2012

Below is the code for calling the menuitem with arguments:

MenuFunction menuFunction;
Args args = new Args();
args.record(CustTable);
menuFunction = new MenuFunction(menuitemDisplayStr(MzkCopyCustomer),MenuItemType::Display);
menuFunction.run(args);

Thanks

Muhammad Zahid.
 

Thursday 25 September 2014

Remove Dynalinks Between Forms in Microsoft Dynamics AX 2012

Some times when we open the child form from another form than the datasource of the child form is sync with the previous form this is due to the dynalink between these two forms and all the data is shown on the child form.

you can use the below code on the init method of the child form after the super() to remove the dynalink between these two forms.

DataArea_DS.query().dataSourceTable(tableNum(DataArea)).clearDynalinks();
UserDataReaFilter_DS.query().dataSourceTable(tableNum(UserDataAreaFilter)).clearDynalinks();

The above two datasources are the datasources of the child form.

For info related to the dynalink you refer to the below link.

http://dynamicsuser.net/forums/p/40062/205388.aspx

Thanks

Muhammad Zahid

Select Marked Records From Grid in Dynamics AX 2012

Below is the Form in which I have selected the three records from the Grid:











Below is the code getting the selected records on the close ok method.

DataArea dataArea1;

dataArea1 = DataArea_DS.getFirst(1);
while(dataArea1.RecId != 0)
{
     info(strFmt('%1,%2',dataArea1.id,dataArea1.name));

    dataArea1 = DataArea_DS.getNext();
}

Below is the result after pressing the ok button on the form.

The records that we have selected will be printed.




















This was all related to this.

Thanks

Muhammad Zahid.

Show or Hide The CheckBoxes On Grid

To show or hide the checkboxes on grid on form you have to set the property "ShowRowLabels" of the Grid.

if the the property ShowRowLabels = yes.Than form grid will look like this:

 


















if the the property ShowRowLabels = no.Than form grid will look like this:




















Thanks

Muhammad Zahid.

Getting the DataSource of the Caller Form

I was working on scenario in which there another form is open from one form and I need to get the datasource from the caller form in my new form.

The code to get the datasource of the caller form is:

CustTable = custTable;

if(element.args().record().TableId == tablenum(CustTable))
{
    custTable = element.args().record();
}


Thanks

Muhammad Zahid.


Friday 29 August 2014

Convert Currency based on the Exchange Rates in Microsoft Dynamics AX 2012

In Microsoft Dynamics there is a method available for converting the amount from one currency to another based on the exchange rates.

The method that I am talking about is curPrice2CurPrice method in Currency table.

Below is the code of this method








You have to pass the price and the old currency in which the price actually is and the new currency in which you are converting the price.

Same method is implemented on Purchase Order Form.You can see the existing behavior if you have R2 installed.Just create new purchase order and than create some purchase order lines in it and than in the purchase order header tab change the currency.

After changing the currency the unit price in the purchase order line will convert based on the currency that you have selected.

You can see the below images before and after changing the currency on purchase order.

 Before changing the currency:

  
After changing the currency:

You can also see the exchange rates on the below navigation path:

GL --> Setup --> Exchange rate type --> Set Default --> check currency for which you need to check the exchange rate for

This was related to the currency and exchange rates.
I hope you like it :)

Thanks

Muhammad Zahid.

Wednesday 23 July 2014

Export to Excel: The number of arguments provided is different from the number of arguments accepted by the method.

I was working on excel based reports was getting the following error:

"The number of arguments provided is different from the number of arguments accepted by the method."

After debugging I found out that when I going to insert the text in excel this error was generating.

the code that was reproducing this error is:

cell.value("my text");

The best solution to get rid of this error is that we should open our workbook for very less amount of time.We should first complete all of our calculations and than open the workbook and  insert the records in excel sheet. 

If the issue is not resolve by applying the above workaround than there are also some other solutions available you can see on the below link:  



I hope you like this post.

Thanks

Muhammad Zahid.





Wednesday 25 June 2014

Export to Excel change cell format to percentage format in Microsoft Dynamics AX 2012

Below is the code snippet to change the cell format to percentage format.

cells.range("D21:D30").numberFormat("0.00%");

Below is the link for more info on excel cells format.

http://www.teachexcel.com/free-excel-macros/m-72,Format-Cells-as-a-Percentage-in-Excel-Number-Formatting.html


Thanks

Muhammad Zahid.

Export to Excel in Microsoft Dynamics AX 2012

Below is the sample code snippet to export the data from Microsoft Dynamics AX to Excel.

Example no 1:

            SysExcelWorkbooks workbooks;
            SysExcelWorkbook workbook;
            SysExcelWorksheets worksheets;
            SysExcelWorksheet worksheet;
            SysExcelCells cells;
            SysExcelCell cell;
   
            application = SysExcelApplication::construct();
            workbooks = application.workbooks();
            workbook = workbooks.add();
            worksheets = workbook.worksheets();
            worksheet = worksheets.itemFromNum(1);
            cells = worksheet.cells();
           
            cell = cells.item(row, col);
       
            cell.value("sample Code");
           
            worksheet.columns().autoFit(); //use to autofit the columns of the excel sheet
       
            application.visible(true);

IF you want to print some Headings in Bold format and in more than one cell:

Example No 2:

             fontSizeRange   = #B+int2str(2)+","+#C+int2str(2);
             mergeCellsRange = #B+int2str(2)+":"+#C+int2str(2);
       
             this.insertValue(row,col,"Project Comparison Budget VS               Actual",true,fontSizeRange,13,true,mergeCellsRange,false,0);
           
             public void insertValue(int         _row,
                                int         _col,
                                anytype     _value,
                               boolean     _isFontBold = false,
                                str         _fontSizeRange = "",
                                int         _fontSizeWeight = 11,
                                boolean     _isMergeCell = false,
                                str         _mergeRange = "",
                                boolean     _allignment  = false,
                                int         _allignmentType = #xlLeft)
            {
       
                cell = this.parmCells().item(_row, _col);
                cell.value(_value);
       
                if (_isFontBold)
                {
                    font = cell.font();
                    font.bold(_isFontBold);
                }
                if (_fontSizeRange != "")
                {
                    worksheetCOM    = this.parmWorksheet().comObject();
                    rangeCOM        = worksheetCOM.Range(_fontSizeRange);
                    fontCOM         = rangeCOM.Font();
                    fontCOM.Size(_fontSizeWeight);
                }
                if (_isMergeCell)
                {
                    range = this.parmCells().range(_mergeRange);
                    range.comObject().MergeCells(1);
                }
                if (_allignment)
                {
                    if (_isMergeCell)
                    {
                        range.horizontalAlignment(_allignmentType);
                    }
                    else
                    {
                        cellCOM =  cell.comObject();
                        range = this.parmCells().range(cellCOM.address()+":"+cellCOM.address());
                        range.horizontalAlignment(_allignmentType);
                    }
                }
            }

This was all related to the export to excel.

If you have any query related to export to excel than feel free to comment.


Thanks

Muhammad Zahid



SSRS Reports Range Bar Chart Show Start and End Date Only

Below are the steps to show the start and end date only in a range bar chart in SSRS reports.

First of all just select the Horizontal Axis of the chart as you can see this in the below image.










Now right click this horizontal axis and than select axis properties.

A new window will open select the first tab i.e Axis Options.As you can see this window in the below image.


As you can see in the above image in the minimum text box select the startdate and in the maximum text box select the end date and in the interval write the expression i.e

=datediff("d", Fields!PSASchedStart.Value, Fields!PSASchedEnd.Value)

after that click ok and than save the report.

After running the report you will see that you can only see the start and end dates in the range bar chart as you can see in the below image.









This was all related to the range bar chart showing the start and end date only.

Below is the link for more information

http://stackoverflow.com/questions/18004792/ssrs-chart-x-axis-show-start-and-end-date-only

If you have any issues feel free to comment on this.

Thanks

Muhammad Zahid.

SSRS Reports Hide Duplicate Records and White Spaces

Some times while working on SSRS reports there are some duplicate records issue occurs.

Like you can see this in the below image.











Now to remove the duplicate records just right click the table and than select properties and than set the hidden property to:

=Fields!ActivityNumber.Value = Previous(Fields!ActivityNumber.value)

AS you can see the property in the below image:








Now after setting this property the data on the report looks like this:








In the above image the duplicate  record is hidden but the issue is that there are some white spaces left between the rows.

Two resolve this issue we have to remove the expression from the hidden property of the table.
And than  select the row and than right click select row group and than select the group properties as you can see this in the below image














After selecting the group properties now select  select visibility and than add the expression that we have added above in the hidden property i.e

=Fields!ActivityNumber.Value = Previous(Fields!ActivityNumber.value)

As you can see this in the below image.



  



Now after doing that the duplicate records will be remove and also the white spaces between the rows will be remove as you can see that in the below image.







The above example that I have given is related to hiding row based on single column.If you want to hide the records based on two or more columns that you can use the below expression.

=(Fields!Voucher.Value = Previous(Fields!Voucher.Value)) And (Fields!AccountNum.Value = Previous(Fields!AccountNum.Value))

The above expression means that if the voucher and the AccountNum both are repeating than report short hide the row.

This was all related to the duplicate records and white spaces.
Below are some more links related to this.

http://glutenfreesql.wordpress.com/2012/10/02/ssrs-hide-duplicates/

http://stackoverflow.com/questions/11562043/trying-to-get-rid-of-white-space-in-ssrs-report

http://dba.stackexchange.com/questions/53727/how-to-hide-rows-in-ssrs-report


If you have any questions related to that than feel free to comment on this.


Thanks

Muhammad Zahid.

Tuesday 3 June 2014

Microsoft Dynamics AX 2012: Uploading data from Excel into our Dynamics Ax table.



In that post I will show you example on how can we import data from excel and than map it on your AX table.

I have created an excel sheet in which I have added some data as you can see this in the image below.

After that I will import that the data into my AX table.






The staging table that I have created on which I will map the Excel data can be seen in the below image.


















Now I will show you the process of Importing this Data into our AX tables.

I have just created a class.In the main method of that class I am calling another method and passing path of my excel sheet as a parameter.

You can see that method in the below image.






Now inside the method ImportData() there is a process written which gets the data from excel cells and than map them into the Ax tables.

You can see the code snippet for that method below.

public void ImportData
(Filename _fileName)
{
    SysExcelApplication     application;
    SysExcelWorkbooks       workbooks;
    SysExcelWorkbook        workbook;
    SysExcelWorksheets      worksheets;
    SysExcelWorksheet       worksheet;
    SysExcelCells           cells;
    COMVariantType          type;
    int                     row ;
    Zahidtable lineImport;
    str offsetType;
    str account;
    str offsetAccount;
    str transactionType;

    application = SysExcelApplication::construct();
    workbooks = application.workbooks();



    try
    {
        workbooks.open(_fileName,0,true);
    }
    catch (Exception::Error)
    {
        throw error('@SYS19358');
    }

    workbook = workbooks.item(1);
    worksheets = workbook.worksheets();
    worksheet = worksheets.itemFromNum(1);
    cells = worksheet.cells();

    row = 2;

    lineImport.clear();

    startLengthyOperation();
    do
    {
        row++;

        try
        {
            lineImport.clear();

            transactionType = this.VarientConversionMethod(cells.item(row, 8).value());

            //For acquisition
            if(transactionType == "Acquisition")
            {
                lineImport.TransType = AssetTransTypeJournal::Acquisition;
                account = this.VarientConversionMethod(cells.item(row, 1).value());
                lineImport.Account = account;
                lineImport.LedgerDimension =       AxdDimensionUtil::getMultiTypeDefaultAccountId(129,                LedgerJournalACType::FixedAssets, [account]);
                lineImport.txt = this.VarientConversionMethod(cells.item(row ,2).value());
                lineImport.AmountCurDebit = this.VarientConversionMethod(cells.item(row, 3).value());
                offsetType = this.VarientConversionMethod(cells.item(row, 4).value());
                offsetAccount = this.VarientConversionMethod(cells.item(row, 5).value());
                lineImport.BookId = this.VarientConversionMethod(cells.item(row, 6).value());
                lineImport.AssetBookId = this.VarientConversionMethod(cells.item(row, 7).value());
            }

            if (offsetType == "ledger")
            {
                lineImport.OffsetAccountType = LedgerJournalACType::Ledger;
                lineImport.OffsetLedgerDimension = AxdDimensionUtil::getLedgerAccountId( [offsetAccount, offsetAccount, 0]);
            }

            ttsBegin;
            lineImport.insert();
            ttsCommit;

        }
        catch(Exception::Error)
        {
            info("Error found while importing data from excel");
        }

        type = cells.item(row+1, 1).value().variantType();
    }
    while (type != COMVariantType::VT_EMPTY);

    endLengthyOperation();

}


In the above code. I am basically calling another method i.e VarientConversionMethod(COMVariant _varientValue).

In that method  I am going to type cast the values that I have fetched from the excel based on the fields on the table.

You can see the code of  that method below.

private anytype VarientConversionMethod(COMVariant _varientValue)
{
    str value;
    real value2;
    switch(_varientValue.variantType())
    {
        case COMVariantType::VT_BSTR:
            value = strFmt("%1", _varientValue.bStr());
            break;
        case COMVariantType::VT_DECIMAL, COMVariantType::VT_R4, COMVariantType::VT_R8:
            value = strFmt("%1",_varientValue.double());
            value2 = System.Convert::ToDecimal(value);
            value = System.Convert::ToString(value2);
            if (Global::numOfDec(_varientValue.double()) == 0)
            {
                value = strFmt("%1",real2int(_varientValue.double()));
            }
            break;
        case COMVariantType::VT_I1, COMVariantType::VT_I2, COMVariantType::VT_I4:
            value = strFmt("%1",_varientValue.int());
            break;
        case COMVariantType::VT_UI1, COMVariantType::VT_UI2, COMVariantType::VT_UI4:
            value = strFmt("%1",_varientValue.uLong());
            break;

        case COMVariantType::VT_DATE:
            value = strFmt("%1",_varientValue.date());
            break;
         case COMVariantType::VT_EMPTY:
            value = '';
            break;
        default:
            throw error(strfmt('Unhandled variant type (%1).', _varientValue.variantType()));
    }

    return value;
}

Now I have run that class and I am successfully able to the record inside my table.

You can see the record inside my staging table in the below image.





This was all related to uploading the Data from Excel into our Microsoft Dynamics AX table.

I hope you like that post.

Thanks

Muhammad Zahid.

Thursday 29 May 2014

The Server is unavailable.Check your configuration and network connection and try again.




Some time when we try to open the AX this error message appears.

The reason for this error message is that AOS service is not started on your machine.

Just go to start menu and than search for the services.msc file and than open it and than find Microsoft Dynamics AX object server and right click it and than select start.

As you can see the image of this in the below image.
















Some times this Dynamics AX object server didnt find in  services.msc file.This is due to the reason that service may be hosted on some other machine.

To check on which machine AOS service is installed you can go to the Microsoft Dynamics AX configuration and than select the connection tab you will see the name of the machine on which AOS service is running.

You can see this in the below image.


















This was all related to this error message.I hope it will help in resolving the issue.

If you have any issue feel free to comment on this.

Thanks

Muhammad Zahid

Monday 28 April 2014

AOT Maps in Microsoft Dynamics AX 2012

Maps are basically use to wrap the tables on run time.Some times there are some cases in which the structure of two or more tables is same with difference in their field names.In these kind of cases the field.

The fields of the maps are basically use to map fields of one or more tables.By the help of a maps we can access the fields of one or more tables with different names.

Steps of Creating the Maps:

For showing the implementation of table maps I have just created the two tables.As you can see them  in the below image.

































After that I will create the map on which I will map the fields of the above tables.

Just go to the Data Dictionary -> Maps right click and than select new map.





















Now add fields to this map.As you can see them in the below image.


















Now right click the mapping node and than select the new mapping and than set the name of the table on which you want to map.

As you can see this in the below image.













Now right click the fields inside that mapping and then set them to the fields of the table on which you are mapping.As you can see this in the below image.










Now I have created a job on which I will map a table on this map and than use it.

You can see that job in the below image.












In the above table I have map the studentA table to our map i,e studentcourse at run time and than I have set the fields of that map and than insert them.As you already know that in the above code the studentA table is already mapped to our map that is why after the insert call the data will insert into the studentA table.

My the help of Maps you can perform any operation you want as you do on table.

This was all related to the AOT Maps.

Below are some useful links related to AOT maps.

http://ajstudi0.blogspot.com/2012/10/microsoft-dynamics-ax-maps.html

http://msdn.microsoft.com/en-us/library/bb278211.aspx 





Friday 21 March 2014

Precision Design In SSRS Reports.

I have developed a simple SSRS report using the Precision Design want to share some properties in it.

Below is the image of simple report I have made  using the precision design.









As you can see in the above report that I am showing the total amount against each budget purpose type.

To do this just right click the row and than select the parent group as you can see this in the below image.





After that a new window will open where you have to select the column on which we have to apply the group and also we can select to add the footer row below if we want to show the total.










After doing that a new column will be created.you can delete that if you don't want it.This column is basically showing the field on which we have applied the group by.As you can see this in the below image.





I have deleted that Column.After that on the footer row I am calculating the sum of the amount.I have also added one more column on which I have put some text.

As you can see this in the below image.





Now you can see in the above images there is a background colour and borders around the cells you can do this just by right click the cell and than  select the table box property as you can see this in the below image.








After that a new window will open where you can select the border node to set the border of the of the cell as you can see this in the below image.



















After select the fill node to set the background colour of the cell.As you can see this in the below image.



















In the above image you can also see the alignment option to set the alignment of the cell.

You can also set the border and background color of the all the cells in single just by selecting all the cells and than right click and than select the properties.

As you can see this in the below image.









These are some simple tips related to precision desing in SSRS reporting.

I hope you like it.If you have any question related to them than feel free to comment.

Thanks

Muhammad Zahid.

Friday 14 February 2014

Display Methods in Microsoft Dynamics AX 2012


Display Methods:

Display methods are basically use to show some calculated data on some fields of the forms.

We can write Display methods on table level as well as on form level.

 Below is the example of form which uses the Display Methods.

Just go to Accounts receivable -> Common -> Free text invoices -> All free text invoices

A free text invoice list page will open as you can see this in the image below.








Now after that click on the view distributions button as you can see this in the above image.

A new form will open which contains the fields based on the display method.

You can see this form in the image below.












In the above image the highlighted fields are those fields which are filled from display method.

Now i will show the Display method against the Amount Field and its property.

Below is the image of the Amount field and its property.














Below is the method definition











Below is another image of the field percentage which is also based on the Display Method.


























This was all related to the Display Methods.

Hope you like that post.

Thanks

Muhammad Zahid.

Thursday 30 January 2014

Implementing Workflows in Microsoft Dynamics AX 2012

Implementing Workflows in Microsoft Dynamics AX 2012:

 WorkFlow:

Workflow is basically a business process that defines how a document flows through the system.

Technical Components:

1. Categories.
2. Types.
3. Approvals.
4. Event Handlers.

Categories:

Categories basically defines in which module workflows can be use.

 Types:

Basically types are the templates which shows the options when we create the workflow.Workflow types contains the Approvals and task.Each approval and task have the different node in the AOT.

Approval:

Approval is basically the task on which we have to assign this task to someone who has to approve or reject the document.

Event Handlers:

When you generate your workflow type or workflow task there are classes added to your project on which events are created in which you write your logic to insert record into some tables based on your event.

For example when the workflow approver approves the  document than the approve event is fire and when the owner of the document submits the record than the event is fire and many more events  fire based on the action of the user.In these events we can write our custome logic if we want.


Implementing A Workflow:

First of all just go to the AOT and than select the workflow -> workflowtypes and than right click and than select the workflow type wizard

As you can see this in the below image:




















A new wizard will open as you can see this in the below image.


One thing you have to do before creating the workflow type is you have to create the query first and then menu item of the document i,e your form.



Query is basically for the table which manages actions of your document i.e approve by for example if the document is for the requisition than purchase requisition id.

You can check the existing purch req table and the query named purchreqdocument for the purchase requisition module for verification.















As you can see in the below image i have put the name of the workflowtype and the query name and the document menuitem name.

If you want to run this workflow on the EP than you can also specify the web menuitem.

You can generate the workflow type for rich client or web client or both.

you can see the options in the above image.

Now click next button you will see all the names of the classes menuitems that will be generate as you can see in the below image.


















After clicking the finish button the wizard will generate the workflowtype project.
As you can see this in the below image.

note:Its mandatory to generate incremental CIL after the generation of the workflow type.




















Now we need to create the Workflow Task.

To do this just go to the task node and than right click Add-in and than select the task wizard.

you can see this in the below image.

























A wizard will open exactly as we did before for the workflow type.

You can see this in the below image.


















As you can see in the above image that all the fields are same as we did for the workflow type except few ones.

Workflow document is basically the name of the workflow type that we created earlier.

Now click next.You will see the new screen on which you have to create the task.

These tasks are basically the tasks that workflow app rover have to do like approve i.e complete the workflow or reject the workflow or request to change the app rover of the workflow.

You can see this in the below image.


















Now click next and you will see all the classes that will be going to generate and than click the finish button your project related to the workflow task will be created.

As you can see this in the below image.

Note: Dont forget to generate the incremental CIL after creation of the project




















Now we need to create the Work Flow Approval

Just go to the approval node and than right click -> addsin -> approval wizard

as you can see this in the below image.

























Now wizard will open where you have to do the all the same steps as you did earlier for the creation of the workflow tasks.

note: don't forget to generate the incrimental CIL after the creation of the project.

After the creation of the workflow approval.Now put the workflow approval and workflow tasks to the supported elements of the workflow type.

As you can see this in the below image.















One more thing you have to do is to write the logic for the initialization of the workflow.Like when the submit button is clicked the workflow should get started.

You can see the exisiting purchreqworkflow class for the purchase requisition workflow.

Basically there is an action type menuitem PurchReqSubmitToWorkflow on which class named PurchReqWorkflow is set.when the user submits the document this menuitem (i.e submit button) is clicked and this class is called which initiates the workflow.

There are lot more events available on which you can write your own custom code.

One more thing you have to do while implementing your workflow is that.You have to set the name of your workflow type and the workflow datasource on the property of the form otherwise your workflow will not be going to work.

For example you can see the existing form of the purchase requisition i.e PurchReqTable.
you can see that in the below image.






There is one more thing you have to do in your workflow that thing is that there will be the table which manages the states of the document in that table you have to write the method submit to workflow  and in that method you have to

Now i will show you our newly created workflow on the client side which we can configure and use.

As I have created my workflow for the procurement and sourcing model.

I just go to the CEU/Procurement and sourcing/Setup/Procurement and sourcing workflows.

And than create new workflow you can see your newly created workflow in it.

You can see this in the below image.




























In the above image you can see our newly created workflow.

This was all from my side related to the implementation of the workflows.

In the next post i will show you on how can we use this workflow on client side.

Thanks

Muhammad Zahid