{ ************************************************************ }
{ Delphi VCL Extensions }
{ }
{ Basic constants and types }
{ }
{ Copyright (c) 2002-2014 SoftGold software company }
{ }
{ ************************************************************ }
unit sgConsts;
{$INCLUDE SGDXF.INC}

interface

uses
  Windows, Classes, Registry, Math, Graphics
{$IFDEF SGDEL_7}
{$IFDEF SG_USE_INDY}
    , IdHTTP, IdAntiFreeze
{$ENDIF}
{$ENDIF}
{$IFDEF SGDEL_2009}
{$IFNDEF SGFPC}
    , Character
{$ENDIF}
{$ENDIF}
{$IFDEF SGDEL_XE3}
{$IFNDEF SGFPC}
    , System.Types, System.UITypes
{$ENDIF}
{$ENDIF}
    , ActiveX;

{$IFNDEF SGDEL_6}

const
{$IFDEF LINUX}
  sLineBreak = #10;
{$ELSE}
  { .$IFDEF MSWINDOWS }
  sLineBreak = #13#10;
  { .$ENDIF }
{$ENDIF}
{$ELSE}

const
  sLineBreak = System.sLineBreak;
{$ENDIF}

type
{$IFNDEF SGDEL_5}
  PColor = ^TColor;
{$ENDIF}
{$IFNDEF SGDEL_2009}
{$IFDEF BCB}
  PCardinal = ^Cardinal;
{$ENDIF}
{$ENDIF}
{$IFNDEF SGDEL_6}
{$IFNDEF PCardinal}
  PCardinal = ^Cardinal;
{$EXTERNALSYM PCardinal}
{$ENDIF}
{$IFNDEF PPointer}
  PPointer = ^Pointer;
{$EXTERNALSYM PPointer}
{$ENDIF}
{$IFNDEF PByte}
  // PByte = ^Byte;
  { .$EXTERNALSYM PByte }
{$ENDIF}
  TRoundToRange = -37 .. 37;

  TSeekOrigin = (soBeginning, soCurrent, soEnd);
{$ENDIF}
{$IFNDEF SGDEL_7}
  UInt64 = Int64;
{$ENDIF}
{$IFNDEF SGDEL_2009}
  PUInt64 = ^UInt64;
{$ENDIF}
  { basic types }

{$IFNDEF SGDEL_2009}
  TSysCharSet = set of AnsiChar;
{$ENDIF}
{$IFNDEF SGFPC}
  sgRawByteString = {$IFDEF SGDEL_2009} RawByteString {$ELSE} AnsiString
  {$ENDIF};
  sgUnicodeStr = {$IFDEF SGDEL_2009} string {$ELSE} WideString {$ENDIF};
  sgUnicodeChar = {$IFDEF SGDEL_2009} Char {$ELSE} WideChar {$ENDIF};
{$ELSE}
  sgRawByteString = AnsiString;
  sgUnicodeStr = WideString;
  sgUnicodeChar = WideChar;
{$ENDIF}
{$IFDEF SGFPC}

  TFontData = record
    Handle: HFont;
    Height: Integer;
    Orientation: Integer;
    Pitch: TFontPitch;
    Style: TFontStylesBase;
    Charset: TFontCharset;
    Name: TFontDataName;
    Quality: TFontQuality;
  end;

  TPenData = record
    Handle: HPen;
    Color: TColor;
    Width: Integer;
    Style: TPenStyle;
  end;

  TBrushData = record
    Handle: HBrush;
    Color: TColor;
    Bitmap: TBitmap;
    Style: TBrushStyle;
    OwnsBitmap: Boolean;
  end;

  TResData = record
    Handle: THandle;
  end;

  PResource = ^TResource;

  TResource = record
    Next: PResource;
    RefCount: Integer;
    Handle: THandle;
    HashCode: Word;
    Owner: TThreadID;
    case Integer of
      0:
        (Data: TResData);
      1:
        (Font: TFontData);
      2:
        (Pen: TPenData);
      3:
        (Brush: TBrushData);
  end;
{$ENDIF}

  TsgSilentMode = (smNo, smNoSplash, smNoMain, smNoAll);

  TsgLogOperation = (loOtherAction, loOpen, loSave, loClose, loException,
    loClipboardCopy, loClipboardPaste, loCreateNew);

  TMeasureToolMode = (mtDistance, mtArea, mtPolylineLength, mtView, mt3DCommon);
  TsgMeasureOperation = (moAddPoint, moStopInput, moContinue, moFinish);

  TsgLogParam = record
    Operation: TsgLogOperation;
    Id: UInt64;
    Obj: TObject;
    Info: String;
  end;

  TsgLogger = class
  public
    function FileLogging(const AParam: TsgLogParam): Integer; virtual; abstract;
  end;

  TsgObjProcTranslate = function(const AKey: string): string of object;
  TCmdSymReplaceProc = function(const AText: sgUnicodeStr): sgUnicodeStr;

  TsgTIFFCompressionType = (ctLZW, ctDeflate, ctJPEG, ctCCITT3, ctCCITT4,
    ctCCITT6, ctRle, ctAuto, ctNone);

  TsgAreaType = (arGeometrical, arContour, arUser, arCalculated);
  TsgButtType = (btNone, btEmpty, btZigZag);
  TsgGeoType = (gtByPattern, gtLine, gtArc);

  TbtiEntity = (btiUndefined, btiConstruction, btiDimConstruction, btiComplex,
    btiComplexBroad, btiComplexLinear, btiElement, btiElementBroad,
    btiElementLinear, btiElementCarved, btiElementModifier, btiArea,
    btiComplexArea, btiLabel, btiDimLabel, btiBlockPattern);

  TsgDimNameVal = (vnDIMASZ, vnDIMBLK, vnDIMBLK1, vnDIMBLK2, vnDIMLRBLK,
    vnDIMSD1, vnDIMSD2, vnDIMSE1, vnDIMSE2, vnDIMCLRD, vnDIMCLRE, vnDIMCLRT,
    vnDIMLWD, vnDIMLWE, vnDIMTIX, vnDIMLFAC, vnDIMDEC, vnDIMTXT, vnDIMTAD,
    vnDIMCEN, vnDIMTXSTY, vnDIMGAP, vnDIMEXE, vnDIMEXO, vnDIMTIH, vnDIMTOH,
    vnDIMSCALE, vnDIMENBL, vnDIMTXTALIGN, vnDIMSAH);
  TsgDimNameVals = set of TsgDimNameVal;

  TsgDimArrowType = (datUndefined{$IFNDEF SGFPC} {$IFDEF SGDEL_6} = -1{$ENDIF}{$ENDIF}, datClosedfilled, datClosedblank, datClosed, datDot, datArchtick, datOblique, datOpen, datOrigin, datOrigin2, datOpen90, datOpen30, datDotsmall, datDotblank, datDotsmallbank, datBoxblank, datBoxfilled, datDatumblank, datDatumfilled, datIntegral, datUserarrow, datNone);

  TsgDimensionType = (dmtRotHorVert, dmtAligned, dmtAngular, dmtDiameter,
    dmtRadius, dmtAngular3Point, dmtOrdinate, dmtUndefined);

  TsgLayoutDetectorMode = (ldmModel, ldmAllLayouts, ldmLayoutByName,
    ldmAllPaperSpaces, ldmCurrentLayout);

  TsgPlotLayoutFlag = (plfPlotViewportBorders, plfShowPlotStyles,
    plfPlotCentered, plfPlotHidden, plfUseStandardScale, plfPlotPlotStyles,
    plfScaleLineweights, plfPrintLineweights, plf256bit, plfDrawViewportsFirst,
    plfModelType, plfUpdatePaper, plfZoomToPaperOnUpdate, plfInitializing,
    plfPrevPlotInit);
  TsgPlotLayoutFlags = set of TsgPlotLayoutFlag;

  TsgPlotType = (ptLastScreenDisplay, ptDrawingExtents, ptDrawingLimits,
    ptViewSpecified, ptWindowSpecified, ptLayoutInformation);

  TsgPlotPaperUnits = (ppuInches, ppuMM, ppuPixels);

  TsgPlotRotation = (prNoRotation, pr90DegreesCounterCW, prUpsideDown,
    pr90DegreesCW);

  TsgPrintMode = (pntNone, pntDirectColor, pntPrint);

  TsgSetConstructionLayerMode = (lmCurrent, lmByPatternName, lmByPatternLayer);

  TSizeMode = (smActual, smMaximum, smCustom, smSame);

  TsgExternalFilesMode = (efNoIterateChildren, efAddXRef, efAddImageDef,
{$IFDEF DATA_LINK}
    efDataLink,
{$ENDIF}
    efConvertXrefInFullPath);
  TsgExternalFilesModes = set of TsgExternalFilesMode;

  TsgLangugeID = (lgAny, lgRussian, lgChina, lgJapanise, lgKorean);
  TsgLangugeIDs = set of TsgLangugeID;

  TsgCopyMode = (cmCopy, cmAppend);

  PsgFloat = ^TsgFloat;
  TsgFloat = Double;

  PF2DPoint = ^TF2DPoint;

  TF2DPoint = packed record
    case Integer of
      0:
        (X, Y: TsgFloat);
      1:
        (V: array [0 .. 1] of TsgFloat);
  end;

  PFPoint = ^TFPoint;

  TFPoint = record
    case Integer of
      0:
        (X, Y, Z: TsgFloat);
      1:
        (V: array [0 .. 2] of TsgFloat);
      2:
        (Point2D: TF2DPoint; Elevation: TsgFloat);
  end;

  // Extended CAD data
  PcadExtendedData = ^TcadExtendedData;

  TcadExtendedData = packed record
    Param1: Pointer; // 4 byte field
    IsDotted: BOOL;
    { Fields below may be added in future versions }
    AnsiStr: PAnsiChar;
  end;

  PcadData = ^TcadData;

  TcadData = packed record
    Tag: Word; // classindex, DXF_LINE, DXF_SOLID etc.
    Count: Word; // number of child entities
    TickCount: Word;
    Flags: Byte; // Flags byte
    // for polylines: low bit <> 0 - is closed
    // for layers:
    // 0 - Visible
    // 2 - Frozen
    // 4 - Locked
    // 8 - IsPlotting
    // for text: low bit = 0 - is SHX - else - TTF
    // for spline is degree
    Style: Byte; // Style (pen, brush...) - for future versions
    Dimension: Integer;
    DashDots: PFPoint;
    DashDotsCount: Integer;
    Color: Integer; // Color of entity
    Ticks: Pointer;
    Thickness: TsgFloat; // for future versions
    Rotation: TsgFloat; // Text or block rotation angle
    Layer: PChar; // Layer name (only one layer for element)
    Text: PChar; // Pointer to text string
    FontName: PChar;
    Handle: THandle;
    Undefined1: Integer;
    Undefined2: TsgFloat; // Double
    Undefined3: TsgFloat; // Double
    CADExtendedData: PcadExtendedData;
    Point: TFPoint; // Coordinates of the first point
    Point1: TFPoint; // Coordinates of the second point
    Point2: TFPoint; // Coordinates of the third point
    Point3: TFPoint; // Coordinates of the fourth point
    case Integer of
      0:
        (Radius, StartAngle, EndAngle, Ratio: TsgFloat; EntityType: Byte);
        // for arcs (NOT in DXFEnum)
      1:
        (Block: THandle; Scale: TFPoint); // for Inserts (NOT in DXFEnum)
      2:
        (FHeight, FScale, RWidth, RHeight: TsgFloat; HAlign, VAlign: Byte);
        // for Text
      3:
        (Points: PFPoint; CountPointOfSegments: Integer);
        // for polylines (in DXFEnum)
  end;

  PsgLineState = ^TsgLineState;

  TsgLineState = packed record
    Point1: TFPoint;
    Point2: TFPoint;
    State: Integer;
  end;

  PdxfPoint = ^TdxfPoint;

  TdxfPoint = record
    X, Y, Z: Single;
  end;

  PdxfData = ^TdxfData;

  TdxfData = packed record
    Tag: Word; // classindex, DXF_LINE, DXF_SOLID etc.
    Count: Word; // number of child entities
    TickCount: Word;
    Flags: Byte; // Flags byte
    // for polylines: low bit <> 0 - is closed
    // for layers: low bit <> 0 - is invisible
    Style: Byte; // Style (pen, brush...) - for future versions
    Dimension: Integer;
    DashDots: PdxfPoint;
    DashDotsCount: Integer;
    Color: Integer; // Color of entity
    Ticks: Pointer;
    Thickness: Single; // for future versions
    Rotation: Single; // Text or block rotation angle
    Layer: PChar; // Layer name (only one layer for element)
    Text: PChar; // Pointer to text string
    FontName: PChar;
    Handle: THandle;
    CADExtendedData: PcadExtendedData;
    Point: TdxfPoint; // Coordinates of the first point
    Point1: TdxfPoint; // Coordinates of the second point
    Point2: TdxfPoint; // Coordinates of the third point
    Point3: TdxfPoint; // Coordinates of the fourth point
    case Integer of
      0:
        (Radius, StartAngle, EndAngle, Ratio: Single; EntityType: Byte);
        // for arcs (NOT in DXFEnum)
      1:
        (Block: THandle; Scale: TdxfPoint); // for Inserts (NOT in DXFEnum)
      2:
        (FHeight, FScale, RWidth, RHeight: Single; HAlign, VAlign: Byte);
        // for Text
      3:
        (Points: PdxfPoint); // for polylines (in DXFEnum)
  end;

  PsgCADPalett = ^TsgCADPalett;
  TsgCADPalett = array [0 .. 255] of Cardinal; // AutoCAD 8-bit colors

  TsgEntityMode = (emCustomDraw, emAskOnDelete, emReadOnly);
  TsgEntityModes = set of TsgEntityMode;

  PsgCustomSelectMode = ^TsgCustomSelectMode;

  TsgCustomSelectMode = packed record
    Mode: TsgEntityModes;
    Color: TColor;
    LineWidth: Integer;
    PenStyle: TPenStyle;
  end;

  PF2DLine = ^TF2DLine;

  TF2DLine = packed record
    Point1: TF2DPoint;
    Point2: TF2DPoint;
  end;

  PsgArcR = ^TsgArcR;

  TsgArcR = record
    Center: TFPoint;
    Radius: Double;
    AngleS: Double;
    AngleE: Double;
  end;

  PsgPlotScale = ^TsgPlotScale;

  TsgPlotScale = record
    Numerator: Double;
    Denomenator: Double;
  end;

  PsgRastrExportParams = ^TsgRastrExportParams;

  TsgRastrExportParams = record
    SizeMode: TSizeMode;
    Width: Integer;
    Height: Integer;
    MaxDim: Integer;
    Depth: TPixelFormat;
    Compression: TsgTIFFCompressionType;
    // early this record was in fSizeDialog - not kernel
    DPU: TPoint;
    MeasureInPixels: Boolean;
    Transparent: Boolean;
    Quality: Double;
    SaveProportion: Boolean;
  end;

const
  clEmpty = $5FFFFFFF;

  DefRastrExportParams: TsgRastrExportParams = (SizeMode: smSame; Width: 640;
    Height: 480; MaxDim: 99999999; Depth: pf24bit; Compression: ctNone;
    DPU: (X: 96; Y: 96); MeasureInPixels: True; Transparent: False; Quality: 1;
    SaveProportion: True);

{$IFDEF SGFPC}
  OLEMISC_ISLINKOBJECT = $40;
{$ENDIF}

type
  TsgCurveProperty = (lpVisible, lpJoin, lpArc);
  TsgCurveProperties = set of TsgCurveProperty;

  TsgListType = (ltNil, ltList, ltFPoint, ltF2DPoint, ltDouble, ltSingle,
    ltFloat, ltInt64, ltInteger, ltPointer, ltHashItem);

  PF2DCurveEx = ^TF2DCurveEx;

  TF2DCurveEx = packed record
    Flags: TsgCurveProperties;
    case Integer of
      0:
        (Line: TF2DLine);
      1:
        (Arc: TsgArcR);
  end;

  PF2DRect = ^TF2DRect;

  TF2DRect = packed record
    case Integer of
      0:
        (Left, Top, Right, Bottom: TsgFloat);
      1:
        (TopLeft, BottomRight: TF2DPoint);
      2:
        (V: array [0 .. 1] of TF2DPoint);
  end;

  PFMatrix = ^TFMatrix;

  TFMatrix = record
    case Integer of
      0:
        (V1, V2, V3, V4: array [0 .. 2] of TsgFloat);
      1:
        (M: array [0 .. 3, 0 .. 2] of TsgFloat);
      2:
        (EX, EY, EZ, E0: TFPoint);
      3:
        (V: array [0 .. 3] of TFPoint);
  end;

  PFRect = ^TFRect;

  TFRect = record
    case Integer of
      0:
        (Left, Top, Z1, Right, Bottom, Z2: TsgFloat);
      1:
        (TopLeft, BottomRight: TFPoint);
      2:
        (V: array [0 .. 1] of TFPoint);
      3:
        (D: array [0 .. 5] of TsgFloat);
  end;

  // 0 - reset clip
  // 1 - clip by coord in extents
  // 2 - clip by cad coords
  // 3 - draw view rect in abviewer
  // 4 - clip using in GetImage(clip rect in screen coords)
  TsgClipping = record
    ClipMode: Integer;
    ClipRect: TFRect;
  end;

  Psgversion = ^TsgVersion;

  TsgVersion = record
    Major: Integer;
    Minor: Integer;
  end;

  TsgCADTracerState = (tsNone, tsActive, tsParallel, tsOrtho);

  TsgTraceRecord = record
    Point: TFPoint;
    TracerState: TsgCADTracerState;
  end;

  TMeasurePolylineOption = (mpoPolyLength, mpoSegmentsAngle, mpoSegmentLength,
    mpoSegmentAngleXY, mpoSegmentAngleByZ, mpoSegmentDX, mpoSegmentDY,
    mpoSegmentDZ);
  TMeasurePolylineOptions = set of TMeasurePolylineOption;

  // Modes of 3D objects intersection
  TIntersectionMode = (imNone, imPoint, imLine, imPlane);
  // Object snap modes
  TObjectSnapMode = (osInsert, osEndPt, osCenter, osNode, osMiddle, osNormal,
    osNearest, osIntersection, osExtension, osDisabled, osGrid, osOrtho,
    osPolar, osAngle, osDinamic, osTrace, osParallel, osQuadrant, osTangent);
  // Object snap state
  TObjectSnapState = set of TObjectSnapMode;

  TParseUnicodeMode = (puU, puM, puDP);
  TParseUnicodeModes = set of TParseUnicodeMode;

  TsgActivePoint = (apLeftTop, apLeftBottom, apCenter, apRightTop,
    apRightBottom);
  // Axes in 3-Dimensional cartesian coordinates
  TsgAxes = (axisX, axisY, axisZ);
  TsgAxisType = (atCenter, atLeft, atRight);

  PsgArcsParams = ^TsgArcsParams;

  TsgArcsParams = record
    Center: TFPoint;
    Radius1: Double;
    AngleS1: Double;
    AngleE1: Double;
    Radius2: Double;
    AngleS2: Double;
    AngleE2: Double;
  end;

  TsgDefaultView = (df2D, df3D);

  TsgFragmentAutoScreen = (fasNone, fasBMP, fasEMF);

  // CAD drawing border size
  TsgBorderSize = Double;
  // CAD drawing border type
  TsgBorderType = (btGlobal, btRatio);
  TsgCachingRasterMode = (crmNone, crmCache, crmDoubleCache);
  // The entities to be drawn
  TsgCADEntities = (ceEntity, cePoint, ceLine, ceSolid, ceTrace, ceCircle,
    ceArc, ceEllipse, cePolyline, ceLWPolyline, ceSpline, ceHelix, ceLeader,
    ceInsert, ceDimension, ceTolerance, ceMText, ceShape, ceText, ceAttdef,
    ceAttrib, ce3dFace, ceImageEnt, ceViewport, ceRegion, ceBody, ce3DSolid,
    cePattern, ceGradient, ceOle2Frame, cePolyPolygon, ceGradientPolygon,
    ceCurvePolygon, ceHatch, ceACADTable, ceFlatPoly, ceFlatHatch, ceXRef,
    ceProxy, cePath, ceWipeOut, ceMLine, ceMPolygon
    {$IFDEF SG_BTI}, cePolyPolyline2D{$ENDIF}, ceSurface, ceSeqEnd,
    ceSolidObject, ceIges, ceStep, ceBrep, ceFlatPoly3D);

  TsgCADEnities = TsgCADEntities{$IFDEF SGDEL_2005}deprecated{$IFDEF SGDEL_2009}'This type is obsolete and will be deleted in the next version. Please, use the following type - TsgCADEntities!'{$ENDIF}{$ENDIF};

  // see below GetCADEntityTypeString and add string there!!
  TsgCADEntityType = (etNone, etCustomVertex, etLine, etPolyLine, etLWPolyLine,
    etRect, etCircle, etEllipse, etMText, etLeader, etPath, etInsert, etBlock,
    etArc, etMulti, etDimAligned, etHatch, etText, etSolid, etSpline,
    etViewPort, etDimension, etSquare, etPoint, etPolyPolygon, etClipInsert,
    etACADTable, etTrace, etTolerance, etShape, etAttdef, etMLine, etWipeOut,
    etImageEnt, etHelix, etOle2Frame, etCloud, etMPolygon, et3dFace
    // {$IFDEF SG_BTI}
    , etConstruction, etDimConstruction, etComplex, etElement, etComplexBroad,
    etComplexLinear, etElementBroad, etElementLinear, etElementCarved,
    etElementModifier, etArea, etComplexArea
    // {$ENDIF}
    , etContainer, etProxy, etCADFill, etBrepEntity, etACIS, etBREP,
    etPathEvacuation, etXRef);

  TsgCADEntityTypes = set of TsgCADEntityType;

  TsgBrepEntities = (seBrepEntity, sBrepEntityTopology, seBrepEntityGeometry,
    seConeSurface, sePlaneSurface, seSphereSurface, seTorusSurface,
    seExactSplineSurface, seEllipsCurve, seExactCurve, seBs3Curve,
    seStraightCurve, seHelixCurve);

  // Style of the CAD-drawing space
  TsgCADSpace = (cs2D, cs3D, csUndefined);

  PsgColor = ^TsgColor;

  TsgColor = packed record
    case Integer of
      0:
        (R, G, B, A: Byte);
      1:
        (V: array [0 .. 3] of Byte);
      2:
        (Color: DWORD);
  end;

  PsgParametrs = ^TsgParametrs;

  TsgParametrs = record
    case Integer of
      0:
        (Param1, Param2, Param3, Param4: Byte);
      1:
        (Params: array [0 .. 3] of Byte);
      2:
        (FirstTwoParams, LastTwoParams: Word);
      3:
        (Parametrs: Integer);
  end;

  TsgActiveColor = (acIndexColor, acRGBColor);
  PsgColorCAD = ^TsgColorCAD;

  TsgColorCAD = packed record
    Active: TsgActiveColor;
    Color: Cardinal;
    AlbumString: string;
  end;

  TsgArrows = record
    case Integer of
      0:
        (Blk, Blk1, Blk2, LrBlk: TsgDimArrowType);
      1:
        (Blks: array [vnDIMBLK .. vnDIMLRBLK] of TsgDimArrowType);
  end;

  PsgDimStyle = ^TsgDimStyle;

  TsgDimStyle = record
    Alt: Boolean;
    AltF: Double;
    APost: string;
    Asz: Double;
    Sah: Boolean;
    Arrows: TsgArrows;
    Cen: Double;
    ClrD: TsgColorCAD;
    ClrE: TsgColorCAD;
    ClrT: TsgColorCAD;
    SD1: Boolean;
    SD2: Boolean;
    SE1: Boolean;
    SE2: Boolean;
    Dec: Integer;
    Exe: Double;
    Exo: Double;
    Gap: Double;
    LFac: Double;
    LwD: Double;
    LwE: Double;
    Post: string;
    Scale: Double;
    Tad: Integer;
    Tih: Boolean;
    Tix: Integer;
    Toh: Boolean;
    Txt: Double;
  end;

{$IFDEF SG_CPUX64}
  // for protection purposes
  TsgPrNativeUInt = NativeUInt;
{$ELSE}
  TsgPrNativeUInt = Cardinal;
{$ENDIF}
  // DWG, DXF distance units mode
  TsgDistUnitsMode = (umDrawing, umUser, umAltUser);
  // DWG format version
  TsgDWGVersion = (acR09, acR10, acR11, acR12, acR13, acR14, acR2000, acR2004,
    acR2007, acR2010, acR2013);

{$IFNDEF SGDEL_6}

const
  ctNode = 0;
  ctInteger = 1;
  ctDouble = 2;
  ctString = 4;
  ctHex = 8;

type
  TsgCodeType = Byte;
{$ELSE}

type
  TsgCodeType = (ctNode, ctInteger, ctDouble, ctString = 4, ctHex = 8);
{$ENDIF}
  PCodeTypes = ^TCodeTypes;
  TCodeTypes = array [-5 .. 1071] of TsgCodeType;

const
  cnstDWGVersionNames: array [TsgDWGVersion] of string = ('acR09', 'acR10',
    'acR11', 'acR12', 'acR13', 'acR14', 'acR2000', 'acR2004', 'acR2007',
    'acR2010', 'acR2013');

type
  TsvgEntity = (svgUndefined, svgContainer, svgGroup, svgGroupDim, svgEntity,
    svgPoint, svgCircle, svgEllipse, svgLine, svgLink, svgPolyline, svgRect,
    svgPath, svgText, svgTextPath, svgUse, svgImage);

  TsgEntityTypeEx = record
    case Byte of
      0:
        (Val: Byte);
      1:
        (CAD: TsgCADEntities);
      2:
        (BTI: TbtiEntity);
      3:
        (SVG: TsvgEntity);
  end;

  TsgGroupType = (gtCAD, gtBTI, gtSVG);

  TsgEntClass = record
    case Byte of
      0:
        (Id: Word);
      1:
        (EG: TsgGroupType; ET: TsgEntityTypeEx);
  end;

  PsgFontParams = ^TsgFontParams;

  TsgFontParams = packed record
    Above: Double;
    Below: Double;
    Width: Double;
    Height: Double;
    Left: Double;
    Bottom: Double;
    Right: Double;
    Top: Double;
    After: Double;
    DY: Double;
    DX: Double;
  end;

  TsgFormResult = (frCancel, frOk, frAdd, frClose, frDelete, frSelectEntities,
    frSelectPoint, frSelectLength, frSelectAngle, frSelectRect, frYes, frNo,
    frIgnore, frDeleteAll, frMerge);

  TsgGradientType = (gtNone, gtCurved, gtCylinder, gtHemiSpherical, gtLinear,
    gtSpherical, gtInvCurved, gtInvCylinder, gtInvHemiSpherical,
    gtInvSpherical, gtOther);
  // Numbers are necessary for compatibility with a TBrushStyle
  TsgHatchStyle = (hsSolid, hsPatternData, hsHorizontal, hsVertical,
    hsFDiagonal, hsBDiagonal, hsCross, hsDiagCross);

  TsgFillStyle = (fsSolid, fsClear, fsHorizontal, fsVertical, fsFDiagonal,
    fsBDiagonal, fsCross, fsDiagCross, fsCAD);

  TsgAttributeMode = (attDisable, attNormal, attEnable);

  PsgHashItem = ^TsgHashItem;

  TsgHashItem = record
    HashCode: UInt64;
    Data: Pointer;
  end;

  PsgHashLnk = ^TsgHashLnk;

  TsgHashLnk = record
    Data: Pointer;
    Index: Integer;
  end;

  // --- Warning
  // --- if TsgHeadVarStruct was changed (added new fields etc)
  // --- function TsgDXFSectionHeader.ToXMLNode and TsgDXFSectionHeader.FromXMLNode
  // --- should be changed also!
  PsgHeadVarStruct = ^TsgHeadVarStruct;

  TsgHeadVarStruct = record
    CEColor: TsgColorCAD;
    CLayer: string;
    CELType: string;
    CELTScale: Double;
    CELWeight: Double;
    CodePage: Integer;
    DimStyle: string;
    DimTextStyle: string;
    DimProps: TsgDimStyle;
    ExtMim: TFPoint;
    ExtMax: TFPoint;
    TextStyle: string;
    FilletRadius: Double;
    InsUnits: Integer;
    LTScale: Double;
    Measurement: Boolean;
    PointDisplayMode: Integer;
    PointDisplaySize: Double;
    TextSize: Double;
    TileMode: Integer;
    UCSORG: TFPoint;
    UCSXDir: TFPoint;
    UCSYDir: TFPoint;
    Version: Byte;
    InsBase: TFPoint;
    AttMode: TsgAttributeMode;
  end;

  TsgHTTPProxyInfo = record
    ProxyHost: string;
    ProxyPort: Integer;
    ProxyNeedPass: Boolean;
    ProxyUser: string;
    ProxyPass: string;
  end;

