Code highlighting

Wednesday, December 20, 2006

AxCreateNewProject tool Version 1.2

I made some additions and modifications to the AxCreateNewProject tool.
The link to the orignal post about the tool:
AxCreateNewProject Version 1.1.

Modifications are descriped on the homepage:
AxCreateNewProject HomePage

Friday, December 08, 2006

A little modification / add-on to Sidax:

I use one of the features of Sidax most of all - it's the recent projects tab. (we have a lot of projects and I have to work with a lot of them at the same time). So performance of this tab is most critical to me.

And what was wrong is that from time to time I would stumble onto project names that didn't exist anymore, but still were up high in the list of recent projects.
So what this modification does is just verify that the project exists before showing it in the list of recent projects.
(this verification is performed only when the recent projects tab is opened, so it won't cause any performance issues)

To add this modification into your sidax installation, you have to do the following:
1. Add a method to Forms\Sidax:
void updateMruProjects()
{
int i;
TreeNode privateProjectTreeNode;
TreeNode sharedProjectTreeNode;
TreeNodeName projectName;

boolean existsProject(TreeNodeName _projectName)
{
TreeNode project;
;
project = privateProjectTreeNode.AOTfindChild(_projectName);
if (project)
return true;
project = sharedProjectTreeNode.AOTfindChild(_projectName);
if (project)
return true;
return false;
}
;
privateProjectTreeNode = SysTreeNode::getPrivateProject();
sharedProjectTreeNode = SysTreeNode::getSharedProject();

for(i = 1; i <= conLen(MruProjects); i++)
{
projectName = conPeek(mruProjects, i);
if (!existsProject(projectName))
{
if (element.openedProjects().exists(projectName))
element.openedProjects().remove(projectName);
MRUProjects = conDel(MRUProjects, conFind(MRUProjects, projectName), 1);
}
}
this.updateHistory();
}


2. Modify an existing method Forms\Sidax\toglleBut, adding 2 lines at the end:
    if (activeTab.id() == historyTab.id() && !collapsed)
element.updateMruProjects();


That's it. Now the next time you open the recent projects tab, the unexistent project won't be shown. Enjoy!

Tuesday, December 05, 2006

Adding Menu References

Many developers often find it very confusing when trying to add a menu reference into an existing menu.
The reference just doesn't want to be added. :)
And what confuses even more is that some of the menus are added normally, while others are not!

Let's look at an example:
"After creating of a new menu - menu1, I want to add 2 existing menus into it as references: Cust and Vend.
I right-click the menu1 node and select add->menu reference. Drag over the Cust menu (and everything goes fine), and then I try to drag over the Vend menu - and it DOESN'T work! I am lost. what can be the reason for this?"

The explanation is simple:
The menus that were expanded since the time you launched the client, can't be added as references.
You can experiment with this: Try opening the AX client and dragging over a menu as a menu reference. You can see that it works. Now, expand the menu in the AOT and try adding it as a menu reference again. You can see that it is impossible to add it any more. So, to avoid having problems when adding a menu as a reference, you should re-enter the Axapta client and, before expanding the menu, add the needed menu as a reference.

Original article:
http://erpkb.com/Axapta/OshibkaSozdanijaSsylkiNaMenju

Friday, November 24, 2006

Description of ClassBuild class:

Today I want to write about using the class ClassBuild.
A collegue of mine recently used this class for extending Axapta's IDE, so I decided you all should know about this class too.

OK, let's start with the declaration of the class:
It's simple, the class isn't extending any other class, a variable of type class ClassNode is declared together with a macro #aot - it contains pathes to all the objects in the AOT
X++:
public class ClassBuild
{
ClassNode classNode;
#aot
}


The class contains the following methods:
  • void new(str _name, boolean _allowExisting = true) - this is the constructor of the class

  • void addMemberVariable(str _variableType, str _variableName) - this method is used to create a variable declaration in a class

  • TreeNode addMethod(str _name, str _source) - this method is used to create new methods and set their source code

  • void addSourceToMethod(str _memberFunction, str _addSource) - using this method we can set the source code of an existing method

  • ClassNode classNode() - this method returns a ClassNode object pointing to the created class

  • public MemberFunction getMethodImplementation(str _methodName, boolean _includeParents) - the method return a MemberFunction object, which has methods to edit or view the source code of the specified method of the class

  • public str name() - the method returns the name of the created class

  • TreeNode overrideMethod(str _name, str _newSource = '') - this method is used to override the method of the parent class in case one exists


  • I will explain how the class should be used on a specific example: (click the image to enlarge)


    Explanation:
    In line 6 we create a new Object of class ClassBuild. Into the constructor we pass the name of the class we want to create and an optional paramter, which controls the execution of code in case the class already exists in the AOT.
    After the execution of this line the class already exists.
    After that we add a method test() to our class and set the source code for this method.
    Then we add a member variable of our class, and will try using this variable in a second method we create - test2(). You can see that here I did this in 2 steps on purpose - to show the way you can use the method addSourceToMethod().
    OK, now all the methods are created and we have to compile our class. For this we can use the method AotCompile() of class TreeNode, which we access through the method classNode of the created class.
    Now, to see how 2 other methods work, we show a message dialog with the name of the class being created and the source code of one of the methods.

    Then, just to show you the class works and is ready to be used, we can call one of its methods for execution.
    For this, we use the class DictClass and its methods, but I will not discuss it in this post.

    That's it. Try running the attached job and see how it works!
    Attachment: Job17.xpo


    There is also another way of creating the same class - by using the UtilElements table: (code provided by AndyD from AxForum)

    UtilIdElements utilIdElements;
    TreeNode tn;
    ;
    utilIdElements.initValue();
    utilIdElements.Name = "newClass";
    utilIdElements.recordType = UtilElementType::Class;
    utilIdElements.insert();
    tn = xUtilIdElements::getNode(utilIdElements);
    tn.AOTcompile(1);
    tn.AOTsave();



    See also: Classes\FormBuild, Classes\DictClass
    Adding an AND condition in a queryRange


    Wamr from AxForum found an interesing feature of fieldId2Ext global method:


    X++:
        Query       q = new Query();
    QueryBuildDataSource qbds;
    ;

    qbds = q.addDataSource(tableNum(InventTable));

    qbds.addRange(fieldNum(InventTable, ItemId)).value("8");
    qbds.addRange(fieldid2ext(fieldNum(InventTable, ItemId),1)).value("2");

    info(qbDS.toString());
     
    But you have to use it with caution, because you won't be able to find this range afterwards. 
    so, searching for
    qbr = qbds.findRange(fieldId2Ext((fieldNum(InventTable, ItemId), 1));
    won't return you the range with the value "2", but the one with the value "8"
     
    You can find the range, specifying the exact occurrence of it in the query:
     
    qbr = qbds.findRange(fieldNum(InventTable, ItemId), 2);

    Monday, November 20, 2006

    AxCreateNewProject
    Homepage

    AxCreateNewProject is a nice tool to help you get started on a project - it will create a shared or a private project with specified project nodes for you and open it in a new window, so that you can start edding objects right away.

    Also included in the zip file: a bmp image to add this tool as a plugin for Tabax


    And after you press OK a project will be created: (see an example below)

    Monday, November 13, 2006

    Sidax - a sidebar tool for DAX 3.0

    Max Belugin (AxCoder) has made some upgrades to his tool - sidebar for Axapta - Sidax.
    Current version is 0.3.7 beta14
    The link to download this great tool is:
    http://erpkb.com/Axapta/Sidax/files?get=sidax0.3.7beta14.zip

    Enjoy!

    Wednesday, November 08, 2006

    Hello, everyone.
    This blog will mostly be about Dynamics AX (formerly Axapta).
    (This is what I do for living and what I am interested in)
    Also, here is a link to another resource of mine, where I am planning to store different projects and thoughts I consider interesting:
    http://infostore.org/user/kashperuk/DynamicsAX

    I want to start off with a small post about Axapta Label System.

    I am translating a book on Axapta (MorphX IT, Steen Andreasen) into Russian language. I will tell about it in more detail in a little while, when the traslation is finished and proof-read.
    So, while doing the translation of an Appendix chapter, I stumbled on something I have never read about in the past.

    It's about searching labels in Axapta:
    "When searching for a label using <> will narrow your search. If you want to look up the label 'Customer', it will perform faster by keying in <Customer> as only labels with the exact text 'Customer' will be found. To find all labels starting with 'Customer', you simply enter <Customer."


    Also, as Max Belugin pointed out to me, regular expressions are used in the search.
    You can read about different Regular expressions by opening the AOT node:
    \System Documentation\Functions\match