2021-07-16

[AX2009] Update SalesLine Qty by Code

 Update sales line Qty manually. This code also update remain qty in SalesLine tabale and qty in InventTrans table.

static void UpdateSalesLineQty(Args _args)
{
    SalesLine       salesLine;
    ;
    ttsbegin;
    salesLine = SalesLine::findInventTransId('14723621_068', true);
    salesLine.SalesQty = 3;//example
    salesLine.modifiedField(fieldnum(SalesLine, SalesQty));
    InventMovement::bufferSetRemainQty(salesLine);
    salesLine.update();
    ttscommit;
    info("Done");
}

2019-09-12

[AX2012] Get Default Dimension Value and Description

This is a job to show value and description of a default dimension.

static void defaultDimension(Args _args)
{
    PurchLine                           purchLine;
    DimensionAttributeValueSetStorage   dimStorage;
    int                                 counter;
    container                           attribute = ["BusinessUnit", "Department", "ItemGroup"];
    DimensionAttribute                  dimensionAttribute;
    DimensionAttributeValue             dimensionAttributeValue;
    ;
   
    purchLine = PurchLine::findRecId(35637329190);//sample to get default dimension
    dimStorage = DimensionAttributeValueSetStorage::find(purchLine.DefaultDimension);
    //all attribute
    for (counter= 1 ; counter<= dimStorage.elements() ; counter++)
    {
        dimensionAttribute = DimensionAttribute::find(dimStorage.getAttributeByIndex(counter));
        dimensionAttributeValue = DimensionAttributeValue::findByDimensionAttributeAndValue(dimensionAttribute, dimStorage.getDisplayValueByDimensionAttribute(dimensionAttribute.RecId));
        info(strFmt("%1 - %2", dimStorage.getDisplayValueByDimensionAttribute(dimensionAttribute.RecId), dimensionAttributeValue.getName()));
    }
   
    //specific attribute
    for (counter= 1 ; counter<= conLen(attribute) ; counter++)
    {
        dimensionAttribute = DimensionAttribute::findByName(conPeek(attribute, counter));
        dimensionAttributeValue = DimensionAttributeValue::findByDimensionAttributeAndValue(dimensionAttribute, dimStorage.getDisplayValueByDimensionAttribute(dimensionAttribute.RecId));
        info(strFmt("%1 - %2", dimStorage.getDisplayValueByDimensionAttribute(dimensionAttribute.RecId), dimensionAttributeValue.getName()));
    }
}

2019-07-26

[AX 2009] Access Form Control by Code

This is a sample to change formstringcontrol label by code without autodeclaration. Control::GroupPayment_M_paymentDescription is a control id. The control id is formed from Control::+"Control Name".

public void run()
{
    FormStringControl   paymentDesc;

    ;

    paymentDesc = element.control(Control::GroupPayment_M_paymentDescription);
    paymentDesc.label("Payment description");
}


//AX2012
element.control(element.controlId(formControlStr(CustInvoice, GroupPayment_M_paymentDescription))).label("Payment description"); 

Form control type
Class
ActiveX
FormActiveXControl
Animate
FormAnimateControl
Button
FormButtonControl
ButtonGroup
FormButtonGroupControl
CheckBox
FormCheckBoxControl
ComboBox
FormComboBoxControl
CommandButton
FormCommandButtonControl
DateEdit
FormDateControl
Grid
FormGridControl
Group
FormGroupControl
GuidEdit
FormGuidControl
HTML
FormHTMLControl
Int64Edit
FormInt64Control
IntEdit
FormIntControl
ListBox
FormListBoxControl
ListView
FormListControl
MenuItemButton
FormFunctionButtonControl
MenuButton
FormMenuButtonControl
Progress
FormProgressControl
RadioButton
FormRadioControl
RealEdit
FormRealControl
StaticText
FormStaticTextControl
StringEdit
FormStringControl
Tab
FormTabControl
TabPage
FormTabPageControl
Table
FormTableControl
TimeEdit
FormTimeControl
Tree
FormTreeControl
Window
FormWindowControl

2018-12-04

[AX 2012] Create Default SpecQty on Product Receipt Posting Form

Table PurchParameters
PurchUpdate recommendedSpecQty(DocumentStatus _documentStatus)
{
    PurchUpdate specQty;

    switch (_documentStatus)
    {

        case DocumentStatus::Invoice :
            specQty = PurchUpdate::PackingSlip;
            break;
           
        case DocumentStatus::PackingSlip :
            specQty = PurchUpdate::ReceiveNow;
            break;


        default:
            specQty = PurchUpdate::All;
            break;
    }

    return specQty;
}
Form PurchEditLines
        if(PurchParameters::find().PromptQty)
        {
            recommendedQty = purchFormLetter.recommendedSpecQty();
            if(recommendedQty != specQty.selection())
            {
                boxFormOnceIsActive = true;

                if(documentStatus != DocumentStatus::PackingSlip)
                {

                    box = BoxFormOnce::construct();
                    box.parmDialogBoxType(DialogBoxType::YesNoBox);
                    box.parmDialogButton(DialogButton::Yes);
                    box.parmTitle("@SYS59372");
                    box.parmText(strFmt("@SYS102340", salesUpdateEnum.index2Name(specQty.selection()), salesUpdateEnum.index2Name(recommendedQty)));
                    box.parmOwner(new SysDictClass(classIdGet(purchEditLinesForm)).name());
                    if(box.prompt() == DialogButton::Yes)
                    {
                        specQty.selection(recommendedQty);
                        specQty.selectionChange();
                    }
                }
                else
                {
                    specQty.selection(recommendedQty);
                    specQty.selectionChange();
                }


                boxFormOnceIsActive = false;
            }
        }

