Getting started with Allplan Python API

Setup

This part describes the necessary installations to start with Allplan PythonPart scripting.

Allplan

Install Allplan version >= 2018-0

Python (optional)

Python is generally installed along with Allplan. You find it in the Allplan program folder in PRG\Python. If you want to install it to your environment, be sure to install the appropriate version.

Python 3.6.1 64 bit

·         Check the installed program:

IDE

Recommended: Visual Studio 2015 Community Edition

Python Tools

Install Python Tools for Visual Studio: http://microsoft.github.io/PTVS/

·         For trouble-free work we recommend using version >= 2.2.6

Check the available Python Environments:

·         In Visual Studio open Tools -> Python Tools -> Python Environment

·         Python 64-bit 3.6.1 should be the default

·         If this version is not available, then you can use the version from the Allplan program path (PRG\Python) by adding it with “+ Custom”

PyLint

For checking code we recommend using PyLint. You can install it by running:

Python –m pip install pylint

Or

Python –m easy_install pylint

Or install it manually:

·         Download and install Package from PyPi: https://pypi.python.org/pypi/pylint/1.4.4#downloads

o   Extract and enter the folder

o   Run: python setup.py install

·         For running PyLint, it may be necessary to download and install Six, Astroid, Colorama and Logilab-Common, too

Intellisense

There are some limitations to Intellisense in Python Tools for Visual Studio. To get it working, read the following notes.

Unknown parameter types

Intellisense does not work with parameters. Create a (temporary) assert to make Intellisense work:

def move_handle(build_ele, handle_prop, input_pnt, doc):

    # Add (temporarily) assert to make Intellisense work

    assert isinstance(build_ele, BuildingElement)

    # Now here Intellisense work for build_ele

    build_ele.change_property(handle_prop, input_pnt)

Exploring examples

With the normal Allplan release, we ship a range of examples showing how to use Allplan Python API. These examples will help you to become familiar with the API.

Project template

Open Python project from ETC\PythonPartsScripts\PythonParts.pyproj.

All shipped Python scripts are stored in this project. The corresponding PythonPart library files (*.pyp files) are stored in ETC\Examples\PythonParts\. You can add this path to your Allplan library.

Following example folders are available:

·         ContentExamples – contains complex PythonPart examples

·         GeometryExamples – contains examples from the Allplan Geometry library

·         PaletteExamples – contains examples demonstrating the palette functionalities

·         ReinforcementExamples – contains examples with special reinforcement functionalities

·         ToolsAndStartExamples – contains helpful start examples

PythonParts.pyproj includes also all necessary general Python scripts:

·         GeneralScripts – Python scripts with the main modules for running a PythonPart in Allplan

·         StdReinfShapeBuilder – Modules helping you to generate reinforcement structures

The project references are predefined for all available Allplan Python interfaces. The predefined paths might be different from the ones in your environment. In this case open PythonParts.pyproj with a text editor and adapt the paths to the referenced *.pyd resources. Normally you will find them in your Allplan program path (PRG).

Change the existing path information to something like:

To import any of these resources in your Python script, use the command:

import NemAll_Python_Geometry as AllplanGeo

For generating your own scripts, you can use this project or define your own project similar to this and store it for example in STD\PythonPartsScripts\ path.

Exploring unit test examples

In addition to the examples shipped with Allplan, we provide a Visual Studio Python project which provides unit tests for all API functions. To examine this project and get familiar with the examples, follow the steps in this section.

Download

You can download the project as a zip archive (NemAll_Python_Geometry_UnitTests.zip) from the Allplan Python documentation website. Please use the link “Download unit tests”.

Extract the archive and open the NemAll_Python_Geometry_UnitTests.pyproj file with Visual Studio 2015 or later.

Running unit tests

To run the tests, update the project reference in NemAll_Python_Geometry.pyd first. You can remove the existing reference and add a new one with the corresponding path. It is usually located in your Allplan program path (PRG). Alternatively you can change the path of the existing reference by opening the NemAll_Python_Geometry_UnitTests.pyproj file with a text editor.

If Python is available (see part Python Tools), then you can run the tests simply by pressing F5 (Start debugging). Everything should run without error.

