The MicroStation Development Library (MDL) and MicroStationAPI provide APIs for developers wanting to create custom applications for MicroStation® from Bentley Systems. We create a MicroStation application as a DLL, written using C++ and built with the Microsoft C++ compiler and linker provided with Visual Studio.
When editing your source code, you can choose whether to use Microsoft Visual Studio, Microsoft Visual Studio Code, or one of your favourite text editors.
When building your app, you can use Visual Studio or the Bentley Systems make (bmake) tools.
A MicroStation DGN model's primary purpose is to be a container of graphic elements. A user creates and manipulates elements in one of eight views of a DGN model.
In a 2D model, all elements are planar: they lie on the same XY plane. In a 3D model, elements may be planar and non-planar. If planar, they don't necessarily lie on the XY plane. How do we test for planarity?
The code shown below is encapsulated in a C++ project. You can download the project to examine the code and kick the tyres.
A CurveVector
is a collection of lines, arcs and other elements that may form an open or closed loop.
The CurveVector::IsPlanarWithDefaultNormal()
method tests most elements for planarity.
Here's some example code …
#include <DgnPlatform/CurveVector.h> #include <DgnPlatform/ElementGeometry.h>
bool IsPlanar (ElementHandleCR eh) const { bool planar { false }; CurveVectorPtr curve = ICurvePathQuery::ElementToCurveVector (eh); if (curve.IsValid ()) { Transform localToWorld; Transform worldToLocal; DRange3d range; if (curve->IsPlanarWithDefaultNormal (localToWorld, worldToLocal, range, nullptr)) { planar = true; } } return planar; }
The Flat Earth Society has a lot to answer for. What do we mean by 'flat'? To be flat, an object should first be planar. Additionally it should be aligned with something that we consider to be a datum. In other words, 'flatness' is a subjective concept.
Here, we attempt a deterministic approach to 'flatness'.
First, define a plane to compare against. For example, suppose that
we're testing for flatness compared to our current position on the globe.
The plane that we want to compare is defined by the local Z axis [0,0,1]
.
Here's some example code. It builds on the above test for planarity, then compares the normal of the planar object to our axis …
bool IsFlat (ElementHandleCR eh, DVec3dCP axis) const
{
bool flat { false };
CurveVectorPtr curve = ICurvePathQuery::ElementToCurveVector (eh);
if (curve.IsValid ())
{
Transform localToWorld;
Transform worldToLocal;
DRange3d range;
// Brien Bastings of Bentley Systems commented:
// One suggestion I have for your flatness test is to supply the normal you are looking for to
// IsPlanarWithDefaultNormal and not just use it to check the result.
// The reason for this is to support line segments. A line may very well lie in the plane
// defined by your desired normal, but the line by itself doesn't uniquely specify a single plane
if (curve->IsPlanarWithDefaultNormal (localToWorld, worldToLocal, range, axis))
{
if (axis)
{
DPoint3d origin;
DVec3d v1, v2, v3;
localToWorld.GetOriginAndVectors (origin, v1, v2, v3);
flat = axis->IsParallelTo (v3);
}
}
}
return flat;
}
Usage …
ElementHandle eh ( /* get element from somewhere */ ); DVec3d axis; axis.Init ( 0., 0., 1. ); // Z axis if (IsFlat (eh, &axis)) { WCharCP msg = L"Element is flat"; mdlOutput_messageCenter (DgnPlatform::OutputMessagePriority::Debug, msg, msg, OutputMessageAlert::None); } else { WCharCP msg = L"Element is not flat"; mdlOutput_messageCenter (DgnPlatform::OutputMessagePriority::Debug, msg, msg, OutputMessageAlert::None); }
Download the IsElementPlanar Source Code. Unpack the ZIP file, retaining the folder structure. The pack includes a Bentley make (bmake) file.
In addition to the MicroStation SDK, you need the following to be installed on your development computer …
The ZIP file does not include the application. You must build the app. before loading it into MicroStation.
Load the app. using MicroStation key-in
mdl load IsElementPlanar
With the app. loaded, you have the following key-ins available …
Command Root | Command Word 1 |
---|---|
ISPLANAR | PICK |
Start picking elements. The app. tells you if a selected element is planar and, if it is planar, whether it is 'flat'. As delivered, the app. compares the element normal to the XY plane to determine 'flatness'.
Return to MicroStationAPI articles index.
Post questions about C++ and the MicroStationAPI to the MicroStation Programming Forum.