[AX 2012] Hide Cancel Button on Dialog

void showTotals()
{
    Dialog          dlg = new Dialog("Totals");
    DialogField     rfpAmount;
    DialogField     settlAmount;
    DialogField     totalAmount;
    formBuildCommandButtonControl   cancelButton;
    ;

    rfpAmount = dlg.addFieldValue(extendedTypeStr(Amount), MIORFPTable.TotalReqAmt, "Cash Advance", "Cash Advance");
    rfpAmount.active(false);
    settlAmount = dlg.addFieldValue(extendedTypeStr(Amount), MIORFPSettlementTable.TotalSetAmt, "Actual", "Actual");
    settlAmount.active(false);
    totalAmount = dlg.addFieldValue(extendedTypeStr(Amount), MIORFPTable.TotalReqAmt - MIORFPSettlementTable.TotalSetAmt, "Settle", "Settle");
    totalAmount.active(false);

    dlg.defaultButton(DialogDefaultButton::Ok);
    dlg.alwaysOnTop(true);
    dlg.dialogForm().form().design().left(48, 4);
    dlg.dialogForm().form().design().top(240, 3);

    cancelButton = dlg.dialogForm().control("cancelButton");
    cancelButton.visible(false);

    dlg.run();
}

2018-10-31

[AX2012] Comparing Two Record

To compare the original and updated (dirty) record, use equal method. Do this below method before write the table record.
void modifiedRecord()
{
    ;
    //in not equal, update user or manager update field
    if(!(MIOSQTable.orig().equal(MIOSQTable)) || !(MIOSQVendReply.orig().equal(MIOSQVendReply)))
    {
        if(isUser)
            MIOSQTable.UserUpdate = NoYes::Yes;
        if(isManager)
            MIOSQTable.ManagerUpdate = NoYes::Yes;
    }
}

2018-10-19

[AX2012] Ledger Dimension Description

display Description getLedgerDimensionDesc()
{
    DimensionStorage                        dimensionStorage;
    DimensionStorageSegment                 segment;
    Description                             dimDesc;
    int                                     hierarchyIndex, hierarchyCount;
    int                                     segmentIndex, segmentCount;
    Name                                    segmentName;
    ;

    dimensionStorage = DimensionStorage::findById(this.LedgerDimension);
    if(!dimensionStorage)
        return dimDesc;

    hierarchyCount = dimensionStorage.hierarchyCount();

    for(hierarchyIndex=1; hierarchyIndex<=hierarchyCount; hierarchyIndex++)
    {
        segmentCount = dimensionStorage.segmentCountForHierarchy(hierarchyIndex);
        for(segmentIndex=1; segmentIndex<=segmentCount; segmentIndex++)
        {
            segment = dimensionStorage.getSegmentForHierarchy(hierarchyIndex, segmentIndex);
            if(segment.parmDimensionAttributeValueId()!=0)
            {
                segmentName = segment.getName();
                if(!dimDesc)
                    dimDesc = segmentName;
                else
                    dimDesc += "-"+segmentName;
            }
        }
    }

    return dimDesc;
}

2018-04-25

[AX2009] AX COM Business Connector

This is how to create a connection from C# to Dynamics AX 2009.
Install AxCom.dll
  1. Run  D:\Setup.exe HideUI=1 AcceptLicenseTerms=1 InstallComBusinessConnector=1 if it is failed, find AxCom.dll from installation and copy the file into C:\Program Files (x86)\Microsoft Dynamics AX\50\Client\Bin.
  2. Register AxCom.dll by regSvr32 in command prompt.
Create a Class in AX
  1. Create axCom class.
  2. Create method getName.
Name getName(Name _name)
{
    ;
    return strfmt("-- %1 --",_name);
}
Create a C# Console program (Just a sample) 
  1. Add reference to AxCom.dll, in tab COM, select Axapta Com Connector 1.2 Type Library.
  2. C# code.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using AxaptaCOMConnector;//AX Business Connector

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            Axapta3             ax = new Axapta3();
            IAxaptaObject       axObj;
            string              axName;
            AxaptaParameterList list = new AxaptaParameterList();
            String              name;

            name = "Default Name";
            //axCOM.Logon("CEU", "", "", "");
            ax.LogonAs("axService", "DAX", "axProxy", "DAX", "Password");//log on as AxService user in DAX domain over on proxy user. Add parameters as needed.
            axObj = ax.CreateObject("axCom", null, null, null, null, null, null);//create object from axCom class in AX

            name = System.Console.ReadLine();//get name from console
          
            //create parameter
            list.Size=1;
            list.set_Element(1, name);
          
            axName = (string)axObj.CallEx("getName", list);//execute method in axCom class
          
            System.Console.WriteLine(axName);//show modified name in console
            System.Console.ReadKey();//wait until hit a key
          
            ax.Logoff();//log out
        }
    }
}