If any error occurs, then you will get a message box with the test failure.

If you run the tests without debugging (press CTRL+F5), then you will get the result in the shown command line window.

Getting familiar with Tests

All tests are structured by API classes. So you can open TestLine2D.py, for example and check all available API methods for the Line2D class.

By changing some test parameters and running the test again, you can try out the possibilities of the current geometry class.

You can also insert some prints for more information about the geometry element.

Creating your first PythonPart

If your environment is prepared, you are ready to start with your own first PythonPart.

File structure

For running a PythonPart in Allplan, you need at least two files:

·         <YourPythonPart>.pyp – can be placed anywhere; however, we recommend placing it in Allplan’s library folder

·         <YourPythonPart>.py – has to be placed in PythonPartsScripts folder, either in ETC, STD or the current project path.
Library is the root folder for the .pyp files in the current project. The simples way is to use the structure of the .py files also for the .pyp files: xxx.prj\Library\Folder1\xyz.pyp uses the script xxx.prj\PythonpartsScripts\Folder1\xyz.py.

·         In addition, there are some optional files:

·         <YourPythonPart>.png – preview image (128x128 px) for Allplan Library; has to be placed next to the <YourPythonPart>.pyp file

·         < YourPythonPart>_deu.xml – localisation xml file for each Allplan language (deu, eng, fr, …). The file contains the translations for each TextId used in the <YourPythonPart>.pyp file

<YourPythonPart>.pyp file

The .pyp file defines the main PythonPart element and links to the corresponding Python script. You can open it in Allplan using drag-and-drop operations or you can select it in the Library.

<?xml version="1.0" encoding="utf-8"?>

<Element>

    <Script>

        <Name>MyPythonPart.py</Name>

        <GeometryExpand>0</GeometryExpand>

    </Script>

</Element>

It contains all necessary parameters for the PythonPart. For each parameter a property will be created in the BuildingElement instance and a corresponding control will be created in the Properties palette. The parameters can be structured in pages.

Add a simple parameter in the following way:

<Element>

    …

    <Page>

        <Name>Page1</Name>

        <Text>MyPythonPart</Text>

 

        <Parameter>

            <Name>Length</Name>

            <Text>Line length</Text>

            <Value>1000.</Value>

            <ValueType>Length</ValueType>

        </Parameter>

    </Page>

</Element>

For more information about the parameter definition, have a look at the “How to define the PythonPart pyp file” documentation.

<YourPythonPart>.py file

The Python script should implement at least the methods for checking the Allplan version and creating the Allplan elements:

import NemAll_Python_Geometry as AllplanGeo

import NemAll_Python_Elements as AllplanElements

 

# Method for checking the supported versions

def check_allplan_version(build_ele, version):

    # Delete unused arguments

    del build_ele

    del version

 

    # Support all versions

    return True

 

# Method for element creation

def create_element(build_ele, doc):

    # Access the parameter property from *.pyp file

    length = build_ele.Length.value

    # Create a 2d line

    line = AllplanGeo.Line2D(0, 0, length, 0)

    # Define common style properties

    common_props = AllplanElements.CommonProperties()

    common_props.GetGlobalProperties()

    # Create a ModelElement instance and add it to elements list

    model_elem_list = [AllplanElements.ModelElement(common_props, line)]

    # Define the handles list

    handle_list = []

    # Return a tuple with elements list and handles list

    return (model_elem_list, handle_list)

If you defined some handles in your PythonPart, you must implement the method for handle move events:

# Method is called after a handle was moved

def move_handle(build_ele, handle_prop, input_pnt, doc):

    # Change the handle properties

    build_ele.change_property(handle_prop, input_pnt)

    # Recreate element with new properties

    return create_element(build_ele, doc)

In some cases it is also helpful to override some other methods from BuildingElementInput.py:

# Method is called after a property was changed in palette

def modify_element_property(build_ele, name, value):

    # Handle dependencies for changed property

    # Return true/false for palette refresh

    return True

 

# Method is called after a control event was fired from palette (e.g. Button was clicked)