{$IFDEF SGDEL_2009}

  TsgNativeInt = NativeInt;
  TsgNativeUInt = NativeUInt;
{$ELSE}
  TsgNativeInt = Integer;
  TsgNativeUInt = Cardinal;
{$ENDIF}
  TsgNativePointer = TsgNativeInt;

  PsgNativeInt = ^TsgNativeInt;
  PsgNativeUInt = ^TsgNativeUInt;

  PsgSubProxyProps = ^TsgSubProxyProps;

  TsgSubProxyProps = packed record
    LayerIndex: Integer; // = -1;
    LTypeIndex: Integer; // = -1;
    ColorID: Integer; // = -1;
    LWeight: Integer;
    Marker: Integer;
    LTScale: Double;
    ProxyType: Integer;
    PlotStyleIndex: Integer;
  end;

  IProxyReader = interface
    function ReadDouble: Double;
    function ReadInteger: Integer;
    function ReadSmallInt: SmallInt;
    function ReadWord: Word;
    function ReadByte: Byte;
    procedure PushPosition;
    procedure PopPosition;
    procedure Seek(ASize: Integer);
    function ReadAnsiPadding: AnsiString;
    function ReadString: string;
    function ReadHandle: UInt64;
    procedure ReadBytes(var Dest; const ACount: UInt64);
    function Position: Pointer;
  end;

{$IFNDEF SGDEL_7}

type
  UInt8 = Byte;
  UInt16 = Word;

  PExtended80Rec = ^TExtended80Rec;

  TExtended80Rec = packed record
    case Integer of
      0:
        (Words: array [0 .. 4] of UInt16);
      1:
        (Bytes: array [0 .. 9] of UInt8);
      2:
        (Frac: TsgNativeUInt; Exp: UInt16;);
  end;

  PExtendedRec = PExtended80Rec;
  TExtendedRec = TExtended80Rec;
{$ENDIF}
  PsgImageProperties = ^TsgImageProperties;

  TsgImageProperties = packed record
    DPI: TF2DPoint;
    Size: TPoint;
  end;

  TsgImportMode = (imView, imImport);

  TsgInsUnits = (iuUnitless, iuInches, iuFeet, iuMiles, iuMillimeters,
    iuCentimeters, iuMeters, iuKilometers, iuMicroinches, iuMils, iuYards,
    iuAngstroms, iuNanometers, iuMicrons, iuDecimeters, iuDecameters,
    iuHectometers, iuGigameters, iuAstronomical, iuLightyears, iuParsecs);

  PsgPoint = ^TPoint;

  TsgDWGSentinel = array [0 .. 15] of Byte;
  PsgDWGHandle = ^TsgDWGHandle;

  TsgDWGHandle = record
    Handle: UInt64;
    Code: Byte;
  end;

  TsgDWGHandleArray = array of TsgDWGHandle;

  PdwgLocator = ^TdwgLocator;

  TdwgLocator = packed record
    RecNumber: Byte;
    Seeker: Integer;
    Size: Integer;
  end;

  PdwgFileHeader = ^TdwgFileHeader;

  TdwgFileHeader = packed record
    VersionID: array [0 .. 5] of AnsiChar;
    Pad: array [0 .. 6] of AnsiChar;
    ImageSeeker: Integer;
    Unknown: Word;
    CodePage: Word;
    Locators: Integer;
  end;

  TsgInternalTextFlag = (itfWinFont, itfInsideMText, itfUseDefaultFont,
    itfSetFontName);
  TsgInternalTextFlags = set of TsgInternalTextFlag;

const
  cnstAddressBit = 3;
{$IFDEF SG_CPUX64}
  cnstAddressHi: Word = (SizeOf(NativeUInt) shl cnstAddressBit) -
    cnstAddressBit;
{$ELSE}
  cnstAddressHi: Word = (SizeOf(Integer) shl cnstAddressBit) - cnstAddressBit;
{$ENDIF}

type
  PsgInt64 = ^TsgInt64;

  TsgInt64 = record
{$IFDEF SG_CPUX64}
    Lo: NativeUInt;
{$ELSE}
    Lo: Integer;
{$ENDIF}
    Hi: Integer;
  end;

  PsgLine = ^TsgLine;

  TsgLine = packed record
    Point1: TFPoint;
    Point2: TFPoint;
  end;

  PsgF2DLine = ^TsgF2DLine;

  TsgF2DLine = packed record
    Point1: TF2DPoint;
    Point2: TF2DPoint;
  end;

  PsgCurveLnk = ^TsgCurveLnk;

  TsgCurveLnk = record
    Flags: Byte;
    Link: TObject;
    P1: Pointer;
    P2: Pointer;
    case Integer of
      0:
        (Line: TsgLine);
      1:
        (Arc: TsgArcR);
  end;

  PsgLittleHeadVarStruct = ^TsgLittleHeadVarStruct;

  TsgLittleHeadVarStruct = packed record
    // InitFlags: LongWord;
    InitFlags: TsgDimNameVals;
    DimDec: Integer;
    DimLFac: Double;
    DimTxt: Double;
    DimTextAlign: Byte;
    DimClrT: TsgColorCAD;
    DimGap: Double;
  end;

  TsgParamType = (ptUndefined, ptObject, ptList, ptPoint, ptDistance, ptAngle,
    ptKey, ptRect, ptAreaCalc);

  TsgParamTypes = set of TsgParamType;

  TsgGridHeaderType = (ghUndefined, ghDescription, ghAreaValue, ghAreaType,
    ghAreaNumber);

  PsgParamData = ^TsgParamData;

  TsgParamData = packed record
    PType: TsgParamType;
    case TsgParamType of
      ptUndefined:
        (DataUnd: Pointer);
      ptObject:
        (DataObj: TObject);
      ptList:
        (DataLst: TList);
      ptPoint:
        (DataPnt: TFPoint);
      ptRect:
        (DataRect: TFRect);
      ptDistance:
        (DataDst: Double);
      ptAngle:
        (DataAng: Double);
      ptKey:
        (DataKey: Integer);
      ptAreaCalc:
        (DataArea: Double);
  end;

  TsgPointClassify = (pcLEFT, pcRIGHT, pcBEYOND, pcBEHIND, pcBETWEEN, pcORIGIN,
    pcDESTINATION, psUNDEFINED);
  TsgPointState = (psInside, psOutside, psBoundary);
  TsgEdgeState = (esTouching, esCrossing, esInessential);

  TsgPopMenuType = (pmtNone, pmtEnter, pmtCancel, pmtClose, pmtActPtMenu,
    pmtActPtLeftTop, pmtActPtLeftBottom, pmtActPtCenter, pmtActPtRightTop,
    pmtActPtRightBottom, pmtAreaMenu, pmtCreateAreaBySelect,
    pmtCreateAreaByPolyline, pmtCreateAreaByRect, pmtCopy, pmtPaste,
    pmtPasteAsBlock, pmtCut, pmtDelete, pmtSelectAll, pmtUndo, pmtRedo,
    pmtZoomIn, pmtZoomOut, pmtFitToSize, pmtCreateCopy, pmtOffset,
    pmtDoubleOffset, pmtMove, pmtMirror, pmtRotate, pmtScale, pmtFindText,
    pmtProperties, pmtOptions, pmtEditAttrib, pmtMatchSettings, pmtSendToBack,
    pmtBringToFront, pmtDrawArcs, pmtDrawLines, pmtAxisType, pmtAxisLeft,
    pmtAxisCenter, pmtAxisRight, pmtAreaProp, pmtClockOrCounterClockWise,
    pmtCW90, pmtCCW90, pmtRotate180, pmtCreateAreaByPoint, pmtFullScreen,
    pmtExitTemplateEditor, pmtExitBlockEditor, pmtBlockEditor,
    pmtCreateAreaByContour, pmtOLE, pmt3DViewSetting, pmtSmoothShading,
    pmtFlatShading, pmtHidenLines, pmtWireframe, pmt2DWireframe,
    pmtViewportActive, pmtViewportDeActive, pmtViewportZoomIn,
    pmtViewportZoomOut, pmtViewportFitToSize, pmtACADTableEdit, pmtFastReport,
    pmtEditHatch, pmtEditMText, pmtEditTextAttdef, pmtShowEntity, pmtUser,
    pmtMetafileToCad, pmtExplodeAll, pmtExplodeAllInserts, pmtCreatePolyline2D,
    pmtCreatePolyline3D, pmtWipeoutRect, pmtWipeoutPolyline, pmtWipeoutShow,
    pmtWipeoutHide, pmtViewportRect, pmtViewportPolyline, pmtViewportObject,
    pmtToCurves, pmtConvertToPolyline, pmtImplement, pmtRecreateBlockAsTemplate,
    pmtDrawFillet, pmtCopyWithBasePoint, pmtChangeDirection, pmtInsertMode,
    pmtIMBasepoint, pmtIMTopLeft, pmtIMTopRight, pmtIMCenter, pmtIMBottomLeft,
    pmtImBottomRight, pmtComplexLine, pmtComplexArc);

  TsgPopMenuTypes = set of TsgPopMenuType;

  PsgPoints3 = ^TsgPoints3;
  TsgPoints3 = array [0 .. 2] of TFPoint;
  PsgPoints4 = ^TsgPoints4;
  TsgPoints4 = array [0 .. 3] of TFPoint;
  TsgPFPoints4 = array [0 .. 3] of PFPoint;
  TsgIndexes4 = array [0 .. 3] of Integer;

  PRectCoords = ^TsgRectCoords;

  TsgRectCoords = record
    Number: string;
    Point: TFPoint;
  end;

  TsgSizesOrientation = (soAuto, soHorizontal, soVertical);

  TsgSizeGenerate = record
    TypeText: TsgSizesOrientation;
    ColorText: TColor;
    TextHeight: Double;
    Offset: Double;
    Precision: Integer;
    Scale: Double;
  end;

  PsgPlotSettingsData = ^TsgPlotSettingsData;

  TsgPlotSettingsData = record
    PageSetupName: string;
    PrintOrConfigName: string;
    PlotLayoutFlags: TsgPlotLayoutFlags;
    PlotPaperUnits: TsgPlotPaperUnits;
    StandardScaleType: Byte;
    NumeratorOfCustomPrintScale: Double;
    DenominatorOfCustomPrintScale: Double;
    PaperSize: string;
    PlotViewName: string;
    UnprintableMargin: TF2DRect;
    PlotPaperSize: TF2DPoint;
    PlotOrigin: TF2DPoint;
    PlotWindowAreaMin: TF2DPoint;
    PlotWindowAreaMax: TF2DPoint;
    PlotRotation: TsgPlotRotation;
    PlotType: TsgPlotType;
    CurrentStyleSheet: string;
    ShadePlotMode: Integer;
    ShadePlotResolutionLevel: Integer;
    ShadePlotCustomDPI: Integer;
    FloatingPointScaleFactor: Double;
    PaperImageOrigin: TF2DPoint;
  end;

  TsgShowEntityMethod = (semProportional, semAbsolute, semFitToSize);

  TsgShowEntitySettings = record
    Method: TsgShowEntityMethod;
    Precision: Double;
  end;

  TsgPropertyType = (prtNone, prtArrowSize, prtArrowType, prtArrowType1,
    prtArrowType2, prtArrowTypeL, prtBackGroundImage, prtColor,
    prtDimExtLineExt, prtDimExtLineExo, prtDimMeasurementsScale,
    prtDimPrecision, prtDimScale, prtDimStyle, prtDimTextAlign, prtDimTextForce,
    prtDimTextSize, prtDimTextColor, prtDimTextOffset, prtDimTextPosVert,
    prtFilletRadius, prtLayer, prtLineType, prtLineTypeScale, prtLineWeight,
    prtPointDisplayMode, prtPointDisplaySize, prtTextFontName, prtTextSize,
    prtTextStyle, prtTextRotation);

{$IFDEF SGDEL_2006}

  TsgRecUInt64 = record
  private
    FHi: Cardinal;
    FLo: Cardinal;
    function GetAll: Int64; inline;
    function GetHi: Cardinal; inline;
    function GetLo: Cardinal;
    procedure SetAll(const Value: Int64); inline;
    procedure SetHi(const Value: Cardinal); inline;
    procedure SetLo(const Value: Cardinal); inline;
  public
    property All: Int64 read GetAll write SetAll;
    property Hi: Cardinal read GetHi write SetHi;
    property Lo: Cardinal read GetLo write SetLo;
    class operator Add(const A, B: TsgRecUInt64): TsgRecUInt64;
    class operator BitwiseOr(const A, B: TsgRecUInt64): TsgRecUInt64;
    class operator Equal(const A, B: TsgRecUInt64): Boolean;
    class operator GreaterThan(const A, B: TsgRecUInt64): Boolean;
    class operator GreaterThanOrEqual(const A, B: TsgRecUInt64): Boolean;
    class operator Implicit(const A: TsgRecUInt64): Int64; inline;
    class operator Implicit(const A: TsgRecUInt64): Integer; inline;
    class operator Implicit(I: Int64): TsgRecUInt64; inline;
    class operator Implicit(I: Integer): TsgRecUInt64; inline;
    class operator LeftShift(const A: TsgRecUInt64; B: Integer): TsgRecUInt64;
    class operator LessThan(const A, B: TsgRecUInt64): Boolean;
    class operator LessThanOrEqual(const A, B: TsgRecUInt64): Boolean;
    class operator Negative(const A: TsgRecUInt64): TsgRecUInt64;
    class operator NotEqual(const A, B: TsgRecUInt64): Boolean;
    class operator RightShift(const A: TsgRecUInt64; B: Integer): TsgRecUInt64;
    class operator Subtract(const A, B: TsgRecUInt64): TsgRecUInt64;
  end;
{$ENDIF}

  TsgUnitsInsertTempl = (uitMilimetr, uitMetr, uitUndefined);

  PsgViewBox = ^TsgViewBox;

  TsgViewBox = packed record
    Mode: Byte;
    case Integer of
      0:
        (X, Y, Width, Height: TsgFloat);
      1:
        (Point, Size: TF2DPoint);
  end;

  PSnapData = ^TSnapData;

  TSnapData = record
    Entity: TObject;
    EntityIntersected: TObject;
    SnapMode: TObjectSnapState;
    SnapType: TObjectSnapMode;
    CADPoint: TFPoint;
    CADPointInUCS: TFPoint;
    Insert: TObject;
  end;

  PPSnapData = ^PSnapData;

{$IFDEF SG_BTI}
  TsgFigureType = (ftFigure, ftQuadrangle, ftTrapezium, ftParallelogram, ftRect,
    ftSquare, ftRhomb, ftSegmentByChordAndLength, ftSegmentByChordAndHeight,
    ftTriangle, ftTriangleRightAngled, ftTriangleByHippuran, ftCircleByLength,
    ftCircleByRadius, ftSectorByAngleAndRadius, ftContour);

  // Basic entity data
  PsgData = ^TsgData;

  TsgData = packed record
    BlockPattern: TObject;
    DimStyle: TObject;
    xByteArray: array [0 .. 6] of Byte;
    xDoubleArray: array [0 .. 10] of Double;
    xIntArray: array [0 .. 1] of Integer;
    xStringArray: array [0 .. 0] of string;
    { Fields below may be added in future versions }
  end;

  // Extended entity data
  PsgExtendedData = ^TsgExtendedData;

  TsgExtendedData = packed record
    Data: TsgData;
    Handle: Pointer;
    Refs0: Pointer;
    Refs1: Pointer;
    Refs2: Pointer;
    Refs3: Pointer;
    Attribs: Pointer;
  end;
{$ENDIF}

  // printer structs
  PPaperFormat = ^TPaperFormat;

  TPaperFormat = packed record
    Name: string;
    Index: Integer;
    PaperSize: TF2DPoint;
    IsXMLFormat: Boolean;
    Margins: TF2DRect;
    Units: TsgPlotPaperUnits;
  end;

  PsgOle2FrameHeaderData = ^TsgOle2FrameHeaderData;

  TsgOle2FrameHeaderData = packed record
    Unknown: Word; // $5580 ($5581 ??)
    Point1: TFPoint;
    Point2: TFPoint;
    Point3: TFPoint;
    Point4: TFPoint;
    EntName: Integer; // ??
    TileModeDescriptor: Integer; // 0 - paper space; 1 - model space
    ReservedInt1: Integer; // 256
    ReservedInt2: Integer; // 1 (or 2 ??)
    ReservedWord: Word; // 1
    ReservedZero: Integer; // 0
    DrawAspect: Integer; // DVASPECT_CONTENT
    Size: Integer; // size ole data
  end;

  TsgParamStrType = (ptArea, ptNumber, ptSubNumber, ptLetNumber, ptPerimeter,
    ptNumberOwner, ptValue, ptValueOwner, ptEmpty);

{$IFNDEF SGDEL_5}
  TListNotification = (lnAdded, lnExtracted, lnDeleted);

  TsgNotificationList = class(TList)
  protected
    procedure Notify(Ptr: Pointer; Action: TListNotification); virtual;
  public
    function Add(Item: Pointer): Integer;
    procedure Delete(Index: Integer);
    function Extract(Item: Pointer): Pointer;
    procedure Insert(Index: Integer; Item: Pointer);
  end;
{$ELSE}

  TsgNotificationList = class(TList);
{$ENDIF}
{$IFNDEF SGDEL_6}

  IInterface = interface
    ['{00000000-0000-0000-C000-000000000046}']
    function QueryInterface(const IID: TGUID; out Obj): HResult; stdcall;
    function _AddRef: Integer; stdcall;
    function _Release: Integer; stdcall;
  end;

  IStreamPersist = interface
    ['{B8CD12A3-267A-11D4-83DA-00C04F60B2DD}']
    procedure LoadFromStream(Stream: TStream);
    procedure SaveToStream(Stream: TStream);
  end;

  { TInterfaced Persistent }

  TInterfacedPersistent = class(TPersistent, IInterface)
  private
    FOwnerInterface: IInterface;
  protected
    { IInterface }
    function _AddRef: Integer; stdcall;
    function _Release: Integer; stdcall;
  public
    function QueryInterface(const IID: TGUID; out Obj): HResult;
      virtual; stdcall;
    procedure AfterConstruction; override;
  end;
{$ENDIF}

  TsgProcOfPointerGetPoint = function(const AObject: Pointer): TFPoint;
  TsgObjProcCompare = function(const A, B: Pointer): Integer of object;
  TsgObjProcNearestCompare = function(const A, B: Pointer): Double of object;
  TsgObjProcGetFPoint = function(const APointer: Pointer): TFPoint of object;
  TsgGetBox = function(Sender: TObject; var ABox: TFRect): Boolean of object;

const
  cnstGUID_Change = '{3322123D-F8FA-4170-9040-A25C271B1887}';
  cnstGUID_CollectionBase = '{17A4E39A-668D-405F-9D2B-56019AC3CA84}';
  cnstGUID_CollectionBaseSort = '{6D1E57A5-542F-4C68-BB84-EFAE2E832F42}';
  cnstGUID_ArrayFPoints = '{F3E4590D-2987-434A-9976-BF94DC24D88F}';
  cnstGUID_ListOfEntities = '{56C91F32-4B45-4217-B790-7D97F89DEBDD}';
  cnstFailCreateGuid: TGUID = '{346ED9BE-02E0-4FC2-9831-1E07719E7796}';
  cntsErrorGuid: TGUID = '{CEBFE042-F13D-40B3-92E6-9BA3A76E8C99}';
  cnstFailNewDrawing: TGUID = '{F42F4557-D19D-433D-884B-79465EFCE73B}';
  GUID_ArrayFPoints: TGUID = ();

  cnstGUID_MainApplication = '{334A4DDC-5237-4BD2-B236-975946B4ADF8}';
  cnstGUID_XMLIde = '{F16043B8-3469-41C2-AD53-C5E86D6CEA57}';
  cnstGUID_ResultNode = '{E52909E5-AA0D-4DD6-B36D-14B9CB335233}';
  cnstGUID_XMLOut = '{F1D6F762-FAC3-4958-93C6-51BFE1E850BD}';

type
  IsgArrayFPoint = interface(IInterface)
    [cnstGUID_ArrayFPoints]
    function GetFPoint(const AIndex: Integer): TFPoint;
    function GetFPointCount: Integer;
    property FPointCount: Integer read GetFPointCount;
    property FPoints[const AIndex: Integer]: TFPoint read GetFPoint;
  end;

  IsgCollectionBase = interface(IInterface)
    [cnstGUID_CollectionBase]
    function GetCount: Integer;
    procedure Delete(const AIndex: Integer);
    property Count: Integer read GetCount;
  end;

  IsgCollectionBaseSort = interface(IsgCollectionBase)
    [cnstGUID_CollectionBaseSort]
    function GetDuplicates: TDuplicates;
    function GetSorted: Boolean;
    procedure SetDuplicates(const AValue: TDuplicates);
    procedure SetSorted(const AValue: Boolean);
    procedure SetProcCompare(const AValue: TsgObjProcCompare);
    property Sorted: Boolean read GetSorted write SetSorted;
    property Duplicates: TDuplicates read GetDuplicates write SetDuplicates;
  end;

  IsgCollectionInt = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): Integer;
    procedure SetItem(const AIndex: Integer; const AValue: Integer);
    property Items[const AIndex: Integer]: Integer read GetItem
      write SetItem; default;
  end;

  IsgCollectionInt64 = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): Int64;
    procedure SetItem(const AIndex: Integer; const AValue: Int64);
    property Items[const AIndex: Integer]: Int64 read GetItem
      write SetItem; default;
  end;

  IsgCollectionSingle = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): Single;
    procedure SetItem(const AIndex: Integer; const AValue: Single);
    property Items[const AIndex: Integer]: Single read GetItem
      write SetItem; default;
  end;

  IsgCollectionDouble = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): Double;
    procedure SetItem(const AIndex: Integer; const AValue: Double);
    property Items[const AIndex: Integer]: Double read GetItem
      write SetItem; default;
  end;

  IsgCollectionFloat = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): TsgFloat;
    procedure SetItem(const AIndex: Integer; const AValue: TsgFloat);
    property Items[const AIndex: Integer]: TsgFloat read GetItem
      write SetItem; default;
  end;

  IsgCollectionF2DPoint = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): TF2DPoint;
    procedure SetItem(const AIndex: Integer; const AValue: TF2DPoint);
    property Items[const AIndex: Integer]: TF2DPoint read GetItem
      write SetItem; default;
  end;

  IsgCollectionFPoint = interface(IsgCollectionBaseSort)
    function GetItem(const AIndex: Integer): TFPoint;
    procedure SetItem(const AIndex: Integer; const AValue: TFPoint);
    property Items[const AIndex: Integer]: TFPoint read GetItem
      write SetItem; default;
  end;

  IsgCollectionPointer = interface(IsgCollectionBaseSort)
    function Add(const AValue: Pointer): Integer;
    function IndexOf(const AValue: Pointer): Integer;
    function GetItem(const AIndex: Integer): Pointer;
    function GetFPointProc: TsgObjProcGetFPoint;
    function Remove(const AValue: Pointer): Integer;
    procedure SetItem(const AIndex: Integer; const AValue: Pointer);
    procedure SetFPointProc(const Value: TsgObjProcGetFPoint);
    property Items[const AIndex: Integer]: Pointer read GetItem
      write SetItem; default;
  end;

  TsgDrawingXMLData = record
    Guid: TGUID;
    Name: string;
    Index: Integer;
    Mode: Integer;
  end;

  IObjectAccess = interface
    ['{0410A9F4-D776-44BF-A612-1DE6661E3A30}']
    function GetObject(out AObject): HResult; stdcall;
  end;

  TsgStreamAdapter = class(TStreamAdapter, IObjectAccess)
  protected
    { IObjectAccess }
    function GetObject(out AObject): HResult; virtual; stdcall;
  public
{$IFDEF SGDEL_2006}
{$IFDEF VER300DOWN}
    function Stat(out statstg: TStatStg; grfStatFlag: Longint)
      : HResult; override;
{$ENDIF}
{$ENDIF}
  end;

  TsgOleStream = class(TStream)
  private
    FStream: IStream;
  protected
    function GetIStream: IStream;
  public
    constructor Create(const Stream: IStream);
    destructor Destroy; override;
    function Read(var Buffer; Count: Longint): Longint; override;
    function Write(const Buffer; Count: Longint): Longint; override;
    function Seek(Offset: Longint; Origin: Word): Longint; override;
  end;

  TsgMainUpdateMode = (mumSilent, mumFullUpdate, mumXmlInterfaceUpdate);

  IsgXMLOut = interface(IInterface)
    [cnstGUID_XMLOut]
    procedure AddToOutput(const Attribs: TStrings);
    procedure AddToOutputNV(const AName, AValue: string);
    procedure AddToError(const Attribs: TStrings);
    procedure AddToErrorNV(const AName, AValue: string);
  end;

  IsgMainApplication = interface(IInterface)
    [cnstGUID_MainApplication]
    procedure CreateUserMenu(const ANames: TStrings;
      const AClicks, AOnOPopups: TList; const AMode: Integer);
    procedure SetRibbonVisible(const Value: Boolean);
    function OpenFile(AFileName: string; AddResent: Boolean): Boolean;
    function LoadFromStream(AStream: TStream; AExt: string): Boolean;
    function SaveFileWithXmlParams(const AXMLParams: string;
      var AStream: TStream; var ANewCreated: Boolean;
      var AFormat: Integer): Integer;
    function SaveBitmapToStream(const ASource: TBitmap;
      const AExportParams: TObject; const AName: string;
      const AStream: TStream): Boolean;
    function CreateDrawing: TGUID;
    function ApplyXML(const AXMLParams: string; AOut: IsgXMLOut): Integer;
    procedure SetCurrDrawingSizes(const AWidth, AHeight: Integer);
    procedure SetDrawingChange(const AGuid: TGUID; const AMode: Integer;
      const AChange: Boolean);
    function CloseDrawingGuid(const AGuid: TGUID): Boolean;
    function GetActualGraphic(const AExportParams: TObject): TGraphic;
    function GetDrawingsCount: Integer;
    function GetDrawingGuid(const AIndex: Integer): TsgDrawingXMLData;
    function GetCurrentDrawingGuid: TGUID;
    function GetCADEditorCurrent: TObject;
    procedure WriteError(const AMessage: string);
    function RotateCurrentDrawing(const AX, AY, AZ: Double): Integer;
    procedure SetCurrentDrawingGuid(const AValue: TGUID);
    procedure MainUpdate(const AMode: TsgMainUpdateMode = mumSilent);
    property CurrentDrawingGuid: TGUID read GetCurrentDrawingGuid
      write SetCurrentDrawingGuid;
    property DrawingGuid[const AIndex: Integer]: TsgDrawingXMLData
      read GetDrawingGuid;
    property DrawingsCount: Integer read GetDrawingsCount;
  end;

  TsgXMLMessage = procedure(const S: WideString) of object;

  IsgXMLIde = interface(IInterface)
    [cnstGUID_XMLIde]
    function ProcessXML(AInput: string): string;
    function GetOnXMLMessage: TsgXMLMessage;
    procedure SetOnXMLMessage(const Value: TsgXMLMessage);
    property OnXMLMessage: TsgXMLMessage read GetOnXMLMessage
      write SetOnXMLMessage;
  end;

  TsgExternalPenMode = (epmNone, epmInternal, epmExternal);

  TsgExternalProps = class
  public
    UseExternalPen: TsgExternalPenMode;
    EntityHandle: Int64;
    Mode: TsgCustomSelectMode;
  end;

const

  { Mathematical Constants }
  cnst1DivPi = 1 / Pi;
  cnstCos30 = 0.86602540378443864676372317075294;
  cnstCos45 = 0.70710678118654752440084436210485;
  cnstCos60 = 0.5;
  cnstCrossYMat: TFMatrix = (M: ((1, 0, 0), (0, -1, 0), (0, 0, 1), (0, 0, 0)));
  cnstIdentityMat: TFMatrix = (M: ((1, 0, 0), (0, 1, 0), (0, 0, 1), (0, 0, 0)));
  cnstFract16: Double = 0.0000152587890625; // 1 / 2^16
  cnstFract32: Double = 0.00000000023283064365386962890625; // 1 / 2^32
  cnstPi = Pi;
  cnstPiDiv2 = cnstPi * 0.5;
  cnstPiMul2 = cnstPi * 2;
  cnstPiMul4 = cnstPi * 4;
  cnstSqrt2 = 1.4142135623730950488016887242097;
  cnstSqrt3 = 1.7320508075688772935274463415059;
  f180DividedByPi: Extended = 57.295779513082320876798154814105; // 180 / Pi
  // the value is used in the RotToView function
  fIsometricRotation = 54.735610317245345684622999669981;
  fPiDividedBy180: Extended = 0.017453292519943295769236907684886; // Pi / 180
  cnstMMPerInch = 25.4;

  cnstEmptyPoints = -1;
  cnstNoInitPoints = -2;
  cnstIndexesNoInit: TsgIndexes4 = (cnstNoInitPoints, cnstNoInitPoints,
    cnstNoInitPoints, cnstNoInitPoints);
  cnstIndexesEmpty: TsgIndexes4 = (cnstEmptyPoints, cnstEmptyPoints,
    cnstEmptyPoints, cnstEmptyPoints);
  cntBitPerByte = 8;
  cntBitPerWord = 16;
  cntLastBitInByte = SizeOf(Byte) * cntBitPerByte - 1;
  cntLastBitInWord = SizeOf(Word) * cntBitPerByte - 1;
  cntMulDiv8 = 3;

  { save result }
  cnstSaveResultOk = 0;
  cnstSaveResultError = 1;
  cnstSaveResultNeedParams = 2;
  cnstSaveResultUndefinedFormat = 3;
  cnstSaveResultUnsupportedFormat = 4;

  { boundary max, min, bad value }

  BadSingValue: Single = -24444444; // bad value for all singles
  cnstIllegal = -$5555 * 65536.0 * 65536.0;
  cnstMaxLongWord = High(LongWord);
  cnstNan = MaxDouble;
  cnstMaxByte = 255;
  cnstMaxWord = 65535;
  cnstMaxInt32 = 2147483647;
  cnstMinInt32 = Integer($80000000); // -2147483648;
  cnstMaxUInt32 = $FFFFFFFF;

  cMaxDoubleValue = 1.7E+10;
  cMinDoubleValue = -cMaxDoubleValue;

  { settings boundaries }
  cnstAnglesByPolarSnap: array [0 .. 8] of TsgFloat = (1, 5, 10, 15, 18, 22.5,
    30, 45, 90);

  { zooming constants }
  cnstScales: array [Boolean] of Double = (5 / 4, 4 / 5);
  cnstLTScale = 3 / 100;

  { graphics constants }

  arrDXFtoRGBColors: TsgCADPalett = ( // AutoCAD 8-bit colors
    $000000, $0000FF, $00FFFF, $00FF00, $FFFF00, $FF0000, $FF00FF, $FFFFFF,
    $808080, $C0C0C0, $0000FF, $7F7FFF, $0000CC, $6666CC, $000099, $4C4C99,
    $00007F, $3F3F7F, $00004C, $26264C, $003FFF, $7F9FFF, $0033CC, $667FCC,
    $002699, $4C5F99, $001F7F, $3F4F7F, $00134C, $262F4C, $007FFF, $7FBFFF,
    $0066CC, $6699CC, $004C99, $4C7299, $003F7F, $3F5F7F, $00264C, $26394C,
    $00BFFF, $7FDFFF, $0099CC, $66B2CC, $007299, $4C8599, $005F7F, $3F6F7F,
    $00394C, $26424C, $00FFFF, $7FFFFF, $00CCCC, $66CCCC, $009999, $4C9999,
    $007F7F, $3F7F7F, $004C4C, $264C4C, $00FFBF, $7FFFDF, $00CC99, $66CCB2,
    $009972, $4C9985, $007F5F, $3F7F6F, $004C39, $264C42, $00FF7F, $7FFFBF,
    $00CC66, $66CC99, $00994C, $4C9972, $007F3F, $3F7F5F, $004C26, $264C39,
    $00FF3F, $7FFF9F, $00CC33, $66CC7F, $009926, $4C995F, $007F1F, $3F7F4F,
    $004C13, $264C2F, $00FF00, $7FFF7F, $00CC00, $66CC66, $009900, $4C994C,
    $007F00, $3F7F3F, $004C00, $264C26, $3FFF00, $9FFF7F, $33CC00, $7FCC66,
    $269900, $5F994C, $1F7F00, $4F7F3F, $134C00, $2F4C26, $7FFF00, $BFFF7F,
    $66CC00, $99CC66, $4C9900, $72994C, $3F7F00, $5F7F3F, $264C00, $394C26,
    $BFFF00, $DFFF7F, $99CC00, $B2CC66, $729900, $85994C, $5F7F00, $6F7F3F,
    $394C00, $424C26, $FFFF00, $FFFF7F, $CCCC00, $CCCC66, $999900, $99994C,
    $7F7F00, $7F7F3F, $4C4C00, $4C4C26, $FFBF00, $FFDF7F, $CC9900, $CCB266,
    $997200, $99854C, $7F5F00, $7F6F3F, $4C3900, $4C4226, $FF7F00, $FFBF7F,
    $CC6600, $CC9966, $994C00, $99724C, $7F3F00, $7F5F3F, $4C2600, $4C3926,
    $FF3F00, $FF9F7F, $CC3300, $CC7F66, $992600, $995F4C, $7F1F00, $7F4F3F,
    $4C1300, $4C2F26, $FF0000, $FF7F7F, $CC0000, $CC6666, $990000, $994C4C,
    $7F0000, $7F3F3F, $4C0000, $4C2626, $FF003F, $FF7F9F, $CC0033, $CC667F,
    $990026, $994C5F, $7F001F, $7F3F4F, $4C0013, $4C262F, $FF007F, $FF7FBF,
    $CC0066, $CC6699, $99004C, $994C72, $7F003F, $7F3F5F, $4C0026, $4C2639,
    $FF00BF, $FF7FDF, $CC0099, $CC66B2, $990072, $994C85, $7F005F, $7F3F6F,
    $4C0039, $4C2642, $FF00FF, $FF7FFF, $CC00CC, $CC66CC, $990099, $994C99,
    $7F007F, $7F3F7F, $4C004C, $4C264C, $BF00FF, $DF7FFF, $9900CC, $B266CC,
    $720099, $854C99, $5F007F, $6F3F7F, $39004C, $42264C, $7F00FF, $BF7FFF,
    $6600CC, $9966CC, $4C0099, $724C99, $3F007F, $5F3F7F, $26004C, $39264C,
    $3F00FF, $9F7FFF, $3300CC, $7F66CC, $260099, $5F4C99, $1F007F, $4F3F7F,
    $13004C, $2F264C, $333333, $5B5B5B, $848484, $ADADAD, $D6D6D6, $FFFFFF);

  clByBlock = $3FFFFFFF; // dxf/dwg color ByBlock
  clByLayer = $2FFFFFFF; // dxf/dwg color ByLayer

  clDXFByBlock = 0;
  clDXFRed = 1;
  clDXFYellow = 2;
  clDXFGreen = 3;
  clDXFAqua = 4;
  clDXFBlue = 5;
  clDXFFuchsia = 6;
  clDXFBlackWhite = 7;
  clDXFGray = 8;
  clDXFSilver = 9;
  clDXFAlternativeBlack = 250; // for replacement of a clDXFBlackWhite
  clDXFDKGray = 251; // dark gray
  clDXFLTGray = 254; // light gray
  clDXFWhite = 255;
  clDXFByLayer = 256;

  cnstSnapMarkerSize = 8;

  cnstDefaultDrawingMode = 0; // dmNormal
  cnstBackgroundColor = clWhite;
  cnstDefaultColor = clBlack;

  cnstPrintBackground: TColor = clBlack;
  cnstPrintDefaultColor: TColor = clWhite;

  cnstPlotWindowAreaColor = $E1E1E1;
  cnstPlotPaperAreaColor = clWhite;
  cnstPlotBackground = $C0C0C0;

  cnstColorCADByBlock: TsgColorCAD = (Active: acIndexColor;
    Color: clDXFByBlock;);
  cnstColorCADByLayer: TsgColorCAD = (Active: acIndexColor;
    Color: clDXFByLayer;);
  cnstColorCADByBlackWhite: TsgColorCAD = (Active: acIndexColor;
    Color: clDXFBlackWhite;);
  cnstColorCADByWhite: TsgColorCAD = (Active: acRGBColor; Color: clWhite;);
  cnstDefaultEntityColor: TsgColorCAD = (Active: acIndexColor;
    Color: clDXFByLayer;);
  cnstColorCADNone: TsgColorCAD = (Active: acRGBColor; Color: clNone);

  cnstLimitByHatch = 1024 * 1024 * 32{$IFDEF SG_CPUX64} * 4{$ENDIF};
{$IFDEF DEBUG}
  cnstLimitTimeByHatch = 60000 * 10; // 10 minutes
{$ELSE}
  cnstLimitTimeByHatch = 60000 * 3; // three minutes
{$ENDIF}
  cnstMaxImgSize = 4096;
  cnstMaxImgSizeSqrt = cnstMaxImgSize * cnstMaxImgSize;
  cnstBadSize = $7FFF;
  cnstBad2DRect: TRect = (Left: cnstBadSize; Top: cnstBadSize;
    Right: - cnstBadSize; Bottom: - cnstBadSize);
  cnstBad2DRectExport: TRect = (Left: $7FFFFFF; Top: $7FFFFFF;
    Right: - $7FFFFFF; Bottom: - $7FFFFFF);
  cnstBadPoint: TFPoint = (X: cnstNan; Y: cnstNan; Z: cnstNan);
  cnstBadRect: TFRect = (Left: 1E20; Top: - 1E20; Z1: 1E20; Right: - 1E20;
    Bottom: 1E20; Z2: - 1E20);
  cnstBadRectF2D: TF2DRect = (Left: 1E20; Top: - 1E20; Right: - 1E20;
    Bottom: 1E20);
  cnstExtrusion: TFPoint = (X: 0; Y: 0; Z: 1);
  cnstF2DPointZero: TF2DPoint = ();
  cnstFPointIllegal: TFPoint = (X: cnstIllegal; Y: cnstIllegal; Z: 0);
  cnstFPointSingle: TFPoint = (X: 1; Y: 1; Z: 1);
  cnstFPointSingleYMinus: TFPoint = (X: 1; Y: - 1; Z: 1);
  cnstFPointSize = SizeOf(TFPoint) div SizeOf(Pointer);
  cnstFPointZero: TFPoint = ();
  cnstPointZero: TPoint = ();
  cnstRectZero: TRect = (Left: 0; Top: 0; Right: 0; Bottom: 0);
  cnstXOrtAxis: TFPoint = (X: 1; Y: 0; Z: 0);
  cnstYOrtAxis: TFPoint = (X: 0; Y: 1; Z: 0);
  cnstZOrtAxis: TFPoint = (X: 0; Y: 0; Z: 1);
  cnstFRectZero: TFRect = ();
  cnstF2DRectZero: TF2DRect = ();
  cnstObjectReserve: Pointer = Pointer($1);

  cnstMaxStringLen = 250;

  cnstPathFlag = 256;
  cnstPathEvacuationFlag = 512;
  cnstPolyPointsNotSolid = 2048;
  cnstPolySignMinus = 256;
  cnstPolySignPlus = 1024;

  { cadeditor constants }
  cnstConfirmUndefined = 0;
  cnstConfirmNo = 1;
  cnstConfirmYes = 2;
  cnstEntitySelectedModeDefault = 7;

  { path evacuation defaults }
  cnstColorCADByPathEvacuation: TsgColorCAD = (Active: acIndexColor;
    Color: 116);
  sLayerPathEvacuation: string = '';

  cnstCreateViewportInNewLayouts: Boolean = True; // for future versions

  cnstDefaulPrinter = 'DWF6 ePlot.pc3';
  cnstDefaulPaperWidth = 210;
  cnstDefaulPaperHeight = 297;
  cnstPrinterNone = 'None';
  cnstNoneDevice = 'none_device';
  cnstMargin = 3.2;
  cnstDefaultMargins: TF2DRect = (Left: cnstMargin; Top: cnstMargin;
    Right: cnstMargin; Bottom: cnstMargin);

  cnstUnprintableMarginWidth = 5;
  cnstUnprintableMarginHeight = cnstUnprintableMarginWidth *
    cnstDefaulPaperHeight / cnstDefaulPaperWidth;
  cnstUnprintableMargins: TF2DRect = (Left: cnstUnprintableMarginWidth;
    Top: cnstUnprintableMarginHeight; Right: cnstUnprintableMarginWidth;
    Bottom: cnstUnprintableMarginHeight);

  cnstDefaultLayoutWidth = cnstDefaulPaperHeight -
    cnstUnprintableMarginHeight * 2;

  cnstDefaultPlotSettingsData: TsgPlotSettingsData = (PageSetupName: '';
    PrintOrConfigName: cnstNoneDevice;
    PlotLayoutFlags: [plfUseStandardScale, plfPlotPlotStyles,
    plfPrintLineweights, plfDrawViewportsFirst]; PlotPaperUnits: ppuMM;
    StandardScaleType: 16; NumeratorOfCustomPrintScale: 1;
    DenominatorOfCustomPrintScale: 1; PaperSize: ''; PlotViewName: '';
    UnprintableMargin: (); PlotPaperSize: (); PlotOrigin: ();
    PlotWindowAreaMin: (); PlotWindowAreaMax: (); PlotRotation: prNoRotation;
    PlotType: ptLayoutInformation; CurrentStyleSheet: ''; ShadePlotMode: 0;
    ShadePlotResolutionLevel: 0; ShadePlotCustomDPI: 100;
    FloatingPointScaleFactor: 1; PaperImageOrigin: (););

  sgDefaultPlotSettingsData: TsgPlotSettingsData = (PageSetupName: '';
    PrintOrConfigName: cnstNoneDevice; PlotLayoutFlags: [plfUseStandardScale];
    PlotPaperUnits: ppuMM; StandardScaleType: 0; NumeratorOfCustomPrintScale: 1;
    DenominatorOfCustomPrintScale: 1; PaperSize: 'ISO_A4_(297.00_x_210.00_MM)';
    PlotViewName: ''; UnprintableMargin: (Left: 20; Top: 7.5; Right: 20;
    Bottom: 7.5); PlotPaperSize: (X: 210; Y: 297); PlotOrigin: ();
    PlotWindowAreaMin: (); PlotWindowAreaMax: ();
    PlotRotation: pr90DegreesCounterCW; PlotType: ptLayoutInformation;
    CurrentStyleSheet: ''; ShadePlotMode: 0; ShadePlotResolutionLevel: 0;
    ShadePlotCustomDPI: 100; FloatingPointScaleFactor: 1;
    PaperImageOrigin: (););

  { raster constant }
  iBitmapSizeWinNT: Integer = 300000000;
  iBitmapSizeWin98: Integer = 16777215;
{$IFDEF SG_EVACUATION}
  iJPEGQuality: Integer = 100;
{$ELSE}
  iJPEGQuality: Integer = 60;
{$ENDIF}
  iMetafileSizeMin = 64;
  iMetafileSizeMax = 31000;
  { string XML export constants }

const
  cnstXMLFileName = 'FileName';
  cnstXMLExternalFile = 'ExternalFile';
  // Dde params
  cnstParAbviewer = '-abviewer';
  cnstParCadEditorX = '-cadeditorx';
  cnstParInventory = '-inventory';
  cnstParCadView = '-cadviewx';
  // Clipping
  cnstXMLClipMode = 'ClipMode';
  cnstXMLClipRect = 'ClipRect';
  // Rastr
  cnstXMLExportParams = 'ExportParams';
  cnstXMLFormat = 'Format';
  cnstXMLWidth = 'Width';
  cnstXMLHeight = 'Height';
  cnstXMLMaxDim = 'MaxDim';
  cnstXMLQuality = 'Quality';
  cnstXMLMeasureInPixels = 'MeasureInPixels';
  cnstXMLTransparent = 'Transparent';
  cnstXMLTransparentColor = 'TransparentColor';
  cnstXMLDpuX = 'DPUX';
  cnstXMLDpuY = 'DPUY';
  cnstXMLSizeMode = 'SizeMode';
  cnstXMLCompression = 'Compression';
  cnstXMLPixelFormat = 'BitPerPixel';
  cnstXMLSaveProportion = 'Proportional';
  // Cad constant
  cnstXMLVersion = 'Version';
  cnstXMLPageWidth = 'PageWidth';
  cnstXMLPageHeight = 'PageHeight';
  cnstXMLMargin = 'Margin';
  cnstXMLDrawMode = 'DrawMode';
  cnstXMLBackgroundColor = 'BackgroundColor';
  cnstXMLDefaultColor = 'DefaultColor';
  cnstXMLNullWidth = 'NullWidth';
  cnstXMLLineWeightScale = 'LineWeightScale';
  cnstXMLSaveLineWeight = 'SaveLineWeight';
  cnstXMLCADQuality = 'CADQuality';
  cnstXMLLayoutExportMode = 'LayoutExportMode';
  cnstXMLLayoutNameExportMode = 'LayoutNameExportMode';
  cnstXMLTitle = 'Title';
  cnstXMLAuthor = 'Author';
  cnstXMLSubjct = 'Subjct';
  cnstXMLKeywords = 'Keywords';
  cnstXMLLineWeights = 'LineWeights';
  cnstXMLUseVectorLineWeight = 'UseVectorLineWeight';
  cnstXMLUseExtentsFromPlotSettings = 'UseExtentsFromPlotSettings';
  cnstXMLHPGLXScale = 'XScale';
  cnstXMLIsConvertImageToOLE = 'IsConvertImageToOLE';

  { string operation constants }

  cnstColor = 'Color';
  cnstColorIndex = 'Color Index';
  cnstColors = 'Colors';
  cnstColorByLayer = 'By Layer';
  cnstColorByBlock = 'By Block';
  cnstColorRed = 'Red';
  cnstColorYellow = 'Yellow';
  cnstColorGreen = 'Green';
  cnstColorLightBlue = 'LightBlue';
  cnstColorBlue = 'Blue';
  cnstColorPurple = 'Purple';
  cnstColorWhite = 'White';
  cnstColorBlackWhite = 'Black/White';
  cnstChooseColor = 'Select color...';
  cnstColorVariesValue = '*VARIES*';
  cnstEmptyFill = 'Empty fill';

  // Section Header
  cnstSectionHEADER = 'HEADER';

  // Section Entities
  cnstSectionENTITIES = 'ENTITIES';

  // Section Blocks
  cnstSectionBLOCKS = 'BLOCKS';

  // Brep constants
  cnstBrepCenterMass = 'CenterMass';
  cnstBrepVolume = 'Volume';
  cnstBrepArea = 'Area';
  cnstBrepOriginalName = 'OriginalName';
  cnstBrepBlock = 'sgBrepBlock_';

  // Section Tables
  cnstSectionTABLES = 'TABLES';
  cnstTableBLOCK_RECORD = 'BLOCK_RECORD';
  cnstTableAPPID = 'APPID';
  cnstTableDIMSTYLE = 'DIMSTYLE';
  cnstTableLAYER = 'LAYER';
  cnstTableLTYPE = 'LTYPE';
  cnstTableSTYLE = 'STYLE';
  cnstTableUCS = 'UCS';
  cnstTableVIEW = 'VIEW';
  cnstTableVPORT = 'VPORT';

  // Section Objects
  cnstObjectsCOLORS = 'COLORS';
  cnstObjectsDICTIONARY = 'DICTIONARY';
  cnstObjectsDICTIONARYVAR = 'DICTIONARYVAR';
  cnstObjectsFIELDLIST = 'FIELDLIST';
  cnstObjectsIMAGEDEFS = 'IMAGEDEFS';
  cnstObjectsLAYOUTS = 'LAYOUTS';
  cnstObjectsMATERIALS = 'MATERIALS';
  cnstObjectsMLINESTYLES = 'MLINESTYLES';
  cnstObjectsPLOTSETTINGS = 'PLOTSETTINGS';
  cnstObjectsSCALELIST = 'SCALELIST';
  cnstObjectsTABLESTYLES = 'TABLESTYLES';
  cnstSectionOBJECTS = 'OBJECTS';

  // Section Classes
  cnstSectionCLASSES = 'CLASSES';

  cnstEnumValuesDelimiter = '|';
  cnstXRefNameDelimiter = '|';
  cnstDStyle = 'DSTYLE';
  cnstMView = 'MVIEW';
  cnstAttMode = '$ATTMODE';
  cnstInternalBlockPrefix = '*';
  cnstObjects = cnstSectionOBJECTS;
  cnstDictionary = cnstObjectsDICTIONARY;
  cnstDictionaryVar = cnstObjectsDICTIONARYVAR;
  cnstGradientName: array [0 .. 8] of string = ('CURVED', 'CYLINDER',
    'HEMISPHERICAL', 'LINEAR', 'SPHERICAL', 'INVCURVED', 'INVCYLINDER',
    'INVHEMISPHERICAL', 'INVSPHERICAL');
  cnstGroupTypeName: array [TsgGroupType] of string = ('', 'BTI', 'SVG');
  cnstROOM: string = 'TEMPLATES';
  cnstROOMAREA: string = 'AREAS OF FILE';
  cnstROOMFILE: string = 'TEMPLATES OF FILE';
  cnstInCorrectBlockPattern: string = 'Incorrect blockpattern';
  cnstShowHandleAsHex = ' Handle = %X';
  cnstMeshBuilderDllPath: string = '';
  cnstMeshBuilderDllExistsTestWas: Boolean = False;
  cnstMeshBuilderNotUsing: Boolean = False;
  cnstDeviationCoefficientDefault = 0.01;
  cnstDeviationCoefficientRealistic = 0.0001;
  cnstLess = '<';
  cnstGreater = '>';
  cnstBackSlash = '\';
  cnstForwardSlash = '/';
  cnstVertSlash = '|';
  cnstCommaPoint = ';';
  cnstColon = ':';
  cnstCopyRight = Char($A9); { '©' }
  cnstLeftBracket = '{';
  cnstRigthBracket = '}';
  cnstRegisteredSign = Char($AE); { '®' }
  cnstSpace = ' ';
  cnstCaret = '^';
  cnstStar = '*';
  cnstBackQuote = '`';
  cnstEquals = '=';
  cnstCaretAndSpace = cnstCaret + cnstSpace;
  cnstComma = ',';
  cnstDegree = Char($B0); { '°' }
  cnstPlusMinusSign = '±';
  cnstPoint = '.';
  cnstPercent = '%';
  cnstAmpersant = '&';
  cnstQuestionMark = '?';
  cnstQuotationMark = '"';
  cnstExclamationPoint = '!';
  cnstEuro = Char($80); { 'ˆ' }
  cnstApos = '''';
  cnstLowLine = '_';
  cnstAt = '@';

  { cnstCheckSymbolAutoCadName : array[0..12] of Char = (
    cnstLess, cnstGreater, cnstForwardSlash, cnstBackSlash, cnstVertSlash,
    cnstCommaPoint, cnstComma, cnstQuestionMark, cnstQuotationMark, cnstColon,
    cnstStar, cnstEquals, cnstBackQuote); }

  sInvalidSymbolAutoCadName = cnstLess + cnstGreater + cnstForwardSlash +
    cnstBackSlash + cnstVertSlash + cnstCommaPoint + cnstComma +
    cnstQuestionMark + cnstQuotationMark + cnstColon + cnstStar + cnstEquals +
    cnstBackQuote;

  cnstInvalidSymbolAutoCadName = [cnstLess, cnstGreater, cnstForwardSlash,
    cnstBackSlash, cnstVertSlash, cnstCommaPoint, cnstComma, cnstQuestionMark,
    cnstQuotationMark, cnstColon, cnstStar, cnstEquals, cnstBackQuote];

  cnstSymbolAngle = cnstLess + ' ';
  cnstSymbolDegree = cnstDegree;

  cnstTypeDP = '%%';
  cnstTypeM = '\M+';
  cnstTypeU = '\U+';
  cnstXRecord = 'XRECORD';
  sACADXDataAppName = 'ACAD';
  sACADXDataAttribAppName = 'AcDbAttr';
  sActiveVPort = '*ACTIVE';
  cnstAdskConstraints = '*ADSK_CONSTRAINTS';
  sBackSlash = cnstBackSlash;
  sByBlock = 'BYBLOCK';
  sByLayer = 'BYLAYER';
  sCircle = 'Circle';
  sContinuous = 'CONTINUOUS';
  sCorruptedDWGFileHeader: string = 'DWG file header is corrupted';
  sDecompressDWGError: string = 'Unexpected error has occurred while DWG file '
    + 'decompressing';
  sDWG2007HeaderError: string = 'Error in DWG 2007 header';
  sDWGFileError: string = 'DWG is corrupted';
  sDXFConverterIsNotInitializedError: string = 'Converter is not initialized';
  sCADImageIsNotInitializedError: string = 'CADImage is not initialized';
  sXMLInterfaceVersionError
    : string = 'CADSoftTools XML version is not supported';
  sXMLInterfaceHatchCreatingError: string = 'Hatch was not created';
  sXMLInterfaceFileNotFoundError: string = 'File not found';
  sXMLInterfaceObjectNotFindHandle = 'Object with handle %s not found';
  sXMLInterfaceObjectsNotFind = 'Objects with handles not found';
  sXMLInterfaceInvalidGuid: string = 'Invalid Guid';
  sXMLInterfaceInvalidIndex: string = 'Invalid Index';
  sXMLInterfaceInvalidHandle: string = 'Invalid Handle';
  sXMLInterfaceFileLoadError: string = 'File not load';
  sXMLInterfaceComFrmError: string = 'Incorrect command format';
  sXMLInterfaceMainApplicationError: string = 'MainApplication nil';
  cnstXMLInterfaceEntityNotFoundError = 'Entity not found';
  cnstXMLInterfaceEntityNotSelectError = 'Entities not selected';
  cnstXMLInterfaceEntityNotHasAttributePoint = 'Attrubute Point not found';
  cnstXMLInterfaceSetValueNotFoundError = 'Set value not found';
  sXMLInterfaceEntityNotFoundError
    : string = cnstXMLInterfaceEntityNotFoundError;
  sXMLInterfaceEntityNotSelectError
    : string = cnstXMLInterfaceEntityNotSelectError;
  sXMLInterfaceEntityNotHasAttributePoint
    : string = cnstXMLInterfaceEntityNotHasAttributePoint;
  sDSFileIsNotInitializedError: string = 'Data segment file in not initialized';
  sDSFileIdexesHeaderReadError: string = 'Indexes header read error';
  sDSFileSegIndexError: string = 'Segment index is invalid';
  sDWGCompilerError: string = 'Unsupported compiler version for DWG %s';
  sEllipse = 'Ellipse';
  sEncryptedByPassword: string = 'Encrypted by password';
  sSatBinCodeError: string = 'Error SAT binary code';
  sCameraStyleIsNoSupported: string = 'Selected Camera Style is not supported';
  sCannotCreateGLBitmap: string = 'Cannot create GLBitmap';
  sGroupIsNotSupported: string = 'Group is not supported';
  sTriangleCount: string = '%d triangle(s)';
  cnstCADToGLSceneErrorWrongMode =
    'Export to "%s" file is possible only if 3D View mode is active.' + #13#10 +
    'Change "Display View" to any 3D mode and try again.';
  sCADToGLSceneErrorWrongMode: string = cnstCADToGLSceneErrorWrongMode;
  cnstCADToGLSceneErrorFileNameIsAbsent = 'Filename is not specified!';
  sCADToGLSceneErrorFileNameIsAbsent
    : string = cnstCADToGLSceneErrorFileNameIsAbsent;
  cnstDescrSTL = 'Stereolithography files';
  cnstDescrSAT = 'Spatial files';
  cnstDescrIGES = 'Initial Graphics Exchange Specification files';
  cnstDescrSTEP = 'STEP files';
  cnstDescrBrep = 'Brep files';
  MeshBuilderDll = 'MeshBuilder.dll';
  cnstMeshBuilderDLLError: string = MeshBuilderDll + ' ' + 'Cannot be loaded!';
  sEntNamesEx: array [-1 .. 14] of string = ('UNKNOW', 'DIMCONSTRUCTION',
    'CONSTRUCTION', 'COMPLEX', 'ELEMENT', 'COMPLEX BROAD', 'COMPLEX LINEAR',
    'ELEMENT BROAD', 'ELEMENT LINEAR', 'ELEMENT CARVED', 'AREA OBJECTS',
    'AREAS UNION', 'LABEL', 'DIMLABEL', 'BLOCK PATTERN', 'ELEMENT MODIFIER');
  sgDimensionArrowTypeNames: array [TsgDimArrowType] of string = ('',
    '_CLOSEDFILLED', '_CLOSEDBLANK', '_CLOSED', '_DOT', '_ARCHTICK', '_OBLIQUE',
    '_OPEN', '_ORIGIN', '_ORIGIN2', '_OPEN90', '_OPEN30', '_DOTSMALL',
    '_DOTBLANK', '_SMALL', '_BOXBLANK', '_BOXFILLED', '_DATUMBLANK',
    '_DATUMFILLED', '_INTEGRAL', '_USERARROW', '_NONE');
  sHatchEntity = 'HATCH';
  sHttp = 'http';
  sInternalDimension = 'sgDim';
  sInternalACADTable = '*TsgTbl';
  sLayerDefPoints = 'DEFPOINTS';
  sLayout = 'Layout';
  sLineWeightFactor = 'LineWeightDispFactor';
  sLoadEntities: string = 'Loading entities...';
  sLoadFile: string = 'Loading file...';
  sMessageAnalysing: string = 'Performing file analysing';
  sMessageCleaning: string = 'Performing file cleaning';
  sModel = 'Model';
  sModelSpace = '*MODEL_SPACE';
  sModelSpace12 = '$MODEL_SPACE';
  sNodeStageUndefined = 'Undefined Stage in TsgNode.Read!';
  sPage: string = 'Page';
  sPaperSpace = '*PAPER_SPACE';
  sPaperSpace12 = '$PAPER_SPACE';
  sPatternANSI31 = 'ANSI31'; // FDiagonal, BDiagonal
  sPatternANSI37 = 'ANSI37'; // DiagCross
  sPatternLINE = 'LINE'; // Horizintal, Vertical
  sPatternNET = 'NET'; // Cross
  sPatternSOLID = 'SOLID';
  sPolyline = 'Polyline';
  sRasterVariables = 'RASTERVARIABLES';
  sViewTableRecord = 'VIEW';
  sUCSTableRecord = 'UCS';
  sAppIDTableRecord = 'APPID';
  sBlockHeader = 'BLOCK HEADER';
  sBlockControl = 'BLOCK CONTROL';
  sShapeFileControl = 'SHAPEFILE CONTROL';
  sViewPortEntityControl = 'VIEWPORT ENTITY CONTROL';
  cntAcDb = 'AcDb';
  cntAcad = 'ACAD';
  cnstFileNameOfShapes = 'sgShapes.shx';
  sNamedObjectsDictionary = 'DICTIONARY (NAMED OBJECTS)';
  // see DWG documentation
  sAcadGroupDictionary = cntAcad + '_GROUP';
  sAcadColor = cntAcad + '_COLOR';
  sAcadMaterialDictionary = cntAcad + '_MATERIAL';
  sAcadWipeOutVarsDictionary = cntAcad + '_WIPEOUT_VARS';
  sAcadImageDict = cntAcad + '_IMAGE_DICT';
  sAcadImageVars = cntAcad + '_IMAGE_VARS';
  sMLineStyle = 'MlineStyle';
  sPlotSettingsMarker = 'PlotSettings';
  sXrecord = 'Xrecord';
  sAcDbPlotSettings = cntAcDb + sPlotSettingsMarker;
  sAcadMLineStyleDictionary = cntAcad + '_MLINESTYLE';
  sAcadLayoutDictionary = cntAcad + '_LAYOUT';
  sAcadScaleListDictionary = cntAcad + '_SCALELIST';
  sAcDbVariableDictionary = cntAcDb + 'VariableDictionary';
  sAcadMLeaderStyleDictionary = cntAcad + '_MLEADERSTYLE';
  sAcadPlotSettingsDictionary = cntAcad + '_PLOTSETTINGS';
  sAcadFieldListDictionary = cntAcad + '_FIELDLIST';
  sAcadTableStyleDictionary = cntAcad + '_TABLESTYLE';
  sDictionaryVarSORTENTS = 'SORTENTS';
  sDictionaryVarOLEFRAME = 'OLEFRAME';
  sDictionaryAcadDataLink = cntAcad + '_DATALINK';
  sAcadSortEnts = cntAcad + '_' + sDictionaryVarSORTENTS;
  sAcDbXrecord = cntAcDb + sXrecord;
  sAcDbColor = cntAcDb + 'Color';
  sDWGPropsDictionary = 'DWGPROPS';
  sDWGPropsXRecord = 'DWGPROPS COOKIE';
  sAcadScaleList = cntAcad + '_SCALELIST';
  sAcadXRecRoundTrip = sACADXDataAppName + '_XREC_ROUNDTRIP';
  sRedlineLayerName = 'Redline_layer';
  sRSBlockSizeError: string = 'Block size error';
  sRSDecoderError: string = 'RS decoder error. DWG file is corrupted!';
  sRSMaxErrors: string = 'The number of errors cannot be more than %d';
  sExporterAuthorInfo
    : string = 'Created by Soft Gold Ltd. www.cadsofttools.com';
  sWebAddress: string = 'www.cadsofttools.com';
  sSOLID = 'SOLID';
  sStandardName = 'STANDARD';
  sStringBreak = #1;
  sSlash = cnstForwardSlash;
  sSlashes = '://';
  sTempFileName = '~cs_temp_file_.';
  sUNKNOWN: string = 'UNKNOWN';
  sUnsupportedNewDWGVer: string = 'Unsupported new DWG version ID:';
  sUnsupportedOldDWGVer: string = 'Unsupported old DWG version ID:';
  sInvalidVersion: string = 'Unsuported version';
  sHatchMemoryLimit: string = 'Hatch Memory Limit';
  sHatchTimeLimit: string = 'Hatch Time Limit';
  sIncorrectNameLayer: string = 'Incorrect Layer Name';
  cnstSymbolUnicode = '\U+';
  cnstLoadError = 'Loading error';
  cnstParsingError = 'Parsing error';
  cnstCreatedFileInfo = 'Created by Soft Gold Ltd. www.cadsofttools.com';
  cnstMaxOLEStream = 1024 * 1024 * 7;
  cnstSceneElement = 'SceneElement';

  cnstVisualRound: Boolean = False;
{$IFDEF SG_BTI}
  cnstLeftSeporator = '%%';
  cnstRightSeporator = '%%';
  cnstActiveAxis: TsgAxisType = atLeft;
  cnstActivePoint: TsgActivePoint = apLeftTop;
  cnstAreaFigues: array [TsgFigureType] of string = ('Figure', 'Quadrangle',
    'Trapezium', 'Parallelogram', 'Rect', 'Square', 'Rhomb',
    'Segment by chord and length', 'Segment by chord and height', 'Triangle',
    'Right triangle', 'Triangle by hippuran', 'Circle by length',
    'Circle by radius', 'Sector by angle and radius', 'Contour');
  cnstParamType: array [TsgParamStrType] of string = (cnstEnumValuesDelimiter +
    'AREA', cnstEnumValuesDelimiter + 'NUMBER', cnstEnumValuesDelimiter +
    'SUBNUMBER', cnstEnumValuesDelimiter + 'LETNUMBER', cnstEnumValuesDelimiter
    + 'PERIMETER', cnstEnumValuesDelimiter + 'NUMBEROWNER',
    cnstEnumValuesDelimiter + 'VALUE', cnstEnumValuesDelimiter +
    'VALUEOWNER', '');
  cnstDefaultValueMask: string = cnstLeftSeporator + cnstEnumValuesDelimiter +
    'NUMBER' + cnstRightSeporator;
  sBoundaryVisible = 'BoundaryVisible';
  sGeron: string = 'Geron';
  sRadin: string = 'Radian';
  sSegmentAH: string = 'SegmentAH';
  sSegmentAL: string = 'SegmentAL';
  sSin: string = 'Sin';
  sSqr: string = 'Sqr';
  sSqrt: string = 'Sqrt';

  cnstBTIExtData = 'EXTDATA';
  cnstBTIFlags = 'Flags';
  cnstBTIAlignment = 'Alignment';
  cnstBTICarvingMode = 'CarvingMode';
  cnstBTIFillColor = 'FillColor';
  cnstBTIIsCircular = 'IsCircular';
  cnstBTILength = 'Length';
  cnstBTISegmentsCount = 'SegmentsCount';
  cnstBTISegmentWidths = 'SegmentWidths';
  cnstBTITypeSnapEntities = 'TypeSnapEntities';
  cnstBTIWidth = 'Width';
  cnstBTIValueMask = 'ValueMask';
  cnstBTIInsUnits = 'InsUnits';
  cnstBTILineType = 'LineType';
  cnstBTIParent = 'Parent';
  cnstBTIAttributes = 'Attributes';
  cnstBTIAttribut = 'Attribut';
  cnstBTIName = 'Name';
  cnstBTIValue = 'Value';
  cnstBTIType = 'Type';
  cnstBTIValues = 'Values';
  cnstBTIDelimiter = 'Delimiter';
{$ENDIF}
  { lisp text constants }

const
  cnstLispEnterFirstPoint = 'Enter first point';
  sLispEnterFirstPoint: string = cnstLispEnterFirstPoint;
  cnstLispEnterPoint = 'Enter point';
  sLispEnterPoint: string = cnstLispEnterPoint;
  cnstLispEnterNextPoint = 'Enter next point';
  sLispEnterNextPoint: string = cnstLispEnterNextPoint;

  cnstLispErrorCastAsBool = 'Lisp casting error: AsBool';
  sLispErrorCastAsBool: string = cnstLispErrorCastAsBool;
  cnstLispErrorCastAsInteger = 'Lisp casting error: AsInteger';
  sLispErrorCastAsInteger: string = cnstLispErrorCastAsInteger;
  cnstLispErrorCastAsList = 'Lisp casting error: AsList';
  sLispErrorCastAsList: string = cnstLispErrorCastAsList;
  cnstLispErrorCastAsReal = 'Lisp casting error: AsReal';
  sLispErrorCastAsReal: string = cnstLispErrorCastAsReal;
  cnstLispErrorTooFewArguments = 'Error: too few arguments';
  sLispErrorTooFewArguments: string = cnstLispErrorTooFewArguments;
  cnstLispErrorTooManyArguments = 'Error: too many arguments';
  sLispErrorTooManyArguments: string = cnstLispErrorTooManyArguments;
  cnstLispErrorUnknownFunction = 'Error: no function definition';
  sLispErrorUnknownFunction: string = cnstLispErrorUnknownFunction;

  { accuracy constants }

  cnstMinDist = 0.001; // 0.01;
  cnstSqrMinDist = cnstMinDist * cnstMinDist;
  fAccuracy = 0.000001; // It is necessary for comparison floating-point numbers
  fDoubleResolution = 1E-09; // 1E-15;
  fExtendedResolution = 1E-15;
  fMaxDoubleValue = 1E99;
  fMinDoubleValue = -1E99;
  fMaxResolution = 1E-100; // for invert matrix and calc matrix scale
  fDivDoubleResolution = 1 / fDoubleResolution;

{$IFNDEF SGDEL_6}
  NaN = 0.0 / 0.0;
(*$EXTERNALSYM NaN*)
(*$HPPEMIT 'static const Extended NaN = 0.0 / 0.0;'*)
{$ENDIF}
  { Group Codes in Numerical Order }
  Info_0 = 0;
  Text_1 = 1;
  Name_2 = 2;
  Text_3 = 3;
  Text_4 = 4;
  Text_5 = 5;
  LineTypeName_6 = 6;
  TextFont_7 = 7;
  LayerName_8 = 8;
  VarName_9 = 9;
  XFirst_10 = 10;
  XOther_11 = 11;
  XOther_12 = 12;
  XOther_13 = 13;
  XOther_14 = 14;
  XOther_15 = 15;
  XOther_16 = 16;
  XOther_17 = 17;
  XOther_18 = 18;
  YFirst_20 = 20;
  YOther_21 = 21;
  YOther_22 = 22;
  YOther_23 = 23;
  YOther_24 = 24;
  YOther_25 = 25;
  YOther_26 = 26;
  YOther_27 = 27;
  YOther_28 = 28;
  ZFirst_30 = 30;
  ZOther_31 = 31;
  ZOther_32 = 32;
  ZOther_33 = 33;
  ZOther_34 = 34;
  ZOther_35 = 35;
  ZOther_36 = 36;
  ZOther_37 = 37;
  Elevation_38 = 38;
  TableOfEntity_39 = 39;
  Float_40 = 40;
  Float_41 = 41;
  Float_42 = 42;
  Float_43 = 43;
  Float_44 = 44;
  Float_45 = 45;
  Float_46 = 46;
  Float_47 = 47;
  Float_48 = 48;
  FloatRepeated_49 = 49;
  Angle_50 = 50;
  Angle_51 = 51;
  Angle_52 = 52;
  Angle_53 = 53;
  Angle_54 = 54;
  Angle_55 = 55;
  Angle_56 = 56;
  Angle_57 = 57;
  Angle_58 = 58;
  Visible_60 = 60;
  ColorNumber_62 = 62;
  Integer_63 = 63;
  UCSVP_65 = 65;
  EntitysBegin_66 = 66;
  PaperSpace_67 = 67;
  Integer_68 = 68;
  Integer_69 = 69;
  Integer_70 = 70;
  Integer_71 = 71;
  Integer_72 = 72;
  Integer_73 = 73;
  Integer_74 = 74;
  Integer_75 = 75;
  Integer_76 = 76;
  Integer_77 = 77;
  Integer_78 = 78;
  Integer_79 = 79;
  Integer_90 = 90;
  Integer_91 = 91;
  Integer_92 = 92;
  Integer_93 = 93;
  Integer_94 = 94;
  Integer_97 = 97;
  String_100 = 100;
  XOther_110 = 110;
  XOther_111 = 111;
  XOther_112 = 112;
  YOther_120 = 120;
  YOther_121 = 121;
  YOther_122 = 122;
  ZOther_130 = 130;
  ZOther_131 = 131;
  ZOther_132 = 132;
  Float_140 = 140;
  Float_141 = 141;
  Float_142 = 142;
  Float_143 = 143;
  Float_144 = 144;
  Float_145 = 145;
  Float_146 = 146;
  Float_147 = 147;
  Float_148 = 148;
  Float_149 = 149;
  Integer_170 = 170;
  Integer_171 = 171;
  Integer_172 = 172;
  Integer_173 = 173;
  Integer_174 = 174;
  Integer_175 = 175;
  Integer_176 = 176;
  Integer_177 = 177;
  Integer_178 = 178;
  Float_211 = 211;
  Extrusion_210 = 210;
  Float_221 = 221;
  Extrusion_220 = 220;
  Extrusion_230 = 230;
  Float_231 = 231;
  Float_239 = 239;
  Integer_271 = 271;
  Word_280 = 280;
  Word_281 = 281;
  Word_282 = 282;
  Word_283 = 283;
  Word_284 = 284;
  Word_285 = 285;
  Word_286 = 286;
  Word_287 = 287;
  Word_288 = 288;
  Word_289 = 289;
  Integer_290 = 290;
  String_302 = 302;
  String_309 = 309;
  String_310 = 310;
  String_330 = 330;
  String_331 = 331;
  String_340 = 340;
  String_341 = 341;
  String_342 = 342;
  Integer_370 = 370;
  Integer_400 = 400;
  String_410 = 410;
  String_411 = 411;
  String_412 = 412;
  String_413 = 413;
  String_414 = 414;
  String_415 = 415;
  String_430 = 430;
  String_431 = 431;
  String_432 = 432;
  String_433 = 433;
  String_434 = 434;
  String_435 = 435;
  String_436 = 436;
  String_437 = 437;
  String_439 = 439;
  String_1000 = 1000;
  String_1001 = 1001;
  String_1002 = 1002;
  String_1003 = 1003;
  String_1005 = 1005;
  Float_1010 = 1010;
  Float_1020 = 1020;
  Float_1030 = 1030;
  Float_1040 = 1040;
  Float_1041 = 1041;
  Float_1042 = 1042;
  Integer_1070 = 1070;
  Integer_1071 = 1071;
  UserDigit = 23111;

  { consts by export }

  cnstOutFileInfo: Boolean = True;

  { consts record }
  cnstDefHeadVarStruct: TsgHeadVarStruct = (CEColor: (Active: acIndexColor;
    Color: clDXFByLayer;); // cnstDefaultEntityColor;
    CLayer: '0'; CELType: sByLayer; CELTScale: 1; CELWeight: - 1.0; CodePage: 0;
    DimStyle: sStandardName; DimTextStyle: sStandardName;
    DimProps: (Alt: False; AltF: 1; APost: ''; Asz: 0.18; Sah: False;
    Arrows: (Blk: datClosedfilled; Blk1: datClosedfilled; Blk2: datClosedfilled;
    LrBlk: datClosedfilled); Cen: 0.09; ClrD: (Active: acIndexColor;
    Color: clDXFByBlock;); ClrE: (Active: acIndexColor; Color: clDXFByBlock;);
    ClrT: (Active: acIndexColor; Color: clDXFByBlock;); SD1: False; SD2: False;
    SE1: False; SE2: False; Dec: 4; Exe: 0.18; Exo: 0.0625; Gap: 0.0625;
    LFac: 1; LwD: - 1.0; LwE: - 1.0; Post: ''; Scale: 1.0; Tad: 0; Tih: True;
    Tix: 0; Toh: True; Txt: 0.18;); TextStyle: sStandardName; FilletRadius: 0.5;
    InsUnits: Byte(iuMillimeters); LTScale: 1; Measurement: False;
    PointDisplayMode: 0; PointDisplaySize: 0; TextSize: 0.18; TileMode: 1;
    UCSORG: (X: 0; Y: 0; Z: 0); UCSXDir: (X: 1; Y: 0; Z: 0);
    UCSYDir: (X: 0; Y: 1; Z: 0); Version: 0; InsBase: (X: 0; Y: 0; Z: 0);
    AttMode: attNormal;);

  cnstSGHeadVarStruct: TsgHeadVarStruct = ();

  bCachingRasterMode: TsgCachingRasterMode = crmCache;
  cnstBorderType: TsgBorderType = btRatio;
  cnstFontParamsZero: TsgFontParams = ();
  cnstViewBoxZero: TsgViewBox = ();
  cnstIniHeadVar: TsgLittleHeadVarStruct = (InitFlags: []; DimDec: 2;
    DimLFac: 0.001; DimTxt: 150; DimTextAlign: 0;
    DimClrT: (Active: acIndexColor; Color: clDXFByBlock); DimGap: 100);
  cnstSnapMaskAll: TObjectSnapState = [osInsert, osEndPt, osCenter, osNode,
    osMiddle, osNearest, osIntersection, osNormal, osParallel];
  cnstSnapMaskNone: TObjectSnapState = [osDisabled];
  cnstSnapMemoryCash: Integer = 10000;
  cnstProxyInfo: TsgHTTPProxyInfo = (ProxyHost: ''; ProxyPort: 0;
    ProxyNeedPass: False; ProxyUser: ''; ProxyPass: '');

  { XML const DATA }
const
  cnstXML_UNSUPPORTED = -1;
  cnstXML_OK = 0;
  cnstXML_ERROR = 1;
  cnstXML_INCORRECT_PDMODE = 2;

  cnstXMLHeader = cnstSectionHEADER;
  cnstXMLTables = cnstSectionTABLES;
  cnstXMLBlocks = cnstSectionBLOCKS;
  cnstXMLEntities = cnstSectionENTITIES;
  cnstXMLObjects = cnstSectionOBJECTS;

  cnstXMLRootNode = 'cadsofttools';

  cnstXMLUnsupported = 'Unsupported';
  cnstXMLNotCorrectName = 'Not the correct name.';
  cnstXMLLineWeigthValueError = 'The lineweight value is out of range.';
  cnstXMLGlobalWidthValueError = 'The globalwidth value is out of range.';
  cnstXMLItemType: array [Boolean] of string = ('Attribute', 'Child');

type
  TsgXMLId = (xmlUndefined, xmlLineWeight, xmlFlags, xmlLineTypeScale,
    xmlLayerName, xmlLineTypeName, xmlName, xmlHandle, xmlSubEntities, xmlColor,
    xmlVisible, xmlLocked, xmlPoint, xmlBasePoint, xmlBulge, xmlStartWidth,
    xmlEndWidth, xmlPoint1, xmlLength, xmlBlockName, xmlExtrusion, xmlAngle,
    xmlScale, xmlAttribs, xmlHeight, xmlRotation, xmlObliqueAngle, xmlText,
    xmlStyleName, xmlAttribTag, xmlAttribValue, xmlArrowSize, xmlPoint2,
    xmlPoint3, xmlControlPoints, xmlCount, xmlKnotsPoints, xmlWeights,
    xmlFitPoints, xmlStartTangentVector, xmlEndTangentVector, xmlDegree,
    xmlKnot, xmlWeight, xmlRadius, xmlCircleLength, xmlArea, xmlEndAngle,
    xmlStartAngle, xmlRadPt, xmlRatio, xmlLineAngle, xmlOffset, xmlIsSolid,
    xmlLines, xmlDash, xmlStartPoint, xmlEndPoint, xmlCenterPoint, xmlEndParam,
    xmlStartParam, xmlMajorPoint, xmlColumnCount, xmlRowCount, xmlColSpacing,
    xmlRowSpacing, xmlRectWidth, xmlTextValue, xmlHatchName, xmlSolidFill,
    xmlWidth, xmlElevation, xmlPatternAngle, xmlPatternScale, xmlFileName,
    xmlDimScaleOverall, xmlJustify, xmlStart, xmlTurns, xmlTurnHeight,
    xmlClockwise, xmlACADVer, xmlCodePage, xmlTextStyle, xmlCLayer, xmlCELType,
    xmlCEColor, xmlCELTScale, xmlCELWeight, xmlDimStyle, xmlDimTextStyle,
    xmlDimBlk, xmlDimBlk1, xmlDimBlk2, xmlDimRBlk, xmlDimAlt, xmlDimAltF,
    xmlDimAPost, xmlDimAsz, xmlDimSah, xmlDimCen, xmlDimClrD, xmlDimClrE,
    xmlDimClrT, xmlDimSD1, xmlDimSD2, xmlDimSE1, xmlDimSE2, xmlDimDec,
    xmlDimExe, xmlDimExo, xmlDimGap, xmlDimLFac, xmlDimLwD, xmlDimLwE,
    xmlDimPost, xmlDimScale, xmlDimTad, xmlDimTih, xmlDimTix, xmlDimToh,
    xmlDimTxt, xmlExtMim, xmlExtMax, xmlFilletRadius, xmlInsUnits, xmlLTScale,
    xmlMeasurement, xmlPointDisplayMode, xmlPointDisplaySize, xmlTextSize,
    xmlTileMode, xmlUCSORG, xmlUCSXDir, xmlUCSYDir, xmlInsBase,
    xmlAttributeMode, xmlHeader, xmlTables, xmlBlocks, xmlEntities, xmlObjects,
    xmlPattern, xmlPatterns, xmlBoundary, xmlBoundaries, xmlPSpaceCenter,
    xmlMSpaceCenter, xmlViewDirection, xmlViewTarget, xmlPSpaceWidth,
    xmlPSpaceHeight, xmlFrontClipPlane, xmlBackClipPlane, xmlMSpaceHeight,
    xmlViewTwistAngle, xmlStatusField, xmlThisID, xmlClippingBoundaryHandle,
    xmlExtData, xmlHandleSave, xmlCircleZoomPercent, xmlUCSOrigin, xmlUCSVP,
    xmlViewAspectRatio, xmlViewCenterPoint, xmlViewHeight, xmlImageDef,
    xmlVertex, xmlVertexes, xmlClosed, xmlPeriodic, xmlRational,
    xmlPaperSpaceBlock, xmlUVector, xmlVVector, xmlSize, xmlCalc, xmlMode,
    xmlArrowhead, xmlLeaderPathType, xmlProperties, xmlDictionaryValue,
    xmlFPointScale, xmlZThick, xmlFrozen, xmlFrozenByNewViewPort, xmlXrefLink,
    xmlIsPlotting, xmlBigFont, xmlFixedHeight, xmlFontName, xmlFontStyle,
    xmlLastHeightUsed, xmlPrimaryFont, xmlTextGenFlags, xmlWidthFactor,
    xmlGlobalWidth, xmlArrowType, xmlArcDefPoint, xmlDefPoint, xmlLinDefPoint1,
    xmlLinDefPoint2, xmlMiddlePoint, xmlRadDefPoint, xmlTransparency,
    xmlTransparentColor, xmlDescription, xmlLayoutScale, xmlModelScale,
{$IFDEF SG_BREP_TOPOLOGY}
    xmlVolumeOCC, xmlAreaOCC, xmlCenterMassOCC, xmlOriginalNameOCC,
{$ENDIF}
    xmlClassId (* xmlClassId only last *) );

  TsgXMLType = record
    Id: TsgXMLId;
    ClassId: TClass;
  end;

  TsgXMLMode = (xmAddSubEntities, xmAddSectionEntities, xmNoSubEntitiesNode,
    xmCallHelp, xmOnlyChildNodes, xmlGetDefaultValue);
  TsgXMLModes = set of TsgXMLMode;

const
  cnstDefaultXMLMode = [xmAddSubEntities];

type

  TsgDataType = (dtUndefined, dtBool, dtByte, dtWord, dtInteger, dtInt64,
    dtColor, dtHandle, dtSingle, dtDouble, dtPointer, dtString, dtPoint,
    dtTF2DPoint, dtTFPoint, dtRect, dtTF2DRect, dtTFRect, dtVersion, dtColorCAD,
    // types by Description
    dtEntHandle, dtEntName, dtList, dtListItem, dtStringInternal, dtBase64,
    dtSingles, dtFPoints2DOr3D, dtProcedure, dtParameters, dtGuid);
  TsgDataTypes = set of TsgDataType;

const
cnstDataTypes:
array [TsgDataType] of record Name: string;
Description:
string;
end
= ((Name: 'Undefined'; Description: 'Undefined value'), (Name: 'Boolean';
  Description: 'Provides an enumeration of the logical True and False values'),
  (Name: 'Byte';
  Description
  : 'Supports positive integers from 0 to 255. Occupies 8 bits of storage'),
  (Name: 'Word';
  Description
  : 'Supports positive integers from 0 to 65535. Occupies 16 bits of storage'),
  (Name: 'Integer';
  Description
  : 'Supports positive and negative integers. Includes 1 bit sign, and 31 bits value'),
  (Name: 'Int64';
  Description
  : 'Supports positive and negative integers. Includes 1 bit sign, and 63 bits value'),
  (Name: 'Color';
  Description
  : 'Represents color values in range from -$7FFFFFFF-1 to $7FFFFFFF. The last 3 bytes represents R, G and B values correspondingly'),
  (Name: 'Handle'; Description: 'Direct Handle via $'), (Name: 'Single';
  Description: 'Supports single-precision floating-point values'),
  (Name: 'Double';
  Description: 'Supports double-precision floating-point values'),
  (Name: 'Pointer';
  Description: 'Provides a general use pointer to any memory based variable'),
  (Name: 'String';
  Description: 'Represents a string of chars, International alphabet'),
  (Name: 'Point';
  Description: 'Represents a record holding X and Y integer values'),
  (Name: 'F2DPoint';
  Description: 'Represents a record holding X and Y double values'),
  (Name: 'FPoint';
  Description: 'Represents a record holding X, Y and Z double values'),
  (Name: 'Rect';
  Description
  : 'Represents a record holding 2D rectangle integer values as either 4 coordinates or 2 points'),
  (Name: 'F2DRect';
  Description
  : 'Represents a record holding 2D rectangle double values as either 4 coordinates or 2 points'),
  (Name: 'FRect';
  Description
  : 'Represents a record holding 3D rectangle double values as either 6 coordinates or 2 points'),
  (Name: 'Version';
  Description
  : 'Represents a record holding major version and minor version integer numbers'),
  (Name: 'ColorCAD'; Description: 'Complex type: [0: Index | 1: RGB; Value;]'),
  // types by Description
  (Name: 'EntHandle'; Description: '$handle or @handle'), (Name: 'EntName';
  Description: 'String value representing an entity name'), (Name: 'List';
  Description: 'Represents a list ob objects'), (Name: 'ListItem';
  Description: 'Represents an object from a list'), (Name: 'StringInternal';
  Description: 'String value for internal use'), (Name: 'Base64';
  Description: 'Represents binary data as string'), (Name: 'Singles';
  Description: 'Represents list of Single values'), (Name: 'FPoints2DOr3D';
  Description: 'Represents list of F2DPoint or FPoint'), (Name: 'Procedure';
  Description: 'A method'), (Name: 'Parameters';
  Description: 'List of parameters'), (Name: 'Guid';
  Description: 'Represents a guid identifier'));

cnstClassIdUniqName = '{14D72A32-CDD2-40A4-BFC3-7D776CE0CA61}';
cnstXMLNames:
array [TsgXMLId] of record Name: string;
ValueType:
TsgDataType;
Description:
string;
end
= ((Name: ''; ValueType: dtUndefined; Description: ''), (Name: 'LineWeight';
  ValueType: dtDouble; Description: 'Line Weight in mm'), (Name: 'Flags';
  ValueType: dtInteger;
  Description
  : 'Flags are not suggested for usage. They have different meanings for particular entities, most of them are represented also directly via other attributes.'),
  (Name: 'LineTypeScale'; ValueType: dtDouble;
  Description: 'Scale for Line Type elements'), (Name: 'Layer';
  ValueType: dtEntName; Description: 'Name of a Layer'), (Name: 'LineType';
  ValueType: dtEntName; Description: 'Name of a LineType'), (Name: 'Name';
  ValueType: dtString; Description: 'Name string value'), (Name: 'Handle';
  ValueType: dtEntHandle; Description: 'Handle value'), (Name: 'SubEntities';
  ValueType: dtList; Description: 'Sub entities list'), (Name: 'Color';
  ValueType: dtColorCAD; Description: 'Color specified with TsgColorCAD'),
  (Name: 'Visible'; ValueType: dtBool;
  Description: 'Specifies entity visibility'), (Name: 'Locked';
  ValueType: dtBool; Description: 'Specifies entity editability'),
  (Name: 'Point'; ValueType: dtTFPoint;
  Description: '3D Point defining entity'), (Name: 'BasePoint';
  ValueType: dtTFPoint; Description: 'Base 3D point'), (Name: 'Bulge';
  ValueType: dtDouble; Description: 'Vertex bulge value'), (Name: 'StartWidth';
  ValueType: dtDouble; Description: 'Start width for a segment'),
  (Name: 'EndWidth'; ValueType: dtDouble;
  Description: 'End width for a segment'), (Name: 'Point1';
  ValueType: dtTFPoint; Description: '3D point defining entity'),
  (Name: 'Length'; ValueType: dtDouble; Description: 'Length value'),
  (Name: 'BlockName'; ValueType: dtEntName; Description: 'Name of a Block'),
  (Name: 'Extrusion'; ValueType: dtTFPoint;
  Description: 'Extrusion direction point'), (Name: 'Angle';
  ValueType: dtDouble; Description: 'Angle value'), (Name: 'Scale';
  ValueType: dtDouble; Description: 'Scale value'), (Name: 'Attribs';
  ValueType: dtList; Description: 'List of attributes'), (Name: 'Height';
  ValueType: dtDouble; Description: 'Height value'), (Name: 'Rotation';
  ValueType: dtDouble; Description: 'Rotation angle'), (Name: 'ObliqueAngle';
  ValueType: dtDouble; Description: 'Oblique angle'), (Name: 'Text';
  ValueType: dtString; Description: 'Text string'), (Name: 'StyleName';
  ValueType: dtString; Description: 'Name of a Style'), (Name: 'Tag';
  ValueType: dtString;
  Description: 'Attribute or attribute definition tag string'), (Name: 'Value';
  ValueType: dtString; Description: 'String value'), (Name: 'ArrowSize';
  ValueType: dtDouble; Description: 'Dimensioning arrow size'), (Name: 'Point2';
  ValueType: dtTFPoint; Description: '3D point defining entity'),
  (Name: 'Point3'; ValueType: dtTFPoint;
  Description: '3D point defining entity'), (Name: 'ControlPoints';
  ValueType: dtFPoints2DOr3D;
  Description: 'List of Controls for spline and based entities'),
  (Name: 'Count'; ValueType: dtInteger;
  Description: 'Number of members in list'), (Name: 'KnotsPoints';
  ValueType: dtFPoints2DOr3D;
  Description: 'List of Knots for spline based entities'), (Name: 'Weights';
  ValueType: dtSingles;
  Description: 'List of Weights for spline based entities'), (Name: 'FitPoints';
  ValueType: dtFPoints2DOr3D;
  Description: 'List of Fits for spline based entities'),
  (Name: 'StartTangentVector'; ValueType: dtTFPoint;
  Description: 'Start tangent direction point'), (Name: 'EndTangentVector';
  ValueType: dtTFPoint; Description: 'End tangent direction point'),
  (Name: 'Degree'; ValueType: dtDouble; Description: 'Degree value'),
  (Name: 'Knot'; ValueType: dtDouble;
  Description: 'Knot value for spline based entities'), (Name: 'Weight';
  ValueType: dtDouble; Description: 'Weight value for spline based entities'),
  (Name: 'Radius'; ValueType: dtDouble; Description: 'Radius value'),
  (Name: 'CircleLength'; ValueType: dtDouble;
  Description: 'Length of a circle'), (Name: 'Area'; ValueType: dtDouble;
  Description: 'Area value'), (Name: 'EndAngle'; ValueType: dtDouble;
  Description: 'End angle value'), (Name: 'StartAngle'; ValueType: dtDouble;
  Description: 'Start angle value'), (Name: 'RadPt'; ValueType: dtTFPoint;
  Description
  : 'End point of the major axis relative to the Center point for Ellipse'),
  (Name: 'Ratio'; ValueType: dtDouble;
  Description
  : 'Ratio of minor axis to major axis for elliptic entities or a two values ratio'),
  (Name: 'LineAngle'; ValueType: dtDouble;
  Description: 'Hatch line tilt angle'), (Name: 'Offset'; ValueType: dtTFPoint;
  Description: '3D offset point'), (Name: 'IsSolid'; ValueType: dtBool;
  Description: 'Specifies if pattern of a dotted line is solid'),
  (Name: 'Lines'; ValueType: dtList;
  Description: 'List of elements for dotted lines'), (Name: 'Dash';
  ValueType: dtDouble;
  Description: 'Dash element from list of elements for dotted lines'),
  (Name: 'StartPoint'; ValueType: dtTFPoint;
  Description: 'Start point, can be used with 2D and 3D entities'),
  (Name: 'EndPoint'; ValueType: dtTFPoint;
  Description: 'End point, can be used with 2D and 3D entities'),
  (Name: 'CenterPoint'; ValueType: dtTFPoint; Description: '3D center point'),
  (Name: 'EndParam'; ValueType: dtTFPoint;
  Description: 'End parameter for 2D Arc and inherited curves'),
  (Name: 'StartParam'; ValueType: dtTFPoint;
  Description: 'Start parameter for 2D Arc and inherited curves'),
  (Name: 'MajorPoint'; ValueType: dtTFPoint;
  Description
  : 'End point of the major axis relative to the Center point for 2D Ellipse'),
  (Name: 'ColumnCount'; ValueType: dtInteger; Description: 'Number of columns'),
  (Name: 'RowCount'; ValueType: dtInteger; Description: 'Number of rows'),
  (Name: 'ColSpacing'; ValueType: dtDouble; Description: 'Spacing for columns'),
  (Name: 'RowSpacing'; ValueType: dtDouble; Description: 'Spacing for rows'),
  (Name: 'RectWidth'; ValueType: dtDouble; Description: 'Width of a rectangle'),
  (Name: 'TextValue'; ValueType: dtString; Description: 'Text string value'),
  (Name: 'HatchName'; ValueType: dtString;
  Description: 'Name of a Hatch pattern'), (Name: 'SolidFill';
  ValueType: dtBool; Description: 'Specifies if a Hatch have solid filling'),
  (Name: 'Width'; ValueType: dtDouble; Description: 'Width value'),
  (Name: 'Elevation'; ValueType: dtTFPoint; Description: 'Elevation value'),
  (Name: 'PatternAngle'; ValueType: dtDouble;
  Description: 'Angle of lines in Hatch pattern'), (Name: 'PatternScale';
  ValueType: dtDouble; Description: 'Scale for Hatch pattern'),
  (Name: 'FileName'; ValueType: dtString; Description: 'File name string'),
  (Name: 'DimScaleOverall'; ValueType: dtDouble;
  Description: 'Overall dimensioning scale factor'), (Name: 'Justify';
  ValueType: dtInteger; Description: 'Specifies justification type'),
  (Name: 'Start'; ValueType: dtTFPoint; Description: 'Start point for Helix'),
  (Name: 'Turns'; ValueType: dtDouble;
  Description: 'Number of turns for Helix'), (Name: 'TurnHeight';
  ValueType: dtDouble; Description: 'Turn height for Helix'),
  (Name: 'Clockwise'; ValueType: dtBool;
  Description: 'Specifies if Helix is twisted clockwise'), (Name: 'ACADVer';
  ValueType: dtString;
  Description: 'Header variable. The AutoCAD drawing database version number'),
  (Name: 'CodePage'; ValueType: dtString;
  Description: 'Header variable. Drawing code page'), (Name: 'TextStyle';
  ValueType: dtString; Description: 'Header variable. Current text style name'),
  (Name: 'CLayer'; ValueType: dtString;
  Description: 'Header variable. Current layer name'), (Name: 'CELType';
  ValueType: dtString;
  Description: 'Header variable. Entity linetype name, or BYBLOCK or BYLAYER'),
  (Name: 'CEColor'; ValueType: dtColorCAD;
  Description: 'Header variable. Current entity color'), (Name: 'CELTScale';
  ValueType: dtDouble;
  Description: 'Header variable. Current entity linetype scale'),
  (Name: 'CELWeight'; ValueType: dtDouble;
  Description: 'Header variable. Lineweight of new objects'), (Name: 'DimStyle';
  ValueType: dtString; Description: 'Header variable. Dimension style name'),
  (Name: 'DIMTXSTY'; ValueType: dtString; Description: 'Dimension text style'),
  (Name: 'DimBlk'; ValueType: dtEntName; Description: 'Arrow block name'),
  (Name: 'DimBlk1'; ValueType: dtEntName;
  Description: 'First arrow block name'), (Name: 'DimBlk2';
  ValueType: dtEntName; Description: 'Second arrow block name'),
  (Name: 'DimRBlk'; ValueType: dtEntName;
  Description: 'Arrow block name for leaders'), (Name: 'DimAlt';
  ValueType: dtBool;
  Description: 'Alternate unit dimensioning performed if nonzero'),
  (Name: 'DimAltF'; ValueType: dtDouble;
  Description: 'Alternate unit scale factor'), (Name: 'DimAPost';
  ValueType: dtString; Description: 'Alternate dimensioning suffix'),
  (Name: 'DimAsz'; ValueType: dtDouble; Description: 'Dimensioning arrow size'),
  (Name: 'DimSah'; ValueType: dtBool;
  Description: 'Use separate arrow blocks if nonzero'), (Name: 'DimCen';
  ValueType: dtDouble; Description: 'Size of center mark/lines'),
  (Name: 'DimClrD'; ValueType: dtColorCAD; Description: 'Dimension line color'),
  (Name: 'DimClrE'; ValueType: dtColorCAD;
  Description: 'Dimension extension line color'), (Name: 'DimClrT';
  ValueType: dtColorCAD; Description: 'Dimension text color'), (Name: 'DimSD1';
  ValueType: dtBool; Description: 'Suppression of first extension line'),
  (Name: 'DimSD2'; ValueType: dtBool;
  Description: 'Suppression of second extension line'), (Name: 'DimSE1';
  ValueType: dtBool; Description: 'First extension line suppressed if nonzero'),
  (Name: 'DimSE2'; ValueType: dtBool;
  Description: 'Second extension line suppressed if nonzero'), (Name: 'DimDec';
  ValueType: dtInteger;
  Description
  : 'Number of decimal places for the tolerance values of aprimary units dimension'),
  (Name: 'DimExe'; ValueType: dtDouble;
  Description: 'Extension line extension'), (Name: 'DimExo';
  ValueType: dtDouble; Description: 'Extension line offset'), (Name: 'DimGap';
  ValueType: dtDouble; Description: 'Dimension line gap'), (Name: 'DimLFac';
  ValueType: dtDouble; Description: 'Linear measurements scale factor'),
  (Name: 'DimLwD'; ValueType: dtDouble;
  Description: 'Dimension line lineweight'), (Name: 'DimLwE';
  ValueType: dtDouble; Description: 'Extension line lineweight'),
  (Name: 'DimPost'; ValueType: dtString;
  Description: 'General dimensioning suffix'), (Name: 'DimScale';
  ValueType: dtDouble; Description: 'Overall dimensioning scale factor'),
  (Name: 'DimTad'; ValueType: dtInteger;
  Description: 'Text above dimension line if nonzero'), (Name: 'DimTih';
  ValueType: dtBool; Description: 'Text inside horizontal if nonzero'),
  (Name: 'DimTix'; ValueType: dtInteger;
  Description: 'Force text inside extensions if nonzero'), (Name: 'DimToh';
  ValueType: dtBool; Description: 'Text outside horizontal if nonzero'),
  (Name: 'DimTxt'; ValueType: dtDouble;
  Description: 'Dimensioning text height'), (Name: 'EXTMIN';
  ValueType: dtTFPoint;
  Description
  : 'Header variable. X, Y, and Z drawing extents lower-left corner (in WCS)'),
  (Name: 'ExtMax'; ValueType: dtTFPoint;
  Description
  : 'Header variable. X, Y, and Z drawing extents upper-right corner (in WCS)'),
  (Name: 'FILLETRAD'; ValueType: dtDouble;
  Description: 'Header variable. Fillet radius'), (Name: 'InsUnits';
  ValueType: dtInteger;
  Description
  : 'Header variable. Default drawing units for AutoCAD DesignCenter blocks'),
  (Name: 'LTScale'; ValueType: dtDouble;
  Description: 'Header variable. Global linetype scale'), (Name: 'Measurement';
  ValueType: dtInteger;
  Description: 'Header variable. Drawing units: 0 = English; 1 = Metric'),
  (Name: 'PDMODE'; ValueType: dtInteger;
  Description: 'Header variable. Point display mode'), (Name: 'PDSIZE';
  ValueType: dtDouble; Description: 'Header variable. Point display size'),
  (Name: 'TextSize'; ValueType: dtDouble;
  Description: 'Header variable. Default text height'), (Name: 'TileMode';
  ValueType: dtInteger;
  Description
  : 'Header variable. 1 for previous release compatibility mode; 0 otherwise'),
  (Name: 'UCSORG'; ValueType: dtTFPoint;
  Description: 'Header variable. Origin of current UCS (in WCS)'),
  (Name: 'UCSXDir'; ValueType: dtTFPoint;
  Description: 'Header variable. Direction of the current UCS X axis (in WCS)'),
  (Name: 'UCSYDir'; ValueType: dtTFPoint;
  Description: 'Header variable. Direction of the current UCS Y axis (in WCS)'),
  (Name: 'InsBase'; ValueType: dtTFPoint;
  Description: 'Header variable. Insertion base set by BASE command (in WCS)'),
  (Name: 'Attmode'; ValueType: dtInteger;
  Description
  : 'Header variable. Attribute visibility: 0 = None 1 = Normal 2 = All'),
  (Name: cnstXMLHeader; ValueType: dtList; Description: 'Header section'),
  (Name: cnstXMLTables; ValueType: dtList; Description: 'Tables section'),
  (Name: cnstXMLBlocks; ValueType: dtList; Description: 'Blocks section'),
  (Name: cnstXMLEntities; ValueType: dtList; Description: 'Entities section'),
  (Name: cnstXMLObjects; ValueType: dtList; Description: 'Objects section'),
  (Name: 'Pattren'; ValueType: dtList;
  Description: 'List of elements of a Hatch pattern'), (Name: 'Pattrens';
  ValueType: dtList; Description: 'List of patterns for Hatches'),
  (Name: 'Boundary'; ValueType: dtList;
  Description: 'List of elements forming a boundary of a Hatch'),
  (Name: 'Boundaries'; ValueType: dtList;
  Description: 'List of boundaries of a Hatch'), (Name: 'PSpaceCenter';
  ValueType: dtTFPoint; Description: 'Viewport center point on layout'),
  (Name: 'MSpaceCenter'; ValueType: dtTFPoint;
  Description: 'Viewport model view area center point'), (Name: 'ViewDirection';
  ValueType: dtTFPoint; Description: 'Viewport view direction vector (in WCS)'),
  (Name: 'ViewTarget'; ValueType: dtTFPoint;
  Description: 'Viewport view target point (in WCS)'), (Name: 'PSpaceWidth';
  ValueType: dtDouble; Description: 'Viewport width on layout'),
  (Name: 'PSpaceHeight'; ValueType: dtDouble;
  Description: 'Viewport height on layout'), (Name: 'FrontClipPlane';
  ValueType: dtDouble; Description: 'Viewport front cut off plane'),
  (Name: 'BackClipPlane'; ValueType: dtDouble;
  Description: 'Viewport back cut off plane'), (Name: 'MSpaceHeight';
  ValueType: dtDouble; Description: 'Viewport model view area height'),
  (Name: 'ViewTwistAngle'; ValueType: dtDouble;
  Description: 'Viewport view twist angle'), (Name: 'StatusField';
  ValueType: dtInteger; Description: 'Viewport status field'), (Name: 'ThisID';
  ValueType: dtInteger; Description: 'Viewport ID'),
  (Name: 'ClippingBoundaryHandle'; ValueType: dtHandle;
  Description
  : 'Handle of an entity that serves as a clipping boundary for the Viewport'),
  (Name: 'ExtData'; ValueType: dtStringInternal; Description: 'Extended data'),
  (Name: 'HandleSave'; ValueType: dtEntHandle;
  Description: 'Value for alternative access to a Handle'),
  (Name: 'CircleZoomPercent'; ValueType: dtInteger;
  Description: 'VPort circle zoom percent'), (Name: 'UCSOrigin';
  ValueType: dtTFPoint; Description: 'VPort UCS origin'), (Name: 'UCSVP';
  ValueType: dtBool; Description: 'Display UCS icon at UCS origin flag'),
  (Name: 'ViewAspectRatio'; ValueType: dtDouble;
  Description: 'VPort view aspect ratio'), (Name: 'ViewCenterPoint';
  ValueType: dtTFPoint; Description: 'VPort view center point'),
  (Name: 'ViewHeight'; ValueType: dtDouble; Description: 'VPort view height'),
  (Name: 'ImageDef'; ValueType: dtHandle;
  Description: 'Handle of ImageDef object of Image entity'), (Name: 'Vertex';
  ValueType: dtListItem; Description: 'Vertex element'), (Name: 'Vertexes';
  ValueType: dtList; Description: 'List of Vertexes'), (Name: 'Closed';
  ValueType: dtBool; Description: 'Specifies if entity is closed'),
  (Name: 'Periodic'; ValueType: dtBool;
  Description: 'Specifies if Spline based entity is periodic'),
  (Name: 'Rational'; ValueType: dtBool;
  Description: 'Specifies if Spline based entity is rational'),
  (Name: 'PaperSpaceBlock'; ValueType: dtEntName; Description: 'Layout name'),
  (Name: 'UVector'; ValueType: dtTFPoint;
  Description: 'UVector for Wipeout and inherited entities'), (Name: 'VVector';
  ValueType: dtTFPoint;
  Description: 'VVector for Wipeout and inherited entities'), (Name: 'Size';
  ValueType: dtTFPoint;
  Description: 'Size of image for Wipeout and inherited entities'),
  (Name: 'Calc'; ValueType: dtProcedure;
  Description: 'Alternative creation method'), (Name: 'Mode';
  ValueType: dtInteger; Description: 'Mode for alternative creation method'),
  (Name: 'Arrowhead'; ValueType: dtBool;
  Description: 'Specifies if arrowhead is present for Leader'),
  (Name: 'LeaderPathType'; ValueType: dtInteger;
  Description: 'Specifies if Leader path is spline'), (Name: 'Properties';
  ValueType: dtList; Description: 'Dimension style properties'),
  (Name: 'DictValue'; ValueType: dtString; Description: 'Dictionary value'),
  (Name: 'PScale'; ValueType: dtTFPoint; Description: 'Scale factor'),
  (Name: 'Thickness'; ValueType: dtDouble; Description: 'Thickness'),
  (Name: 'Frozen'; ValueType: dtBool;
  Description: 'Specifies if Layer is frozen'), (Name: 'FrozenByNewViewPort';
  ValueType: dtBool;
  Description: 'Specifies if Layer is frozen for new Viewports'),
  (Name: 'XrefLink'; ValueType: dtBool;
  Description: 'Specifies if entity is externally dependent on an xref'),
  (Name: 'IsPlotting'; ValueType: dtBool;
  Description: 'Specifies if this layer will be plotted'), (Name: 'BigFont';
  ValueType: dtString; Description: 'Bigfont file name for Style'),
  (Name: 'FixedHeight'; ValueType: dtDouble;
  Description: 'Fixed text heigh for Style'), (Name: 'FontName';
  ValueType: dtString; Description: 'Font name'), (Name: 'FontStyle';
  ValueType: dtInteger; Description: 'Font style'), (Name: 'LastHeightUsed';
  ValueType: dtDouble; Description: 'Last used font height for Style'),
  (Name: 'PrimaryFont'; ValueType: dtString;
  Description: 'Primary font file name for Style'), (Name: 'TextGenFlags';
  ValueType: dtInteger; Description: 'Text generation flags for Style'),
  (Name: 'WidthFactor'; ValueType: dtDouble;
  Description: 'Width factor for Style'), (Name: 'GlobalWidth';
  ValueType: dtDouble; Description: 'Global width value'), (Name: 'ArrowType';
  ValueType: dtByte; Description: 'Arrow type for entities'),
  (Name: 'ArcDefPoint'; ValueType: dtTFPoint;
  Description: 'Point defining dimension arc for angular Dimension'),
  (Name: 'DefPoint'; ValueType: dtTFPoint;
  Description: 'Definition point for Dimension'), (Name: 'LinDefPoint1';
  ValueType: dtTFPoint;
  Description: 'Start point of the first extension line for Dimension'),
  (Name: 'LinDefPoint2'; ValueType: dtTFPoint;
  Description: 'Start point of the second extension line for Dimension'),
  (Name: 'MiddlePoint'; ValueType: dtTFPoint;
  Description: 'Middle point of dimension text for Dimension'),
  (Name: 'RadDefPoint'; ValueType: dtTFPoint;
  Description: 'Definition point for diameter, radius, and angular Dimensions'),
  (Name: 'Transparency'; ValueType: dtBool;
  Description: 'Definition transparency for imageent'),
  (Name: 'TransparentColor'; ValueType: dtColor;
  Description: 'Definition transparent color for imageent'),
  (Name: 'Description'; ValueType: dtColor; Description: 'Description'),
  (Name: 'LayoutScale'; ValueType: dtColor; Description: 'Layout units scale'),
  (Name: 'ModelScale'; ValueType: dtColor; Description: 'Model units scale'),
{$IFDEF SG_BREP_TOPOLOGY}
  (Name: 'Volume'; ValueType: dtDouble;
  Description: 'Volume value, for BREP topology'), (Name: 'Area';
  ValueType: dtDouble; Description: 'Area value, for BREP topology'),
  (Name: 'CenterMass'; ValueType: dtTFPoint;
  Description: 'Center mass point, for BREP topology'), (Name: 'OriginalName';
  ValueType: dtString; Description: 'Original name, for BREP topology'),
{$ENDIF}
  (Name: cnstClassIdUniqName; ValueType: dtUndefined; Description: '')
  // alwas last element!
  );

cnstMaxSaveHandleXML = 200;
cnstMaxSaveHandleXMLError = cnstMaxSaveHandleXML + 1;
cnstSignHandle = cnstAt;
cnstXMLPrefix = 'cst';
cnstXMLValue = 'Value';
cnstXMLEnabled = 'Enabled';
cnstXMLValues = 'Values';
cnstXMLValuesSeparator = '|';
cnstXMLSuccess = 'Success';
cnstXMLError = 'Error';
cnstXMLErrors = 'Errors';
cnstXMLResult = 'Result';
cnstXMLResults = 'Results';
cnstXMLMessage = 'Message';
cnstXMLName = 'Name';
cnstXMLOutput = 'Output';
cnstXMLCommand = 'Command';
cnstXMLInstruction = 'Instruction';
cnstXMLValueError = 'value error';
cnstXMLType = 'Type';
cnstXMLTypeEvent = 'event';
cnstXMLTypeCommand = 'command';
cnstXMLException = 'Exception';
cnstXMLCreated = 'Created';
cnstXMLDeleted = 'Deleted';
cnstXMLUpdated = 'Updated';
cnstXMLPosition = 'Position';
cnstXMLParserError = 'Parser' + cnstXMLError;
cnstXMLIntfaceVersion:
TsgVersion = (Major: 2; Minor: 0);
cnstXMLWarning = 'Warning';
cnstXMLWarnings = cnstXMLWarning + 's';

{ consts }
cnstGenIso = 'GENISO';
cnstStandard = 'STANDARD';
cnstGost = 'GOST';
cnstActiveStyles:
array [TsgLangugeID] of string = (
{$IFNDEF SG_EVACUATION}
  cnstGenIso, cnstGost,
{$ELSE}
  cnstStandard, cnstStandard,
{$ENDIF}
  cnstStandard, cnstStandard, cnstStandard);

cnstCadStyles:
array [0 ..
{$IFNDEF SG_EVACUATION}2{$ELSE}0{$ENDIF}] of record LangIds: TsgLangugeIDs;
Name:
string;
Font:
string;
FFile:
string;
end
= ((LangIds: []; Name: cnstStandard; Font: 'Arial'; FFile: 'Arial.ttf')
{$IFNDEF SG_EVACUATION}
  , (LangIds: [lgAny]; Name: cnstGenIso; Font: ''; FFile: 'Geniso.shx'),
  (LangIds: [lgRussian]; Name: cnstGost; Font: ''; FFile: 'Gost.shx')
{$ENDIF}
  );

// bUseFastDraw: Boolean = True; //For future versions

bAutoCapturePoint:
Boolean = True;
bLineWeightOn:
Boolean = True;
cIPointsCnt = 8;
cnstArea = 16;
cnstBadHandle = 0;
cnstBlockPattern = MaxInt;
cnstBorderSize:
Double = 1 / 8;
cnstPrecisionFactor:
Integer = 4;
cnstClassID_HTML = 2;
cnstClassID_SVG = 1;
cnstClassID_XML = 0;
cnstComplex = 1;
cnstComplexArea = 17;
cnstComplexBroad = 3;
cnstComplexLinear = 4;
cnstConstruction = 0;
// {$IFDEF SG_EVACUATION} for future version
// cnstDefaultTTFFont = 'Arial';
// {$ELSE}
// cnstDefaultTTFFont = {$IFDEF SG_BTI_INTERFACE}'Gost'{$ELSE}'Arial'{$ENDIF};
// {$ENDIF}
cnstDefaultTTFFont = 'Arial';

cnstDefColor:
Integer = clWhite;
cnstDimConstruction = MAXBYTE;
cnstDimLabel = 33;
cnstElement = 2;
cnstElementBroad = 5;
cnstElementCarved = 7;
cnstElementLinear = 6;
cnstElementModifier = 8;
cnstLabel = 32;
cnstLoop4:
array [-3 .. 7] of Integer = (1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3);

cnstSizePrecision:
array [0 .. 8] of Byte = (0, 1, 2, 3, 4, 5, 6, 7, 8);
cnstSizeScale:
array [0 .. 24] of Double = (10000, 5000, 2000, 1000, 500, 200, 100, 50, 20, 10,
  5, 2, 1, 0.5, 0.2, 0.1, 0.05, 0.02, 0.01, 0.005, 0.002, 0.001, 0.0005,
  0.0002, 0.0001);
cnstUndefined = -1;
cnstUseProxy:
Boolean = False;
DXF_3DFACE = 20;
DXF_ACIS = 107;
DXF_ACIS_BEGIN = 106;
DXF_ACIS_END = 108;
DXF_ARC = 9;
DXF_ATTDEF = 17;
DXF_ATTRIB = 23;
DXF_BEGIN_INSERT = 102;
DXF_BEGIN_POLYLINE = 100;
DXF_BEGIN_VIEWPORT = 104;
DXF_BLOCK = 2;
DXF_CIRCLE = 8;
DXF_DIMENSION = 14;
DXF_ELLIPSE = 18;
DXF_END_INSERT = 103;
DXF_END_POLYLINE = 101;
DXF_END_VIEWPORT = 105;
DXF_HATCH = 21;
DXF_IMAGE_ENT = 22;
DXF_INSERT = 13;
DXF_LAYER = 4;
DXF_LINE = 6;
DXF_LTYPE = 3;
DXF_LWPOLYLINE = 11;
DXF_MTEXT = 16;
DXF_POINT = 19;
DXF_POLYLINE = 10;
DXF_SEC_BLOCKS = 1;
DXF_SEC_ENTITIES = 2;
DXF_SEC_LAYERS = 4;
DXF_SEC_LTYPE = 3;
DXF_SEC_TABLES = 0;
DXF_SOLID = 7;
DXF_SPLINE = 12;
DXF_TABLE = 1;
DXF_TEXT = 15;
DXF_UNKNOWN = 0;
DXF_VERTEX = 5;
fDXFLineWeightByBlock:
Double = -1.0;
fDXFLineWeightByLayer:
Double = -2.0;
fDXFLineWeightDefault:
Double = -3.0;
fLineWeightByBlock:
Double = -2.0;
fLineWeightByLayer:
Double = -1.0;
fLineWeightDefault:
Double = -3.0;
fLineWeightFactor:
Double = 1.0;
// Windows text height factor
fWinTextHeightFactor:
Extended = 1.6000000000;
// Windows text Y-offset factor by height
fWinTextYOffsetFactor:
Extended = 0.2700000000;
// Default numbers of parts for parsing circle
iDefaultNumberOfCircleParts = 48;
// Default numbers of parts for parsing spline
iDefaultNumberOfSplineParts = 24;
// Min numbers of parts for parsing spline and circle
iMinNumberOfPart = 5;
// Max numbers of parts for parsing spline and circle
iMaxNumberOfPart = 255;
iCurrentNumberOfCircleParts:
Integer = iDefaultNumberOfCircleParts;
iCurrentNumberOfSplineParts:
Integer = iDefaultNumberOfSplineParts;
iMaxNumDottedLines:
Integer = 8000; { Maximum count of the lines in a dotted polyline
  or curve (if count of lines more then
  iMaxNumDottedLines we draws solid-polyline) }
iMinNumberOfCircleParts = 4;
cnstDegreeOfSpline = 3;
sgDXFLineWeights:
array [0 .. 23] of Integer = (0, 5, 9, 13, 15, 18, 20, 25, 30, 35, 40, 50, 53,
  60, 70, 80, 90, 100, 106, 120, 140, 158, 200, 211);
{$IFDEF SG_UNITS_MM}
fCellMargin = 6.0;
fDoubleLineInterval = 4.5;
{$ELSE}
fCellMargin = 0.06;
fDoubleLineInterval = 0.045;
{$ENDIF}
{$IFDEF SG_BTI}
cnstAreaCreateMode:
Integer = 2;
cnstBoundaryVisible:
Boolean = True;
{$ENDIF}
cnst2DCurvePoly = 0;
cnst2DCurveLine = 1;
cnst2DCurveArc = 2;
cnst2DCurveEllipse = 3;
cnst2DCurveSpline = 4;
cnst2DCurveUndefined = 255;

cnstSoftwareSoftGold = 'Software\SoftGold\';
cnstCompany = 'Soft Gold';
cnstCompanyCST = 'CADSoftTools';
cnstResources = 'Resources';
cnstSHXPath = 'SHX';

SHX_FONTTYPE = 8;
cnstSHX_FONTTYPE:
TsgNativePointer = (SHX_FONTTYPE shl 24);
cnstSHX_FONTSHAPE:
TsgNativePointer = $10000000;

cntCRC8Table:
array [Byte] of Word = ($0000, $C0C1, $C181, $0140, $C301, $03C0, $0280, $C241,
  $C601, $06C0, $0780, $C741, $0500, $C5C1, $C481, $0440, $CC01, $0CC0, $0D80,
  $CD41, $0F00, $CFC1, $CE81, $0E40, $0A00, $CAC1, $CB81, $0B40, $C901, $09C0,
  $0880, $C841, $D801, $18C0, $1980, $D941, $1B00, $DBC1, $DA81, $1A40, $1E00,
  $DEC1, $DF81, $1F40, $DD01, $1DC0, $1C80, $DC41, $1400, $D4C1, $D581, $1540,
  $D701, $17C0, $1680, $D641, $D201, $12C0, $1380, $D341, $1100, $D1C1, $D081,
  $1040, $F001, $30C0, $3180, $F141, $3300, $F3C1, $F281, $3240, $3600, $F6C1,
  $F781, $3740, $F501, $35C0, $3480, $F441, $3C00, $FCC1, $FD81, $3D40, $FF01,
  $3FC0, $3E80, $FE41, $FA01, $3AC0, $3B80, $FB41, $3900, $F9C1, $F881, $3840,
  $2800, $E8C1, $E981, $2940, $EB01, $2BC0, $2A80, $EA41, $EE01, $2EC0, $2F80,
  $EF41, $2D00, $EDC1, $EC81, $2C40, $E401, $24C0, $2580, $E541, $2700, $E7C1,
  $E681, $2640, $2200, $E2C1, $E381, $2340, $E101, $21C0, $2080, $E041, $A001,
  $60C0, $6180, $A141, $6300, $A3C1, $A281, $6240, $6600, $A6C1, $A781, $6740,
  $A501, $65C0, $6480, $A441, $6C00, $ACC1, $AD81, $6D40, $AF01, $6FC0, $6E80,
  $AE41, $AA01, $6AC0, $6B80, $AB41, $6900, $A9C1, $A881, $6840, $7800, $B8C1,
  $B981, $7940, $BB01, $7BC0, $7A80, $BA41, $BE01, $7EC0, $7F80, $BF41, $7D00,
  $BDC1, $BC81, $7C40, $B401, $74C0, $7580, $B541, $7700, $B7C1, $B681, $7640,
  $7200, $B2C1, $B381, $7340, $B101, $71C0, $7080, $B041, $5000, $90C1, $9181,
  $5140, $9301, $53C0, $5280, $9241, $9601, $56C0, $5780, $9741, $5500, $95C1,
  $9481, $5440, $9C01, $5CC0, $5D80, $9D41, $5F00, $9FC1, $9E81, $5E40, $5A00,
  $9AC1, $9B81, $5B40, $9901, $59C0, $5880, $9841, $8801, $48C0, $4980, $8941,
  $4B00, $8BC1, $8A81, $4A40, $4E00, $8EC1, $8F81, $4F40, $8D01, $4DC0, $4C80,
  $8C41, $4400, $84C1, $8581, $4540, $8701, $47C0, $4680, $8641, $8201, $42C0,
  $4380, $8341, $4100, $81C1, $8081, $4040);

cntCRC32Table:
array [Byte] of Cardinal = ($00000000, $77073096, $EE0E612C, $990951BA,
  $076DC419, $706AF48F, $E963A535, $9E6495A3, $0EDB8832, $79DCB8A4, $E0D5E91E,
  $97D2D988, $09B64C2B, $7EB17CBD, $E7B82D07, $90BF1D91, $1DB71064, $6AB020F2,
  $F3B97148, $84BE41DE, $1ADAD47D, $6DDDE4EB, $F4D4B551, $83D385C7, $136C9856,
  $646BA8C0, $FD62F97A, $8A65C9EC, $14015C4F, $63066CD9, $FA0F3D63, $8D080DF5,
  $3B6E20C8, $4C69105E, $D56041E4, $A2677172, $3C03E4D1, $4B04D447, $D20D85FD,
  $A50AB56B, $35B5A8FA, $42B2986C, $DBBBC9D6, $ACBCF940, $32D86CE3, $45DF5C75,
  $DCD60DCF, $ABD13D59, $26D930AC, $51DE003A, $C8D75180, $BFD06116, $21B4F4B5,
  $56B3C423, $CFBA9599, $B8BDA50F, $2802B89E, $5F058808, $C60CD9B2, $B10BE924,
  $2F6F7C87, $58684C11, $C1611DAB, $B6662D3D, $76DC4190, $01DB7106, $98D220BC,
  $EFD5102A, $71B18589, $06B6B51F, $9FBFE4A5, $E8B8D433, $7807C9A2, $0F00F934,
  $9609A88E, $E10E9818, $7F6A0DBB, $086D3D2D, $91646C97, $E6635C01, $6B6B51F4,
  $1C6C6162, $856530D8, $F262004E, $6C0695ED, $1B01A57B, $8208F4C1, $F50FC457,
  $65B0D9C6, $12B7E950, $8BBEB8EA, $FCB9887C, $62DD1DDF, $15DA2D49, $8CD37CF3,
  $FBD44C65, $4DB26158, $3AB551CE, $A3BC0074, $D4BB30E2, $4ADFA541, $3DD895D7,
  $A4D1C46D, $D3D6F4FB, $4369E96A, $346ED9FC, $AD678846, $DA60B8D0, $44042D73,
  $33031DE5, $AA0A4C5F, $DD0D7CC9, $5005713C, $270241AA, $BE0B1010, $C90C2086,
  $5768B525, $206F85B3, $B966D409, $CE61E49F, $5EDEF90E, $29D9C998, $B0D09822,
  $C7D7A8B4, $59B33D17, $2EB40D81, $B7BD5C3B, $C0BA6CAD, $EDB88320, $9ABFB3B6,
  $03B6E20C, $74B1D29A, $EAD54739, $9DD277AF, $04DB2615, $73DC1683, $E3630B12,
  $94643B84, $0D6D6A3E, $7A6A5AA8, $E40ECF0B, $9309FF9D, $0A00AE27, $7D079EB1,
  $F00F9344, $8708A3D2, $1E01F268, $6906C2FE, $F762575D, $806567CB, $196C3671,
  $6E6B06E7, $FED41B76, $89D32BE0, $10DA7A5A, $67DD4ACC, $F9B9DF6F, $8EBEEFF9,
  $17B7BE43, $60B08ED5, $D6D6A3E8, $A1D1937E, $38D8C2C4, $4FDFF252, $D1BB67F1,
  $A6BC5767, $3FB506DD, $48B2364B, $D80D2BDA, $AF0A1B4C, $36034AF6, $41047A60,
  $DF60EFC3, $A867DF55, $316E8EEF, $4669BE79, $CB61B38C, $BC66831A, $256FD2A0,
  $5268E236, $CC0C7795, $BB0B4703, $220216B9, $5505262F, $C5BA3BBE, $B2BD0B28,
  $2BB45A92, $5CB36A04, $C2D7FFA7, $B5D0CF31, $2CD99E8B, $5BDEAE1D, $9B64C2B0,
  $EC63F226, $756AA39C, $026D930A, $9C0906A9, $EB0E363F, $72076785, $05005713,
  $95BF4A82, $E2B87A14, $7BB12BAE, $0CB61B38, $92D28E9B, $E5D5BE0D, $7CDCEFB7,
  $0BDBDF21, $86D3D2D4, $F1D4E242, $68DDB3F8, $1FDA836E, $81BE16CD, $F6B9265B,
  $6FB077E1, $18B74777, $88085AE6, $FF0F6A70, $66063BCA, $11010B5C, $8F659EFF,
  $F862AE69, $616BFFD3, $166CCF45, $A00AE278, $D70DD2EE, $4E048354, $3903B3C2,
  $A7672661, $D06016F7, $4969474D, $3E6E77DB, $AED16A4A, $D9D65ADC, $40DF0B66,
  $37D83BF0, $A9BCAE53, $DEBB9EC5, $47B2CF7F, $30B5FFE9, $BDBDF21C, $CABAC28A,
  $53B39330, $24B4A3A6, $BAD03605, $CDD70693, $54DE5729, $23D967BF, $B3667A2E,
  $C4614AB8, $5D681B02, $2A6F2B94, $B40BBE37, $C30C8EA1, $5A05DF1B, $2D02EF8D);

arDWGCodePages:
array [0 .. 60] of Word = (0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
  0, 0, 0, // 0..20
  0, 0, 0, 0, 0, 0, 0, // 21..27
  1250, // 28   ANSI_1250  ANSI - Central European
  1251, // 29   ANSI_1251  ANSI - Cyrillic
  1252, // 30   ANSI_1252  ANSI - Latin I
  0, // 31
  1253, // 32   ANSI_1253  ANSI - Greek
  1254, // 33   ANSI_1254  ANSI - Turkish
  1255, // 34   ANSI_1255  ANSI - Hebrew
  1256, // 35   ANSI_1256  ANSI - Arabic
  1257, // 36   ANSI_1257  ANSI - Baltic
  874, // 37   ANSI_874   ANSI/OEM - Thai (same as 28605, ISO 8859-15)
  932, // 38   ANSI_932   ANSI/OEM - Japanese, Shift-JIS
  936, // 39   ANSI_936   ANSI/OEM - Simplified Chinese (PRC, Singapore)
  949, // 40   ANSI_949   ANSI/OEM - Korean (Unified Hangul Code)
  950, // 41   ANSI_950   ANSI/OEM - Traditional Chinese (Taiwan;
  // Hong Kong SAR, PRC)
  1361, // 42   ANSI_1361  Win Korean Johab
  1200, // 43   ANSI_1200  Unicode (reserved)
  1258, // 44   ANSI_1258  ANSI/OEM - Vietnamese
  0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // 45..60
  );

arDWGVersions:
array [TsgDWGVersion] of Byte = (16, 17, 18, 19, 20, 21, 23, 25, 27, 29, 31);

const
  cnstSizeModeName: array [TSizeMode] of string = ('Actual', 'Maximum',
    'Custom', 'Same');
  cnstTiffCompessionName: array [TsgTIFFCompressionType] of string = ('LZW',
    'Deflate', 'JPEG', 'CCITT3', 'CCITT4', 'CCITT6', 'Rle', 'Auto', 'None');
  cnstPixelFormat: array [TPixelFormat] of string = ('Device', '1bit', '4bit',
    '8bit', '15bit', '16bit', '24bit', '32bit', 'Custom');

  cntClassDXFIMAGE = 'IMAGE';
  cntClassDXFMPOLYGON = 'MPOLYGON';
  cntClassDXFIMAGEDEF = 'IMAGEDEF';
  cntClassDXFIMAGEDEFREACTOR = 'IMAGEDEF_REACTOR';
  cntClassDXFWIPEOUT = 'WIPEOUT';
  cntClassDXFWIPEOUTVARIABLES = 'WIPEOUTVARIABLES';
  cntClassDXFACDB_MLEADERSTYLE_CLASS = 'ACDB_MLEADERSTYLE_CLASS';
  cntClassDXFEXAC_ESW = 'EXAC_ESW';
  cntClassDXFTABLESTYLE = 'TABLESTYLE';
  cntClassDXFACAD_TABLE = 'ACAD_TABLE';
  cntClassDXFACDBDICTIONARYWDFLT = 'ACDBDICTIONARYWDFLT';
  cntClassDXFSCALE = 'SCALE';
  cntClassDXFDICTIONARYVAR = 'DICTIONARYVAR';
  cntClassDXFCELLSTYLEMAP = 'CELLSTYLEMAP';
  cntClassDXFACDBPLACEHOLDER = 'ACDBPLACEHOLDER';
  cntClassDXFRASTERVARIABLES = sRasterVariables;
  cntClassDXFTABLEGEOMETRY = 'TABLEGEOMETRY';
  cntClassDXFLAYOUT = 'LAYOUT';

  cntImageExportAsImage = 0;
  cntImageExportAsOLE2Frame = 1;
  cntImageExportAsFile = 2;

  cnstWipeoutVariablesDisplayImageFrame = True;
  cnstRasterVariablesDisplayImageFrame = True;

  cntCPlusPlusClassNameRasterImage = cntAcDb + 'RasterImage';
  cntCPlusPlusClassNameRasterImageDef = cntAcDb + 'RasterImageDef';
  cntCPlusPlusClassNameImageDefReactor = cntCPlusPlusClassNameRasterImageDef +
    'Reactor';
  cntCPlusPlusClassNameWipeout = cntAcDb + 'Wipeout';
  cntCPlusPlusClassNameWipeoutVariables = cntAcDb + 'WipeoutVariables';
  cntCPlusPlusClassNameMPolygon = cntAcDb + 'MPolygon';
  cntCPlusPlusClassTableStyle = cntAcDb + 'TableStyle';
  cntCPlusPlusClassTable = cntAcDb + 'Table';
  cntCPlusPlusClassDictionaryWithDefault = cntAcDb + 'DictionaryWithDefault';
  cntCPlusPlusClassScale = cntAcDb + 'Scale';
  cntCPlusPlusClassDictionaryVar = cntAcDb + 'DictionaryVar';
  cntCPlusPlusClassCellStyleMap = cntAcDb + 'CellStyleMap';
  cntCPlusPlusClassPlaceHolder = cntAcDb + 'PlaceHolder';
  cntCPlusPlusClassLayout = cntAcDb + 'Layout';
  cntCPlusPlusClassRasterVariables = cntAcDb + 'RasterVariables';
  cntCPlusPlusClassTableGeometry = cntAcDb + 'TableGeometry';

  cntAppNameISM = 'ISM';
  cntAppNameWipeOutDXF = '"WipeOut"';
  cntAppNameWipeOutDWG =
    'WipeOut|AutoCAD Express Tool|expresstools@autodesk.com';
  cntAppNameAcMPolygonObj15DXF = '"AcMPolygonObj15"';
  cntAppNameAcMPolygonObj15DWG =
    'AcMPolygonObj15|Version(1.0.0.0) Product Desc:     Object enabler for the AcDbMPolygon entity|Company:          Autodesk,Inc.|WEB Address:      www.autodesk.com';
  cntAppNameObjectDBX = 'ObjectDBX Classes';

  cntItemClassIDEntity = $1F2;
  cntItemClassIDObject = $1F3;
  cntDWGObjCodeUNSUSED = 0;

  sAcadSectHeader = cntAcDb + ':Header';
  sAcadSectClasses = cntAcDb + ':Classes';
  sAcadSectHandles = cntAcDb + ':Handles';
  sAcadSectObjects = cntAcDb + ':AcDbObjects';
  sAcadSectSummaryInfo = cntAcDb + ':SummaryInfo';
  sAcadSectTemplate = cntAcDb + ':Template';
  sAcadSectPrototype = 'AcDb:' + 'AcDsPrototype_1b';

  cnstCRCInitUnknown = MaxInt;

  cnstFileHeaderCRCXOR: array [3 .. 6] of Word = ($A598, $8101, $3CC4, $8461);
  cntFileHeaderEndSentinel: TsgDWGSentinel = ($95, $A0, $4E, $28, $99, $82, $1A,
    $E5, $5E, $41, $E0, $5F, $9D, $3A, $4D, $00);

  cnstHeaderVarCRCInit = $C0C1;
  cnstHeaderVariablesBeginSentinel: TsgDWGSentinel = ($CF, $7B, $1F, $23, $FD,
    $DE, $38, $A9, $5F, $7C, $68, $B8, $4E, $6D, $33, $5F);
  cnstHeaderVariablesEndSentinel: TsgDWGSentinel = ($30, $84, $E0, $DC, $02,
    $21, $C7, $56, $A0, $83, $97, $47, $B1, $92, $CC, $A0);

  cnstClassesSectionCRCInit = cnstHeaderVarCRCInit;
  cnstClassesSectionBeginSentinel: TsgDWGSentinel = ($8D, $A1, $C4, $B8, $C4,
    $A9, $F8, $C5, $C0, $DC, $F4, $5F, $E7, $CF, $B6, $8A);
  cnstClassesSectionEndSentinel: TsgDWGSentinel = ($72, $5E, $3B, $47, $3B, $56,
    $07, $3A, $3F, $23, $0B, $A0, $18, $30, $49, $75);

  cnstImageDataBeginSentinel: TsgDWGSentinel = ($1F, $25, $6D, $07, $D4, $36,
    $28, $28, $9D, $57, $CA, $3F, $9D, $44, $10, $2B);
  cnstImageDataEndSentinel: TsgDWGSentinel = ($E0, $DA, $92, $F8, $2B, $C9, $D7,
    $D7, $62, $A8, $35, $C0, $62, $BB, $EF, $D4);

  cnstSecondFileHeaderCRCInit = cnstHeaderVarCRCInit;
  cnstSecondFileHeaderBeginSentinel: TsgDWGSentinel = ($D4, $7B, $21, $CE, $28,
    $93, $9F, $BF, $53, $24, $40, $09, $12, $3C, $AA, $01);
  cnstSecondFileHeaderEndSentinel: TsgDWGSentinel = ($2B, $84, $DE, $31, $D7,
    $6C, $60, $40, $AC, $DB, $BF, $F6, $ED, $C3, $55, $FE);

  cnstObjectCRCInit = cnstHeaderVarCRCInit;
  cnstSectionObjMapCRCInit = cnstHeaderVarCRCInit;
  cnstSectionObjMapMaxSize = 2032;

  cntDWGObjHandleType0 = 0;
  cntDWGObjHandleType2 = 2;
  cntDWGObjHandleType3 = 3;
  cntDWGObjHandleType4 = 4;
  cntDWGObjHandleType5 = 5;
  cntDWGObjHandleType6 = 6;
  cntDWGObjHandleType8 = 8;
  cntDWGObjHandleTypeA = $A;
  cntDWGObjHandleTypeC = $C;
  cntDWGObjHandleTypeMax = cntDWGObjHandleTypeC;

  cntDWGObjHandleSoftOwner = cntDWGObjHandleType2;
  cntDWGObjHandleHardOwner = cntDWGObjHandleType3;
  cntDWGObjHandleSoftPointer = cntDWGObjHandleType4;
  cntDWGObjHandleHardPointer = cntDWGObjHandleType5;

  cntDWGSectHeaderIndex = 0;
  cntDWGSectClassesIndex = 1;
  cntDWGSectHandlesIndex = 2;
  cntDWGSectObjectsIndex = 3;
  cntDWGSectSummaryInfoIndex = 4;
  cntDWGSectTemplateIndex = 5;
  cntDWGSectPrototypeIndex = 6;
  cntDWGSectMaxIndex = cntDWGSectPrototypeIndex;

  cnstDWGDictionaries: array [0 .. 11] of string = (sNamedObjectsDictionary,
    sAcadGroupDictionary, sAcadMaterialDictionary, sAcadMLineStyleDictionary,
    sAcadLayoutDictionary, sAcadScaleListDictionary, sAcDbVariableDictionary,
    sAcadMLeaderStyleDictionary, sAcadWipeOutVarsDictionary,
    sDWGPropsDictionary, sAcadImageDict, sAcadImageVars);

  cntViewPortPerspectiveLensLength = 50;
  cntViewPortCircleZoomPercent = 100;
  cntImageBrightness = 50;
  cntImageContrast = cntImageBrightness;
  cntImageFade = 0;
  cntXCodeDrwPropBase = 1;
  cntXCodeDrwPropTitle = 2;
  cntXCodeDrwPropSubject = 3;
  cntXCodeDrwPropAuthor = 4;
  cntXCodeDrwPropComments = 6;
  cntXCodeDrwPropKeywords = 7;
  cntXCodeDrwPropLastSavedBy = 8;
  cntXCodeDrwPropRevisionNumber = 9;
  cntXCodeDrwPropCustomSummaryInfo1 = 300;
  cntXCodeDrwPropCustomSummaryInfo2 = 301;
  cntXCodeDrwPropCustomSummaryInfo3 = 303;
  cntXCodeDrwPropCustomSummaryInfo4 = 304;
  cntXCodeDrwPropCustomSummaryInfo5 = 305;
  cntXCodeDrwPropCustomSummaryInfo6 = 306;
  cntXCodeDrwPropCustomSummaryInfo7 = 307;
  cntXCodeDrwPropCustomSummaryInfo8 = 308;
  cntXCodeDrwPropCustomSummaryInfo9 = 309;
  cntXCodeDrwPropUnknown40 = 40;
  cntXCodeDrwPropUnknown41 = 41;
  cntXCodeDrwPropUnknown42 = 42;
  cntXCodeDrwPropHyperlinkBase = 1;
  cntXCodeDrwPropCustomSummaryInfoCount = 90;
{$IFNDEF KEY_WOW64_32KEY}
  KEY_WOW64_32KEY = $0200;
{$EXTERNALSYM KEY_WOW64_32KEY}
{$ENDIF}
{$IFNDEF KEY_WOW64_64KEY}
  KEY_WOW64_64KEY = $0100;
{$EXTERNALSYM KEY_WOW64_64KEY}
{$ENDIF}
  cnstGeneratedHandlesCapacity = 1048576;

type
  TsgSATFileHeader = record
    Version: Integer;
    VersionOriginal: Integer;
    TotalNumRecords: Integer;
    CountNumOfEnt: Integer;
    LeastSignBit: Integer;
    FileProducerInfo: string;
    MillimetersByEachUnit: Double;
    Resabs: Double;
    Resnor: Double;
  end;

const
  // ACIS SAT file constants
  cntACISBinFileIdent: AnsiString = 'ACIS BinaryFile';
  cntSatBinTagChar = 2; // 1 byte integer value
  cntSatBinTagShort = 3; // 2 bytes integer value
  cntSatBinTagLong = 4; // 4 bytes integer value
  cntSatBinTagFloat = 5; // 4 bytes ftoaling point value
  cntSatBinTagDouble = 6; // 8 bytes ftoaling point value
  cntSatBinTagStr = 7;
  // followed by a char length value, followed by the specified
  // number of characters, or Tag 8, followed by a short length
  // value, followed by the specified number of characters, or Tag 9
  // followed by a long length value, followed by the specified
  // number of characters.
  cntSatBinTagStrWordSized = 8;
  cntSatBinTagStrLongSized = 9;
  cntSatBinTagLogicalTrue = 10;
  cntSatBinTagLogicalFalse = 11;
  cntSatBinTagPointer = 12;
  // $rec_num Pointer reference to a save file record number index
  cntSatBinTagStringIdent = 13;
  // followed by a char length value followed by the specified number of characters
  cntSatBinTagSubident = 14;
  // followed by a char length value followed by the specified number of characters
  cntSatBinTagSubtypeStart = 15;
  cntSatBinTagSubtypeEnd = 16;
  cntSatBinTagTerminator = 17;
  cntSatBinTagPosition = 19;
  // followed by 3 doubles representing x, y, z coordinates
  cntSatBinTagVector = 20;
  // followed by 3 doubles representing x, y, z components
  cntSatBinTagEnumChar = 21;
  cntSatDefVersion = 200;

  cntPtInxBodyLump = 3;
  cntPtInxBodyTransform = 5;

  cntPtInxLumpNextLump = 3;
  cntPtInxLumpNextLumpEarlyVersion = 2;
  cntPtInxLumpFirstShellInLump = 4;
  cntPtInxLumpBodyContainingLump = 1;

  cntPtInxShellNextShell = 3;
  cntPtInxShellFirstSubshellShell = 2;
  cntPtInxShellFirstFaceInShell = 5;
  cntPtInxShellLumpContainingShell = 1;

  cntPtInxFaceSurfaceOnWhichFaceLies = 7;
  cntPtInxFaceFirstLoopBoundingFace = 4;
  cntPtInxFaceNextFace = 3;

  cntPtInxLoopFirstCoedge = 4;
  cntPtInxLoopNextLoopInBoundaryOfFace = 3;

  cntPtInxCoedgeNextCoedge = 3;
  cntPtInxCoedgeEdge = 6;

  cntPtInxEdgeStartVertex = 3;
  cntPtInxEdgeEndVertex = 4;
  cntPtInxEdgeCurve = 6;

  cntPtInxVertexPoint = 4;
  cntPtInxVertexTVertexVertexPoint = 4;

  sSatRecNumPtr = '$';
  sSatSubtypeStart = '{';
  sSatSubtypeEnd = '}';
  sSatSubident = '-';
  sSatEofStr = '#';
  sSatDelimiter0 = ' '; // #$7F;
  cnstSAT_DS = '.';
  sSatBld = 'bld';
  sSatBldcur = 'bldcur';
  sSatBody = 'body';
  sSatBlend = 'blend';
  sSatClosed = 'closed';
  sSatShell = 'shell';
  sSatColorAdeskAttrib = 'color-adesk-attrib';
  sSatDXIDattrib1 = 'DXID-attrib';
  sSatDXIDattrib2 = '-attrib';
  sSatEdge = 'edge';
  sSatTEdge = 'tedge-edge';
  sSatCoedge = 'coedge';
  sSatTCoedge = 'tcoedge-coedge';
  sSatExact = 'exact';
  sSatExactcur = sSatExact + 'cur';
  sSatExactsur = sSatExact + 'sur';
  sSatExactIntCur = sSatExact + '_int_cur';
  sSatSweep = 'sweep';
  sSatSweepsur = sSatSweep + 'sur';
  sSatFace = 'face';
  sSatFull = 'full';
  sSatInt = 'int';
  sSatCurve = '-curve';
  sSatEllipseCurve = 'ellipse' + sSatCurve;
  sSatIntcurveWord = 'intcurve';
  sSatIntCurve = sSatIntcurveWord + sSatCurve;
  sSatStraightCurve = 'straight' + sSatCurve;
  sSatLoop = 'loop';
  sSatLump = 'lump';
  sSatNubs = 'nubs';
  sSatNull = 'null';
  sSatNullbs = 'nullbs';
  sSatNurbs = 'nurbs';
  sSatOpen = 'open';
  sSatPar = 'par';
  sSatParcur = 'parcur';
  sSatPeriodic = 'periodic';
  sSatSurface = '-surface';
  sSatPlaneSurface = 'plane' + sSatSurface;
  sSatTorusSurface = 'torus' + sSatSurface;
  sSatSphereSurface = 'sphere' + sSatSurface;
  sSatSplineSurface = 'spline' + sSatSurface;
  sSatConeSurface = 'cone' + sSatSurface;
  sSatPoint = 'point';
  sSatReversed = 'reversed';
  sSatReverse_v = 'reverse_v';
  sSatForward = 'forward';
  sSatSurf = 'surf';
  sSatSurfintcur = 'surfintcur';
  sSarIntIntCur = 'int_int_cur';
  sSatTVertex = 'tvertex-vertex';
  sSatVertex = 'vertex';
  sSatTransForm = 'transform';
  sSatAttrib = 'attrib';
  sSatUnknown = 'unknown';
  sSatHelix = 'helix';
  sSatBinFileBeginIndent: AnsiString = 'ACIS BinaryFile';
  sSatBinFileEndIndent
    : AnsiString = 'End'#$0E#$02'of'#$0E#$04'ACIS'#$0D#$04'data';
  sSatDefHeaderString = 'ACIS File Header';

  sSatTypeCurve: array [0 .. 3] of string = (sSatEllipseCurve, sSatIntCurve,
    sSatStraightCurve, sSatHelix);
  sSatTypeSpline: array [0 .. 4] of string = (sSatExact, sSatPar, sSatSurf,
    sSatBld, sSatBlend);
  sSatTypeSurface: array [0 .. 4] of string = (sSatConeSurface,
    sSatPlaneSurface, sSatTorusSurface, sSatSphereSurface, sSatSplineSurface);
  sSatTypeIntCur: array [0 .. 3] of string = (sSatExactcur, sSatSurfintcur,
    sSarIntIntCur, sSatExactIntCur);
  sSatTypeSplineSurface: array [0 .. 1] of string = (sSatExactsur,
    sSatSweepsur);
  sSatIdentClosureCurve: array [0 .. 2] of string = (sSatOpen, sSatClosed,
    sSatPeriodic);
  sSatIdentClosureSurface: array [0 .. 3] of string = (sSatOpen, sSatClosed,
    sSatPeriodic, sSatUnknown);
  sSatIdentType: array [0 .. 2] of string = (sSatNullbs, sSatNurbs, sSatNubs);
  sSatIdentSingularities: array [0 .. 3] of string = ('none', 'low',
    'high', 'both');

var
  // bUseTTFFonts: Boolean = False;
  bSearchSHXPaths: Boolean = True;
  bUseGDIPlusForRastImgRotate: Boolean = True;
  bUseSHXFonts: Boolean = True;
  bEasyEditing: Boolean = True;
  bEasyDrawing: Boolean = True;
  CADPreview: Boolean = False;
  KeepOriginal: Boolean = False; // save/load/assign original stream
  sDefaultSHXFont: string = 'simplex.shx'; // 'txt.shx';
  sDefaultSHXPath: string = '';
  sDefaultTTFFont: string = cnstDefaultTTFFont;
  sgClientRect: TRect = (Left: MaxInt; Top: MaxInt; Right: - MaxInt;
    Bottom: - MaxInt);
  sgClientRectForSnap: TRect;
  sgVisibleArea: TPoint; // !Snap!
  sSHXSearchPaths: string = '';
  vLogs: TList = nil;
  XMLIds: TStringList = nil;
{$IFDEF SG_MODULE_LOG}
  LogFileName: string = '';
  Log: TStringList = nil;
{$ENDIF}

function InsertSpace(S: string): string;
  function GetNumberOfCircleParts: Integer;
    function GetNumberOfSplineParts: Integer;
      function GetXMLHelp(AXMLType: TsgXMLType): string;

        procedure SetNumberOfCircleParts(const ANumber: Integer);
          procedure SetNumberOfSplineParts(const ANumber: Integer);

          { convert functions }
            function ConvertToMeasurePolylineOptions(const AValues: Integer)
              : TMeasurePolylineOptions;
              function ConvertFromMeasurePolylineOptions(const AValues
                : TMeasurePolylineOptions): Integer;

              // get string for TsgCADEntityType
                function GetCADEntityTypeString(ACADEntityType
                  : TsgCADEntityType): string;

                {
                  function GetPaperIndex

                  AName - paperspace block name

                  Function return paperspace index
                  -1:
                  0:   AName = '[*|$]MODEL_SPACE';
                  1:   AName = '[*|$]PAPER_SPACE';
                  2:   AName = '[*|$]PAPER_SPACE0';
                  3:   AName = '[*|$]PAPER_SPACE1';
                  ...
                  N+2:  [*|$]PAPER_SPACE[N];

                  Note: result is not layout index!!!
                }
                  function GetPaperIndex(const AName: string): Integer;

                  { make and create functions }

                    function CreatePFPoint2DProc(const AX, AY,
                      AZ: TsgFloat): Pointer;
                      function CreatePFPointProc(const AX, AY,
                        AZ: TsgFloat): Pointer;
                        function CreateParamData: PsgParamData;
                          function CreatePsgCurveLink(const AFlag: Byte)
                            : PsgCurveLnk;
                            procedure MakeArcs(const AArcs: TsgArcsParams;
                              var AArcR1, AArcR2: TsgArcR);
                              function MakePointFrom3D(const APoint: TFPoint;
                                const AGDI: Boolean = False): TPoint;
                                function MakeDXFFromFPoint
                                  (const AFPoint: TFPoint): TdxfPoint;
                                  function MakeDXFPoint(const AX, AY,
                                    AZ: Single): TdxfPoint;
                                    function MakeF2DPoint(const AX,
                                      AY: TsgFloat): TF2DPoint;
                                      function MakeF2DPointFrom3D
                                        (const APoint: TFPoint): TF2DPoint;
                                        function MakeF2DPointFromPoint
                                        (const APoint: TPoint): TF2DPoint;
                                        function MakeF2DRect(const ALeft, ATop,
                                        ARight, ABottom: TsgFloat): TF2DRect;
                                        function MakeF2DRectByPoints
                                        (const ALeftTop,
                                        ARightBottom: TF2DPoint): TF2DRect;
                                        function MakeF2dRectFromFRect
                                        (ARect: TFRect): TF2DRect;
                                        function MakeF2DLine(const A,
                                        B: TF2DPoint): TF2DLine;
                                        function MakeF2DLineFrom3D
                                        (const ALine: TsgLine): TF2DLine;
                                        function MakeFRectFromF2dRect
                                        (ARect: TF2DRect): TFRect;
                                        function MakeFPoint(const AX,
                                        AY: TsgFloat;
                                        const AZ: TsgFloat = 0): TFPoint;
                                        function MakeFPointFrom2D
                                        (const APoint: TF2DPoint): TFPoint;
                                        function MakeFPointFromDXF
                                        (const AdxfPoint: TdxfPoint): TFPoint;
                                        function MakeFPointFromPoint
                                        (const APoint: TPoint): TFPoint;
                                        function MakeFRect(const ALeft, ATop,
                                        AZ1, ARight, ABottom,
                                        AZ2: TsgFloat): TFRect;
                                        function MakeFRect2D(const ALeft, ATop,
                                        ARight, ABottom: Extended): TFRect;
                                        function MakeFRectByPoints
                                        (const ALeftTop,
                                        ARightBottom: TFPoint): TFRect;
                                        function MakeFRectByF2DPoints
                                        (const ALeftTop,
                                        ARightBottom: TF2DPoint): TFRect;
                                        function MakeLine(const APoint1,
                                        APoint2: TFPoint): TsgLine;
                                        procedure MakePoints3(const AP1, AP2,
                                        AP3: TFPoint; APoints3: PDouble);
                                        procedure MakePoints4(const AP1, AP2,
                                        AP3, AP4: TFPoint; APoints4: PDouble);
                                        procedure MakePoints4L
                                        (const AList: TList; APoints4: PDouble);
                                        function MakeRectFromFRect
                                        (const ARect: TFRect): TRect;
                                        function MakeRectFromF2DRect
                                        (const ARect: TF2DRect): TRect;
                                        function MakeRightPath
                                        (APath: string): string;
                                        function MakeViewBox(const AX, AY,
                                        AWidth, AHeight: Double): TsgViewBox;
                                        function MakeVersion(const AMajor,
                                        AMinor: Integer): TsgVersion;
                                        function NewFPoint
                                        (const APoint: TFPoint)
                                        : PFPoint; overload;
                                        function NewFPoint(const AX,
                                        AY: TsgFloat; const AZ: TsgFloat = 0)
                                        : PFPoint; overload;
                                        procedure SetMinMaxUInt64
                                        (const AHandle: UInt64;
                                        var AMin, AMax: UInt64);
                                        {$IFDEF SG_INLINE}inline; {$ENDIF}
                                        procedure SetBitmapTransparent
                                        (const ABitmap: TBitmap;
                                        const ATransparent: Boolean;
                                        const ATransparentColor
                                        : Integer = clEmpty);

                                        { Log procedure }
                                        procedure FileLoging
                                        (const AParam: TsgLogParam); overload;
                                        procedure FileLoging(const AOperation
                                        : TsgLogOperation;
                                        const AParam: Pointer;
                                        const AFileName: string = '';
                                        const AId: UInt64 = 0); overload;
                                        procedure RegisterLogger
                                        (const ALogger: TsgLogger);
                                        function UnRegisterLoger
                                        (const ALogger: TsgLogger): Boolean;

                                        { Supports for older versions }
{$IFNDEF SGDEL_2009}
                                        function AnsiStrAlloc(ASize: Cardinal)
                                        : PAnsiChar;
{$ENDIF}
                                        function BadRect: TFRect;
                                        function BadPoint: TFPoint;
                                        function MaxTsgFloat: Extended;
                                        function GetRectWidth
                                        (const ARect: TRect): Integer;
                                        {$IFDEF SG_INLINE}inline; {$ENDIF}
                                        function GetRectHeight
                                        (const ARect: TRect): Integer;
                                        {$IFDEF SG_INLINE}inline; {$ENDIF}
                                        // this functions uses in demos
                                        procedure ClearList(AList: TList;
                                        ClearCapacity: Boolean = True);
                                        procedure ClearListOfList
                                        (AListOfList: TList;
                                        ClearCapacity: Boolean = True);
                                        procedure ClearListWithNilCheck
                                        (AList: TList;
                                        ClearCapacity: Boolean = True);
                                        procedure ClearObjects
                                        (const AStrings: TStrings;
                                        Clear: Boolean = True);
                                        procedure ClearParamData
                                        (const APParam: PsgParamData);
                                        procedure ClearRecordList(AList: TList;
                                        ClearCapacity: Boolean = True);
                                        procedure ClearRecordListOfList
                                        (AListOfList: TList;
                                        ClearCapacity: Boolean = True);
                                        procedure ClearRecordObjects
                                        (const AStrings: TStrings;
                                        Clear: Boolean = True);
                                        procedure DisposeAndNil(var ARec);
                                        procedure DisposeDeleteFromList
                                        (AList: TList; const AIndex: Integer);
                                        // don't use for record with strings!
                                        procedure DisposeParamData
                                        (var AParam: PsgParamData);
                                        procedure FreeAndNil(var AObj);
                                        procedure FreeList(var AList: TList);
                                        procedure FreeListOfList
                                        (var AList: TList);
                                        procedure FreeMemAndNil(var P: Pointer);
                                        procedure FreeRecordList
                                        (var AList: TList);
                                        procedure FreeRecordListOfList
                                        (var AListOfList: TList);
                                        procedure FreeRecordStringList
                                        (var AList: TStrings);
                                        function IsZero(const A: Double;
                                        Epsilon: Double = 0): Boolean;
                                        function DistanceFPoint(const AP1,
                                        AP2: TFPoint;
                                        const AResolution
                                        : Double = fDoubleResolution): Double;
                                        function IsEqual(const A, B: Extended;
                                        AResolution
                                        : Extended = fDoubleResolution)
                                        : Boolean; overload;
                                        function IsEqual(const A, B: TsgFloat;
                                        AResolution: Double = fDoubleResolution)
                                        : Boolean; overload;
                                        function IsEqualFPoints(const Point1,
                                        Point2: TFPoint;
                                        Epsilon: Double =
                                        fDoubleResolution): Boolean;
                                        procedure SwapInts(var A,
                                        B: Cardinal); overload;
                                        procedure SwapInts(var A,
                                        B: Integer); overload;
                                        procedure CopyLists(const Destination,
                                        Source: TList;
                                        const AMode: TsgCopyMode = cmCopy);
                                        function GetDecimalSeparator: Char;
                                        function SetDecimalSeparator
                                        (const ADecimalSeparator: Char): Char;

                                        function GetAttributeMode
                                        (const AIndex: Integer)
                                        : TsgAttributeMode;
                                        function HasObject(const AObject,
                                        AObjectCurrent: Pointer): Boolean;
                                        {$IFDEF SG_INLINE}inline; {$ENDIF}
{$IFDEF SG_BTI}
                                        procedure ClearXDataStrings
                                        (var AXData: TsgExtendedData);
{$ENDIF}
                                        function SGHeadVarStruct
                                        (const AMM: Boolean =
{$IFDEF SG_UNITS_MM}True{$ELSE}False{$ENDIF}): TsgHeadVarStruct;
                                        function SGDefaultImageSize
                                        (const AMM: Boolean =
{$IFDEF SG_UNITS_MM}True{$ELSE}False{$ENDIF}): TFRect;

                                        function GetArrowByte
                                        (const AType: TsgDimArrowType): Byte;
                                        function GetArrowType(const AType: Byte)
                                        : TsgDimArrowType;
                                        function GetPlotRotation
                                        (const AType: Integer): TsgPlotRotation;

                                        // return supported dwg version by first bytes of content
                                        function GetAppID: string;
                                        function GetDWGVersion
                                        (const S: AnsiString;
                                        var AVersion: TsgDWGVersion): Integer;

{$IFNDEF SGDEL_5}
                                        function SameText(const S1,
                                        S2: string): Boolean;
{$ENDIF}
{$IFNDEF SGDEL_6}
                                        function WideUpperCase
                                        (const S: WideString): WideString;
{$ENDIF}
                                        function GetXMLId(const AName: string)
                                        : TsgXMLId;
                                        procedure CreateXMLIdTable;
                                        function GetSaveResultStr
                                        (const ASaveResult: Integer): string;

                                        // Interface references convertation
                                        function CreateStreamFromStgMedium
                                        (const AStgMed: TStgMedium;
                                        out AStream: TStream;
                                        var ANewCreated: Boolean): Boolean;

                                        var
                                        CodeTypes: PCodeTypes = nil;

implementation

uses SysUtils{$IFNDEF SGDEL_6}, ComObj{$ENDIF};

function GetNumberOfCircleParts: Integer;
begin
  Result := iCurrentNumberOfCircleParts;
  if Result < iMinNumberOfPart then
    Result := iDefaultNumberOfCircleParts;
end;

function GetNumberOfSplineParts: Integer;
begin
  Result := iCurrentNumberOfSplineParts;
  if Result < iMinNumberOfPart then
    Result := iDefaultNumberOfSplineParts;
end;

function InsertSpace(S: string): string;
var
  I: Integer;
{$IFNDEF SGDEL_2009UP}
  function IsUpper(C: Char): Boolean;
  begin
    Result := (C >= 'A') and (C <= 'Z');
  end;
{$ENDIF}

begin
  for I := Length(S) downto 2 do
    if IsUpper(S[I]) and not IsUpper(S[I - 1]) then
      Insert(' ', S, I);
  Result := S;
end;

function GetXMLHelp(AXMLType: TsgXMLType): string;
begin
  // Result := InsertSpace(cnstXMLNames[AXMLType.Id].Name)  + '; Type:' + cnstXMLTypes[AXMLType.Id];
end;

procedure SetNumber(const AValue, ADefault: Integer; var ANumber: Integer);
begin
  ANumber := AValue;
  if ANumber < iMinNumberOfPart then
    ANumber := ADefault
  else if ANumber > iMaxNumberOfPart then
    ANumber := iMaxNumberOfPart;
end;

procedure SetNumberOfCircleParts(const ANumber: Integer);
begin
  SetNumber(ANumber, iDefaultNumberOfCircleParts, iCurrentNumberOfCircleParts);
end;

function ConvertToMeasurePolylineOptions(const AValues: Integer)
  : TMeasurePolylineOptions;
var
  I: TMeasurePolylineOption;
  J: Integer;
begin
  Result := [];
  if AValues > 0 then
  begin
    J := 0;
    for I := Low(TMeasurePolylineOption) to High(TMeasurePolylineOption) do
    begin
      if AValues and (1 shl J) <> 0 then
        Include(Result, I);
      Inc(J);
    end;
  end;
end;

function ConvertFromMeasurePolylineOptions(const AValues
  : TMeasurePolylineOptions): Integer;
var
  I: TMeasurePolylineOption;
  J: Integer;
begin
  Result := 0;
  J := 0;
  for I := Low(TMeasurePolylineOption) to High(TMeasurePolylineOption) do
  begin
    if I in AValues then
      Result := Result or (1 shl J);
    Inc(J);
  end;
end;

procedure SetNumberOfSplineParts(const ANumber: Integer);
begin
  SetNumber(ANumber, iDefaultNumberOfSplineParts, iCurrentNumberOfSplineParts);
end;

function GetCADEntityTypeString(ACADEntityType: TsgCADEntityType): string;
begin
  Result := '';
  case ACADEntityType of
    etNone:
      Result := '';
    etCustomVertex:
      Result := 'CustomVertex';
    etLine:
      Result := 'Line';
    etPolyLine:
      Result := 'PolyLine';
    etLWPolyLine:
      Result := 'LWPolyLine';
    etRect:
      Result := 'Rect';
    etCircle:
      Result := 'Circle';
    etEllipse:
      Result := 'Ellipse';
    etMText:
      Result := 'MText';
    etLeader:
      Result := 'Leader';
    etPath:
      Result := 'Path';
    etInsert:
      Result := 'Insert';
    etBlock:
      Result := 'Block';
    etArc:
      Result := 'Arc';
    etMulti:
      Result := 'Multi';
    etDimAligned:
      Result := 'DimAligned';
    etHatch:
      Result := 'Hatch';
    etText:
      Result := 'Text';
    etSolid:
      Result := 'Solid';
    etSpline:
      Result := 'Spline';
    etViewPort:
      Result := 'ViewPort';
    etDimension:
      Result := 'Dimension';
    etSquare:
      Result := 'Square';
    etPoint:
      Result := 'Point';
    etPolyPolygon:
      Result := 'PolyPolygon';
    etClipInsert:
      Result := 'ClipInsert';
    etACADTable:
      Result := 'ACADTable';
    etTrace:
      Result := 'Trace';
    etTolerance:
      Result := 'Tolerance';
    etShape:
      Result := 'Shape';
    etAttdef:
      Result := 'Attdef';
    etMLine:
      Result := 'MLine';
    etWipeOut:
      Result := 'WipeOut';
    etImageEnt:
      Result := 'ImageEnt';
    etHelix:
      Result := 'Helix';
    etOle2Frame:
      Result := 'Ole2Frame';
    etCloud:
      Result := 'Cloud';
    etMPolygon:
      Result := 'MPolygon';
    etConstruction:
      Result := 'Construction';
    etDimConstruction:
      Result := 'DimConstruction';
    etComplex:
      Result := 'Complex';
    etElement:
      Result := 'Element';
    etComplexBroad:
      Result := 'ComplexBroad';
    etComplexLinear:
      Result := 'ComplexLinear';
    etElementBroad:
      Result := 'ElementBroad';
    etElementLinear:
      Result := 'ElementLinear';
    etElementCarved:
      Result := 'ElementCarved';
    etElementModifier:
      Result := 'ElementModifier';
    etArea:
      Result := 'Area';
    etComplexArea:
      Result := 'ComplexArea';
    etContainer:
      Result := 'Container';
    etProxy:
      Result := 'Proxy';
    etPathEvacuation:
      Result := 'PathEvacuation';
    etXRef:
      Result := 'XRef';
  end;
end;

function GetPaperIndex(const AName: string): Integer;
var
  vName: string;
  Err: Integer;
begin
  Result := -1;
  vName := AnsiUpperCase(AName);
  if (Length(vName) > 0) and (vName[1] = '$') then
    vName[1] := '*';
  if vName = sModelSpace then
    Result := 0
  else if Pos(sPaperSpace, vName) = 1 then
  begin
    Delete(vName, 1, Length(sPaperSpace));
    if Length(vName) = 0 then
      Result := 1
    else
    begin
      Val(vName, Result, Err);
      if Err > 0 then
        Result := -1
      else
        Inc(Result, 2);
    end;
  end;
end;

function CreatePFPoint2DProc(const AX, AY, AZ: TsgFloat): Pointer;
var
  vPFPoint: PFPoint;
begin
  New(vPFPoint);
  vPFPoint^ := MakeFPoint(AX, AY, 0);
  Result := vPFPoint;
end;

function CreatePFPointProc(const AX, AY, AZ: TsgFloat): Pointer;
var
  vPFPoint: PFPoint;
begin
  New(vPFPoint);
  vPFPoint^ := MakeFPoint(AX, AY, AZ);
  Result := vPFPoint;
end;

function CreateParamData: PsgParamData;
begin
  New(Result);
  FillChar(Result^, SizeOf(Result^), 0);
end;

function CreatePsgCurveLink(const AFlag: Byte): PsgCurveLnk;
begin
  New(Result);
  FillChar(Result^, SizeOf(Result^), 0);
  Result^.Flags := AFlag;
end;

procedure MakeArcs(const AArcs: TsgArcsParams; var AArcR1, AArcR2: TsgArcR);
begin
  AArcR1.Center := AArcs.Center;
  AArcR1.Radius := AArcs.Radius1;
  AArcR1.AngleS := AArcs.AngleS1;
  AArcR1.AngleE := AArcs.AngleE1;

  AArcR2.Center := AArcs.Center;
  AArcR2.Radius := AArcs.Radius2;
  AArcR2.AngleS := AArcs.AngleS2;
  AArcR2.AngleE := AArcs.AngleE2;
end;

function MakeDXFFromFPoint(const AFPoint: TFPoint): TdxfPoint;
begin
  Result.X := AFPoint.X;
  Result.Y := AFPoint.Y;
  Result.Z := AFPoint.Z;
end;

function MakeDXFPoint(const AX, AY, AZ: Single): TdxfPoint;
begin
  Result.X := AX;
  Result.Y := AY;
  Result.Z := AZ;
end;

function MakeF2DPoint(const AX, AY: TsgFloat): TF2DPoint;
begin
  Result.X := AX;
  Result.Y := AY;
end;

function MakeF2DPointFrom3D(const APoint: TFPoint): TF2DPoint;
begin
  Result.X := APoint.X;
  Result.Y := APoint.Y;
end;

function MakeF2DPointFromPoint(const APoint: TPoint): TF2DPoint;
begin
  Result.X := APoint.X;
  Result.Y := APoint.Y;
end;

function MakeF2DRect(const ALeft, ATop, ARight, ABottom: TsgFloat): TF2DRect;
begin
  Result.Left := ALeft;
  Result.Top := ATop;
  Result.Right := ARight;
  Result.Bottom := ABottom;
end;

function MakeF2DRectByPoints(const ALeftTop, ARightBottom: TF2DPoint): TF2DRect;
begin
  Result.TopLeft := ALeftTop;
  Result.BottomRight := ARightBottom;
end;

function MakeF2dRectFromFRect(ARect: TFRect): TF2DRect;
begin
  Result.Left := ARect.Left;
  Result.Top := ARect.Top;
  Result.Bottom := ARect.Bottom;
  Result.Right := ARect.Right;
end;

function MakeF2DLine(const A, B: TF2DPoint): TF2DLine;
begin
  Result.Point1 := A;
  Result.Point2 := B;
end;

function MakeF2DLineFrom3D(const ALine: TsgLine): TF2DLine;
begin
  Result.Point1.X := ALine.Point1.X;
  Result.Point1.Y := ALine.Point1.Y;
  Result.Point2.X := ALine.Point2.X;
  Result.Point2.Y := ALine.Point2.Y;
end;

function MakeFRectFromF2dRect(ARect: TF2DRect): TFRect;
begin
  Result.TopLeft := MakeFPoint(ARect.TopLeft.X, ARect.TopLeft.Y, 0);
  Result.BottomRight := MakeFPoint(ARect.BottomRight.X, ARect.BottomRight.Y, 0);
end;

function MakeRectFromFRect(const ARect: TFRect): TRect;
begin
  Result := MakeRectFromF2DRect(MakeF2dRectFromFRect(ARect));
end;

function MakeRectFromF2DRect(const ARect: TF2DRect): TRect;

  function GetValue(const AValue: Double): Integer;
  begin
    if AValue >= cnstMaxInt32 then
      Result := cnstMaxInt32
    else if AValue <= cnstMinInt32 then
      Result := cnstMinInt32
    else
      Result := Round(AValue);
  end;

begin
  Result.Top := GetValue(ARect.Top);
  Result.Left := GetValue(ARect.Left);
  Result.Bottom := GetValue(ARect.Bottom);
  Result.Right := GetValue(ARect.Right);
end;

function MakeFPoint(const AX, AY: TsgFloat; const AZ: TsgFloat = 0): TFPoint;
begin
  Result.X := AX;
  Result.Y := AY;
  Result.Z := AZ;
end;

function MakeFPointFrom2D(const APoint: TF2DPoint): TFPoint;
begin
  Result.X := APoint.X;
  Result.Y := APoint.Y;
  Result.Z := 0;
end;

function MakeFPointFromDXF(const AdxfPoint: TdxfPoint): TFPoint;
begin
  Result.X := AdxfPoint.X;
  Result.Y := AdxfPoint.Y;
  Result.Z := AdxfPoint.Z;
end;

function MakeFPointFromPoint(const APoint: TPoint): TFPoint;
begin
  Result.X := APoint.X;
  Result.Y := APoint.Y;
  Result.Z := 0;
end;

function MakePointFrom3D(const APoint: TFPoint;
  const AGDI: Boolean = False): TPoint;

  procedure DoFixExtent(var AValue: Integer; const AMax: Integer);
  begin
    if AValue < -AMax then
      AValue := -AMax
    else if AValue > AMax then
      AValue := AMax;
  end;

begin
  Result.X := Round(APoint.X);
  Result.Y := Round(APoint.Y);
  if AGDI then
  begin
    DoFixExtent(Result.X, MaxInt);
    DoFixExtent(Result.Y, MaxInt);
  end;
end;

function MakeFRect(const ALeft, ATop, AZ1, ARight, ABottom,
  AZ2: TsgFloat): TFRect;
begin
  Result.Left := ALeft;
  Result.Top := ATop;
  Result.Z1 := AZ1;
  Result.Right := ARight;
  Result.Bottom := ABottom;
  Result.Z2 := AZ2;
end;

function MakeFRect2D(const ALeft, ATop, ARight, ABottom: Extended): TFRect;
begin
  Result.Left := ALeft;
  Result.Top := ATop;
  Result.Z1 := 0;
  Result.Right := ARight;
  Result.Bottom := ABottom;
  Result.Z2 := 0;
end;

function MakeFRectByPoints(const ALeftTop, ARightBottom: TFPoint): TFRect;
begin
  Result.TopLeft := ALeftTop;
  Result.BottomRight := ARightBottom;
end;

function MakeFRectByF2DPoints(const ALeftTop, ARightBottom: TF2DPoint): TFRect;
begin
  Result.Left := ALeftTop.X;
  Result.Top := ALeftTop.Y;
  Result.Z1 := 0;
  Result.Right := ARightBottom.X;
  Result.Bottom := ARightBottom.Y;
  Result.Z2 := 0;
end;

function MakeLine(const APoint1, APoint2: TFPoint): TsgLine;
begin
  Result.Point1 := APoint1;
  Result.Point2 := APoint2;
end;

procedure MakePoints3(const AP1, AP2, AP3: TFPoint; APoints3: PDouble);
begin
  PsgPoints3(APoints3)^[0] := AP1;
  PsgPoints3(APoints3)^[1] := AP2;
  PsgPoints3(APoints3)^[2] := AP3;
end;

procedure MakePoints4(const AP1, AP2, AP3, AP4: TFPoint; APoints4: PDouble);
begin
  PsgPoints4(APoints4)^[0] := AP1;
  PsgPoints4(APoints4)^[1] := AP2;
  PsgPoints4(APoints4)^[2] := AP3;
  PsgPoints4(APoints4)^[3] := AP4;
end;

procedure MakePoints4L(const AList: TList; APoints4: PDouble);
begin
  PsgPoints4(APoints4)^[0] := PFPoint(AList.List[0])^;
  PsgPoints4(APoints4)^[1] := PFPoint(AList.List[1])^;
  PsgPoints4(APoints4)^[2] := PFPoint(AList.List[2])^;
  PsgPoints4(APoints4)^[3] := PFPoint(AList.List[3])^;
end;

function MakeRightPath(APath: string): string;
var
  vLength: Integer;
begin
  vLength := Length(APath);
  if vLength > 0 then
    if APath[vLength] <> '\' then
      APath := APath + '\';
  Result := APath;
end;

function MakeViewBox(const AX, AY, AWidth, AHeight: Double): TsgViewBox;
begin
  Result.Mode := 0;
  Result.X := AX;
  Result.Y := AY;
  Result.Width := AWidth;
  Result.Height := AHeight;
end;

function MakeVersion(const AMajor, AMinor: Integer): TsgVersion;
begin
  Result.Major := AMajor;
  Result.Minor := AMinor;
end;

function NewFPoint(const AX, AY: TsgFloat; const AZ: TsgFloat = 0): PFPoint;
begin
  New(Result);
  Result^.X := AX;
  Result^.Y := AY;
  Result^.Z := AZ;
end;

function NewFPoint(const APoint: TFPoint): PFPoint; overload;
begin
  Result := NewFPoint(APoint.X, APoint.Y, APoint.Z);
end;

procedure SetMinMaxUInt64(const AHandle: UInt64; var AMin, AMax: UInt64);
{$IFDEF SG_INLINE}inline; {$ENDIF}
begin
  if AMin > AHandle then
    AMin := AHandle;
  if AMax < AHandle then
    AMax := AHandle;
end;

procedure SetBitmapTransparent(const ABitmap: TBitmap;
  const ATransparent: Boolean; const ATransparentColor: Integer = clEmpty);
begin
  ABitmap.Transparent := ATransparent;
  if ATransparent then
  begin
    ABitmap.TransparentMode := tmAuto;
    if ATransparentColor <> clEmpty then
    begin
      ABitmap.TransparentMode := tmFixed;
      ABitmap.TransparentColor := ATransparentColor;
      ABitmap.Canvas.Brush.Color := ATransparentColor;
      ABitmap.Canvas.FillRect(Rect(0, 0, ABitmap.Width, ABitmap.Height));
    end;
  end;
end;

{ Log procedure }

procedure FileLoging(const AParam: TsgLogParam);
var
  I: Integer;
begin
  if Assigned(vLogs) then
    for I := 0 to vLogs.Count - 1 do
      TsgLogger(vLogs[I]).FileLogging(AParam);
end;

procedure FileLoging(const AOperation: TsgLogOperation; const AParam: Pointer;
  const AFileName: string = ''; const AId: UInt64 = 0);
var
  vParam: TsgLogParam;
begin
  FillChar(vParam, SizeOf(vParam), 0);
  vParam.Operation := AOperation;
  vParam.Obj := AParam;
  vParam.Info := AFileName;
  vParam.Id := AId;
  FileLoging(vParam);
end;

procedure RegisterLogger(const ALogger: TsgLogger);
begin
  if not Assigned(vLogs) then
    vLogs := TList.Create;
  vLogs.Add(ALogger);
end;

function UnRegisterLoger(const ALogger: TsgLogger): Boolean;
begin
  Result := False;
  if Assigned(vLogs) then
  begin
    Result := vLogs.Remove(ALogger) > -1;
    if vLogs.Count = 0 then
      FreeAndNil(vLogs);
  end;
end;

{$IFNDEF SGDEL_2009}

function AnsiStrAlloc(ASize: Cardinal): PAnsiChar;
begin
  Result := StrAlloc(ASize);
end;
{$ENDIF}

function BadRect: TFRect;
begin
  Result := cnstBadRect;
end;

function BadPoint: TFPoint;
begin
  Result := MakeFPoint(cnstNan, cnstNan, cnstNan);
end;

function MaxTsgFloat: Extended;
begin
  case SizeOf(TsgFloat) of
    4:
      Result := MaxSingle;
    8:
      Result := MaxDouble;
    10:
      Result := MaxExtended;
  else
    Result := MaxSingle;
  end;
end;

function GetRectWidth(const ARect: TRect): Integer;
begin
  Result := ARect.Right - ARect.Left;
end;

function GetRectHeight(const ARect: TRect): Integer;
begin
  Result := ARect.Bottom - ARect.Top;
end;

procedure ClearList(AList: TList; ClearCapacity: Boolean = True);
var
  I: Integer;
begin
  if AList = nil then
    Exit;
  for I := 0 to AList.Count - 1 do
    TObject(AList.List[I]).Free;
  if ClearCapacity then
    AList.Clear
  else
    AList.Count := 0;
end;

procedure ClearListOfList(AListOfList: TList; ClearCapacity: Boolean = True);
var
  I, K: Integer;
  vList: TList;
begin
  if AListOfList = nil then
    Exit;
  for I := AListOfList.Count - 1 downto 0 do
    if AListOfList.List[I] <> nil then
    begin
      vList := AListOfList.List[I];
      for K := vList.Count - 1 downto 0 do
        if vList.List[K] <> nil then
          TObject(vList.List[K]).Free;
      vList.Free;
    end;
  if ClearCapacity then
    AListOfList.Clear
  else
    AListOfList.Count := 0;
end;

procedure ClearListWithNilCheck(AList: TList; ClearCapacity: Boolean = True);
var
  I: Integer;
begin
  if AList = nil then
    Exit;
  for I := 0 to AList.Count - 1 do
    if AList.List[I] <> nil then
      TObject(AList.List[I]).Free;
  if ClearCapacity then
    AList.Clear
  else
    AList.Count := 0;
end;

procedure ClearObjects(const AStrings: TStrings; Clear: Boolean = True);
var
  I: Integer;
begin
  if AStrings = nil then
    Exit;
  for I := 0 to AStrings.Count - 1 do
  begin
    AStrings.Objects[I].Free;
    AStrings.Objects[I] := nil;
  end;
  if Clear then
    AStrings.Clear;
end;

procedure ClearParamData(const APParam: PsgParamData);
begin
  if APParam <> nil then
  begin
    if (APParam^.PType = ptList) and (APParam^.DataLst <> nil) then
      APParam^.DataLst.Free;
    FillChar(APParam^, SizeOf(APParam^), 0);
  end;
end;

procedure ClearRecordList(AList: TList; ClearCapacity: Boolean = True);
var
  I: Integer;
begin
  if AList = nil then
    Exit;
  for I := 0 to AList.Count - 1 do
    Dispose(AList.List[I]);
  if ClearCapacity then
    AList.Clear
  else
    AList.Count := 0;
end;

procedure ClearRecordListOfList(AListOfList: TList;
  ClearCapacity: Boolean = True);
var
  I, K: Integer;
  vList: TList;
begin
  if AListOfList = nil then
    Exit;
  for I := AListOfList.Count - 1 downto 0 do
    if AListOfList.List[I] <> nil then
    begin
      vList := AListOfList.List[I];
      for K := vList.Count - 1 downto 0 do
        if vList.List[K] <> nil then
          Dispose(vList.List[K]);
      vList.Free;
    end;
  if ClearCapacity then
    AListOfList.Clear
  else
    AListOfList.Count := 0;
end;

procedure ClearRecordObjects(const AStrings: TStrings; Clear: Boolean = True);
var
  I: Integer;
begin
  if AStrings = nil then
    Exit;
  for I := 0 to AStrings.Count - 1 do
  begin
    Dispose(Pointer(AStrings.Objects[I]));
    AStrings.Objects[I] := nil;
  end;
  if Clear then
    AStrings.Clear;
end;

procedure DisposeAndNil(var ARec);
var
  vRec: Pointer absolute ARec;
begin
  if vRec <> nil then
  begin
    Dispose(vRec);
    vRec := nil;
  end;
end;

procedure DisposeDeleteFromList(AList: TList; const AIndex: Integer);
begin
  Dispose(AList.List[AIndex]);
  AList.Delete(AIndex);
end;

procedure DisposeParamData(var AParam: PsgParamData);
begin
  ClearParamData(AParam);
  Dispose(AParam)
end;

procedure FreeAndNil(var AObj);
var
  vObj: TObject;
begin
  if Pointer(AObj) <> nil then
  begin
    vObj := TObject(AObj);
    Pointer(AObj) := nil;
    vObj.Destroy;
  end;
end;

procedure FreeList(var AList: TList);
begin
  ClearList(AList);
  FreeAndNil(AList);
end;

procedure FreeMemAndNil(var P: Pointer);
begin
  if P <> nil then
  begin
    FreeMem(P);
    P := nil
  end;
end;

procedure FreeListOfList(var AList: TList);
begin
  ClearListOfList(AList);
  FreeAndNil(AList);
end;

procedure FreeRecordList(var AList: TList);
begin
  ClearRecordList(AList);
  FreeAndNil(AList);
end;

procedure FreeRecordListOfList(var AListOfList: TList);
begin
  ClearRecordListOfList(AListOfList);
  FreeAndNil(AListOfList);
end;

procedure FreeRecordStringList(var AList: TStrings);
begin
  ClearRecordObjects(AList, True);
  FreeAndNil(AList);
end;

{$IFDEF SG_BTI}

procedure ClearXDataStrings(var AXData: TsgExtendedData);
var
  I: Integer;
begin
  for I := Low(AXData.Data.xStringArray) to High(AXData.Data.xStringArray) do
    SetLength(AXData.Data.xStringArray[I], 0);
end;
{$ENDIF}

function SGHeadVarStruct(const AMM: Boolean =
{$IFDEF SG_UNITS_MM}True{$ELSE}False{$ENDIF}): TsgHeadVarStruct;
const
{$IFDEF SG_EVACUATION}
  cnstTextSizeInt = 0.5;
  cnstArrowSizeInt = 0.25;
  cnstDimExeInt = 0.25;
  cnstDimExoInt = 0.0868;
  cnstDimGapInt = 0.0868;
{$ELSE}
  cnstTextSizeInt = 2.5;
  cnstArrowSizeInt = 2.5;
  cnstDimExeInt = 2.5;
  cnstDimExoInt = 0.868;
  cnstDimGapInt = 0.868;
{$ENDIF}
  cnstSGDefaultHeadVarStruct: TsgHeadVarStruct =
    (CEColor: (Active: acIndexColor; Color: clDXFByLayer;);
    // cnstDefaultEntityColor;
    CLayer: '0'; CELType: sByLayer; CELTScale: 1; CELWeight: - 1.0; CodePage: 0;
    DimStyle: sStandardName; DimTextStyle: sStandardName;
    DimProps: (Alt: False; AltF: 1; APost: ''; Asz: cnstArrowSizeInt;
    Sah: False; Arrows: (Blk: datClosedfilled; Blk1: datClosedfilled;
    Blk2: datClosedfilled; LrBlk: datClosedfilled); Cen: 0.09;
    ClrD: (Active: acIndexColor; Color: clDXFByBlock;);
    ClrE: (Active: acIndexColor; Color: clDXFByBlock;);
    ClrT: (Active: acIndexColor; Color: clDXFByBlock;); SD1: False; SD2: False;
    SE1: False; SE2: False; Dec: 2; Exe: cnstDimExeInt; Exo: cnstDimExoInt;
    Gap: cnstDimGapInt; LFac: 1; LwD: - 1.0; LwE: - 1.0; Post: ''; Scale: 1.0;
    Tad: 0; Tih: False; Tix: 0; Toh: False; Txt: cnstTextSizeInt;);
    TextStyle: sStandardName; FilletRadius: 0.5; InsUnits: Byte(iuMeters);
    LTScale: 1; Measurement: True; PointDisplayMode: 0; PointDisplaySize: 0;
    TextSize: cnstTextSizeInt; TileMode: 1; UCSORG: (X: 0; Y: 0; Z: 0);
    UCSXDir: (X: 1; Y: 0; Z: 0); UCSYDir: (X: 0; Y: 1; Z: 0); Version: 0;
    AttMode: attNormal;);

begin
  Result := cnstSGDefaultHeadVarStruct;
  if AMM then
  begin
    Result.CELTScale := 1000;
    Result.FilletRadius := 250;
    Result.TextSize := 250;
    Result.InsUnits := Byte(iuMillimeters);
    Result.PointDisplaySize := 50;
    Result.DimProps.LFac := 0.001;
    Result.DimProps.Txt := Result.TextSize;
    Result.DimProps.Asz := 250;
    Result.DimProps.Exe := 250;
    Result.DimProps.Exo := 80;
    Result.DimProps.Gap := 80;
  end;
end;

function SGDefaultImageSize(const AMM: Boolean =
{$IFDEF SG_UNITS_MM}True{$ELSE}False{$ENDIF}): TFRect;
const
  cnstImageSizeM: TFRect = (Left: - 148.5; Top: 105; Z1: 0; Right: 148.5;
    Bottom: - 105; Z2: 0);
  cnstImageSizeMM: TFRect = (Left: - 148500; Top: 105000; Z1: 0; Right: 148500;
    Bottom: - 105000; Z2: 0);
begin
  if AMM then
    Result := cnstImageSizeMM
  else
    Result := cnstImageSizeM;
end;

function DistanceFPoint(const AP1, AP2: TFPoint;
  const AResolution: Double): Double;
var
  vSqr, vX, vY, vZ: Extended;
begin
  vX := AP1.X - AP2.X;
  vY := AP1.Y - AP2.Y;
  vZ := AP1.Z - AP2.Z;
  vSqr := Sqr(vX) + Sqr(vY) + Sqr(vZ);
  if vSqr > AResolution then
    Result := Sqrt(vSqr)
  else
    Result := 0;
end;

function IsEqual(const A, B: TsgFloat;
  AResolution: Double = fDoubleResolution): Boolean;
var
  Epsilon: Double;
begin
  Epsilon := Max(Min(Abs(A), Abs(B)) * AResolution, AResolution);
  if A > B then
    Result := (A - B) <= Epsilon
  else
    Result := (B - A) <= Epsilon;
  // Result := Abs(A - B) <= AResolution
end;

function IsEqual(const A, B: Extended;
  AResolution: Extended = fDoubleResolution): Boolean;
var
  Epsilon: Extended;
begin
  Epsilon := Max(Min(Abs(A), Abs(B)) * AResolution, AResolution);
  if A > B then
    Result := (A - B) <= Epsilon
  else
    Result := (B - A) <= Epsilon;
  // Result := Abs(A - B) <= AResolution
end;

function IsEqualFPoints(const Point1, Point2: TFPoint;
  Epsilon: Double = fDoubleResolution): Boolean;
begin
  Result := IsZero(Point1.X - Point2.X, Epsilon) and
    IsZero(Point1.Y - Point2.Y, Epsilon) and
    IsZero(Point1.Z - Point2.Z, Epsilon);
end;

function IsZero(const A: Double; Epsilon: Double): Boolean;
begin
  if Epsilon = 0 then
    Epsilon := fDoubleResolution;
  Result := Abs(A) <= Epsilon;
end;

procedure SwapInts(var A, B: Cardinal);
begin
  SwapInts(Integer(A), Integer(B));
end;

procedure SwapInts(var A, B: Integer);
asm
  {$IFDEF CPUX64}
  mov eax,dword ptr [rcx]
  xchg eax,dword ptr [rdx]
  mov dword ptr [rcx],eax
  {$ELSE}
  MOV	ECX,[EAX]
  XCHG	ECX,[EDX]
  MOV	[EAX],ECX
  {$ENDIF}
end;

procedure CopyLists(const Destination, Source: TList;
  const AMode: TsgCopyMode = cmCopy);
var
  vIndex: Integer;
begin
  case AMode of
    cmAppend:
      begin
        vIndex := Destination.Count;
        Destination.Count := Destination.Count + Source.Count;
        CopyMemory(@Destination.List[vIndex], Source.List,
          Source.Count * SizeOf(Pointer));
      end;
  else
    Destination.Count := Source.Count;
    CopyMemory(Destination.List, Source.List, Source.Count * SizeOf(Pointer));
  end;
end;

function GetDecimalSeparator: Char;
begin
{$IFDEF SGDEL_XE}
  Result := FormatSettings.DecimalSeparator;
{$ELSE}
  Result := DecimalSeparator
{$ENDIF}
end;

function SetDecimalSeparator(const ADecimalSeparator: Char): Char;
begin
{$IFDEF SGDEL_XE}
  Result := FormatSettings.DecimalSeparator;
  FormatSettings.DecimalSeparator := ADecimalSeparator;
{$ELSE}
  Result := DecimalSeparator;
  DecimalSeparator := ADecimalSeparator;
{$ENDIF}
end;

function GetAttributeMode(const AIndex: Integer): TsgAttributeMode;
begin
  case AIndex of
    0:
      Result := attDisable;
    1:
      Result := attNormal;
  else
    Result := attEnable;
  end;
end;

function HasObject(const AObject, AObjectCurrent: Pointer): Boolean;
{$IFDEF SG_INLINE}inline; {$ENDIF}
begin
  if AObject = cnstObjectReserve then // has style
    Result := AObjectCurrent <> cnstObjectReserve
  else // has current style
    Result := AObjectCurrent = AObject;
end;

function GetArrowByte(const AType: TsgDimArrowType): Byte;
begin
  case AType of
    datUndefined:
      Result := MAXBYTE;
  else
    Result := Byte(AType);
  end;
end;

function GetArrowType(const AType: Byte): TsgDimArrowType;
begin
  case AType of
    MAXBYTE:
      Result := datUndefined;
  else
    Result := TsgDimArrowType(AType);
    if AType > Byte(High(TsgDimArrowType)) then
      Result := datClosedfilled;
  end;
end;

function GetPlotRotation(const AType: Integer): TsgPlotRotation;
begin
  Result := TsgPlotRotation(AType);
  if AType > Integer(High(TsgPlotRotation)) then
    Result := prNoRotation;
end;

{$IFDEF SGDEL_2006}
{ TsgUInt64 }

{ private }

function TsgRecUInt64.GetAll: Int64;
begin
  Result := Int64(FHi) shl 32 + FLo;
end;

function TsgRecUInt64.GetHi: Cardinal;
begin
  Result := FHi;
end;

function TsgRecUInt64.GetLo: Cardinal;
begin
  Result := FLo;
end;

procedure TsgRecUInt64.SetAll(const Value: Int64);
begin
  FLo := Value;
  FHi := Int64(Value) shr 32;
end;

procedure TsgRecUInt64.SetHi(const Value: Cardinal);
begin
  FHi := Value;
end;

procedure TsgRecUInt64.SetLo(const Value: Cardinal);
begin
  FLo := Value;
end;

{ public }

class operator TsgRecUInt64.Add(const A, B: TsgRecUInt64): TsgRecUInt64;
begin
  Result.All := A.All + B.All;
end;

class operator TsgRecUInt64.BitwiseOr(const A, B: TsgRecUInt64): TsgRecUInt64;
begin
  Result.All := A.All or B.All;
end;

class operator TsgRecUInt64.Equal(const A, B: TsgRecUInt64): Boolean;
begin
  Result := (A.FHi = B.FHi) and (A.FLo = B.FLo);
end;

class operator TsgRecUInt64.GreaterThan(const A, B: TsgRecUInt64): Boolean;
begin
  Result := A.FHi > B.FHi;
  if not Result and (A.FHi = B.FHi) then
    Result := A.FLo > B.FLo;
end;

class operator TsgRecUInt64.GreaterThanOrEqual(const A,
  B: TsgRecUInt64): Boolean;
begin
  Result := not(A < B);
end;

class operator TsgRecUInt64.Implicit(const A: TsgRecUInt64): Int64;
begin
  Result := A.GetAll;
end;

class operator TsgRecUInt64.Implicit(const A: TsgRecUInt64): Integer;
begin
  Result := A.FLo;
end;

class operator TsgRecUInt64.Implicit(I: Int64): TsgRecUInt64;
begin
  Result.All := I;
end;

class operator TsgRecUInt64.Implicit(I: Integer): TsgRecUInt64;
begin
  Result.Lo := I;
  Result.Hi := 0;
end;

class operator TsgRecUInt64.LeftShift(const A: TsgRecUInt64; B: Integer)
  : TsgRecUInt64;
begin
  Result.All := A.All shl B;
end;

class operator TsgRecUInt64.LessThan(const A, B: TsgRecUInt64): Boolean;
begin
  Result := A.FHi < B.FHi;
  if not Result and (A.FHi = B.FHi) then
    Result := A.FLo < B.FLo;
end;

class operator TsgRecUInt64.LessThanOrEqual(const A, B: TsgRecUInt64): Boolean;
begin
  Result := not(A > B);
end;

class operator TsgRecUInt64.Negative(const A: TsgRecUInt64): TsgRecUInt64;
begin
  Result.All := -A.All;
end;

class operator TsgRecUInt64.NotEqual(const A, B: TsgRecUInt64): Boolean;
begin
  Result := (A.FHi <> B.FHi) or (A.FLo <> B.FLo);
end;

class operator TsgRecUInt64.RightShift(const A: TsgRecUInt64; B: Integer)
  : TsgRecUInt64;
begin
  Result.All := A.All shr B;
end;

class operator TsgRecUInt64.Subtract(const A, B: TsgRecUInt64): TsgRecUInt64;
begin
  Result.All := A.All - B.All;
end;

{$ENDIF}

function GetAppID: string;
begin
{$IFDEF SG_ABVIEWER}
  Result := 'ABViewer';
{$ELSE}
{$IFDEF SG_BTI}
  Result := 'Inventory';
{$ELSE}
  Result := '';
{$ENDIF}
{$ENDIF}
end;

{ Function GetDWGVersion

  If result:
  - 0 - version supported;
  - 1 - version not supported;
  - else - unknown
}
function GetDWGVersion(const S: AnsiString;
  var AVersion: TsgDWGVersion): Integer;
{
  Version         Header             AutoCAD Version

  DWG R1.0     MC0.0            AutoCAD Release 1.0
  DWG R1.2     AC1.2            AutoCAD Release 1.2
  DWG R1.40    AC1.40           AutoCAD Release 1.40
  DWG R2.05    AC1.50           AutoCAD Release 2.05
  DWG R2.10    AC2.10           AutoCAD Release 2.10
  DWG R2.21    AC2.21           AutoCAD Release 2.21
  DWG R2.22    AC1001, AC2.22   AutoCAD Release 2.22
  DWG R2.50    AC1002           AutoCAD Release 2.50
  DWG R2.60    AC1003           AutoCAD Release 2.60
  DWG R9       AC1004           AutoCAD Release 9
  DWG R10      AC1006           AutoCAD Release 10
  DWG R11/12   AC1009           AutoCAD Release 11, AutoCAD Release 12
  DWG R13      AC1012           AutoCAD Release 13
  DWG R14      AC1014           AutoCAD Release 14
  DWG 2000     AC1015           AutoCAD 2000, AutoCAD 2000i, AutoCAD 2002
  DWG 2004     AC1018           AutoCAD 2004, AutoCAD 2005, AutoCAD 2006
  DWG 2007     AC1021           AutoCAD 2007, AutoCAD 2008, AutoCAD 2009
  DWG 2010     AC1024           AutoCAD 2010, AutoCAD 2011, AutoCAD 2012
  DWG 2013     AC1027           AutoCAD 2013
}
const
  cnstAC10 = $30314341; // 'AC10'
  cnstAC2Dot = $2E324341; // 'AC2.'
  // cnstAC1Dot  = $2E314341;  // 'AC1.'
  // cnstMC0Dot  = $2E304D41;  // 'MC0.'

var
  vP: PCardinal;

  function PackDCB(const ADCB: Word): Integer;
  begin
    Result := 10 * (ADCB and $F) + (ADCB shr 8) and $F;
  end;

begin
  Result := 0;
  try
    if Length(S) >= 4 then
    begin
      vP := PPointer(@S)^;
      case vP^ of
        cnstAC10:
          begin
            if Length(S) >= 6 then
            begin
              Inc(vP);
              case PackDCB(PWord(vP)^) of
                1 .. 4:
                  AVersion := acR09; // '01'..'04'
                6:
                  AVersion := acR10; // '06'
                9:
                  AVersion := acR12; // '09'
                12:
                  AVersion := acR13; // '12'
                13 .. 14:
                  AVersion := acR14; // '13'..'14'
                15:
                  AVersion := acR2000; // '15'
                18:
                  AVersion := acR2004; // '18'
                21:
                  AVersion := acR2007; // '21'
                24:
                  AVersion := acR2010; // '24'
                27:
                  AVersion := acR2013; // '27'
              else
                Result := 2 + Ord(PackDCB(vP^) > 1);
              end;
            end
            else
              Result := 1;
          end;
        cnstAC2Dot:
          if Length(S) >= 6 then
          begin
            Inc(vP);
            case PackDCB(PWord(vP)^) of
              10, 21 .. 22:
                AVersion := acR09; // '10', '21'..'22' (DWG R2.10/R2.21/R2.22)
            else
              Result := 2;
            end;
          end
          else
            Result := 1;
      else
        Result := 1;
      end; { case }
    end
    else
      Result := 1;
  except
    Result := 255;
  end;
end;

{$IFNDEF SGDEL_6}
{$IFNDEF SGDEL_5}

function SameText(const S1, S2: string): Boolean;
begin
  Result := CompareText(S1, S2) = 0
end;

{ TsgNotificationList }

procedure TsgNotificationList.Notify(Ptr: Pointer; Action: TListNotification);
begin
end;

function TsgNotificationList.Add(Item: Pointer): Integer;
begin
  Result := inherited Add(Item);
  if Item <> nil then
    Notify(Item, lnAdded);
end;

function TsgNotificationList.Extract(Item: Pointer): Pointer;
var
  I: Integer;
begin
  Result := nil;
  I := IndexOf(Item);
  if I >= 0 then
  begin
    Result := Item;
    List^[I] := nil;
    Delete(I);
    Notify(Result, lnExtracted);
  end;
end;

procedure TsgNotificationList.Delete(Index: Integer);
var
  Temp: Pointer;
begin
  Temp := Items[Index];
  inherited Delete(Index);
  if Temp <> nil then
    Notify(Temp, lnDeleted);
end;

procedure TsgNotificationList.Insert(Index: Integer; Item: Pointer);
begin
  inherited Insert(Index, Item);
  if Item <> nil then
    Notify(Item, lnAdded);
end;
{$ENDIF}

function WideUpperCase(const S: WideString): WideString;
var
  vLen: Integer;
begin
  vLen := Length(S);
  SetString(Result, PWideChar(S), vLen);
  if vLen > 0 then
    CharUpperBuffW(Pointer(Result), vLen);
end;

{ TInterfacedPersistent }

procedure TInterfacedPersistent.AfterConstruction;
begin
  inherited;
  if GetOwner <> nil then
    GetOwner.GetInterface(IInterface, FOwnerInterface);
end;

function TInterfacedPersistent._AddRef: Integer;
begin
  if FOwnerInterface <> nil then
    Result := FOwnerInterface._AddRef
  else
    Result := -1;
end;

function TInterfacedPersistent._Release: Integer;
begin
  if FOwnerInterface <> nil then
    Result := FOwnerInterface._Release
  else
    Result := -1;
end;

function TInterfacedPersistent.QueryInterface(const IID: TGUID;
  out Obj): HResult;
const
  E_NOINTERFACE = HResult($80004002);
begin
  if GetInterface(IID, Obj) then
    Result := 0
  else
    Result := E_NOINTERFACE;
end;

{$ENDIF}

procedure CreateXMLIdTable;
var
  I: TsgXMLId;
begin
  XMLIds := TStringList.Create;
  XMLIds.Duplicates := dupIgnore;
  XMLIds.Sorted := True;
{$IFDEF SGDEL_6}
  XMLIds.CaseSensitive := True;
{$ENDIF}
  for I := Low(TsgXMLId) to High(TsgXMLId) do
  begin
    if not(I in [xmlUndefined, xmlClassId]) then // reserved
      XMLIds.AddObject(LowerCase(cnstXMLNames[I].Name), Pointer(I));
  end;
end;

function GetXMLId(const AName: string): TsgXMLId;
var
  vIndex: Integer;
begin
  Result := xmlUndefined;
{$IFNDEF SG_OPENING_IN_THEADS}
  if XMLIds = nil then
    CreateXMLIdTable;
{$ENDIF}
  if Length(AName) > 0 then
  begin
    vIndex := XMLIds.IndexOf(LowerCase(AName));
    if vIndex > -1 then
      Result := TsgXMLId(XMLIds.Objects[vIndex]);
  end;
end;

function GetSaveResultStr(const ASaveResult: Integer): string;
begin
  case ASaveResult of
    cnstSaveResultOk:
      Result := 'OK';
    cnstSaveResultNeedParams:
      Result := 'Need parametrs';
    cnstSaveResultUndefinedFormat:
      Result := 'Undefined format';
    cnstSaveResultUnsupportedFormat:
      Result := sInvalidVersion;
  else
    Result := 'Error';
  end;
end;

{ TsgStreamAdapter }

function TsgStreamAdapter.GetObject(out AObject): HResult;
begin
  if @AObject <> nil then
  begin
    Pointer(AObject) := Self;
    Result := S_OK;
  end
  else
    Result := E_POINTER;
end;

{$IFDEF SGDEL_2006}
{$IFDEF VER300DOWN}

function TsgStreamAdapter.Stat(out statstg: TStatStg;
  grfStatFlag: Integer): HResult;
var
  vfi: TByHandleFileInformation;
begin
  if (@statstg <> nil) and (Stream is TFileStream) and
    GetFileInformationByHandle(TFileStream(Stream).Handle, vfi) then
  begin
    statstg.pwcsName := StringToOleStr(TFileStream(Stream).FileName);
    statstg.dwType := STGTY_STREAM;
    statstg.cbSize := Stream.Size;
    statstg.mtime := vfi.ftLastWriteTime;
    statstg.ctime := vfi.ftCreationTime;
    statstg.atime := vfi.ftLastAccessTime;
    statstg.grfMode := 0;
    statstg.grfLocksSupported := LOCK_WRITE;
    statstg.clsid := GUID_NULL;
    statstg.grfStateBits := 0;
    statstg.reserved := 0;
    Result := S_OK;
  end
  else
    Result := inherited Stat(statstg, grfStatFlag);
end;
{$ENDIF}
{$ENDIF}
{ TsgOleStream }

constructor TsgOleStream.Create(const Stream: IStream);
begin
  FStream := Stream;
end;

destructor TsgOleStream.Destroy;
begin
  inherited;
end;

function TsgOleStream.Read(var Buffer; Count: Longint): Longint;
begin
  { OleCheck } (FStream.Read(@Buffer, Count, @Result));
end;

function TsgOleStream.Seek(Offset: Longint; Origin: Word): Longint;
var
  Pos: {$IFDEF SGDEL_D10} UInt64 {$ELSE} Largeint {$ENDIF};
begin
  { OleCheck } (FStream.Seek(Offset, Origin, Pos));
  Result := Longint(Pos);
end;

function TsgOleStream.Write(const Buffer; Count: Longint): Longint;
begin
  { OleCheck } (FStream.Write(@Buffer, Count, @Result));
end;

function TsgOleStream.GetIStream: IStream;
begin
  Result := FStream;
end;

function CreateStreamFromStgMedium(const AStgMed: TStgMedium;
  out AStream: TStream; var ANewCreated: Boolean): Boolean;
var
  vStm: IStream;
  vObjAccess: IObjectAccess;
  vObj: TObject;
begin
  AStream := nil;
  ANewCreated := True;
  if AStgMed.tymed and TYMED_FILE <> 0 then
    AStream := TFileStream.Create
      (WideCharToString(AStgMed.lpszFileName), fmCreate)
  else if AStgMed.tymed and TYMED_ISTREAM <> 0 then
  begin
{$IFDEF SGFPC}
    if Succeeded(IUnknown(AStgMed.pstm).QueryInterface(IObjectAccess,
      vObjAccess)) then
{$ELSE}
    if Succeeded(IUnknown(AStgMed.stm).QueryInterface(IObjectAccess, vObjAccess))
    then
{$ENDIF}
    begin
      if Succeeded(vObjAccess.GetObject(vObj)) and (vObj is TStreamAdapter) then
      begin
        AStream := TStreamAdapter(vObj).Stream;
        ANewCreated := False;
      end;
    end
    else
{$IFDEF SGFPC}
      if Succeeded(IUnknown(AStgMed.pstm).QueryInterface(IStream, vStm)) then
{$ELSE}
      if Succeeded(IUnknown(AStgMed.stm).QueryInterface(IStream, vStm)) then
{$ENDIF}
        AStream := TsgOleStream.Create(vStm);
  end;
  Result := AStream <> nil;
end;

procedure InitCodeTypes;
var
  I: Integer;
begin
  if CodeTypes = nil then
    GetMem(CodeTypes, SizeOf(TCodeTypes));
  for I := Low(CodeTypes^) to High(CodeTypes^) do
    case I of
      60 .. 79, 90 .. 99, 170 .. 179, 270 .. 279, 280 .. 289, 290, 370 .. 389,
        400 .. 409, 420 .. 429, 440 .. 459, 1060 .. 1071:
        begin
          CodeTypes^[I] := ctInteger;
        end;
      10 .. 59, 110 .. 149, 210 .. 239, 460 .. 469, 1010 .. 1059:
        begin
          CodeTypes^[I] := ctDouble;
        end;
      5, 105, 320 .. 329, 330 .. 369, 390 .. 399
{$IFNDEF SG_BTI_HANDELS}, 1005{$ENDIF}:
        begin
          CodeTypes^[I] := ctHex;
        end;
      0 .. 4, 6 .. 9, 100, 102, 300 .. 309, 410 .. 419, 430 .. 439, 470 .. 479,
        999, 1000 .. 1004, {$IFDEF SG_BTI_HANDELS}1005, {$ENDIF}1006 .. 1009:
        begin
          CodeTypes^[I] := ctString;
        end;
    else
      CodeTypes^[I] := ctNode;
    end;
end;

procedure FreeCodeTypes;
begin
  FreeMemAndNil(Pointer(CodeTypes));
end;

initialization

InitCodeTypes;
cnstSGHeadVarStruct := SGHeadVarStruct
  ({$IFDEF SG_UNITS_MM}True{$ELSE}False{$ENDIF});
{$IFDEF SG_MODULE_LOG}
if IsLibrary then
  LogFileName := ChangeFileExt(GetModuleName(HInstance), '.log')
else
  LogFileName := ChangeFileExt(ParamStr(0), '.log');
Log := TStringList.Create;
if FileExists(LogFileName) then
  Log.LoadFromFile(LogFileName);
{$ENDIF}
GUID_ArrayFPoints := StringToGUID(cnstGUID_ArrayFPoints);
{$IFDEF SG_OPENING_IN_THEADS}
CreateXMLIdTable;
{$ENDIF}

finalization

FreeCodeTypes;
FreeList(vLogs);
{$IFDEF SG_MODULE_LOG}
FreeAndNil(Log);
{$ENDIF}
FreeAndNil(XMLIds);

end.
