types.pp 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251
  1. {
  2. This file is part of the Free Pascal run time library.
  3. Copyright (c) 2002 by Florian Klaempfl,
  4. member of the Free Pascal development team.
  5. See the file COPYING.FPC, included in this distribution,
  6. for details about the copyright.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. **********************************************************************}
  11. {$MODE OBJFPC}
  12. unit Types;
  13. interface
  14. {$modeswitch advancedrecords}
  15. {$modeswitch class}
  16. {$if defined(win32) or defined(win64) or defined(wince)}
  17. uses
  18. Windows;
  19. {$elseif defined(win16)}
  20. uses
  21. WinTypes;
  22. {$endif}
  23. {$if defined(win32) or defined(win64)}
  24. const
  25. RT_RCDATA = Windows.RT_RCDATA deprecated 'Use Windows.RT_RCDATA instead';
  26. {$elseif defined(win16)}
  27. const
  28. RT_RCDATA = WinTypes.RT_RCDATA deprecated 'Use WinTypes.RT_RCDATA instead';
  29. {$endif}
  30. type
  31. TEndian = Objpas.TEndian;
  32. TDirection = (FromBeginning, FromEnd);
  33. TValueRelationship = -1..1;
  34. DWORD = LongWord;
  35. PLongint = System.PLongint;
  36. PSmallInt = System.PSmallInt;
  37. {$ifndef FPUNONE}
  38. PDouble = System.PDouble;
  39. {$endif}
  40. PByte = System.PByte;
  41. Largeint = int64;
  42. LARGE_INT = LargeInt;
  43. PLargeInt = ^LargeInt;
  44. LargeUint = qword;
  45. LARGE_UINT= LargeUInt;
  46. PLargeuInt = ^LargeuInt;
  47. TBooleanDynArray = array of Boolean;
  48. TByteDynArray = array of Byte;
  49. TCardinalDynArray = array of Cardinal;
  50. TInt64DynArray = array of Int64;
  51. TIntegerDynArray = array of Integer;
  52. TLongWordDynArray = array of LongWord;
  53. TPointerDynArray = array of Pointer;
  54. TQWordDynArray = array of QWord;
  55. TShortIntDynArray = array of ShortInt;
  56. TSmallIntDynArray = array of SmallInt;
  57. TStringDynArray = array of AnsiString;
  58. TObjectDynArray = array of TObject;
  59. TWideStringDynArray = array of WideString;
  60. TWordDynArray = array of Word;
  61. TCurrencyArray = Array of currency;
  62. {$ifndef FPUNONE}
  63. TSingleDynArray = array of Single;
  64. TDoubleDynArray = array of Double;
  65. TExtendedDynArray = array of Extended;
  66. TCompDynArray = array of Comp;
  67. {$endif}
  68. {$if defined(win32) or defined(win64) or defined(wince)}
  69. TArray4IntegerType = Windows.TArray4IntegerType;
  70. TSmallPoint = Windows.TSmallPoint;
  71. PSmallPoint = Windows.PSmallPoint;
  72. TSize = Windows.TSize;
  73. TagSize = Windows.tagSize deprecated;
  74. PSize = Windows.PSize;
  75. TPoint = Windows.TPoint;
  76. TagPoint = Windows.TagPoint deprecated;
  77. PPoint = Windows.PPoint;
  78. TRect = Windows.TRect;
  79. PRect = Windows.PRect;
  80. TSplitRectType = Windows.TSplitRectType;
  81. const
  82. srLeft = TSplitRectType.srLeft;
  83. srRight = TSplitRectType.srRight;
  84. srTop = TSplitRectType.srTop;
  85. srBottom = TSplitRectType.srBottom;
  86. type
  87. {$else}
  88. {$i typshrdh.inc}
  89. TagSize = tSize deprecated;
  90. TagPoint = TPoint deprecated;
  91. {$endif}
  92. { TPointF }
  93. PPointF = ^TPointF;
  94. TPointF =
  95. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  96. packed
  97. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  98. record
  99. x,y : Single;
  100. public
  101. function Add(const apt: TPoint): TPointF;
  102. function Add(const apt: TPointF): TPointF;
  103. function Distance(const apt : TPointF) : Single;
  104. function DotProduct(const apt : TPointF) : Single;
  105. function IsZero : Boolean;
  106. function Subtract(const apt : TPointF): TPointF;
  107. function Subtract(const apt : TPoint): TPointF;
  108. procedure SetLocation(const apt :TPointF);
  109. procedure SetLocation(const apt :TPoint);
  110. procedure SetLocation(ax,ay : Single);
  111. procedure Offset(const apt :TPointF);
  112. procedure Offset(const apt :TPoint);
  113. procedure Offset(dx,dy : Single);
  114. function Scale (afactor:Single) : TPointF;
  115. function Ceiling : TPoint;
  116. function Truncate: TPoint;
  117. function Floor : TPoint;
  118. function Round : TPoint;
  119. function Length : Single;
  120. class function Create(const ax, ay: Single): TPointF; overload; static; inline;
  121. class function Create(const apt: TPoint): TPointF; overload; static; inline;
  122. class operator = (const apt1, apt2 : TPointF) : Boolean;
  123. class operator <> (const apt1, apt2 : TPointF): Boolean;
  124. class operator + (const apt1, apt2 : TPointF): TPointF;
  125. class operator - (const apt1, apt2 : TPointF): TPointF;
  126. class operator - (const apt1 : TPointF): TPointF;
  127. class operator * (const apt1, apt2: TPointF): TPointF;
  128. class operator * (const apt1: TPointF; afactor: single): TPointF;
  129. class operator * (afactor: single; const apt1: TPointF): TPointF;
  130. class operator / (const apt1: TPointF; afactor: single): TPointF;
  131. class operator := (const apt: TPoint): TPointF;
  132. class operator ** (const apt1, apt2: TPointF): Single; // scalar product
  133. end;
  134. { TSizeF }
  135. PSizeF = ^TSizeF;
  136. TSizeF =
  137. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  138. packed
  139. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  140. record
  141. cx,cy : Single;
  142. public
  143. function Add(const asz: TSize): TSizeF;
  144. function Add(const asz: TSizeF): TSizeF;
  145. function Distance(const asz : TSizeF) : Single;
  146. function IsZero : Boolean;
  147. function Subtract(const asz : TSizeF): TSizeF;
  148. function Subtract(const asz : TSize): TSizeF;
  149. function Scale (afactor:Single) : TSizeF;
  150. function Ceiling : TSize;
  151. function Truncate: TSize;
  152. function Floor : TSize;
  153. function Round : TSize;
  154. function Length : Single;
  155. class function Create(const ax, ay: Single): TSizeF; overload; static; inline;
  156. class function Create(const asz: TSize): TSizeF; overload; static; inline;
  157. class operator = (const asz1, asz2 : TSizeF) : Boolean;
  158. class operator <> (const asz1, asz2 : TSizeF): Boolean;
  159. class operator + (const asz1, asz2 : TSizeF): TSizeF;
  160. class operator - (const asz1, asz2 : TSizeF): TSizeF;
  161. class operator - (const asz1 : TSizeF): TSizeF;
  162. class operator * (const asz1: TSizeF; afactor: single): TSizeF;
  163. class operator * (afactor: single; const asz1: TSizeF): TSizeF;
  164. class operator := (const apt: TPointF): TSizeF;
  165. class operator := (const asz: TSize): TSizeF;
  166. class operator := (const asz: TSizeF): TPointF;
  167. property Width: Single read cx write cx;
  168. property Height: Single read cy write cy;
  169. end;
  170. { TRectF }
  171. PRectF = ^TRectF;
  172. TRectF =
  173. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  174. packed
  175. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  176. record
  177. private
  178. function GetLocation: TPointF;
  179. function GetSize: TSizeF;
  180. procedure SetSize(AValue: TSizeF);
  181. function GetHeight: Single; inline;
  182. function GetWidth: Single; inline;
  183. procedure SetHeight(AValue: Single);
  184. procedure SetWidth (AValue: Single);
  185. public
  186. constructor Create(Origin: TPointF); // empty rect at given origin
  187. constructor Create(Origin: TPointF; AWidth, AHeight: Single);
  188. constructor Create(ALeft, ATop, ARight, ABottom: Single);
  189. constructor Create(P1, P2: TPointF; Normalize: Boolean = False);
  190. constructor Create(R: TRectF; Normalize: Boolean = False);
  191. constructor Create(R: TRect; Normalize: Boolean = False);
  192. class operator = (L, R: TRectF): Boolean;
  193. class operator <> (L, R: TRectF): Boolean;
  194. class operator + (L, R: TRectF): TRectF; // union
  195. class operator * (L, R: TRectF): TRectF; // intersection
  196. class operator := (const arc: TRect): TRectF;
  197. class function Empty: TRectF; static;
  198. procedure NormalizeRect;
  199. function IsEmpty: Boolean;
  200. function Contains(Pt: TPointF): Boolean;
  201. function Contains(R: TRectF): Boolean;
  202. function IntersectsWith(R: TRectF): Boolean;
  203. class function Intersect(R1: TRectF; R2: TRectF): TRectF; static;
  204. procedure Intersect(R: TRectF);
  205. class function Union(R1, R2: TRectF): TRectF; static;
  206. class function Union(const Points: array of TPointF): TRectF; static;
  207. procedure SetLocation(X, Y: Single);
  208. procedure SetLocation(P: TPointF);
  209. procedure Inflate(DX, DY: Single);
  210. procedure Inflate(DL, DT, DR, DB: Single);
  211. function CenterPoint: TPointF;
  212. procedure Union (const r: TRectF); inline;
  213. procedure Offset (const dx,dy : Single); inline;
  214. procedure Offset (DP: TPointF); inline;
  215. property Width : Single read GetWidth write SetWidth;
  216. property Height : Single read GetHeight write SetHeight;
  217. property Size : TSizeF read getSize write SetSize;
  218. property Location: TPointF read getLocation write setLocation;
  219. case Integer of
  220. 0: (Left, Top, Right, Bottom: Single);
  221. 1: (TopLeft, BottomRight: TPointF);
  222. end;
  223. TDuplicates = (dupIgnore, dupAccept, dupError);
  224. TPoint3D =
  225. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  226. packed
  227. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  228. record
  229. public
  230. Type TSingle3Array = array[0..2] of single;
  231. constructor Create(const ax,ay,az:single);
  232. procedure Offset(const adeltax,adeltay,adeltaz:single); inline;
  233. procedure Offset(const adelta:TPoint3D); inline;
  234. public
  235. case Integer of
  236. 0: (data:TSingle3Array);
  237. 1: (x,y,z : single);
  238. end;
  239. type
  240. TOleChar = WideChar;
  241. POleStr = PWideChar;
  242. PPOleStr = ^POleStr;
  243. TListCallback = procedure(data,arg:pointer) of object;
  244. TListStaticCallback = procedure(data,arg:pointer);
  245. const
  246. GUID_NULL: TGUID = '{00000000-0000-0000-0000-000000000000}';
  247. STGTY_STORAGE = 1;
  248. STGTY_STREAM = 2;
  249. STGTY_LOCKBYTES = 3;
  250. STGTY_PROPERTY = 4;
  251. STREAM_SEEK_SET = 0;
  252. STREAM_SEEK_CUR = 1;
  253. STREAM_SEEK_END = 2;
  254. LOCK_WRITE = 1;
  255. LOCK_EXCLUSIVE = 2;
  256. LOCK_ONLYONCE = 4;
  257. STATFLAG_DEFAULT = 0;
  258. STATFLAG_NONAME = 1;
  259. STATFLAG_NOOPEN = 2;
  260. {$ifndef Wince}
  261. // in Wince these are in unit windows. Under 32/64 in ActiveX.
  262. // for now duplicate them. Not that bad for untyped constants.
  263. E_FAIL = HRESULT($80004005);
  264. E_INVALIDARG = HRESULT($80070057);
  265. STG_E_INVALIDFUNCTION = HRESULT($80030001);
  266. STG_E_FILENOTFOUND = HRESULT($80030002);
  267. STG_E_PATHNOTFOUND = HRESULT($80030003);
  268. STG_E_TOOMANYOPENFILES = HRESULT($80030004);
  269. STG_E_ACCESSDENIED = HRESULT($80030005);
  270. STG_E_INVALIDHANDLE = HRESULT($80030006);
  271. STG_E_INSUFFICIENTMEMORY = HRESULT($80030008);
  272. STG_E_INVALIDPOINTER = HRESULT($80030009);
  273. STG_E_NOMOREFILES = HRESULT($80030012);
  274. STG_E_DISKISWRITEPROTECTED = HRESULT($80030013);
  275. STG_E_SEEKERROR = HRESULT($80030019);
  276. STG_E_WRITEFAULT = HRESULT($8003001D);
  277. STG_E_READFAULT = HRESULT($8003001E);
  278. STG_E_SHAREVIOLATION = HRESULT($80030020);
  279. STG_E_LOCKVIOLATION = HRESULT($80030021);
  280. STG_E_FILEALREADYEXISTS = HRESULT($80030050);
  281. STG_E_INVALIDPARAMETER = HRESULT($80030057);
  282. STG_E_MEDIUMFULL = HRESULT($80030070);
  283. STG_E_PROPSETMISMATCHED = HRESULT($800300F0);
  284. STG_E_ABNORMALAPIEXIT = HRESULT($800300FA);
  285. STG_E_INVALIDHEADER = HRESULT($800300FB);
  286. STG_E_INVALIDNAME = HRESULT($800300FC);
  287. STG_E_UNKNOWN = HRESULT($800300FD);
  288. STG_E_UNIMPLEMENTEDFUNCTION = HRESULT($800300FE);
  289. STG_E_INVALIDFLAG = HRESULT($800300FF);
  290. STG_E_INUSE = HRESULT($80030100);
  291. STG_E_NOTCURRENT = HRESULT($80030101);
  292. STG_E_REVERTED = HRESULT($80030102);
  293. STG_E_CANTSAVE = HRESULT($80030103);
  294. STG_E_OLDFORMAT = HRESULT($80030104);
  295. STG_E_OLDDLL = HRESULT($80030105);
  296. STG_E_SHAREREQUIRED = HRESULT($80030106);
  297. STG_E_EXTANTMARSHALLINGS = HRESULT($80030108);
  298. STG_E_DOCFILECORRUPT = HRESULT($80030109);
  299. STG_E_BADBASEADDRESS = HRESULT($80030110);
  300. STG_E_INCOMPLETE = HRESULT($80030201);
  301. STG_E_TERMINATED = HRESULT($80030202);
  302. STG_S_CONVERTED = $00030200;
  303. STG_S_BLOCK = $00030201;
  304. STG_S_RETRYNOW = $00030202;
  305. STG_S_MONITORING = $00030203;
  306. {$endif}
  307. {$if (not defined(win32)) and (not defined(win64)) and (not defined(wince))}
  308. type
  309. PCLSID = PGUID;
  310. TCLSID = TGUID;
  311. PDWord = ^DWord;
  312. PDisplay = Pointer;
  313. PEvent = Pointer;
  314. TXrmOptionDescRec = record
  315. end;
  316. XrmOptionDescRec = TXrmOptionDescRec;
  317. PXrmOptionDescRec = ^TXrmOptionDescRec;
  318. Widget = Pointer;
  319. WidgetClass = Pointer;
  320. ArgList = Pointer;
  321. Region = Pointer;
  322. _FILETIME =
  323. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  324. packed
  325. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  326. record
  327. dwLowDateTime : DWORD;
  328. dwHighDateTime : DWORD;
  329. end;
  330. TFileTime = _FILETIME;
  331. FILETIME = _FILETIME;
  332. PFileTime = ^TFileTime;
  333. {$else}
  334. type
  335. PCLSID = Windows.PCLSID;
  336. TCLSID = Windows.CLSID;
  337. TFiletime = Windows.TFileTime;
  338. Filetime = Windows.FileTime;
  339. PFiletime = Windows.PFileTime;
  340. {$endif Windows}
  341. type
  342. tagSTATSTG = record
  343. pwcsName : POleStr;
  344. dwType : DWord;
  345. cbSize : Large_uint;
  346. mtime : TFileTime;
  347. ctime : TFileTime;
  348. atime : TFileTime;
  349. grfMode : DWord;
  350. grfLocksSupported : DWord;
  351. clsid : TCLSID;
  352. grfStateBits : DWord;
  353. reserved : DWord;
  354. end;
  355. TStatStg = tagSTATSTG;
  356. STATSTG = TStatStg;
  357. PStatStg = ^TStatStg;
  358. { classes depends on these interfaces, we can't use the activex unit in classes though }
  359. IClassFactory = Interface(IUnknown) ['{00000001-0000-0000-C000-000000000046}']
  360. Function CreateInstance(Const unkOuter : IUnknown;Const riid : TGUID;Out vObject) : HResult;StdCall;
  361. Function LockServer(fLock : LongBool) : HResult;StdCall;
  362. End;
  363. ISequentialStream = interface(IUnknown)
  364. ['{0c733a30-2a1c-11ce-ade5-00aa0044773d}']
  365. function Read(pv : Pointer;cb : DWORD;pcbRead : PDWORD) : HRESULT;stdcall;
  366. function Write(pv : Pointer;cb : DWORD;pcbWritten : PDWORD): HRESULT;stdcall;
  367. end;
  368. IStream = interface(ISequentialStream) ['{0000000C-0000-0000-C000-000000000046}']
  369. function Seek(dlibMove : LargeInt; dwOrigin : DWORD; out libNewPosition : LargeUInt) : HResult;stdcall;
  370. function SetSize(libNewSize : LargeUInt) : HRESULT;stdcall;
  371. function CopyTo(stm: IStream;cb : LargeUInt;out cbRead : LargeUInt; out cbWritten : LargeUInt) : HRESULT;stdcall;
  372. function Commit(grfCommitFlags : DWORD) : HRESULT;stdcall;
  373. function Revert : HRESULT;stdcall;
  374. function LockRegion(libOffset : LargeUInt;cb : LargeUInt; dwLockType : DWORD) : HRESULT;stdcall;
  375. function UnlockRegion(libOffset : LargeUInt;cb : LargeUInt; dwLockType : DWORD) : HRESULT;stdcall;
  376. Function Stat(out statstg : TStatStg;grfStatFlag : DWORD) : HRESULT;stdcall;
  377. function Clone(out stm : IStream) : HRESULT;stdcall;
  378. end;
  379. function EqualRect(const r1,r2 : TRect) : Boolean;
  380. function Rect(Left,Top,Right,Bottom : Integer) : TRect; inline;
  381. function RectF(Left,Top,Right,Bottom : Single) : TRectF; inline;
  382. function Bounds(ALeft,ATop,AWidth,AHeight : Integer) : TRect; inline;
  383. function Point(x,y : Integer) : TPoint; inline;
  384. function PointF(x,y: Single) : TPointF; inline;
  385. function PtInRect(const Rect : TRect; const p : TPoint) : Boolean;
  386. function IntersectRect(var Rect : TRect; const R1,R2 : TRect) : Boolean;
  387. function UnionRect(var Rect : TRect; const R1,R2 : TRect) : Boolean;
  388. function IsRectEmpty(const Rect : TRect) : Boolean;
  389. function OffsetRect(var Rect : TRect;DX : Integer;DY : Integer) : Boolean;
  390. function CenterPoint(const Rect: TRect): TPoint;
  391. function InflateRect(var Rect: TRect; dx: Integer; dy: Integer): Boolean;
  392. function Size(AWidth, AHeight: Integer): TSize; inline;
  393. function Size(const ARect: TRect): TSize;
  394. {$ifndef VER3_0}
  395. type
  396. TBitConverter = class
  397. generic class procedure UnsafeFrom<T>(const ASrcValue: T; var ADestination: Array of Byte; AOffset: Integer = 0); static; {inline;}
  398. generic class procedure From<T>(const ASrcValue: T; var ADestination: Array of Byte; AOffset: Integer = 0); static;
  399. generic class function UnsafeInTo<T>(const ASource: Array of Byte; AOffset: Integer = 0): T; static; {inline;}
  400. generic class function InTo<T>(const ASource: Array of Byte; AOffset: Integer = 0): T; static;
  401. end;
  402. {$endif}
  403. implementation
  404. Uses Math;
  405. {$if (not defined(win32)) and (not defined(win64)) and (not defined(wince))}
  406. {$i typshrd.inc}
  407. {$endif}
  408. function EqualRect(const r1,r2 : TRect) : Boolean;
  409. begin
  410. EqualRect:=(r1.left=r2.left) and (r1.right=r2.right) and (r1.top=r2.top) and (r1.bottom=r2.bottom);
  411. end;
  412. function Rect(Left,Top,Right,Bottom : Integer) : TRect; inline;
  413. begin
  414. Rect.Left:=Left;
  415. Rect.Top:=Top;
  416. Rect.Right:=Right;
  417. Rect.Bottom:=Bottom;
  418. end;
  419. function RectF(Left,Top,Right,Bottom : Single) : TRectF; inline;
  420. begin
  421. RectF.Left:=Left;
  422. RectF.Top:=Top;
  423. RectF.Right:=Right;
  424. RectF.Bottom:=Bottom;
  425. end;
  426. function Bounds(ALeft,ATop,AWidth,AHeight : Integer) : TRect; inline;
  427. begin
  428. Bounds.Left:=ALeft;
  429. Bounds.Top:=ATop;
  430. Bounds.Right:=ALeft+AWidth;
  431. Bounds.Bottom:=ATop+AHeight;
  432. end;
  433. function Point(x,y : Integer) : TPoint; inline;
  434. begin
  435. Point.x:=x;
  436. Point.y:=y;
  437. end;
  438. function PointF(x,y: Single) : TPointF; inline;
  439. begin
  440. PointF.x:=x;
  441. PointF.y:=y;
  442. end;
  443. function PtInRect(const Rect : TRect;const p : TPoint) : Boolean;
  444. begin
  445. PtInRect:=(p.y>=Rect.Top) and
  446. (p.y<Rect.Bottom) and
  447. (p.x>=Rect.Left) and
  448. (p.x<Rect.Right);
  449. end;
  450. function IntersectRect(var Rect : TRect;const R1,R2 : TRect) : Boolean;
  451. var
  452. lRect: TRect;
  453. begin
  454. lRect := R1;
  455. if R2.Left > R1.Left then
  456. lRect.Left := R2.Left;
  457. if R2.Top > R1.Top then
  458. lRect.Top := R2.Top;
  459. if R2.Right < R1.Right then
  460. lRect.Right := R2.Right;
  461. if R2.Bottom < R1.Bottom then
  462. lRect.Bottom := R2.Bottom;
  463. // The var parameter is only assigned in the end to avoid problems
  464. // when passing the same rectangle in the var and const parameters.
  465. // See http://bugs.freepascal.org/view.php?id=17722
  466. Result:=not IsRectEmpty(lRect);
  467. if Result then
  468. Rect := lRect
  469. else
  470. FillChar(Rect,SizeOf(Rect),0);
  471. end;
  472. function UnionRect(var Rect : TRect;const R1,R2 : TRect) : Boolean;
  473. var
  474. lRect: TRect;
  475. begin
  476. lRect:=R1;
  477. if R2.Left<R1.Left then
  478. lRect.Left:=R2.Left;
  479. if R2.Top<R1.Top then
  480. lRect.Top:=R2.Top;
  481. if R2.Right>R1.Right then
  482. lRect.Right:=R2.Right;
  483. if R2.Bottom>R1.Bottom then
  484. lRect.Bottom:=R2.Bottom;
  485. Result:=not IsRectEmpty(lRect);
  486. if Result then
  487. Rect := lRect
  488. else
  489. FillChar(Rect,SizeOf(Rect),0);
  490. end;
  491. function IsRectEmpty(const Rect : TRect) : Boolean;
  492. begin
  493. IsRectEmpty:=(Rect.Right<=Rect.Left) or (Rect.Bottom<=Rect.Top);
  494. end;
  495. function OffsetRect(var Rect : TRect;DX : Integer;DY : Integer) : Boolean;
  496. begin
  497. Result:=assigned(@Rect);
  498. if Result then
  499. with Rect do
  500. begin
  501. inc(Left,dx);
  502. inc(Top,dy);
  503. inc(Right,dx);
  504. inc(Bottom,dy);
  505. end;
  506. end;
  507. function Avg(a, b: Longint): Longint;
  508. begin
  509. if a < b then
  510. Result := a + ((b - a) shr 1)
  511. else
  512. Result := b + ((a - b) shr 1);
  513. end;
  514. function CenterPoint(const Rect: TRect): TPoint;
  515. begin
  516. with Rect do
  517. begin
  518. Result.X := Avg(Left, Right);
  519. Result.Y := Avg(Top, Bottom);
  520. end;
  521. end;
  522. function InflateRect(var Rect: TRect; dx: Integer; dy: Integer): Boolean;
  523. begin
  524. Result:=assigned(@Rect);
  525. if Result then
  526. with Rect do
  527. begin
  528. dec(Left, dx);
  529. dec(Top, dy);
  530. inc(Right, dx);
  531. inc(Bottom, dy);
  532. end;
  533. end;
  534. function Size(AWidth, AHeight: Integer): TSize; inline;
  535. begin
  536. Result.cx := AWidth;
  537. Result.cy := AHeight;
  538. end;
  539. function Size(const ARect: TRect): TSize; inline;
  540. begin
  541. Result.cx := ARect.Right - ARect.Left;
  542. Result.cy := ARect.Bottom - ARect.Top;
  543. end;
  544. { TPointF}
  545. function TPointF.Add(const apt: TPoint): TPointF;
  546. begin
  547. result.x:=x+apt.x;
  548. result.y:=y+apt.y;
  549. end;
  550. function TPointF.Add(const apt: TPointF): TPointF;
  551. begin
  552. result.x:=x+apt.x;
  553. result.y:=y+apt.y;
  554. end;
  555. function TPointF.Subtract(const apt : TPointF): TPointF;
  556. begin
  557. result.x:=x-apt.x;
  558. result.y:=y-apt.y;
  559. end;
  560. function TPointF.Subtract(const apt: TPoint): TPointF;
  561. begin
  562. result.x:=x-apt.x;
  563. result.y:=y-apt.y;
  564. end;
  565. function TPointF.Distance(const apt : TPointF) : Single;
  566. begin
  567. result:=sqrt(sqr(apt.x-x)+sqr(apt.y-y));
  568. end;
  569. function TPointF.DotProduct(const apt: TPointF): Single;
  570. begin
  571. result:=x*apt.x+y*apt.y;
  572. end;
  573. function TPointF.IsZero : Boolean;
  574. begin
  575. result:=SameValue(x,0.0) and SameValue(y,0.0);
  576. end;
  577. procedure TPointF.Offset(const apt :TPointF);
  578. begin
  579. x:=x+apt.x;
  580. y:=y+apt.y;
  581. end;
  582. procedure TPointF.Offset(const apt: TPoint);
  583. begin
  584. x:=x+apt.x;
  585. y:=y+apt.y;
  586. end;
  587. procedure TPointF.Offset(dx,dy : Single);
  588. begin
  589. x:=x+dx;
  590. y:=y+dy;
  591. end;
  592. function TPointF.Scale(afactor: Single): TPointF;
  593. begin
  594. result.x:=afactor*x;
  595. result.y:=afactor*y;
  596. end;
  597. function TPointF.Ceiling: TPoint;
  598. begin
  599. result.x:=ceil(x);
  600. result.y:=ceil(y);
  601. end;
  602. function TPointF.Truncate: TPoint;
  603. begin
  604. result.x:=trunc(x);
  605. result.y:=trunc(y);
  606. end;
  607. function TPointF.Floor: TPoint;
  608. begin
  609. result.x:=Math.floor(x);
  610. result.y:=Math.floor(y);
  611. end;
  612. function TPointF.Round: TPoint;
  613. begin
  614. result.x:=System.round(x);
  615. result.y:=System.round(y);
  616. end;
  617. function TPointF.Length: Single;
  618. begin //distance(self) ?
  619. result:=sqrt(sqr(x)+sqr(y));
  620. end;
  621. class operator TPointF.= (const apt1, apt2 : TPointF) : Boolean;
  622. begin
  623. result:=SameValue(apt1.x,apt2.x) and SameValue(apt1.y,apt2.y);
  624. end;
  625. class operator TPointF.<> (const apt1, apt2 : TPointF): Boolean;
  626. begin
  627. result:=NOT (SameValue(apt1.x,apt2.x) and Samevalue(apt1.y,apt2.y));
  628. end;
  629. class operator TPointF. * (const apt1, apt2: TPointF): TPointF;
  630. begin
  631. result.x:=apt1.x*apt2.x;
  632. result.y:=apt1.y*apt2.y;
  633. end;
  634. class operator TPointF. * (afactor: single; const apt1: TPointF): TPointF;
  635. begin
  636. result:=apt1.Scale(afactor);
  637. end;
  638. class operator TPointF. * (const apt1: TPointF; afactor: single): TPointF;
  639. begin
  640. result:=apt1.Scale(afactor);
  641. end;
  642. class operator TPointF. ** (const apt1, apt2: TPointF): Single;
  643. begin
  644. result:=apt1.x*apt2.x + apt1.y*apt2.y;
  645. end;
  646. class operator TPointF.+ (const apt1, apt2 : TPointF): TPointF;
  647. begin
  648. result.x:=apt1.x+apt2.x;
  649. result.y:=apt1.y+apt2.y;
  650. end;
  651. class operator TPointF.- (const apt1, apt2 : TPointF): TPointF;
  652. begin
  653. result.x:=apt1.x-apt2.x;
  654. result.y:=apt1.y-apt2.y;
  655. end;
  656. class operator TPointF. - (const apt1: TPointF): TPointF;
  657. begin
  658. Result.x:=-apt1.x;
  659. Result.y:=-apt1.y;
  660. end;
  661. class operator TPointF. / (const apt1: TPointF; afactor: single): TPointF;
  662. begin
  663. result:=apt1.Scale(1/afactor);
  664. end;
  665. class operator TPointF. := (const apt: TPoint): TPointF;
  666. begin
  667. Result.x:=apt.x;
  668. Result.y:=apt.y;
  669. end;
  670. procedure TPointF.SetLocation(const apt :TPointF);
  671. begin
  672. x:=apt.x; y:=apt.y;
  673. end;
  674. procedure TPointF.SetLocation(const apt: TPoint);
  675. begin
  676. x:=apt.x; y:=apt.y;
  677. end;
  678. procedure TPointF.SetLocation(ax,ay : Single);
  679. begin
  680. x:=ax; y:=ay;
  681. end;
  682. class function TPointF.Create(const ax, ay: Single): TPointF;
  683. begin
  684. Result.x := ax;
  685. Result.y := ay;
  686. end;
  687. class function TPointF.Create(const apt: TPoint): TPointF;
  688. begin
  689. Result.x := apt.X;
  690. Result.y := apt.Y;
  691. end;
  692. { TSizeF }
  693. function TSizeF.Add(const asz: TSize): TSizeF;
  694. begin
  695. result.cx:=cx+asz.cx;
  696. result.cy:=cy+asz.cy;
  697. end;
  698. function TSizeF.Add(const asz: TSizeF): TSizeF;
  699. begin
  700. result.cx:=cx+asz.cx;
  701. result.cy:=cy+asz.cy;
  702. end;
  703. function TSizeF.Subtract(const asz : TSizeF): TSizeF;
  704. begin
  705. result.cx:=cx-asz.cx;
  706. result.cy:=cy-asz.cy;
  707. end;
  708. function TSizeF.Subtract(const asz: TSize): TSizeF;
  709. begin
  710. result.cx:=cx-asz.cx;
  711. result.cy:=cy-asz.cy;
  712. end;
  713. function TSizeF.Distance(const asz : TSizeF) : Single;
  714. begin
  715. result:=sqrt(sqr(asz.cx-cx)+sqr(asz.cy-cy));
  716. end;
  717. function TSizeF.IsZero : Boolean;
  718. begin
  719. result:=SameValue(cx,0.0) and SameValue(cy,0.0);
  720. end;
  721. function TSizeF.Scale(afactor: Single): TSizeF;
  722. begin
  723. result.cx:=afactor*cx;
  724. result.cy:=afactor*cy;
  725. end;
  726. function TSizeF.Ceiling: TSize;
  727. begin
  728. result.cx:=ceil(cx);
  729. result.cy:=ceil(cy);
  730. end;
  731. function TSizeF.Truncate: TSize;
  732. begin
  733. result.cx:=trunc(cx);
  734. result.cy:=trunc(cy);
  735. end;
  736. function TSizeF.Floor: TSize;
  737. begin
  738. result.cx:=Math.floor(cx);
  739. result.cy:=Math.floor(cy);
  740. end;
  741. function TSizeF.Round: TSize;
  742. begin
  743. result.cx:=System.round(cx);
  744. result.cy:=System.round(cy);
  745. end;
  746. function TSizeF.Length: Single;
  747. begin //distance(self) ?
  748. result:=sqrt(sqr(cx)+sqr(cy));
  749. end;
  750. class operator TSizeF.= (const asz1, asz2 : TSizeF) : Boolean;
  751. begin
  752. result:=SameValue(asz1.cx,asz2.cx) and SameValue(asz1.cy,asz2.cy);
  753. end;
  754. class operator TSizeF.<> (const asz1, asz2 : TSizeF): Boolean;
  755. begin
  756. result:=NOT (SameValue(asz1.cx,asz2.cx) and Samevalue(asz1.cy,asz2.cy));
  757. end;
  758. class operator TSizeF. * (afactor: single; const asz1: TSizeF): TSizeF;
  759. begin
  760. result:=asz1.Scale(afactor);
  761. end;
  762. class operator TSizeF. * (const asz1: TSizeF; afactor: single): TSizeF;
  763. begin
  764. result:=asz1.Scale(afactor);
  765. end;
  766. class operator TSizeF.+ (const asz1, asz2 : TSizeF): TSizeF;
  767. begin
  768. result.cx:=asz1.cx+asz2.cx;
  769. result.cy:=asz1.cy+asz2.cy;
  770. end;
  771. class operator TSizeF.- (const asz1, asz2 : TSizeF): TSizeF;
  772. begin
  773. result.cx:=asz1.cx-asz2.cx;
  774. result.cy:=asz1.cy-asz2.cy;
  775. end;
  776. class operator TSizeF. - (const asz1: TSizeF): TSizeF;
  777. begin
  778. Result.cx:=-asz1.cx;
  779. Result.cy:=-asz1.cy;
  780. end;
  781. class operator TSizeF. := (const apt: TPointF): TSizeF;
  782. begin
  783. Result.cx:=apt.x;
  784. Result.cy:=apt.y;
  785. end;
  786. class operator TSizeF. := (const asz: TSize): TSizeF;
  787. begin
  788. Result.cx := asz.cx;
  789. Result.cy := asz.cy;
  790. end;
  791. class operator TSizeF. := (const asz: TSizeF): TPointF;
  792. begin
  793. Result.x := asz.cx;
  794. Result.y := asz.cy;
  795. end;
  796. class function TSizeF.Create(const ax, ay: Single): TSizeF;
  797. begin
  798. Result.cx := ax;
  799. Result.cy := ay;
  800. end;
  801. class function TSizeF.Create(const asz: TSize): TSizeF;
  802. begin
  803. Result.cx := asz.cX;
  804. Result.cy := asz.cY;
  805. end;
  806. { TRectF }
  807. class operator TRectF. * (L, R: TRectF): TRectF;
  808. begin
  809. Result := TRectF.Intersect(L, R);
  810. end;
  811. class operator TRectF. + (L, R: TRectF): TRectF;
  812. begin
  813. Result := TRectF.Union(L, R);
  814. end;
  815. class operator TRectF. := (const arc: TRect): TRectF;
  816. begin
  817. Result.Left:=arc.Left;
  818. Result.Top:=arc.Top;
  819. Result.Right:=arc.Right;
  820. Result.Bottom:=arc.Bottom;
  821. end;
  822. class operator TRectF. <> (L, R: TRectF): Boolean;
  823. begin
  824. Result := not(L=R);
  825. end;
  826. class operator TRectF. = (L, R: TRectF): Boolean;
  827. begin
  828. Result :=
  829. SameValue(L.Left,R.Left) and SameValue(L.Right,R.Right) and
  830. SameValue(L.Top,R.Top) and SameValue(L.Bottom,R.Bottom);
  831. end;
  832. constructor TRectF.Create(ALeft, ATop, ARight, ABottom: Single);
  833. begin
  834. Left := ALeft;
  835. Top := ATop;
  836. Right := ARight;
  837. Bottom := ABottom;
  838. end;
  839. constructor TRectF.Create(P1, P2: TPointF; Normalize: Boolean);
  840. begin
  841. TopLeft := P1;
  842. BottomRight := P2;
  843. if Normalize then
  844. NormalizeRect;
  845. end;
  846. constructor TRectF.Create(Origin: TPointF);
  847. begin
  848. TopLeft := Origin;
  849. BottomRight := Origin;
  850. end;
  851. constructor TRectF.Create(Origin: TPointF; AWidth, AHeight: Single);
  852. begin
  853. TopLeft := Origin;
  854. Width := AWidth;
  855. Height := AHeight;
  856. end;
  857. constructor TRectF.Create(R: TRectF; Normalize: Boolean);
  858. begin
  859. Self := R;
  860. if Normalize then
  861. NormalizeRect;
  862. end;
  863. constructor TRectF.Create(R: TRect; Normalize: Boolean);
  864. begin
  865. Self := R;
  866. if Normalize then
  867. NormalizeRect;
  868. end;
  869. function TRectF.CenterPoint: TPointF;
  870. begin
  871. Result.X := (Right-Left) / 2 + Left;
  872. Result.Y := (Bottom-Top) / 2 + Top;
  873. end;
  874. function TRectF.Contains(Pt: TPointF): Boolean;
  875. begin
  876. Result := (Left <= Pt.X) and (Pt.X < Right) and (Top <= Pt.Y) and (Pt.Y < Bottom);
  877. end;
  878. function TRectF.Contains(R: TRectF): Boolean;
  879. begin
  880. Result := (Left <= R.Left) and (R.Right <= Right) and (Top <= R.Top) and (R.Bottom <= Bottom);
  881. end;
  882. class function TRectF.Empty: TRectF;
  883. begin
  884. Result := TRectF.Create(0,0,0,0);
  885. end;
  886. function TRectF.GetHeight: Single;
  887. begin
  888. result:=bottom-top;
  889. end;
  890. function TRectF.GetLocation: TPointF;
  891. begin
  892. result.x:=Left; result.y:=top;
  893. end;
  894. function TRectF.GetSize: TSizeF;
  895. begin
  896. result.cx:=width; result.cy:=height;
  897. end;
  898. function TRectF.GetWidth: Single;
  899. begin
  900. result:=right-left;
  901. end;
  902. procedure TRectF.Inflate(DX, DY: Single);
  903. begin
  904. Left:=Left-dx;
  905. Top:=Top-dy;
  906. Right:=Right+dx;
  907. Bottom:=Bottom+dy;
  908. end;
  909. procedure TRectF.Intersect(R: TRectF);
  910. begin
  911. Self := Intersect(Self, R);
  912. end;
  913. class function TRectF.Intersect(R1: TRectF; R2: TRectF): TRectF;
  914. begin
  915. Result := R1;
  916. if R2.Left > R1.Left then
  917. Result.Left := R2.Left;
  918. if R2.Top > R1.Top then
  919. Result.Top := R2.Top;
  920. if R2.Right < R1.Right then
  921. Result.Right := R2.Right;
  922. if R2.Bottom < R1.Bottom then
  923. Result.Bottom := R2.Bottom;
  924. end;
  925. function TRectF.IntersectsWith(R: TRectF): Boolean;
  926. begin
  927. Result := (Left < R.Right) and (R.Left < Right) and (Top < R.Bottom) and (R.Top < Bottom);
  928. end;
  929. function TRectF.IsEmpty: Boolean;
  930. begin
  931. Result := (CompareValue(Right,Left)<=0) or (CompareValue(Bottom,Top)<=0);
  932. end;
  933. procedure TRectF.NormalizeRect;
  934. var
  935. x: Single;
  936. begin
  937. if Top>Bottom then
  938. begin
  939. x := Top;
  940. Top := Bottom;
  941. Bottom := x;
  942. end;
  943. if Left>Right then
  944. begin
  945. x := Left;
  946. Left := Right;
  947. Right := x;
  948. end
  949. end;
  950. procedure TRectF.Inflate(DL, DT, DR, DB: Single);
  951. begin
  952. Left:=Left-dl;
  953. Top:=Top-dt;
  954. Right:=Right+dr;
  955. Bottom:=Bottom+db;
  956. end;
  957. procedure TRectF.Offset(const dx, dy: Single);
  958. begin
  959. left:=left+dx; right:=right+dx;
  960. bottom:=bottom+dy; top:=top+dy;
  961. end;
  962. procedure TRectF.Offset(DP: TPointF);
  963. begin
  964. left:=left+DP.x; right:=right+DP.x;
  965. bottom:=bottom+DP.y; top:=top+DP.y;
  966. end;
  967. procedure TRectF.SetHeight(AValue: Single);
  968. begin
  969. bottom:=top+avalue;
  970. end;
  971. procedure TRectF.SetLocation(X, Y: Single);
  972. begin
  973. Offset(X-Left, Y-Top);
  974. end;
  975. procedure TRectF.SetLocation(P: TPointF);
  976. begin
  977. SetLocation(P.X, P.Y);
  978. end;
  979. procedure TRectF.SetSize(AValue: TSizeF);
  980. begin
  981. bottom:=top+avalue.cy;
  982. right:=left+avalue.cx;
  983. end;
  984. procedure TRectF.SetWidth(AValue: Single);
  985. begin
  986. right:=left+avalue;
  987. end;
  988. class function TRectF.Union(const Points: array of TPointF): TRectF;
  989. var
  990. i: Integer;
  991. begin
  992. if Length(Points) > 0 then
  993. begin
  994. Result.TopLeft := Points[Low(Points)];
  995. Result.BottomRight := Points[Low(Points)];
  996. for i := Low(Points)+1 to High(Points) do
  997. begin
  998. if Points[i].X < Result.Left then Result.Left := Points[i].X;
  999. if Points[i].X > Result.Right then Result.Right := Points[i].X;
  1000. if Points[i].Y < Result.Top then Result.Top := Points[i].Y;
  1001. if Points[i].Y > Result.Bottom then Result.Bottom := Points[i].Y;
  1002. end;
  1003. end else
  1004. Result := Empty;
  1005. end;
  1006. procedure TRectF.Union(const r: TRectF);
  1007. begin
  1008. left:=min(r.left,left);
  1009. top:=min(r.top,top);
  1010. right:=max(r.right,right);
  1011. bottom:=max(r.bottom,bottom);
  1012. end;
  1013. class function TRectF.Union(R1, R2: TRectF): TRectF;
  1014. begin
  1015. Result:=R1;
  1016. Result.Union(R2);
  1017. end;
  1018. { TPoint3D }
  1019. constructor TPoint3D.Create(const ax,ay,az:single);
  1020. begin
  1021. x:=ax; y:=ay; z:=az;
  1022. end;
  1023. procedure TPoint3D.Offset(const adeltax,adeltay,adeltaz:single);
  1024. begin
  1025. x:=x+adeltax; y:=y+adeltay; z:=z+adeltaz;
  1026. end;
  1027. procedure TPoint3D.Offset(const adelta:TPoint3D);
  1028. begin
  1029. x:=x+adelta.x; y:=y+adelta.y; z:=z+adelta.z;
  1030. end;
  1031. {$ifndef VER3_0}
  1032. generic class procedure TBitConverter.UnsafeFrom<T>(const ASrcValue: T; var ADestination: Array of Byte; AOffset: Integer = 0);
  1033. begin
  1034. move(ASrcValue, ADestination[AOffset], SizeOf(T));
  1035. end;
  1036. generic class procedure TBitConverter.From<T>(const ASrcValue: T; var ADestination: Array of Byte; AOffset: Integer = 0);
  1037. begin
  1038. if AOffset < 0 then
  1039. System.Error(reRangeError);
  1040. if IsManagedType(T) then
  1041. System.Error(reInvalidCast);
  1042. if Length(ADestination) < (SizeOf(T) + AOffset) then
  1043. System.Error(reRangeError);
  1044. TBitConverter.specialize UnsafeFrom<T>(ASrcValue, ADestination, AOffset);
  1045. end;
  1046. generic class function TBitConverter.UnsafeInTo<T>(const ASource: Array of Byte; AOffset: Integer = 0): T;
  1047. begin
  1048. move(ASource[AOffset], Result, SizeOf(T));
  1049. end;
  1050. generic class function TBitConverter.InTo<T>(const ASource: Array of Byte; AOffset: Integer = 0): T;
  1051. begin
  1052. if AOffset < 0 then
  1053. System.Error(reRangeError);
  1054. if IsManagedType(T) then
  1055. System.Error(reInvalidCast);
  1056. if Length(ASource) < (SizeOf(T) + AOffset) then
  1057. System.Error(reRangeError);
  1058. Result := TBitConverter.specialize UnsafeInTo<T>(ASource, AOffset);
  1059. end;
  1060. {$endif}
  1061. end.