def on_control_event(build_ele, event_id):

    # Handle all relevant event_ids

    # Return true/false for palette refresh

    return True

Quick start with HelloWorld example

Copy the example to STD (or the current project path) in the following way:

·         Copy ETC\Examples\PythonParts\ToolsAndStartExamples\HelloWorld.pyp to STD\Library\

·         From ETC\PythonPartsScripts\ToolsAndStartExamples\ copy following files to STD\PythonPartsScripts\

o   HelloWorld.py

o   __init__.py

·         Open the copied HelloWorld.pyp file with a text editor and adapt the path to the HelloWorld.py in the following way:

<Element>

    <Script>

        <Name>HelloWorld.py</Name>

        …

    </Script>

    …

</Element>

You can now customize this example for your needs.

Debugging

You can debug the python .py files with the help of PTVS.

An additional tool which is helpful for debugging and understanding PythonParts is the Allplan trace window. Switch it on using the Services application (Allmenu).

Preliminary

For debugging the PythonParts you need at least PTVSD 3.0.0 in the Allplan\PRG\PythonParts folder.

You can download PTVSD from https://pypi.python.org/pypi/ptvsd.

Unzip the file ptvsd-3.0.0.zip and copy the ptvsd folder under the Allplan Python folder PRG\Python\ptvsd.

Check your path settings in the PythonParts.pyproj file in the Allplan ETC Path: ETC\PythonPartsScripts\PythonParts.pyproj.

The correct settings are shown in Exploring examples -> Project template.

First debug steps

Start Visual Studio and open the file: ETC\PythonPartsScripts\PythonParts.pyproj.

You can now open the ETC\PythonPartsScripts\ToolsAndStartExamples\HelloWorld.py file and place a breakpoint into the create_element method:

Start Allplan and double click the StartPythonDebug PythonPart in the Library:

Confirm the following message box:

Switch back to Visual Studio and choose “Attach to Process”:

For transport choose Python remote (ptvsd) and set PythonParts@localhost as the qualifier:

Finally confirm by clicking “Attach”.

The StartPythonDebug PythonPart runs to the point where the program flow asks for the origin. Quit the PythonPart with ESC or the Close button. Start ETC\PythonPartsScripts\ToolsAndStartExamples\HelloWorld.py in the library. The program will stop at your breakpoint:

Trace output

The Allplan trace informs you about open .py files and other messages from the .py files. You can also see the output of the print commands of your .py files in the Allplan trace.

Load BuildingElementPalette.py

Load BuildingElementInput.py

Load BuildingElementInput.py

 

Create common string table:

 

BuildingElement Stringtable read file: C:\ProgramData\Nemetschek\2018_Python\2018\Etc\PythonPartsScripts\GeneralScripts\Stringtable\BuildingElement_deu.xml

self.build_ele = xml_ele.read_element_parameter(file_name)C:\ProgramData\Nemetschek\2018_Python\2018\ETC\Examples\PythonParts\ToolsAndStartExamples\HelloWorld.pyp

BuildingElementXML read_element_parameter:  C:\ProgramData\Nemetschek\2018_Python\2018\ETC\Examples\PythonParts\ToolsAndStartExamples\HelloWorld.pyp

BuildingElement Stringtable read file: C:\ProgramData\Nemetschek\2018_Python\2018\ETC\Examples\PythonParts\ToolsAndStartExamples\HelloWorld_deu.xml

 

read file: C:\ProgramData\Nemetschek\2018_Python\2018\ETC\Examples\PythonParts\ToolsAndStartExamples\HelloWorld_deu.xml not found

 

Script = ToolsAndStartExamples\HelloWorld

Troubleshooting

Please consider the following notes on troubleshooting.

Message box

It can happen that you get a message box if you open a .pyproj file with Visual Studio. Confirm the message box:

The message box is a result of PTVS. Visual Studio works without any interference and we cannot see the effects of this message.

Stop debugging

In some cases it can happen that you have to stop Allplan using Task Manager after stopping the debug session:

Pyproj file modification detected

In case of file modification of the .pyproj file outside the environment, choose “Ignore” and restart Visual Studio in order to get the newest changes in the .pyproj file: