drivers.pas 144 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632
  1. { $Id$ }
  2. {********[ SOURCE FILE OF GRAPHICAL FREE VISION ]**********}
  3. { }
  4. { System independent clone of DRIVERS.PAS }
  5. { }
  6. { Interface Copyright (c) 1992 Borland International }
  7. { }
  8. { Copyright (c) 1996, 1997, 1998, 1999 by Leon de Boer }
  9. { [email protected] - primary e-mail addr }
  10. { [email protected] - backup e-mail addr }
  11. { }
  12. { Original FormatStr kindly donated by Marco Schmidt }
  13. { }
  14. { Mouse callback hook under FPC with kind assistance of }
  15. { Pierre Muller, Gertjan Schouten & Florian Klaempfl. }
  16. { }
  17. {****************[ THIS CODE IS FREEWARE ]*****************}
  18. { }
  19. { This sourcecode is released for the purpose to }
  20. { promote the pascal language on all platforms. You may }
  21. { redistribute it and/or modify with the following }
  22. { DISCLAIMER. }
  23. { }
  24. { This SOURCE CODE is distributed "AS IS" WITHOUT }
  25. { WARRANTIES AS TO PERFORMANCE OF MERCHANTABILITY OR }
  26. { ANY OTHER WARRANTIES WHETHER EXPRESSED OR IMPLIED. }
  27. { }
  28. {*****************[ SUPPORTED PLATFORMS ]******************}
  29. { 16 and 32 Bit compilers }
  30. { DOS - Turbo Pascal 7.0 + (16 Bit) }
  31. { DPMI - Turbo Pascal 7.0 + (16 Bit) }
  32. { - FPC 0.9912+ (GO32V2) (32 Bit) }
  33. { WINDOWS - Turbo Pascal 7.0 + (16 Bit) }
  34. { - Delphi 1.0+ (16 Bit) }
  35. { WIN95/NT - Delphi 2.0+ (32 Bit) }
  36. { - Virtual Pascal 2.0+ (32 Bit) }
  37. { - Speedsoft Sybil 2.0+ (32 Bit) }
  38. { - FPC 0.9912+ (32 Bit) }
  39. { OS2 - Virtual Pascal 1.0+ (32 Bit) }
  40. { - Speed Pascal 1.0+ (32 Bit) }
  41. { }
  42. {******************[ REVISION HISTORY ]********************}
  43. { Version Date Fix }
  44. { ------- --------- --------------------------------- }
  45. { 1.00 26 Jul 96 First DOS/DPMI platform release }
  46. { 1.10 18 Nov 97 Windows conversion added. }
  47. { 1.20 29 Aug 97 Platform.inc sort added. }
  48. { 1.30 10 Jun 98 Virtual pascal 2.0 code added. }
  49. { 1.40 13 Jul 98 Added FormatStr by Marco Schmidt. }
  50. { 1.50 14 Jul 98 Fixed width = 0 in FormatStr. }
  51. { 1.60 13 Aug 98 Complete rewrite of FormatStr. }
  52. { 1.70 10 Sep 98 Added mouse int hook for FPC. }
  53. { 1.80 10 Sep 98 Checks run & commenting added. }
  54. { 1.90 15 Oct 98 Fixed for FPC version 0.998 }
  55. { 1.91 18 Feb 99 Added PrintStr functions }
  56. { 1.92 18 Feb 99 FormatStr literal '%' fix added }
  57. { 1.93 10 Jul 99 Sybil 2.0 code added }
  58. { 1.94 15 Jul 99 Fixed for FPC 0.9912 release }
  59. { 1.95 26 Jul 99 Windows..Scales to GFV system font }
  60. { 1.96 30 Jul 99 Fixed Ctrl+F1..F10 in GetKeyEvent }
  61. { 1.97 07 Sep 99 InitEvent, DoneEvent fixed for OS2 }
  62. { 1.98 09 Sep 99 GetMouseEvent fixed for OS2. }
  63. { 1.99 03 Nov 99 FPC windows support added. }
  64. { 2.00 26 Nov 99 Graphics stuff moved to GFVGraph }
  65. {**********************************************************}
  66. UNIT Drivers;
  67. {<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>}
  68. INTERFACE
  69. {<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>}
  70. {====Include file to sort compiler platform out =====================}
  71. {$I Platform.inc}
  72. {====================================================================}
  73. {==== Compiler directives ===========================================}
  74. {$IFNDEF PPC_FPC} { FPC doesn't support these switches }
  75. {$F+} { Force far calls - Used because of the ShowMouseProc etc... }
  76. {$A+} { Word Align Data }
  77. {$B-} { Allow short circuit boolean evaluations }
  78. {$O-} { This unit may >>> NOT <<< be overlaid }
  79. {$G+} { 286 Code optimization - if you're on an 8088 get a real computer }
  80. {$P-} { Normal string variables }
  81. {$N-} { No 80x87 code generation }
  82. {$E+} { Emulation is on }
  83. {$ENDIF}
  84. {$X+} { Extended syntax is ok }
  85. {$R-} { Disable range checking }
  86. {$S-} { Disable Stack Checking }
  87. {$I-} { Disable IO Checking }
  88. {$Q-} { Disable Overflow Checking }
  89. {$V-} { Turn off strict VAR strings }
  90. {====================================================================}
  91. USES
  92. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  93. {$IFNDEF PPC_SPEED} { NON SPEED COMPILER }
  94. {$IFDEF PPC_FPC} { FPC WINDOWS COMPILER }
  95. Windows, { Standard unit }
  96. {$ELSE} { OTHER COMPILERS }
  97. WinTypes, WinProcs, { Standard units }
  98. {$ENDIF}
  99. {$IFDEF PPC_DELPHI} { DELPHI3+ COMPILER }
  100. SysUtils, Messages, { Standard unit }
  101. {$ENDIF}
  102. {$ELSE} { SYBIL2+ COMPILER }
  103. WinBase, WinDef, WinUser, WinGDI, { Standard units }
  104. {$ENDIF}
  105. {$ENDIF}
  106. {$IFDEF OS_OS2} { OS2 CODE }
  107. {$IFDEF PPC_Virtual} { VIRTUAL PASCAL UNITS }
  108. OS2Def, OS2Base, OS2PMAPI, { Standard units }
  109. {$ENDIF}
  110. {$IFDEF PPC_Speed} { SPEED PASCAL UNITS }
  111. BseDos, Os2Def, { Standard units }
  112. {$ENDIF}
  113. {$ENDIF}
  114. Common, GFVGraph, Objects; { GFV standard units }
  115. {***************************************************************************}
  116. { PUBLIC CONSTANTS }
  117. {***************************************************************************}
  118. {---------------------------------------------------------------------------}
  119. { EVENT TYPE MASKS }
  120. {---------------------------------------------------------------------------}
  121. CONST
  122. evMouseDown = $0001; { Mouse down event }
  123. evMouseUp = $0002; { Mouse up event }
  124. evMouseMove = $0004; { Mouse move event }
  125. evMouseAuto = $0008; { Mouse auto event }
  126. evKeyDown = $0010; { Key down event }
  127. evCommand = $0100; { Command event }
  128. evBroadcast = $0200; { Broadcast event }
  129. {---------------------------------------------------------------------------}
  130. { EVENT CODE MASKS }
  131. {---------------------------------------------------------------------------}
  132. CONST
  133. evNothing = $0000; { Empty event }
  134. evMouse = $000F; { Mouse event }
  135. evKeyboard = $0010; { Keyboard event }
  136. evMessage = $FF00; { Message event }
  137. {---------------------------------------------------------------------------}
  138. { EXTENDED KEY CODES }
  139. {---------------------------------------------------------------------------}
  140. CONST
  141. kbNoKey = $0000; kbAltEsc = $0100; kbEsc = $011B;
  142. kbAltSpace = $0200; kbCtrlIns = $0400; kbShiftIns = $0500;
  143. kbCtrlDel = $0600; kbShiftDel = $0700; kbAltBack = $0800;
  144. kbAltShiftBack= $0900; kbBack = $0E08; kbCtrlBack = $0E7F;
  145. kbShiftTab = $0F00; kbTab = $0F09; kbAltQ = $1000;
  146. kbCtrlQ = $1011; kbAltW = $1100; kbCtrlW = $1117;
  147. kbAltE = $1200; kbCtrlE = $1205; kbAltR = $1300;
  148. kbCtrlR = $1312; kbAltT = $1400; kbCtrlT = $1414;
  149. kbAltY = $1500; kbCtrlY = $1519; kbAltU = $1600;
  150. kbCtrlU = $1615; kbAltI = $1700; kbCtrlI = $1709;
  151. kbAltO = $1800; kbCtrlO = $180F; kbAltP = $1900;
  152. kbCtrlP = $1910; kbAltLftBrack = $1A00; kbAltRgtBrack = $1B00;
  153. kbCtrlEnter = $1C0A; kbEnter = $1C0D; kbAltA = $1E00;
  154. kbCtrlA = $1E01; kbAltS = $1F00; kbCtrlS = $1F13;
  155. kbAltD = $2000; kbCtrlD = $2004; kbAltF = $2100;
  156. kbCtrlF = $2106; kbAltG = $2200; kbCtrlG = $2207;
  157. kbAltH = $2300; kbCtrlH = $2308; kbAltJ = $2400;
  158. kbCtrlJ = $240A; kbAltK = $2500; kbCtrlK = $250B;
  159. kbAltL = $2600; kbCtrlL = $260C; kbAltSemiCol = $2700;
  160. kbAltQuote = $2800; kbAltOpQuote = $2900; kbAltBkSlash = $2B00;
  161. kbAltZ = $2C00; kbCtrlZ = $2C1A; kbAltX = $2D00;
  162. kbCtrlX = $2D18; kbAltC = $2E00; kbCtrlC = $2E03;
  163. kbAltV = $2F00; kbCtrlV = $2F16; kbAltB = $3000;
  164. kbCtrlB = $3002; kbAltN = $3100; kbCtrlN = $310E;
  165. kbAltM = $3200; kbCtrlM = $320D; kbAltComma = $3300;
  166. kbAltPeriod = $3400; kbAltSlash = $3500; kbAltGreyAst = $3700;
  167. kbSpaceBar = $3920; kbF1 = $3B00; kbF2 = $3C00;
  168. kbF3 = $3D00; kbF4 = $3E00; kbF5 = $3F00;
  169. kbF6 = $4000; kbF7 = $4100; kbF8 = $4200;
  170. kbF9 = $4300; kbF10 = $4400; kbHome = $4700;
  171. kbUp = $4800; kbPgUp = $4900; kbGrayMinus = $4A2D;
  172. kbLeft = $4B00; kbCenter = $4C00; kbRight = $4D00;
  173. kbAltGrayPlus = $4E00; kbGrayPlus = $4E2B; kbEnd = $4F00;
  174. kbDown = $5000; kbPgDn = $5100; kbIns = $5200;
  175. kbDel = $5300; kbShiftF1 = $5400; kbShiftF2 = $5500;
  176. kbShiftF3 = $5600; kbShiftF4 = $5700; kbShiftF5 = $5800;
  177. kbShiftF6 = $5900; kbShiftF7 = $5A00; kbShiftF8 = $5B00;
  178. kbShiftF9 = $5C00; kbShiftF10 = $5D00; kbCtrlF1 = $5E00;
  179. kbCtrlF2 = $5F00; kbCtrlF3 = $6000; kbCtrlF4 = $6100;
  180. kbCtrlF5 = $6200; kbCtrlF6 = $6300; kbCtrlF7 = $6400;
  181. kbCtrlF8 = $6500; kbCtrlF9 = $6600; kbCtrlF10 = $6700;
  182. kbAltF1 = $6800; kbAltF2 = $6900; kbAltF3 = $6A00;
  183. kbAltF4 = $6B00; kbAltF5 = $6C00; kbAltF6 = $6D00;
  184. kbAltF7 = $6E00; kbAltF8 = $6F00; kbAltF9 = $7000;
  185. kbAltF10 = $7100; kbCtrlPrtSc = $7200; kbCtrlLeft = $7300;
  186. kbCtrlRight = $7400; kbCtrlEnd = $7500; kbCtrlPgDn = $7600;
  187. kbCtrlHome = $7700; kbAlt1 = $7800; kbAlt2 = $7900;
  188. kbAlt3 = $7A00; kbAlt4 = $7B00; kbAlt5 = $7C00;
  189. kbAlt6 = $7D00; kbAlt7 = $7E00; kbAlt8 = $7F00;
  190. kbAlt9 = $8000; kbAlt0 = $8100; kbAltMinus = $8200;
  191. kbAltEqual = $8300; kbCtrlPgUp = $8400; kbF11 = $8500;
  192. kbF12 = $8600; kbShiftF11 = $8700; kbShiftF12 = $8800;
  193. kbCtrlF11 = $8900; kbCtrlF12 = $8A00; kbAltF11 = $8B00;
  194. kbAltF12 = $8C00; kbCtrlUp = $8D00; kbCtrlMinus = $8E00;
  195. kbCtrlCenter = $8F00; kbCtrlGreyPlus= $9000; kbCtrlDown = $9100;
  196. kbCtrlTab = $9400; kbAltHome = $9700; kbAltUp = $9800;
  197. kbAltPgUp = $9900; kbAltLeft = $9B00; kbAltRight = $9D00;
  198. kbAltEnd = $9F00; kbAltDown = $A000; kbAltPgDn = $A100;
  199. kbAltIns = $A200; kbAltDel = $A300; kbAltTab = $A500;
  200. { ------------------------------- REMARK ------------------------------ }
  201. { New keys not initially defined by Borland in their unit interface. }
  202. { ------------------------------ END REMARK --- Leon de Boer, 15May96 - }
  203. kbFullStop = $342E; kbComma = $332C; kbBackSlash = $352F;
  204. kbApostrophe = $2827; kbSemiColon = $273B; kbEqual = $0D3D;
  205. kbGreaterThan = $343E; kbLessThan = $333C; kbQuestion = $353F;
  206. kbQuote = $2822; kbColon = $273A; kbPlus = $0D2B;
  207. kbPipe = $2B7C; kbSlash = $2B5C; kbExclaim = $0221;
  208. kbAt = $0340; kbNumber = $0423; kbPercent = $0625;
  209. kbCaret = $075E; kbAmpersand = $0826; kbAsterix = $092A;
  210. kbLeftBracket = $0A28; kbRightBracket= $0B29; kbApprox = $2960;
  211. kbTilde = $297E; kbDollar = $0524; kbMinus = $0C2D;
  212. kbUnderline = $0C5F; kbLeftSqBr = $1A5B; kbRightSqBr = $1B5D;
  213. kbLeftCurlyBr = $1A7B; kbRightCurlyBr= $1B7D;
  214. {---------------------------------------------------------------------------}
  215. { KEYBOARD STATE AND SHIFT MASKS }
  216. {---------------------------------------------------------------------------}
  217. CONST
  218. kbRightShift = $0001; { Right shift key }
  219. kbLeftShift = $0002; { Left shift key }
  220. kbCtrlShift = $0004; { Control key down }
  221. kbAltShift = $0008; { Alt key down }
  222. kbScrollState = $0010; { Scroll lock on }
  223. kbNumState = $0020; { Number lock on }
  224. kbCapsState = $0040; { Caps lock on }
  225. kbInsState = $0080; { Insert mode on }
  226. kbBothShifts = kbRightShift + kbLeftShift; { Right & Left shifts }
  227. {---------------------------------------------------------------------------}
  228. { MOUSE BUTTON STATE MASKS }
  229. {---------------------------------------------------------------------------}
  230. CONST
  231. mbLeftButton = $01; { Left mouse button }
  232. mbRightButton = $02; { Right mouse button }
  233. mbMiddleButton = $04; { Middle mouse button }
  234. {---------------------------------------------------------------------------}
  235. { SCREEN CRT MODE CONSTANTS }
  236. {---------------------------------------------------------------------------}
  237. CONST
  238. smBW80 = $0002; { Black and white }
  239. smCO80 = $0003; { Colour mode }
  240. smMono = $0007; { Monochrome mode }
  241. smFont8x8 = $0100; { 8x8 font mode }
  242. {***************************************************************************}
  243. { PUBLIC TYPE DEFINITIONS }
  244. {***************************************************************************}
  245. { ******************************* REMARK ****************************** }
  246. { The TEvent definition is completely compatable with all existing }
  247. { code but adds two new fields ID and Data into the message record }
  248. { which helps with WIN/NT and OS2 message processing. }
  249. { ****************************** END REMARK *** Leon de Boer, 11Sep97 * }
  250. {---------------------------------------------------------------------------}
  251. { EVENT RECORD DEFINITION }
  252. {---------------------------------------------------------------------------}
  253. TYPE
  254. TEvent = PACKED RECORD
  255. What: Word; { Event type }
  256. Case Word Of
  257. evNothing: (); { ** NO EVENT ** }
  258. evMouse: (
  259. Buttons: Byte; { Mouse buttons }
  260. Double: Boolean; { Double click state }
  261. Where: TPoint); { Mouse position }
  262. evKeyDown: ( { ** KEY EVENT ** }
  263. Case Integer Of
  264. 0: (KeyCode: Word); { Full key code }
  265. 1: (CharCode: Char; { Char code }
  266. ScanCode: Byte)); { Scan code }
  267. evMessage: ( { ** MESSAGE EVENT ** }
  268. Command: Word; { Message command }
  269. Id : Word; { Message id }
  270. Data : Real; { Message data }
  271. Case Word Of
  272. 0: (InfoPtr: Pointer); { Message pointer }
  273. 1: (InfoLong: Longint); { Message longint }
  274. 2: (InfoWord: Word); { Message word }
  275. 3: (InfoInt: Integer); { Message integer }
  276. 4: (InfoByte: Byte); { Message byte }
  277. 5: (InfoChar: Char)); { Message character }
  278. END;
  279. PEvent = ^TEvent;
  280. {---------------------------------------------------------------------------}
  281. { ERROR HANDLER FUNCTION DEFINITION }
  282. {---------------------------------------------------------------------------}
  283. TYPE
  284. TSysErrorFunc = FUNCTION (ErrorCode: Integer; Drive: Byte): Integer;
  285. {***************************************************************************}
  286. { INTERFACE ROUTINES }
  287. {***************************************************************************}
  288. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  289. { BUFFER MOVE ROUTINES }
  290. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  291. {-CStrLen------------------------------------------------------------
  292. Returns the length of string S, where S is a control string using tilde
  293. characters ('~') to designate shortcut characters. The tildes are
  294. excluded from the length of the string, as they will not appear on
  295. the screen. For example, given the string '~B~roccoli' as its
  296. parameter, CStrLen returns 8.
  297. 25May96 LdB
  298. ---------------------------------------------------------------------}
  299. FUNCTION CStrLen (Const S: String): Integer;
  300. {-MoveStr------------------------------------------------------------
  301. Moves a string into a buffer for use with a view's WriteBuf or WriteLine.
  302. Dest must be a TDrawBuffer (or an equivalent array of words). The
  303. characters in Str are moved into the low bytes of corresponding words
  304. in Dest. The high bytes of the words are set to Attr, or remain
  305. unchanged if Attr is zero.
  306. 25May96 LdB
  307. ---------------------------------------------------------------------}
  308. PROCEDURE MoveStr (Var Dest; Const Str: String; Attr: Byte);
  309. {-MoveCStr-----------------------------------------------------------
  310. The characters in Str are moved into the low bytes of corresponding
  311. words in Dest. The high bytes of the words are set to Lo(Attr) or
  312. Hi(Attr). Tilde characters (~) in the string toggle between the two
  313. attribute bytes passed in the Attr word.
  314. 25May96 LdB
  315. ---------------------------------------------------------------------}
  316. PROCEDURE MoveCStr (Var Dest; Const Str: String; Attrs: Word);
  317. {-MoveBuf------------------------------------------------------------
  318. Count bytes are moved from Source into the low bytes of corresponding
  319. words in Dest. The high bytes of the words in Dest are set to Attr,
  320. or remain unchanged if Attr is zero.
  321. 25May96 LdB
  322. ---------------------------------------------------------------------}
  323. PROCEDURE MoveBuf (Var Dest, Source; Attr: Byte; Count: Word);
  324. {-MoveChar------------------------------------------------------------
  325. Moves characters into a buffer for use with a view's WriteBuf or
  326. WriteLine. Dest must be a TDrawBuffer (or an equivalent array of words).
  327. The low bytes of the first Count words of Dest are set to C, or
  328. remain unchanged if Ord(C) is zero. The high bytes of the words are
  329. set to Attr, or remain unchanged if Attr is zero.
  330. 25May96 LdB
  331. ---------------------------------------------------------------------}
  332. PROCEDURE MoveChar (Var Dest; C: Char; Attr: Byte; Count: Word);
  333. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  334. { KEYBOARD SUPPORT ROUTINES }
  335. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  336. {-GetAltCode---------------------------------------------------------
  337. Returns the scancode corresponding to Alt+Ch key that is given.
  338. 25May96 LdB
  339. ---------------------------------------------------------------------}
  340. FUNCTION GetAltCode (Ch: Char): Word;
  341. {-GetCtrlCode--------------------------------------------------------
  342. Returns the scancode corresponding to Alt+Ch key that is given.
  343. 25May96 LdB
  344. ---------------------------------------------------------------------}
  345. FUNCTION GetCtrlCode (Ch: Char): Word;
  346. {-GetAltChar---------------------------------------------------------
  347. Returns the ascii character for the Alt+Key scancode that was given.
  348. 25May96 LdB
  349. ---------------------------------------------------------------------}
  350. FUNCTION GetAltChar (KeyCode: Word): Char;
  351. {-GetCtrlChar--------------------------------------------------------
  352. Returns the ascii character for the Ctrl+Key scancode that was given.
  353. 25May96 LdB
  354. ---------------------------------------------------------------------}
  355. FUNCTION GetCtrlChar (KeyCode: Word): Char;
  356. {-CtrlToArrow--------------------------------------------------------
  357. Converts a WordStar-compatible control key code to the corresponding
  358. cursor key code.
  359. 25May96 LdB
  360. ---------------------------------------------------------------------}
  361. FUNCTION CtrlToArrow (KeyCode: Word): Word;
  362. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  363. { KEYBOARD CONTROL ROUTINES }
  364. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  365. {-GetShiftState------------------------------------------------------
  366. Returns a byte containing the current Shift key state. The return
  367. value contains a combination of the kbXXXX constants for shift states.
  368. 08Jul96 LdB
  369. ---------------------------------------------------------------------}
  370. FUNCTION GetShiftState: Byte;
  371. {-GetKeyEvent--------------------------------------------------------
  372. Checks whether a keyboard event is available. If a key has been pressed,
  373. Event.What is set to evKeyDown and Event.KeyCode is set to the scan
  374. code of the key. Otherwise, Event.What is set to evNothing.
  375. 19May98 LdB
  376. ---------------------------------------------------------------------}
  377. PROCEDURE GetKeyEvent (Var Event: TEvent);
  378. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  379. { MOUSE CONTROL ROUTINES }
  380. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  381. {-ShowMouse----------------------------------------------------------
  382. Decrements the hide counter and if zero the mouse is shown on screen.
  383. 30Jun98 LdB
  384. ---------------------------------------------------------------------}
  385. PROCEDURE ShowMouse;
  386. {-HideMouse----------------------------------------------------------
  387. If mouse hide counter is zero it removes the cursor from the screen.
  388. The hide counter is then incremented by one count.
  389. 30Jun98 LdB
  390. ---------------------------------------------------------------------}
  391. PROCEDURE HideMouse;
  392. {-GetMouseEvent------------------------------------------------------
  393. Checks whether a mouse event is available. If a mouse event has occurred,
  394. Event.What is set to evMouseDown, evMouseUp, evMouseMove, or evMouseAuto
  395. and the button and double click variables are set appropriately.
  396. 06Jan97 LdB
  397. ---------------------------------------------------------------------}
  398. PROCEDURE GetMouseEvent (Var Event: TEvent);
  399. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  400. { EVENT HANDLER CONTROL ROUTINES }
  401. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  402. {-InitEvents---------------------------------------------------------
  403. Initializes the event manager, enabling the mouse handler routine and
  404. under DOS/DPMI shows the mouse on screen. It is called automatically
  405. by TApplication.Init.
  406. 02May98 LdB
  407. ---------------------------------------------------------------------}
  408. PROCEDURE InitEvents;
  409. {-DoneEvents---------------------------------------------------------
  410. Terminates event manager and disables the mouse and under DOS hides
  411. the mouse. It is called automatically by TApplication.Done.
  412. 02May98 LdB
  413. ---------------------------------------------------------------------}
  414. PROCEDURE DoneEvents;
  415. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  416. { VIDEO CONTROL ROUTINES }
  417. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  418. {-InitVideo---------------------------------------------------------
  419. Initializes the video manager, Saves the current screen mode in
  420. StartupMode, and switches to the mode indicated by ScreenMode.
  421. 19May98 LdB
  422. ---------------------------------------------------------------------}
  423. PROCEDURE InitVideo;
  424. {-DoneVideo---------------------------------------------------------
  425. Terminates the video manager by restoring the initial screen mode
  426. (given by StartupMode), clearing the screen, and restoring the cursor.
  427. Called automatically by TApplication.Done.
  428. 03Jan97 LdB
  429. ---------------------------------------------------------------------}
  430. PROCEDURE DoneVideo;
  431. {-ClearScreen--------------------------------------------------------
  432. Does nothing provided for compatability purposes only.
  433. 04Jan97 LdB
  434. ---------------------------------------------------------------------}
  435. PROCEDURE ClearScreen;
  436. {-SetVideoMode-------------------------------------------------------
  437. Does nothing provided for compatability purposes only.
  438. 04Jan97 LdB
  439. ---------------------------------------------------------------------}
  440. PROCEDURE SetVideoMode (Mode: Word);
  441. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  442. { ERROR CONTROL ROUTINES }
  443. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  444. {-InitSysError-------------------------------------------------------
  445. Error handling is not yet implemented so this simply sets
  446. SysErrActive=True (ie it lies) and exits.
  447. 20May98 LdB
  448. ---------------------------------------------------------------------}
  449. PROCEDURE InitSysError;
  450. {-DoneSysError-------------------------------------------------------
  451. Error handling is not yet implemented so this simply sets
  452. SysErrActive=False and exits.
  453. 20May98 LdB
  454. ---------------------------------------------------------------------}
  455. PROCEDURE DoneSysError;
  456. {-SystemError---------------------------------------------------------
  457. Error handling is not yet implemented so this simply drops through.
  458. 20May98 LdB
  459. ---------------------------------------------------------------------}
  460. FUNCTION SystemError (ErrorCode: Integer; Drive: Byte): Integer;
  461. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  462. { STRING FORMAT ROUTINES }
  463. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  464. {-PrintStr-----------------------------------------------------------
  465. Does nothing provided for compatability purposes only.
  466. 30Jun98 LdB
  467. ---------------------------------------------------------------------}
  468. PROCEDURE PrintStr (CONST S: String);
  469. {-FormatStr----------------------------------------------------------
  470. A string formatting routine that given a string that includes format
  471. specifiers and a list of parameters in Params, FormatStr produces a
  472. formatted output string in Result.
  473. 18Feb99 LdB
  474. ---------------------------------------------------------------------}
  475. PROCEDURE FormatStr (Var Result: String; CONST Format: String; Var Params);
  476. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  477. { >> NEW QUEUED EVENT HANDLER ROUTINES << }
  478. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  479. {-PutEventInQueue-----------------------------------------------------
  480. If there is room in the queue the event is placed in the next vacant
  481. position in the queue manager.
  482. 17Mar98 LdB
  483. ---------------------------------------------------------------------}
  484. FUNCTION PutEventInQueue (Var Event: TEvent): Boolean;
  485. {-NextQueuedEvent----------------------------------------------------
  486. If there are queued events the next event is loaded into event else
  487. evNothing is returned.
  488. 17Mar98 LdB
  489. ---------------------------------------------------------------------}
  490. PROCEDURE NextQueuedEvent(Var Event: TEvent);
  491. {***************************************************************************}
  492. { INITIALIZED PUBLIC VARIABLES }
  493. {***************************************************************************}
  494. {---------------------------------------------------------------------------}
  495. { INITIALIZED DOS/DPMI VARIABLES }
  496. {---------------------------------------------------------------------------}
  497. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  498. { ******************************* REMARK ****************************** }
  499. { In Hi-Res graphics modes where the usual mouse handler will not }
  500. { work these can be set so the user can provide his own hide, show }
  501. { and redraw on move routines, otherwise leave them set as nil. }
  502. { ****************************** END REMARK *** Leon de Boer, 20Jul98 * }
  503. TYPE DrawProc = PROCEDURE;
  504. CONST
  505. HideMouseProc: DrawProc = Nil; { Hide mouse procedure }
  506. ShowMouseProc: DrawProc = Nil; { Show mouse procedure }
  507. MouseMoveProc: DrawProc = Nil; { Mouse moved procedure }
  508. PROCEDURE HideMouseCursor;
  509. PROCEDURE ShowMouseCursor;
  510. {$ENDIF}
  511. {---------------------------------------------------------------------------}
  512. { INITIALIZED WIN/NT VARIABLES }
  513. {---------------------------------------------------------------------------}
  514. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  515. CONST
  516. AppWindow : HWnd = 0; { Application window }
  517. DefGfvFont : HFont = 0; { Default GFV font }
  518. DefFontWeight: Integer = fw_Normal; { Default font weight }
  519. DefFontStyle : String = 'Times New Roman'; { Default font style }
  520. {$ENDIF}
  521. {---------------------------------------------------------------------------}
  522. { INITIALIZED OS2 VARIABLES }
  523. {---------------------------------------------------------------------------}
  524. {$IFDEF OS_OS2} { OS2 CODE }
  525. CONST
  526. AppWindow : HWnd = 0; { Application window }
  527. Anchor : HAB = 0; { Anchor block }
  528. MsgQue : HMq = 0; { Message queue }
  529. DefGFVFont : LongInt = 0; { Default font style }
  530. DefPointer : HPointer = 0; { Default pointer }
  531. DefFontStyle: String = 'Times'; { Default font style }
  532. {$ENDIF}
  533. {---------------------------------------------------------------------------}
  534. { INITIALIZED DOS/DPMI/WIN/NT/OS2 VARIABLES }
  535. {---------------------------------------------------------------------------}
  536. CONST
  537. CheckSnow : Boolean = False; { Compatability only }
  538. MouseEvents : Boolean = False; { Mouse event state }
  539. MouseReverse : Boolean = False; { Mouse reversed }
  540. HiResScreen : Boolean = False; { Compatability only }
  541. CtrlBreakHit : Boolean = False; { Compatability only }
  542. SaveCtrlBreak: Boolean = False; { Compatability only }
  543. SysErrActive : Boolean = False; { Compatability only }
  544. FailSysErrors: Boolean = False; { Compatability only }
  545. ButtonCount : Byte = 0; { Mouse button count }
  546. DoubleDelay : Word = 8; { Double click delay }
  547. RepeatDelay : Word = 8; { Auto mouse delay }
  548. SysColorAttr : Word = $4E4F; { System colour attr }
  549. SysMonoAttr : Word = $7070; { System mono attr }
  550. StartupMode : Word = $FFFF; { Compatability only }
  551. CursorLines : Word = $FFFF; { Compatability only }
  552. ScreenBuffer : Pointer = Nil; { Compatability only }
  553. SaveInt09 : Pointer = Nil; { Compatability only }
  554. SysErrorFunc : TSysErrorFunc = SystemError; { System error ptr }
  555. {---------------------------------------------------------------------------}
  556. { >>> NEW INITIALIZED DOS/DPMI/WIN/NT/OS2 VARIABLES <<< }
  557. {---------------------------------------------------------------------------}
  558. CONST
  559. DefLineNum : Integer = 25; { Default line number }
  560. DefFontHeight : Integer = 0; { Default font height }
  561. SysFontWidth : Integer = 8; { System font width }
  562. SysFontHeight : Integer = 16; { System font height }
  563. {***************************************************************************}
  564. { UNINITIALIZED PUBLIC VARIABLES }
  565. {***************************************************************************}
  566. {---------------------------------------------------------------------------}
  567. { UNINITIALIZED DOS/DPMI/WIN/NT/OS2 VARIABLES }
  568. {---------------------------------------------------------------------------}
  569. VAR
  570. MouseIntFlag: Byte; { Mouse in int flag }
  571. MouseButtons: Byte; { Mouse button state }
  572. ScreenWidth : Byte; { Screen text width }
  573. ScreenHeight: Byte; { Screen text height }
  574. ScreenMode : Word; { Screen mode }
  575. MouseWhere : TPoint; { Mouse position }
  576. {<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>}
  577. IMPLEMENTATION
  578. {<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>}
  579. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  580. {$IFDEF PPC_FPC} { FPC DOS COMPILER }
  581. USES Go32; { Standard unit }
  582. {$ENDIF}
  583. {$ENDIF}
  584. {***************************************************************************}
  585. { PRIVATE INTERNAL CONSTANTS }
  586. {***************************************************************************}
  587. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  588. {---------------------------------------------------------------------------}
  589. { DOS/DPMI MOUSE INTERRUPT EVENT QUEUE SIZE }
  590. {---------------------------------------------------------------------------}
  591. CONST EventQSize = 16; { Default irq bufsize }
  592. {$ENDIF}
  593. {---------------------------------------------------------------------------}
  594. { DOS/DPMI/WIN/NT/OS2 NEW EVENT QUEUE MAX SIZE }
  595. {---------------------------------------------------------------------------}
  596. CONST QueueMax = 64; { Max new queue size }
  597. {***************************************************************************}
  598. { PRIVATE INTERNAL TYPES }
  599. {***************************************************************************}
  600. {$IFDEF OS_WINDOWS} { DOS/DPMI CODE }
  601. {---------------------------------------------------------------------------}
  602. { SYBIL2+ WIN/NT COMPILER TYPE FIX UPS }
  603. {---------------------------------------------------------------------------}
  604. {$IFDEF PPC_SPEED} { SYBIL2+ COMPILER }
  605. TYPE TLogFont = LogFont; { Type fix up }
  606. TYPE TMsg = Msg; { Type fix up }
  607. TYPE TTextMetric = TextMetric; { Type fix up }
  608. {$ENDIF}
  609. {$ENDIF}
  610. {***************************************************************************}
  611. { PRIVATE INTERNAL INITIALIZED VARIABLES }
  612. {***************************************************************************}
  613. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  614. {---------------------------------------------------------------------------}
  615. { DOS/DPMI INITIALIZED VARIABLES }
  616. {---------------------------------------------------------------------------}
  617. {$IFDEF GO32V2} { GO32V2 needs these }
  618. CONST
  619. RealSeg: Word = 0; { Real mode segment }
  620. RealOfs: Word = 0; { Real mode offset }
  621. MouseCallback: Pointer = Nil; { Mouse call back ptr }
  622. {$ENDIF}
  623. {$ENDIF}
  624. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  625. {---------------------------------------------------------------------------}
  626. { WIN/NT TABLE OF ALT + ASCII CODES FROM VIRTUAL CODES }
  627. {---------------------------------------------------------------------------}
  628. CONST AltVirtualToAscii: Array [0..127] Of Word =
  629. ($00, $00, $00, $00, $00, $00, $00, $00,
  630. kbAltBack, kbAltTab, $00, $00, $00, kbEnter, $00, $00,
  631. {10H} $00, $00, $00, $00, $00, $00, $00, $00,
  632. $00, $00, $00, kbEsc, $00, $00, $00, $00,
  633. {20H} kbAltSpace, kbAltPgUp, kbAltPgDn, kbAltEnd, kbAltHome,
  634. kbAltLeft, kbAltUp, kbAltRight,
  635. kbAltDown, $00, $00, $00, $00, kbAltIns, kbAltDel, $00,
  636. {30H} kbAlt0, kbAlt1, kbAlt2, kbAlt3, kbAlt4, kbAlt5, kbAlt6, kbAlt7,
  637. kbAlt8, kbAlt9, $00, $00, $00, $00, $00, $00,
  638. {40H} $00, kbAltA, kbAltB, kbAltC, kbAltD, kbAltE, kbAltF, kbAltG,
  639. kbAltH, kbAltI, kbAltJ, kbAltK, kbAltL, kbAltM, kbAltN, kbAltO,
  640. {50H} kbAltP, kbAltQ, kbAltR, kbAltS, kbAltT, kbAltU, kbAltV, kbAltW,
  641. kbAltX, kbAltY, kbAltZ, $00, $00, $00, $00, $00,
  642. {60H} $00, $00, $00, $00, $00, $00, $00, $00,
  643. $00, $00, $372A, $4E2B, $00, $4A2D, $00, $352F,
  644. {70H} kbAltF1, kbAltF2, kbAltF3, kbAltF4, kbAltF5, kbAltF6, kbAltF7, kbAltF8,
  645. kbAltF9, kbAltF10, $00, $00, $00, $00, $00, $00);
  646. {---------------------------------------------------------------------------}
  647. { WIN/NT TABLE OF WINDOWS ASCII TO INTERNATIONAL ASCII }
  648. {---------------------------------------------------------------------------}
  649. CONST WinAsciiToIntAscii: Array [128..255] Of Byte = (
  650. {80H} $00, $00, $00, $00, $00, $00, $00, $00,
  651. $00, $00, $00, $00, $00, $00, $00, $00,
  652. {90H} $00, $00, $00, $00, $00, $00, $00, $00,
  653. $00, $00, $00, $00, $00, $00, $00, $00,
  654. {A0H} $00, $AD, $BD, $9C, $CF, $BE, $B3, $F5,
  655. $00, $B8, $A6, $AE, $AA, $B0, $A9, $00,
  656. {B0H} $F8, $F1, $FD, $00, $EF, $E6, $F4, $00,
  657. $3C, $3E, $A7, $AF, $AC, $AB, $F3, $A8,
  658. {C0H} $B7, $B5, $B6, $C7, $8E, $8F, $92, $80,
  659. $D4, $90, $D2, $D3, $DE, $D6, $D7, $D8,
  660. {D0H} $D1, $A5, $E3, $E0, $E2, $E5, $99, $00,
  661. $9D, $EB, $E9, $EA, $9A, $ED, $E7, $E1,
  662. {E0H} $85, $A0, $83, $C6, $84, $86, $91, $87,
  663. $8A, $82, $88, $89, $8D, $A1, $8C, $8B,
  664. {F0H} $D0, $A4, $95, $A2, $93, $E4, $94, $F6,
  665. $9B, $97, $A3, $96, $81, $EC, $E8, $98);
  666. {$ENDIF}
  667. {---------------------------------------------------------------------------}
  668. { DOS/DPMI/WIN/NT/OS2 ALT KEY SCANCODES FROM KEYS (0-127) }
  669. {---------------------------------------------------------------------------}
  670. CONST AltCodes: Array [0..127] Of Byte = (
  671. $00, $00, $00, $00, $00, $00, $00, $00, { $00 - $07 }
  672. $00, $00, $00, $00, $00, $00, $00, $00, { $08 - $0F }
  673. $00, $00, $00, $00, $00, $00, $00, $00, { $10 - $17 }
  674. $00, $00, $00, $00, $00, $00, $00, $00, { $18 - $1F }
  675. $00, $00, $00, $00, $00, $00, $00, $00, { $20 - $27 }
  676. $00, $00, $00, $00, $00, $82, $00, $00, { $28 - $2F }
  677. $81, $78, $79, $7A, $7B, $7C, $7D, $7E, { $30 - $37 }
  678. $7F, $80, $00, $00, $00, $83, $00, $00, { $38 - $3F }
  679. $00, $1E, $30, $2E, $20, $12, $21, $22, { $40 - $47 }
  680. $23, $17, $24, $25, $26, $32, $31, $18, { $48 - $4F }
  681. $19, $10, $13, $1F, $14, $16, $2F, $11, { $50 - $57 }
  682. $2D, $15, $2C, $00, $00, $00, $00, $00, { $58 - $5F }
  683. $00, $00, $00, $00, $00, $00, $00, $00, { $60 - $67 }
  684. $00, $00, $00, $00, $00, $00, $00, $00, { $68 - $6F }
  685. $00, $00, $00, $00, $00, $00, $00, $00, { $70 - $77 }
  686. $00, $00, $00, $00, $00, $00, $00, $00); { $78 - $7F }
  687. {***************************************************************************}
  688. { PRIVATE INTERNAL INITIALIZED VARIABLES }
  689. {***************************************************************************}
  690. {---------------------------------------------------------------------------}
  691. { NEW CONTROL VARIABLES }
  692. {---------------------------------------------------------------------------}
  693. CONST
  694. HideCount : Integer = 0; { Cursor hide count }
  695. QueueCount: Word = 0; { Queued message count }
  696. QueueHead : Word = 0; { Queue head pointer }
  697. QueueTail : Word = 0; { Queue tail pointer }
  698. {***************************************************************************}
  699. { PRIVATE INTERNAL UNINITIALIZED VARIABLES }
  700. {***************************************************************************}
  701. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  702. {---------------------------------------------------------------------------}
  703. { UNINITIALIZED DOS/DPMI VARIABLES }
  704. {---------------------------------------------------------------------------}
  705. VAR
  706. LastDouble : Boolean; { Last double buttons }
  707. LastButtons: Byte; { Last button state }
  708. DownButtons: Byte; { Last down buttons }
  709. EventCount : Word; { Events in queue }
  710. AutoDelay : Word; { Delay time count }
  711. DownTicks : Word; { Down key tick count }
  712. AutoTicks : Word; { Held key tick count }
  713. LastWhereX : Word; { Last x position }
  714. LastWhereY : Word; { Last y position }
  715. DownWhereX : Word; { Last x position }
  716. DownWhereY : Word; { Last y position }
  717. EventQHead : Pointer; { Head of queue }
  718. EventQTail : Pointer; { Tail of queue }
  719. EventQueue : Array [0..EventQSize - 1] Of TEvent; { Event queue }
  720. EventQLast : RECORD END; { Simple end marker }
  721. {---------------------------------------------------------------------------}
  722. { ABSOLUTE PRIVATE DOS/DPMI ADDRESS VARIABLES }
  723. {---------------------------------------------------------------------------}
  724. VAR
  725. {$IFNDEF GO32V1}
  726. ShiftState: Byte Absolute $40:$17; { Shift state mask }
  727. Ticks: Word Absolute $40:$6C; { DOS tick counter }
  728. {$ENDIF}
  729. {$IFDEF GO32V2} { GO32V2 registers }
  730. ActionRegs: TRealRegs; { Real mode registers }
  731. {$ENDIF}
  732. {$ENDIF}
  733. {---------------------------------------------------------------------------}
  734. { UNINITIALIZED DOS/DPMI/WIN/NT/OS2 VARIABLES }
  735. {---------------------------------------------------------------------------}
  736. VAR
  737. SaveExit: Pointer; { Saved exit pointer }
  738. Queue : Array [0..QueueMax-1] Of TEvent; { New message queue }
  739. {***************************************************************************}
  740. { PRIVATE INTERNAL ROUTINES }
  741. {***************************************************************************}
  742. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  743. { DOS/DPMI ONLY PRIVATE INTERNAL ROUTINES }
  744. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  745. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  746. {$IFDEF GO32V2} { GO32V2 CODE }
  747. {---------------------------------------------------------------------------}
  748. { MouseTrap -> Platforms GO32V2 - FPC COMPILER Updated 10Sep98 LdB }
  749. {---------------------------------------------------------------------------}
  750. PROCEDURE Mouse_Trap; FAR; ASSEMBLER;
  751. ASM
  752. PUSH %ES; { Save ES register }
  753. PUSH %DS; { Save DS register }
  754. PUSHL %EDI; { Save register }
  755. PUSHL %ESI; { Save register }
  756. ;{ caution : ds is not the selector for our data !! }
  757. PUSH %ES; { Push data seg }
  758. POP %DS; { Load data seg }
  759. PUSHL %EDI; { Actionregs address }
  760. MOVL MOUSECALLBACK, %EAX; { Fetch callback addr }
  761. CMPL $0, %EAX; { Check for nil ptr }
  762. JS .L_NoCallBack; { Ignore if nil }
  763. POPL %EAX; { %EAX = @actionregs }
  764. MOVL (%EAX), %EDI; { EDI from actionregs }
  765. MOVL 4(%EAX), %ESI; { ESI from actionregs }
  766. MOVL 16(%EAX), %EBX; { EBX from actionregs }
  767. MOVL 20(%EAX), %EDX; { EDX from actionregs }
  768. MOVL 24(%EAX), %ECX; { ECX from actionregs }
  769. MOVL 28(%EAX), %EAX; { EAX from actionregs }
  770. CALL *MOUSECALLBACK; { Call callback proc }
  771. .L_NoCallBack:
  772. POPL %ESI; { Recover register }
  773. POPL %EDI; { Recover register }
  774. POP %DS; { Restore DS register }
  775. POP %ES; { Restore ES register }
  776. MOVL (%ESI), %EAX;
  777. MOVL %EAX, %ES:42(%EDI); { Set as return addr }
  778. ADDW $4, %ES:46(%EDI); { adjust stack }
  779. IRET; { Interrupt return }
  780. END;
  781. {$ENDIF}
  782. {$IFDEF PPC_FPC} { FPC COMPILER CODE }
  783. {---------------------------------------------------------------------------}
  784. { Mouse_Action -> Platforms DPMI - FPC COMPILER Updated 10Sep98 LdB }
  785. {---------------------------------------------------------------------------}
  786. PROCEDURE Mouse_Action (Mask : Integer; P : Pointer);
  787. VAR Error: Word; ErrStr: String; {$IFDEF GO32V2} Rg: TRealRegs; {$ENDIF}
  788. BEGIN
  789. {$IFDEF GO32V1} { GO32V1 CODE }
  790. ErrStr := 'GO32V1 mouse handler set failed !!'; { Set error string }
  791. ASM
  792. MOVL $0xFF, %EAX; { GO32v1 special id }
  793. MOVL P, %ECX; { Fuction to chain }
  794. MOVL $0x20, %EBX; { Event queue size > 0 }
  795. MOVL $0x12345678, %EDX; { Test for version ? }
  796. INT $0x33; { Call special wrapper }
  797. CMPW $0xFF0, %AX; { AX=$FF0 if success }
  798. JNZ .L_GO32V1Err;
  799. MOVW $0, %AX; { Zero register }
  800. JMP .LGO32V1Ok; { Now jump over }
  801. .L_GO32V1Err:
  802. MOVW $0xFFFF, %AX; { -1 to register }
  803. .L_GO32V1Ok:
  804. MOVW %AX, Error; { Set error result }
  805. END;
  806. {$ENDIF}
  807. {$IFDEF GO32V2} { GO32V2 CODE }
  808. Error := 0; { Preset no error }
  809. ErrStr := 'GO32V2 mouse handler set failed !!'; { Set error string }
  810. If (P <> MouseCallBack) Then Begin { Check func different }
  811. If (RealSeg <> 0) Then Begin { Remove old calback }
  812. Rg.AX := 12; { Function id }
  813. Rg.CX := 0; { Zero mask register }
  814. Rg.ES := 0; { Zero proc seg }
  815. Rg.DX := 0; { Zero proc ofs }
  816. RealIntr($33, Rg); { Stop INT 33 callback }
  817. ASM
  818. MOVW $0x304, %AX; { Set function id }
  819. MOVW REALSEG, %CX; { Bridged real seg }
  820. MOVW REALOFS, %DX; { Bridged real ofs }
  821. INT $0x31; { Release bridge }
  822. END;
  823. End;
  824. MouseCallback := P; { Set call back addr }
  825. If (P <> Nil) Then Begin { Check non nil proc }
  826. ASM
  827. LEAL ACTIONREGS, %EDI; { Addr of actionregs }
  828. LEAL MOUSE_TRAP, %ESI; { Procedure address }
  829. PUSH %DS; { Save DS segment }
  830. PUSH %ES; { Save ES segment }
  831. PUSH %DS;
  832. POP %ES; { ES now has dataseg }
  833. PUSH %CS;
  834. POP %DS; { DS now has codeseg }
  835. MOVW $0x303, %AX; { Function id }
  836. INT $0x31; { Call DPMI bridge }
  837. POP %ES; { Restore ES segment }
  838. POP %DS; { Restore DS segment }
  839. MOVW %CX, REALSEG; { Transfer real seg }
  840. MOVW %DX, REALOFS; { Transfer real ofs }
  841. MOVW $0, %AX; { Preset zero error }
  842. JNC .L_call_ok; { Branch if ok }
  843. MOVW $0xFFFF, %AX; { Force a -1 error }
  844. .L_call_ok:
  845. MOVW %AX, ERROR; { Return error state }
  846. END;
  847. Rg.CX := Mask; { Set mask register }
  848. End Else Begin
  849. Rg.EDI := 0; { Zero proc register }
  850. Rg.CX := 0; { Zero mask register }
  851. End;
  852. If (Error = 0) Then Begin { If no error }
  853. Rg.AX := 12; { Set function id }
  854. Rg.ES := RealSeg; { Real mode segment }
  855. Rg.DX := RealOfs; { Real mode offset }
  856. RealIntr($33, Rg); { Set interrupt 33 }
  857. End Else Begin
  858. RealSeg := 0; { Zero real mode seg }
  859. RealOfs := 0; { Zero real mode ofs }
  860. End;
  861. End;
  862. {$ENDIF}
  863. If (Error <> 0) Then Begin { Error encountered }
  864. WriteLn(ErrStr); { Write error }
  865. ReadLn; { Wait for user to see }
  866. End;
  867. END;
  868. {$ENDIF}
  869. {---------------------------------------------------------------------------}
  870. { MouseInt -> Platforms DOS/DPMI - Updated 30Jun98 LdB }
  871. {---------------------------------------------------------------------------}
  872. PROCEDURE MouseInt; FAR; ASSEMBLER;
  873. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  874. ASM
  875. MOV SI, SEG @DATA; { Fetch data segment }
  876. MOV DS, SI; { Fix data segment }
  877. MOV SI, CX; { Transfer x position }
  878. MOV MouseButtons, BL; { Update mouse buttons }
  879. MOV MouseWhere.X, SI; { Update x position }
  880. MOV MouseWhere.Y, DX; { Update y position }
  881. CMP EventCount, EventQSize; { Check if queue full }
  882. JZ @@QueueFull; { Queue is full exit }
  883. MOV ES, Seg0040; { Fetch DOS segment }
  884. MOV AX, ES:Ticks; { Fetch dos tick count }
  885. MOV DI, WORD PTR EventQTail; { Address of tail }
  886. PUSH DS; { Push to stack }
  887. POP ES; { ES to data segment }
  888. CLD; { Store forward }
  889. STOSW; { Store tick count }
  890. XCHG AX, BX; { Transfer register }
  891. STOSW; { Store button state }
  892. XCHG AX, SI; { Transfer register }
  893. STOSW; { Store x position }
  894. XCHG AX, DX; { Transfer register }
  895. STOSW; { Store y position }
  896. CMP DI, OFFSET EventQLast; { Roll if at queue end }
  897. JNE @@NoRollNeeded; { Not at queue end }
  898. MOV DI, OFFSET EventQueue; { Roll back to start }
  899. @@NoRollNeeded:
  900. MOV WORD PTR EventQTail, DI; { Update queue tail }
  901. INC EventCount; { One message added }
  902. @@QueueFull:
  903. MOV MouseIntFlag, 1; { Set interrupt flag }
  904. MOV SI, WORD PTR MouseMoveProc; { Low address word }
  905. OR SI, WORD PTR MouseMoveProc+2; { "OR" high word }
  906. JZ @@Exit; { No move call so exit }
  907. DB $66; PUSH AX; { Store EAX }
  908. DB $66; PUSH BX; { Store EBX }
  909. DB $66; PUSH CX; { Store ECX }
  910. DB $66; PUSH DX; { Store EDX }
  911. DB $66; PUSH SI; { Store ESI }
  912. DB $66; PUSH DI; { Store EDI }
  913. DB $66; PUSH BP; { Store EBP }
  914. PUSH ES; { Store ES }
  915. PUSH BP; { Standard BP push }
  916. MOV BP, SP; { Transfer stack ptr }
  917. CALL MouseMoveProc; { Standard procedure }
  918. POP BP; { Standard BP recover }
  919. POP ES; { Recover ES }
  920. DB $66; POP BP; { Recover EBP }
  921. DB $66; POP DI; { Recover EDI }
  922. DB $66; POP SI; { Recover ESI }
  923. DB $66; POP DX; { Recover EDX }
  924. DB $66; POP CX; { Recover ECX }
  925. DB $66; POP BX; { Recover EBX }
  926. DB $66; POP AX; { Recover EAX }
  927. @@Exit:
  928. END;
  929. {$ENDIF}
  930. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  931. ASM
  932. MOVW %CX, %SI; { Transfer x position }
  933. MOVB %BL, MOUSEBUTTONS; { Update mouse buttons }
  934. MOVW %SI, MOUSEWHERE; { Update x position }
  935. MOVW %DX, MOUSEWHERE+2; { Update y position }
  936. CMPW $16, EVENTCOUNT; { Check if queue full }
  937. JZ .L_QueueFull; { Queue is full exit }
  938. PUSH %ES; { Save segment }
  939. MOVW $0x40, %AX; { Fetch DOS segment }
  940. MOVW %AX, %ES; { Transfer to segment }
  941. MOVL $0x6C, %EDI; { Address of ticks }
  942. MOVW %ES:(%EDI), %AX; { Fetch dos tick count }
  943. POP %ES; { Recover segment }
  944. MOVL EVENTQTAIL, %EDI; { Queue tail address }
  945. CLD; { Store forward }
  946. STOSW; { Store tick count }
  947. XCHGW %BX, %AX; { Transfer register }
  948. STOSW; { Store button state }
  949. XCHGW %SI, %AX; { Transfer register }
  950. STOSW; { Store x position }
  951. XCHGW %DX, %AX; { Transfer register }
  952. STOSW; { Store y position }
  953. LEAL EVENTQLAST, %EAX; { Roll point address }
  954. CMPL %EAX, %EDI; { Roll if at queue end }
  955. JNE .L_NoRollNeeded; { Not at queue end }
  956. LEAL EVENTQUEUE, %EDI; { Roll back to start }
  957. .L_NoRollNeeded:
  958. MOVL %EDI, EVENTQTAIL; { Update queue tail }
  959. INCW EVENTCOUNT; { One message added }
  960. .L_QueueFull:
  961. MOVB $1, MOUSEINTFLAG; { Set interrupt flag }
  962. MOVL MOUSEMOVEPROC, %EAX; { Load proc address }
  963. CMPL $0, %EAX; { Check for nil ptr }
  964. JZ .L_Exit; { No move call so exit }
  965. PUSHL %EAX; { Store EAX }
  966. PUSHL %EBX; { Store EBX }
  967. PUSHL %ECX; { Store ECX }
  968. PUSHL %EDX; { Store EDX }
  969. PUSHL %ESI; { Store ESI }
  970. PUSHL %EDI; { Store EDI }
  971. PUSHL %EBP; { Store EBP }
  972. PUSH %ES; { Store ES }
  973. CALL %EAX; { Standard procedure }
  974. POP %ES; { Recover ES }
  975. POPL %EBP; { Recover EBP }
  976. POPL %EDI; { Recover EDI }
  977. POPL %ESI; { Recover ESI }
  978. POPL %EDX; { Recover EDX }
  979. POPL %ECX; { Recover ECX }
  980. POPL %EBX; { Recover EBX }
  981. POPL %EAX; { Recover EAX }
  982. .L_Exit:
  983. END;
  984. {$ENDIF}
  985. {---------------------------------------------------------------------------}
  986. { HideMouseCursor -> Platforms DOS/DPMI - Updated 10Sep98 LdB }
  987. {---------------------------------------------------------------------------}
  988. PROCEDURE HideMouseCursor; ASSEMBLER;
  989. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  990. ASM
  991. CMP MouseEvents, 0; { Check mouse system }
  992. JZ @@Exit; { Branch if not active }
  993. MOV AX, WORD PTR [HideMouseProc]; { Fetch offset of addr }
  994. OR AX, WORD PTR [HideMouseProc+2]; { Check for nil ptr }
  995. JZ @@UseMouseInt; { Branch if nil }
  996. CALL FAR PTR [HideMouseProc]; { Call hide mouse }
  997. JMP @@Exit; { Now exit }
  998. @@UseMouseInt:
  999. MOV AX, $2; { Load function id }
  1000. PUSH BP; { Safety!! save reg }
  1001. INT $33; { Hide the mouse }
  1002. POP BP; { Restore register }
  1003. @@Exit:
  1004. END;
  1005. {$ENDIF}
  1006. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1007. ASM
  1008. CMPB $0, MouseEvents; { Check mouse system }
  1009. JZ .L_Exit; { Branch if not active }
  1010. MOVL HideMouseProc, %EAX; { Fetch address }
  1011. ORL %EAX, %EAX; { Check for nil ptr }
  1012. JZ .L_UseMouseInt; { Branch if nil }
  1013. CALL HideMouseProc; { Call show mouse }
  1014. JMP .L_Exit; { Now exit }
  1015. .L_UseMouseInt:
  1016. MOVW $2, %AX; { Load function id }
  1017. PUSHL %EBP; { Save regigister }
  1018. INT $0x33; { Hide the mouse }
  1019. POPL %EBP; { Restore register }
  1020. .L_Exit:
  1021. END;
  1022. {$ENDIF}
  1023. {---------------------------------------------------------------------------}
  1024. { ShowMouseCursor -> Platforms DOS/DPMI - Updated 10Sep98 LdB }
  1025. {---------------------------------------------------------------------------}
  1026. PROCEDURE ShowMouseCursor; ASSEMBLER;
  1027. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1028. ASM
  1029. CMP MouseEvents, 0; { Check mouse system }
  1030. JZ @@Exit; { Branch if not active }
  1031. MOV AX, WORD PTR [ShowMouseProc]; { Fetch offset of addr }
  1032. OR AX, WORD PTR [ShowMouseProc+2]; { Check for nil ptr }
  1033. JZ @@UseMouseInt; { Branch if nil }
  1034. CALL FAR PTR [ShowMouseProc]; { Call show mouse }
  1035. JMP @@Exit; { Now exit }
  1036. @@UseMouseInt:
  1037. MOV AX, $1; { Load function id }
  1038. PUSH BP; { Safety!! save reg }
  1039. INT $33; { Show the mouse }
  1040. POP BP; { Restore register }
  1041. @@Exit:
  1042. END;
  1043. {$ENDIF}
  1044. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1045. ASM
  1046. CMPB $0, MouseEvents; { Check mouse system }
  1047. JZ .L_Exit; { Branch if not active }
  1048. MOVL ShowMouseProc, %EAX; { Fetch address }
  1049. ORL %EAX, %EAX; { Check for nil ptr }
  1050. JZ .L_UseMouseInt; { Branch if nil }
  1051. CALL ShowMouseProc; { Call show mouse }
  1052. JMP .L_Exit; { Now exit }
  1053. .L_UseMouseInt:
  1054. MOVW $1, %AX; { Load function id }
  1055. PUSHL %EBP; { Save regigister }
  1056. INT $0x33; { Hide the mouse }
  1057. POPL %EBP; { Restore register }
  1058. .L_Exit:
  1059. END;
  1060. {$ENDIF}
  1061. {---------------------------------------------------------------------------}
  1062. { HookMouse -> Platforms DOS/DPMI - Updated 27Aug98 LdB }
  1063. {---------------------------------------------------------------------------}
  1064. PROCEDURE HookMouse;
  1065. BEGIN
  1066. {$IFDEF ASM_BP} { BP COMPTABABLE ASM }
  1067. ASM
  1068. MOV AX, $000C; { Set user interrupt }
  1069. MOV CX, $FFFF; { For all event masks }
  1070. MOV DX, OFFSET CS:MouseInt; { Mouse int is hook }
  1071. PUSH CS; { Push code segment }
  1072. POP ES; { ES:DX -> MouseInt }
  1073. PUSH BP; { Safety!! save reg }
  1074. INT $33; { Hook the routine }
  1075. POP BP; { Restore register }
  1076. END;
  1077. {$ENDIF}
  1078. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1079. {$IFDEF GO32V2} { GO32V2 CODE }
  1080. Lock_Code(Pointer(@Mouse_Trap), 400); { Lock trap code }
  1081. Lock_Data(ActionRegs, SizeOf(ActionRegs)); { Lock registers }
  1082. {$ENDIF}
  1083. Mouse_Action(-1, @MouseInt); { Set masks/interrupt }
  1084. {$ENDIF}
  1085. END;
  1086. {---------------------------------------------------------------------------}
  1087. { UnHookMouse -> Platforms DOS/DPMI - Updated 27Aug98 LdB }
  1088. {---------------------------------------------------------------------------}
  1089. PROCEDURE UnHookMouse;
  1090. BEGIN
  1091. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1092. ASM
  1093. MOV AX, $000C; { Set user interrupt }
  1094. XOR CX, CX; { Clear all masks }
  1095. XOR DX, DX; { Clear register }
  1096. MOV ES, CX; { ES:DX -> Nil }
  1097. PUSH BP; { Safety!! save reg }
  1098. INT $33; { Release mouse hook }
  1099. POP BP; { Restore register }
  1100. END;
  1101. {$ENDIF}
  1102. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1103. Mouse_Action(0, Nil); { Clear mask/interrupt }
  1104. {$IFDEF GO32V2} { GO32V2 CODE }
  1105. Unlock_Code(Pointer(@Mouse_Trap), 400); { Release trap code }
  1106. Unlock_Data(ActionRegs, SizeOf(TRealRegs)); { Release registers }
  1107. {$ENDIF}
  1108. {$ENDIF}
  1109. END;
  1110. {---------------------------------------------------------------------------}
  1111. { GetMousePosition -> Platforms DOS/DPMI - Updated 19May98 LdB }
  1112. {---------------------------------------------------------------------------}
  1113. PROCEDURE GetMousePosition (Var X, Y: Integer); ASSEMBLER;
  1114. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1115. ASM
  1116. MOV AX, $3; { Set function id }
  1117. PUSH BP; { Safety!! save reg }
  1118. INT $33; { Get button data }
  1119. POP BP; { Restore register }
  1120. LES DI, X; { Adress of x }
  1121. MOV ES:[DI], CX; { Return x position }
  1122. LES DI, Y; { Adress of y }
  1123. MOV ES:[DI], DX; { Return y position }
  1124. END;
  1125. {$ENDIF}
  1126. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1127. ASM
  1128. MOVW $3, %AX; { Set function id }
  1129. PUSHL %EBP; { Save register }
  1130. INT $0x33; { Get button data }
  1131. POPL %EBP; { Restore register }
  1132. MOVL X, %EDI; { Adress of x }
  1133. MOVW %CX, (%EDI); { Return x position }
  1134. MOVL Y, %EDI; { Adress of y }
  1135. MOVW %DX, (%EDI); { Return y position }
  1136. END;
  1137. {$ENDIF}
  1138. {$ENDIF}
  1139. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1140. { DOS/DPMI/WIN/NT/OS2 PRIVATE INTERNAL ROUTINES }
  1141. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1142. {---------------------------------------------------------------------------}
  1143. { ExitDrivers -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 08Jun98 LdB }
  1144. {---------------------------------------------------------------------------}
  1145. PROCEDURE ExitDrivers; FAR;
  1146. BEGIN
  1147. DoneSysError; { Relase error trap }
  1148. DoneEvents; { Close event driver }
  1149. ExitProc := SaveExit; { Restore old exit }
  1150. END;
  1151. {---------------------------------------------------------------------------}
  1152. { DetectVideo -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 19May98 LdB }
  1153. {---------------------------------------------------------------------------}
  1154. PROCEDURE DetectVideo;
  1155. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1156. ASSEMBLER;
  1157. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1158. ASM
  1159. MOV AH, $0F; { Set function id }
  1160. PUSH BP; { Safety!! save reg }
  1161. INT $10; { Get current crt mode }
  1162. POP BP; { Restore register }
  1163. PUSH AX; { Hold result }
  1164. MOV AX, $1130; { Set function id }
  1165. MOV BH, 0; { Zero register }
  1166. MOV DL, 0; { Zero register }
  1167. PUSH BP; { Safety!! save reg }
  1168. INT $10; { Get ext-video mode }
  1169. POP BP; { Restore register }
  1170. POP AX; { Recover held value }
  1171. MOV DH, AH; { Transfer high mode }
  1172. CMP DL, 25; { Check screen ht }
  1173. SBB AH, AH; { Subtract borrow }
  1174. INC AH; { Make #1 if in high }
  1175. CMP AL, smMono; { Is screen mono }
  1176. JZ @@Exit1; { Exit of mono }
  1177. CMP AL, smBW80; { Is screen B&W }
  1178. JZ @@Exit1; { Exit if B&W }
  1179. MOV AX, smCO80; { Else set to colour }
  1180. @@Exit1:
  1181. MOV ScreenMode, AX; { Hold screen mode }
  1182. END;
  1183. {$ENDIF}
  1184. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1185. ASM
  1186. MOVB $0x0F, %AH; { Set function id }
  1187. PUSHL %EBP; { Save register }
  1188. INT $0x10; { Get current crt mode }
  1189. POPL %EBP; { Restore register }
  1190. PUSHL %EAX; { Hold result }
  1191. MOVW $0x1130, %AX; { Set function id }
  1192. MOVB $0, %BH; { Zero register }
  1193. MOVB $0, %DL; { Zero register }
  1194. PUSHL %EBP; { Safety!! save reg }
  1195. INT $0x10; { Get ext-video mode }
  1196. POPL %EBP; { Restore register }
  1197. POPL %EAX; { Recover held value }
  1198. MOVB %AH, %DH; { Transfer high mode }
  1199. CMPB $25, %DL; { Check screen ht }
  1200. SBB %AH, %AH; { Subtract borrow }
  1201. INCB %AH; { Make #1 if in high }
  1202. CMPB $07, %AL; { Is screen mono }
  1203. JZ .L_Exit1; { Exit of mono }
  1204. CMPB $02, %AL; { Is screen B&W }
  1205. JZ .L_Exit1; { Exit if B&W }
  1206. MOVW $03, %AX; { Else set to colour }
  1207. .L_Exit1:
  1208. MOVW %AX, SCREENMODE; { Hold screen mode }
  1209. END;
  1210. {$ENDIF}
  1211. {$ENDIF}
  1212. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1213. VAR Dc: HDC;
  1214. BEGIN
  1215. Dc := GetDc(0); { Get screen context }
  1216. If ((GetDeviceCaps(Dc, BitsPixel) > 1) OR { Colour capacity }
  1217. (GetDeviceCaps(Dc, Planes) > 1)) Then { Colour capacity }
  1218. ScreenMode := smCO80 Else ScreenMode := smMono; { Screen mode }
  1219. ReleaseDc(0, Dc); { Release context }
  1220. END;
  1221. {$ENDIF}
  1222. {$IFDEF OS_OS2} { OS2 CODE }
  1223. VAR Ps: Hps; Dc: Hdc; Colours: LongInt;
  1224. BEGIN
  1225. Ps := WinGetPS(HWND_Desktop); { Get desktop PS }
  1226. Dc := GpiQueryDevice(Ps); { Get gpi context }
  1227. DevQueryCaps(Dc, Caps_Phys_Colors, 1, Colours); { Colour capacity }
  1228. If (Colours> 2) Then ScreenMode := smCO80 { Colour screen }
  1229. Else ScreenMode := smMono; { Mono screen }
  1230. WinReleasePS(Ps); { Release desktop PS }
  1231. END;
  1232. {$ENDIF}
  1233. {---------------------------------------------------------------------------}
  1234. { DetectMouse -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 19May98 LdB }
  1235. {---------------------------------------------------------------------------}
  1236. FUNCTION DetectMouse: Byte;
  1237. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1238. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1239. ASSEMBLER;
  1240. ASM
  1241. MOV AX, $3533; { Set function id }
  1242. PUSH BP; { Safety!! save reg }
  1243. INT $21; { Get mouse interrupt }
  1244. POP BP; { Restore register }
  1245. MOV AX, ES; { Transfer register }
  1246. OR AX, BX; { Check for nil ptr }
  1247. JZ @@Exit2; { Jump no mouse driver }
  1248. XOR AX, AX; { Set function id }
  1249. PUSH BP; { Safety!! save reg }
  1250. INT $33; { Reset mouse }
  1251. POP BP; { Restore register }
  1252. OR AX, AX; { Check for success }
  1253. JZ @@Exit2; { Reset mouse failed }
  1254. MOV AX, BX; { Return button count }
  1255. @@Exit2:
  1256. END;
  1257. {$ENDIF}
  1258. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1259. ASSEMBLER;
  1260. ASM
  1261. MOVW $0x200, %AX; { Get real mode int }
  1262. MOVW $0x33, %BX; { Vector 33H }
  1263. PUSHL %EBP; { Save register }
  1264. INT $0x31; { Get the address }
  1265. POPL %EBP; { Restore register }
  1266. MOVW %CX, %AX; { Transfer register }
  1267. ORW %DX, %AX; { Check for nil ptr }
  1268. JZ .L_Exit2; { Jump no mouse driver }
  1269. XORW %AX, %AX; { Set function id }
  1270. PUSHL %EBP; { Save register }
  1271. INT $0x33; { Reset mouse driver }
  1272. POPL %EBP; { Restore register }
  1273. ORW %AX, %AX; { Check for success }
  1274. JZ .L_Exit2; { Reset mouse failed }
  1275. MOVW %BX, %AX; { Return button count }
  1276. .L_Exit2:
  1277. END;
  1278. {$ENDIF}
  1279. {$ENDIF}
  1280. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1281. BEGIN
  1282. If (GetSystemMetrics(sm_MousePresent) <> 0) Then
  1283. DetectMouse := 2 Else DetectMouse := 0; { Buttons present }
  1284. END;
  1285. {$ENDIF}
  1286. {$IFDEF OS_OS2} { OS2 CODE }
  1287. BEGIN
  1288. DetectMouse := WinQuerySysValue(HWND_Desktop,
  1289. SV_CMouseButtons); { Buttons present }
  1290. END;
  1291. {$ENDIF}
  1292. {***************************************************************************}
  1293. { INTERFACE ROUTINES }
  1294. {***************************************************************************}
  1295. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1296. { BUFFER MOVE ROUTINES }
  1297. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1298. {---------------------------------------------------------------------------}
  1299. { CStrLen -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1300. {---------------------------------------------------------------------------}
  1301. FUNCTION CStrLen (Const S: String): Integer;
  1302. VAR I, J: Integer;
  1303. BEGIN
  1304. J := 0; { Set result to zero }
  1305. For I := 1 To Length(S) Do
  1306. If (S[I] <> '~') Then Inc(J); { Inc count if not ~ }
  1307. CStrLen := J; { Return length }
  1308. END;
  1309. {---------------------------------------------------------------------------}
  1310. { MoveStr -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 10Jul99 LdB }
  1311. {---------------------------------------------------------------------------}
  1312. PROCEDURE MoveStr (Var Dest; Const Str: String; Attr: Byte);
  1313. VAR I: Word; P: PWord;
  1314. BEGIN
  1315. For I := 1 To Length(Str) Do Begin { For each character }
  1316. P := @TWordArray(Dest)[I-1]; { Pointer to word }
  1317. If (Attr <> 0) Then WordRec(P^).Hi := Attr; { Copy attribute }
  1318. WordRec(P^).Lo := Byte(Str[I]); { Copy string char }
  1319. End;
  1320. END;
  1321. {---------------------------------------------------------------------------}
  1322. { MoveCStr -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 10Jul99 LdB }
  1323. {---------------------------------------------------------------------------}
  1324. PROCEDURE MoveCStr (Var Dest; Const Str: String; Attrs: Word);
  1325. VAR B: Byte; I, J: Word; P: PWord;
  1326. BEGIN
  1327. J := 0; { Start position }
  1328. For I := 1 To Length(Str) Do Begin { For each character }
  1329. If (Str[I] <> '~') Then Begin { Not tilde character }
  1330. P := @TWordArray(Dest)[J]; { Pointer to word }
  1331. If (Lo(Attrs) <> 0) Then
  1332. WordRec(P^).Hi := Lo(Attrs); { Copy attribute }
  1333. WordRec(P^).Lo := Byte(Str[I]); { Copy string char }
  1334. Inc(J); { Next position }
  1335. End Else Begin
  1336. B := Hi(Attrs); { Hold attribute }
  1337. WordRec(Attrs).Hi := Lo(Attrs); { Copy low to high }
  1338. WordRec(Attrs).Lo := B; { Complete exchange }
  1339. End;
  1340. End;
  1341. END;
  1342. {---------------------------------------------------------------------------}
  1343. { MoveBuf -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 10Jul99 LdB }
  1344. {---------------------------------------------------------------------------}
  1345. PROCEDURE MoveBuf (Var Dest, Source; Attr: Byte; Count: Word);
  1346. VAR I: Word; P: PWord;
  1347. BEGIN
  1348. For I := 1 To Count Do Begin
  1349. P := @TWordArray(Dest)[I-1]; { Pointer to word }
  1350. If (Attr <> 0) Then WordRec(P^).Hi := Attr; { Copy attribute }
  1351. WordRec(P^).Lo := TByteArray(Source)[I-1]; { Copy source data }
  1352. End;
  1353. END;
  1354. {---------------------------------------------------------------------------}
  1355. { MoveChar -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 10Jul99 LdB }
  1356. {---------------------------------------------------------------------------}
  1357. PROCEDURE MoveChar (Var Dest; C: Char; Attr: Byte; Count: Word);
  1358. VAR I: Word; P: PWord;
  1359. BEGIN
  1360. For I := 1 To Count Do Begin
  1361. P := @TWordArray(Dest)[I-1]; { Pointer to word }
  1362. If (Attr <> 0) Then WordRec(P^).Hi := Attr; { Copy attribute }
  1363. If (Ord(C) <> 0) Then WordRec(P^).Lo := Byte(C); { Copy character }
  1364. End;
  1365. END;
  1366. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1367. { KEYBOARD SUPPORT ROUTINES }
  1368. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1369. {---------------------------------------------------------------------------}
  1370. { GetAltCode -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1371. {---------------------------------------------------------------------------}
  1372. FUNCTION GetAltCode (Ch: Char): Word;
  1373. BEGIN
  1374. GetAltCode := 0; { Preset zero return }
  1375. Ch := UpCase(Ch); { Convert upper case }
  1376. If (Ch < #128) Then
  1377. GetAltCode := AltCodes[Ord(Ch)] SHL 8 { Return code }
  1378. Else If (Ch = #240) Then GetAltCode := $0200 { Return code }
  1379. Else GetAltCode := 0; { Return zero }
  1380. END;
  1381. {---------------------------------------------------------------------------}
  1382. { GetCtrlCode -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1383. {---------------------------------------------------------------------------}
  1384. FUNCTION GetCtrlCode (Ch: Char): Word;
  1385. BEGIN
  1386. GetCtrlCode := GetAltCode(Ch) OR (Ord(Ch) - $40); { Ctrl+key code }
  1387. END;
  1388. {---------------------------------------------------------------------------}
  1389. { GetAltChar -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1390. {---------------------------------------------------------------------------}
  1391. FUNCTION GetAltChar (KeyCode: Word): Char;
  1392. VAR I: Integer;
  1393. BEGIN
  1394. GetAltChar := #0; { Preset fail return }
  1395. If (Lo(KeyCode) = 0) Then Begin { Extended key }
  1396. If (Hi(KeyCode) < 128) Then Begin { Key between 0-127 }
  1397. I := 0; { Start at first }
  1398. While (I < 128) AND (Hi(KeyCode) <> AltCodes[I])
  1399. Do Inc(I); { Search for match }
  1400. If (I < 128) Then GetAltChar := Chr(I); { Return character }
  1401. End Else
  1402. If (Hi(KeyCode)=$02) Then GetAltChar := #240; { Return char }
  1403. End;
  1404. END;
  1405. {---------------------------------------------------------------------------}
  1406. { GetCtrlChar -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1407. {---------------------------------------------------------------------------}
  1408. FUNCTION GetCtrlChar (KeyCode: Word): Char;
  1409. VAR C: Char;
  1410. BEGIN
  1411. C := #0; { Preset #0 return }
  1412. If (Lo(KeyCode) > 0) AND (Lo(KeyCode) <= 26) Then { Between 1-26 }
  1413. C := Chr(Lo(KeyCode) + $40); { Return char A-Z }
  1414. GetCtrlChar := C; { Return result }
  1415. END;
  1416. {---------------------------------------------------------------------------}
  1417. { CtrlToArrow -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 25May96 LdB }
  1418. {---------------------------------------------------------------------------}
  1419. FUNCTION CtrlToArrow (KeyCode: Word): Word;
  1420. CONST NumCodes = 11;
  1421. CtrlCodes : Array [0..NumCodes-1] Of Char =
  1422. (#19, #4, #5, #24, #1, #6, #7, #22, #18, #3, #8);
  1423. ArrowCodes: Array [0..NumCodes-1] Of Word =
  1424. (kbLeft, kbRight, kbUp, kbDown, kbHome, kbEnd, kbDel, kbIns,
  1425. kbPgUp, kbPgDn, kbBack);
  1426. VAR I: Integer;
  1427. BEGIN
  1428. CtrlToArrow := KeyCode; { Preset key return }
  1429. For I := 0 To NumCodes - 1 Do
  1430. If WordRec(KeyCode).Lo = Byte(CtrlCodes[I]) { Matches a code }
  1431. Then Begin
  1432. CtrlToArrow := ArrowCodes[I]; { Return key stroke }
  1433. Exit; { Now exit }
  1434. End;
  1435. END;
  1436. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1437. { KEYBOARD CONTROL ROUTINES }
  1438. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1439. {---------------------------------------------------------------------------}
  1440. { GetShiftState -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 08Jul96 LdB }
  1441. {---------------------------------------------------------------------------}
  1442. FUNCTION GetShiftState: Byte;
  1443. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1444. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1445. ASSEMBLER;
  1446. ASM
  1447. MOV ES, Seg0040; { Load DOS segment }
  1448. XOR AX, AX;
  1449. MOV DX, AX; { Clear registers }
  1450. MOV AL, ES:[$0017]; { Read shift state }
  1451. END;
  1452. {$ENDIF}
  1453. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1454. BEGIN
  1455. ASM
  1456. MOVW $0x0200, %AX; { Set function id }
  1457. PUSHL %EBP; { Save register }
  1458. INT $0x16; { Get shift status }
  1459. POPL %EBP; { Restore register }
  1460. END;
  1461. END;
  1462. {$ENDIF}
  1463. {$ENDIF}
  1464. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1465. CONST vk_Scroll = $91; { Borland forgot this! }
  1466. VAR B: Byte;
  1467. BEGIN
  1468. B := 0; { Clear all masks }
  1469. If (GetKeyState(vk_Shift) AND $80 <> 0) Then
  1470. B := B OR kbBothShifts; { Set both shifts }
  1471. If (GetKeyState(vk_Control) AND $80 <> 0) Then
  1472. B := B OR kbCtrlShift; { Set control mask }
  1473. If (GetKeyState(vk_Menu) AND $80 <> 0) Then
  1474. B := B OR kbAltShift; { Set alt mask }
  1475. If (GetKeyState(vk_Scroll) AND $81 <> 0) Then
  1476. B := B OR kbScrollState; { Set scroll lock mask }
  1477. If (GetKeyState(vk_NumLock) AND $81 <> 0) Then
  1478. B := B OR kbNumState; { Set number lock mask }
  1479. If (GetKeyState(vk_Capital) AND $81 <> 0) Then
  1480. B := B OR kbCapsState; { Set caps lock mask }
  1481. If (GetKeyState(vk_Insert) AND $81 <> 0) Then
  1482. B := B OR kbInsState; { Set insert mask }
  1483. GetShiftState := B; { Return masks }
  1484. END;
  1485. {$ENDIF}
  1486. {$IFDEF OS_OS2} { OS2 CODE }
  1487. VAR Key: KbdInfo;
  1488. BEGIN
  1489. Key.cb := SizeOf(Key); { Keyboard size }
  1490. If KbdGetStatus(Key, 0) = 0 Then { Get key status }
  1491. GetShiftState := Key.fsState Else { Return shift state }
  1492. GetShiftState := 0; { Failed so return 0 }
  1493. END;
  1494. {$ENDIF}
  1495. {---------------------------------------------------------------------------}
  1496. { GetKeyEvent -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 30Jul99 LdB }
  1497. {---------------------------------------------------------------------------}
  1498. PROCEDURE GetKeyEvent (Var Event: TEvent);
  1499. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1500. ASSEMBLER;
  1501. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1502. ASM
  1503. MOV AH, $1; { Set function id }
  1504. PUSH BP; { Safety!! save reg }
  1505. INT $16; { Check for keypress }
  1506. POP BP; { Restore register }
  1507. MOV AX, $0; { Zero register AX }
  1508. MOV BX, AX; { Zero register BX }
  1509. JZ @@Exit3; { No keypress jump }
  1510. MOV AH, $00; { Set function id }
  1511. PUSH BP; { Safety!! save reg }
  1512. INT $16; { Read the key }
  1513. POP BP; { Restore register }
  1514. XCHG AX, BX; { Exchange registers }
  1515. MOV AX, evKeyDown; { Set keydown event }
  1516. @@Exit3:
  1517. LES DI, Event; { ES:DI -> Event }
  1518. MOV ES:[DI].TEvent.What, AX; { Store event mask }
  1519. MOV ES:[DI].TEvent.KeyCode, BX; { Store key code }
  1520. END;
  1521. {$ENDIF}
  1522. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1523. ASM
  1524. MOVB $1, %AH; { Set function id }
  1525. PUSHL %EBP; { Save register }
  1526. INT $0x16; { Check for keypress }
  1527. POPL %EBP; { Restore register }
  1528. MOVW $0x0, %AX; { Zero register AX }
  1529. MOVW %AX, %BX; { Zero register BX }
  1530. JZ .L_Exit3; { No keypress jump }
  1531. MOVB $0, %AH; { Set function id }
  1532. PUSHL %EBP; { Save register }
  1533. INT $0x16; { Read the key }
  1534. POPL %EBP; { Restore register }
  1535. XCHGW %BX, %AX; { Exchange registers }
  1536. MOVW $0x10, %AX; { Set keydown event }
  1537. .L_Exit3:
  1538. MOVL Event, %EDI; { EDI -> Event }
  1539. CLD;
  1540. STOSW; { Store event mask }
  1541. XCHGW %BX, %AX; { Transfer key code }
  1542. STOSW; { Store key code }
  1543. END;
  1544. {$ENDIF}
  1545. {$ENDIF}
  1546. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1547. CONST NumPos: Byte = 0; Numeric: Byte = 0;
  1548. VAR Handled: Boolean; B: Byte; Msg: TMsg;
  1549. BEGIN
  1550. Event.What := evNothing; { Preset no event }
  1551. {$IFDEF PPC_FPC} { FPC WINDOWS COMPILER }
  1552. If (PeekMessage(@Msg, 0, 0, WM_MouseFirst-1, pm_Remove)
  1553. OR PeekMessage(@Msg, 0, WM_MouseLast+1, $FFFF, pm_Remove))
  1554. {$ELSE} { OTHER COMPILERS }
  1555. If (PeekMessage(Msg, 0, 0, WM_MouseFirst-1, pm_Remove)
  1556. OR PeekMessage(Msg, 0, WM_MouseLast+1, $FFFF, pm_Remove))
  1557. {$ENDIF}
  1558. Then Begin { Non mouse message }
  1559. Handled := False; { Preset not handled }
  1560. Case Msg.Message Of
  1561. WM_Char: Begin { CHARACTER KEY }
  1562. NumPos := 0; { Zero number position }
  1563. Event.CharCode := Char(Msg.wParam); { Transfer character }
  1564. If (Event.CharCode > #127) Then
  1565. Event.CharCode := Chr(WinAsciiToIntAscii[
  1566. Ord(Event.CharCode)]); { Convert to ascii }
  1567. Event.ScanCode := Lo(HiWord(Msg.lParam)); { Transfer scan code }
  1568. If (Event.CharCode <> #0) Then Begin { If valid key then }
  1569. Event.What := evKeyDown; { Key down event }
  1570. Handled := True; { Message was handled }
  1571. If (Event.KeyCode = kbTab) AND { Tab key is special }
  1572. (GetShiftState AND kbBothShifts <> 0) Then { Check shift state }
  1573. Event.KeyCode := kbShiftTab; { If set make shifttab }
  1574. End;
  1575. End;
  1576. WM_SysKeyDown: Begin { SYSTEM KEY DOWN }
  1577. If (NumPos > 0) Then Begin { Numerics entry op }
  1578. Case Msg.wParam Of
  1579. VK_Insert: B := 0; { Key value = 0 }
  1580. VK_End: B := 1; { Key value = 1 }
  1581. VK_Down: B := 2; { Key value = 2 }
  1582. VK_Next: B := 3; { Key value = 3 }
  1583. VK_Left: B := 4; { Key value = 4 }
  1584. VK_Clear: B := 5; { Key value = 5 }
  1585. VK_Right: B := 6; { Key value = 6 }
  1586. VK_Home: B := 7; { Key value = 7 }
  1587. VK_Up: B := 8; { Key value = 8 }
  1588. VK_Prior: B := 9; { Key value = 9 }
  1589. VK_NumPad0..VK_NumPad9: B := Msg.wParam
  1590. - $60; { Numbic key pad }
  1591. Else NumPos := 0; { Invalid key }
  1592. End;
  1593. If ((NumPos > 0) AND (NumPos < 4)) AND { Valid position }
  1594. ((B >= $0) AND (B <= $9)) Then Begin { Valid key }
  1595. Numeric := Numeric*10 + B; { Adjust numeric }
  1596. Inc(NumPos); { Next position }
  1597. If (NumPos = 4) Then Begin { We have three keys }
  1598. Event.What := evKeyDown; { Set keydown event }
  1599. Event.CharCode := Chr(Numeric); { Transfer code }
  1600. NumPos := 0; { Zero number position }
  1601. End;
  1602. Handled := True; { Message was handled }
  1603. End Else NumPos := 0; { Zero number position }
  1604. End;
  1605. If (Msg.WParam = vk_Menu) Then Begin { ALT key down }
  1606. Numeric := 0; { Zero numeric }
  1607. NumPos := 1; { Set to start point }
  1608. Handled := True; { Message was handled }
  1609. End;
  1610. If NOT Handled Then Begin { Key press not handled }
  1611. If (Lo(Msg.wParam) < 128) Then Begin { Ignore if above 128 }
  1612. If (Msg.wParam = vk_F10) Then Begin { F10 reports oddly }
  1613. If (GetKeyState(vk_Shift) AND $80 <> 0)
  1614. Then Event.KeyCode := kbShiftF10 Else{ Shift F10 }
  1615. If (GetKeyState(vk_Menu) AND $80 <> 0)
  1616. Then Event.KeyCode := kbAltF10 Else { Alt F10 }
  1617. If (GetKeyState(vk_Control) AND $80 <> 0)
  1618. Then Event.KeyCode := kbCtrlF10 { Ctrl F10 }
  1619. Else Event.KeyCode := kbF10; { Normal F10 }
  1620. End Else Event.KeyCode :=
  1621. AltVirtualToAscii[Lo(Msg.wParam)]; { Convert key code }
  1622. End Else Event.KeyCode := 0; { Clear Event.keycode }
  1623. If (Event.KeyCode <> 0) Then Begin { If valid key then }
  1624. Event.What := evKeyDown; { Key down event }
  1625. Handled := True; { Message was handled }
  1626. End;
  1627. End;
  1628. End;
  1629. WM_KeyDown: Begin { ARROWS/F1..F12 KEYS }
  1630. If (((Msg.WParam >= Vk_F1) AND (Msg.WParam <= Vk_F12)) OR
  1631. ((Msg.WParam >= Vk_Prior) AND (Msg.WParam <= Vk_Delete)))
  1632. Then Begin { Special key press }
  1633. Event.CharCode := #0; { Clear char code }
  1634. Event.ScanCode := Lo(HiWord(Msg.LParam)); { Create scan code }
  1635. If (GetKeyState(vk_Shift) AND $80 <> 0)
  1636. Then Begin { Shift key down }
  1637. Case Msg.wParam Of
  1638. vk_F1..vk_F9: Event.KeyCode :=
  1639. Event.KeyCode + $1900; { Shift F1..F9 keys }
  1640. vk_F11: Event.KeyCode := kbShiftF11; { Shift F11 key }
  1641. vk_F12: Event.KeyCode := kbShiftF12; { Shift F12 key }
  1642. End;
  1643. End Else If (GetKeyState(vk_Control) AND $80 <> 0)
  1644. Then Begin { Control key down }
  1645. Case Msg.wParam Of
  1646. vk_F1..vk_F9: Event.KeyCode :=
  1647. Event.KeyCode + $2300; { Ctrl F1..F9 keys }
  1648. vk_F11: Event.KeyCode := kbCtrlF11; { Ctrl F11 key }
  1649. vk_F12: Event.KeyCode := kbCtrlF12; { Ctrl F12 key }
  1650. End;
  1651. End;
  1652. If (Event.KeyCode <> 0) Then Begin { If valid key then }
  1653. Event.What := evKeyDown; { Key down event }
  1654. Handled := True; { Message was handled }
  1655. End;
  1656. End;
  1657. NumPos := 0; { Zero number position }
  1658. End;
  1659. End;
  1660. If NOT Handled Then Begin { Check we did not handle }
  1661. TranslateMessage(Msg); { Translate message }
  1662. DispatchMessage(Msg); { Dispatch message }
  1663. End;
  1664. End;
  1665. END;
  1666. {$ENDIF}
  1667. {$IFDEF OS_OS2} { OS2 CODE }
  1668. VAR Msg: QMsg;
  1669. BEGIN
  1670. Event.What := evNothing; { Preset no event }
  1671. If (WinPeekMsg(Anchor, Msg, 0, 0, WM_MouseFirst-1, pm_Remove)
  1672. OR WinPeekMsg(Anchor, Msg, 0, WM_MouseLast+1, $FFFFFFFF, pm_Remove))
  1673. Then Begin { Check for message }
  1674. If (Msg.Msg = WM_Char) AND { Character message }
  1675. (Msg.Mp1 AND KC_KeyUp <> 0) AND { Key released }
  1676. (Msg.Mp1 AND KC_Composite = 0) { Not composite key }
  1677. Then Begin
  1678. If (Short1FromMP(Msg.Mp1) AND KC_ScanCode <> 0 )
  1679. Then Begin
  1680. Event.ScanCode := Ord(Char4FromMP(Msg.Mp1)); { Return scan code }
  1681. Event.CharCode := Char1FromMP(Msg.Mp2); { Return char code }
  1682. If (Event.CharCode = Chr($E0)) Then Begin
  1683. Event.CharCode := #0;
  1684. Event.ScanCode := Byte(Char2FromMP(Msg.Mp2));
  1685. End;
  1686. If (Event.KeyCode <> 0) Then
  1687. Event.What := evKeyDown; { Key down event }
  1688. End;
  1689. End;
  1690. If (Event.What = evNothing) Then { Event not handled }
  1691. WinDispatchMsg(Anchor, Msg); { Disptach message }
  1692. End;
  1693. END;
  1694. {$ENDIF}
  1695. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1696. { MOUSE CONTROL ROUTINES }
  1697. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  1698. {---------------------------------------------------------------------------}
  1699. { HideMouse -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 30Jun98 LdB }
  1700. {---------------------------------------------------------------------------}
  1701. PROCEDURE HideMouse;
  1702. BEGIN
  1703. If (HideCount = 0) Then Begin { Is mouse hidden yet? }
  1704. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1705. HideMouseCursor; { Hide mouse cursor }
  1706. {$ENDIF}
  1707. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1708. ShowCursor(False); { Hide mouse cursor }
  1709. {$ENDIF}
  1710. {$IFDEF OS_OS2} { OS2 CODE }
  1711. If (AppWindow <> 0) Then { Window valid }
  1712. WinShowCursor(AppWindow, False); { Hide mouse cursor }
  1713. {$ENDIF}
  1714. End;
  1715. Inc(HideCount); { Inc hide count }
  1716. END;
  1717. {---------------------------------------------------------------------------}
  1718. { ShowMouse -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 30Jun98 LdB }
  1719. {---------------------------------------------------------------------------}
  1720. PROCEDURE ShowMouse;
  1721. BEGIN
  1722. Dec(HideCount); { Dec hide count }
  1723. If (HideCount = 0) Then Begin { Is mouse visible? }
  1724. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1725. ShowMouseCursor; { Show mouse cursor }
  1726. {$ENDIF}
  1727. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1728. ShowCursor(True); { Show mouse cursor }
  1729. {$ENDIF}
  1730. {$IFDEF OS_OS2} { OS2 CODE }
  1731. If (AppWindow <> 0) Then { Window valid }
  1732. WinShowCursor(AppWindow, True); { Show mouse cursor }
  1733. {$ENDIF}
  1734. End;
  1735. END;
  1736. {---------------------------------------------------------------------------}
  1737. { GetMouseEvent -> Platforms DOS/DPMI/WINDOWS/OS2 - Updated 09Sep98 LdB }
  1738. {---------------------------------------------------------------------------}
  1739. PROCEDURE GetMouseEvent (Var Event: TEvent);
  1740. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  1741. ASSEMBLER;
  1742. {$IFDEF ASM_BP} { BP COMPATABLE ASM }
  1743. ASM
  1744. CMP MouseEvents, 0; { Any mouse events }
  1745. JNZ @@MouseOk; { Check mouse active }
  1746. JMP @@NoEventExit; { Mouse not active }
  1747. @@MouseOk:
  1748. CLI; { Disable interrupts }
  1749. CMP EventCount, 0; { Check event count }
  1750. JNE @@MouseEventInQueue; { If > 0 event avail }
  1751. MOV BL, MouseButtons; { Fetch mouse buttons }
  1752. MOV CX, MouseWhere.Word[0]; { Fetch mouse where.x }
  1753. MOV DX, MouseWhere.Word[2]; { Fetch mouse where.y }
  1754. MOV ES, Seg0040; { DOS DAT SEG }
  1755. MOV DI, ES:Ticks; { Fetch current time }
  1756. JMP @@NextMsgReady; { Now process }
  1757. @@MouseEventInQueue:
  1758. MOV SI, WORD PTR EventQHead; { Event queue head }
  1759. CLD; { Direction forward }
  1760. LODSW; { Fetch word 1 }
  1761. XCHG AX, DI; { Set timer ticks }
  1762. LODSW; { Fetch word 2 }
  1763. XCHG AX, BX; { Set button masks }
  1764. LODSW; { Fetch word 3 }
  1765. XCHG AX, CX; { Set mouse x position }
  1766. LODSW; { Fetch word 4 }
  1767. XCHG AX, DX; { Set mouse y position }
  1768. CMP SI, OFFSET EventQLast; { Check if roll needed }
  1769. JNE @@NoRoll;
  1770. MOV SI, OFFSET EventQueue; { Roll back to start }
  1771. @@NoRoll:
  1772. MOV WORD PTR EventQHead, SI; { Update queue head }
  1773. DEC EventCount; { One event cleared }
  1774. @@NextMsgReady:
  1775. STI; { Enable interrupts }
  1776. CMP MouseReverse, 0; { Check mouse reversed }
  1777. JE @@MouseNormal;
  1778. MOV BH, BL; { Transfer button mask }
  1779. AND BH, 3; { Clear others masks }
  1780. JE @@MouseNormal; { Neither set exit }
  1781. CMP BH, 3; { Check not all set }
  1782. JE @@MouseNormal; { Both set exit }
  1783. XOR BL, 3; { Invert button masks }
  1784. @@MouseNormal:
  1785. MOV BH, [LastDouble]; { Load last double }
  1786. MOV AL, [LastButtons]; { Load last buttons }
  1787. CMP AL, BL; { Are buttons same? }
  1788. JE @@SameButtonsDown;
  1789. OR AL, AL; { Any last buttons? }
  1790. JE @@ButtonsDown;
  1791. OR BL, BL; { Any buttons down? }
  1792. JE @@MouseUp;
  1793. MOV BL, AL; { Transfer new buttons }
  1794. @@SameButtonsDown:
  1795. CMP CX, [LastWhereX]; { Mouse moved from x }
  1796. JNE @@MouseMove;
  1797. CMP DX, [LastWhereY]; { Mouse moved from y }
  1798. JNE @@MouseMove;
  1799. OR BL, BL; { Any buttons pressed? }
  1800. JE @@NoButtonsDown;
  1801. MOV AX, DI; { Current tick count }
  1802. SUB AX, [AutoTicks]; { Subtract last count }
  1803. CMP AX, [AutoDelay]; { Greater than delay? }
  1804. JAE @@MouseAuto; { Mouse auto event }
  1805. @@NoButtonsDown:
  1806. JMP @@NoEventExit; { No event exit }
  1807. @@ButtonsDown:
  1808. MOV BH, 0; { Preset no dbl click }
  1809. CMP BL, [DownButtons]; { Check to last down }
  1810. JNE @@MouseDown;
  1811. CMP CX, [DownWhereX]; { Check x position }
  1812. JNE @@MouseDown;
  1813. CMP DX, [DownWhereY]; { Check y position }
  1814. JNE @@MouseDown;
  1815. MOV AX, DI; { Transfer tick count }
  1816. SUB AX, [DownTicks]; { Sub last down count }
  1817. CMP AX, [DoubleDelay]; { Greater than delay? }
  1818. JAE @@MouseDown;
  1819. MOV BH, 1; { Double click }
  1820. @@MouseDown:
  1821. MOV [DownButtons], BL; { Hold down buttons }
  1822. MOV [DownWhereX], CX; { Hold x down point }
  1823. MOV [DownWhereY], DX; { Hold y down point }
  1824. MOV [DownTicks], DI; { Hold tick value }
  1825. MOV [AutoTicks], DI; { Hold tick value }
  1826. MOV AX, [RepeatDelay]; { Load delay count }
  1827. MOV [AutoDelay], AX; { Set delay time }
  1828. MOV AX, evMouseDown; { Mouse down event }
  1829. JMP @@UpdateValues; { Update, svae & exit }
  1830. @@MouseUp:
  1831. MOV AX, evMouseUp; { Mouse button up }
  1832. JMP @@UpdateValues; { Update, save & exit }
  1833. @@MouseMove:
  1834. MOV AX, evMouseMove; { Mouse has moved }
  1835. JMP @@UpdateValues; { Update, save & exit }
  1836. @@MouseAuto:
  1837. MOV AX, evMouseAuto; { Mouse auto event }
  1838. MOV [AutoTicks], DI; { Reset auto ticks }
  1839. MOV [AutoDelay], 1; { Reset delay count }
  1840. @@UpdateValues:
  1841. MOV [LastButtons], BL; { Save last buttons }
  1842. MOV [LastDouble], BH; { Save double state }
  1843. MOV [LastWhereX], CX; { Save x position }
  1844. MOV [LastWhereY], DX; { Save y position }
  1845. JMP @@StoreAndExit; { Now store and exit }
  1846. @@NoEventExit:
  1847. XOR AX, AX; { Clear register }
  1848. MOV BX, AX; { Clear register }
  1849. MOV CX, AX; { Clear register }
  1850. MOV DX, AX; { Clear register }
  1851. @@StoreAndExit:
  1852. LES DI, Event; { Address of event }
  1853. CLD; { Set direction fwd }
  1854. STOSW; { Save 1st word }
  1855. XCHG AX, BX; { Transfer register }
  1856. STOSW; { Save 2nd word }
  1857. XCHG AX, CX; { Transfer register }
  1858. STOSW; { Save 3rd word }
  1859. XCHG AX, DX; { Transfer register }
  1860. STOSW; { Save 4th word }
  1861. END;
  1862. {$ENDIF}
  1863. {$IFDEF ASM_FPC} { FPC COMPATABLE ASM }
  1864. ASM
  1865. CMPB $0, MOUSEEVENTS; { Any mouse events }
  1866. JNZ .L_MouseOk; { Check mouse active }
  1867. JMP .L_NoEventExit; { Mouse not active }
  1868. .L_MouseOk:
  1869. CLI;
  1870. CMPW $0, EVENTCOUNT; { Check event count }
  1871. JNE .L_MouseEventInQueue; { If > 0 event avail }
  1872. MOVB MOUSEBUTTONS, %BL; { Fetch mouse buttons }
  1873. MOVW MOUSEWHERE, %CX; { Fetch mouse where.x }
  1874. MOVW MOUSEWHERE+2, %DX; { Fetch mouse where.y }
  1875. PUSH %ES; { Save segment }
  1876. MOVW $0x40, %AX; { Fetch DOS segment }
  1877. MOVW %AX, %ES; { Transfer to segment }
  1878. MOVL $0x6C, %EDI; { Tick address }
  1879. MOVW %ES:(%EDI), %DI; { Fetch dos tick count }
  1880. POP %ES; { Recover segment }
  1881. JMP .L_NextMsgReady; { Now process }
  1882. .L_MouseEventInQueue:
  1883. MOVL EVENTQHEAD, %ESI; { Event queue head }
  1884. CLD; { Direction forward }
  1885. LODSW; { Fetch word 1 }
  1886. XCHGW %DI, %AX; { Set timer ticks }
  1887. LODSW; { Fetch word 2 }
  1888. XCHGW %BX, %AX; { Set button masks }
  1889. LODSW; { Fetch word 3 }
  1890. XCHGW %CX, %AX; { Set mouse x position }
  1891. LODSW; { Fetch word 4 }
  1892. XCHGW %DX, %AX; { Set mouse y position }
  1893. LEAL EVENTQLAST, %EAX; { Address of roll pt }
  1894. CMPL %EAX, %ESI; { Check if roll needed }
  1895. JNE .L_NoHeadRoll;
  1896. LEAL EVENTQUEUE, %ESI; { Roll back to start }
  1897. .L_NoHeadRoll:
  1898. MOVL %ESI, EVENTQHEAD; { Update queue head }
  1899. DECW EVENTCOUNT; { One event cleared }
  1900. .L_NextMsgReady:
  1901. STI; { Enable interrupts }
  1902. CMPB $0, MOUSEREVERSE; { Check mouse reversed }
  1903. JE .L_MouseNormal;
  1904. MOVB %BL, %BH; { Transfer button mask }
  1905. ANDB $3, %BH; { Clear others masks }
  1906. JE .L_MouseNormal; { Neither set exit }
  1907. CMPB $3, %BH; { Check not all set }
  1908. JE .L_MouseNormal; { Both set exit }
  1909. XORB $3, %BL; { Invert button masks }
  1910. .L_MouseNormal:
  1911. MOVB LASTDOUBLE, %BH; { Load last double }
  1912. MOVB LASTBUTTONS, %AL; { Load last buttons }
  1913. CMPB %BL, %AL; { Are buttons same? }
  1914. JE .L_SameButtonsDown;
  1915. ORB %AL, %AL; { Any last buttons? }
  1916. JE .L_ButtonsDown;
  1917. ORB %BL, %BL; { Any buttons down? }
  1918. JE .L_MouseUp;
  1919. MOVB %AL, %BL; { Transfer new buttons }
  1920. .L_SameButtonsDown:
  1921. CMPW LASTWHEREX, %CX; { Mouse moved from x }
  1922. JNE .L_MouseMove;
  1923. CMPW LASTWHEREY, %DX; { Mouse moved from y }
  1924. JNE .L_MouseMove;
  1925. ORB %BL, %BL; { Any buttons pressed? }
  1926. JE .L_NoButtonsDown;
  1927. MOVW %DI, %AX; { Current tick count }
  1928. SUBW AUTOTICKS, %AX; { Subtract last count }
  1929. CMPW AUTODELAY, %AX; { Greater than delay? }
  1930. JAE .L_MouseAuto; { Mouse auto event }
  1931. .L_NoButtonsDown:
  1932. JMP .L_NoEventExit; { No event exit }
  1933. .L_ButtonsDown:
  1934. MOVB $0, %BH; { Preset no dbl click }
  1935. CMPB DOWNBUTTONS, %BL; { Check to last down }
  1936. JNE .L_MouseDown;
  1937. CMPW DOWNWHEREX, %CX; { Check x position }
  1938. JNE .L_MouseDown;
  1939. CMPW DOWNWHEREY, %DX; { Check y position }
  1940. JNE .L_MouseDown;
  1941. MOVW %DI, %AX; { Transfer tick count }
  1942. SUBW DOWNTICKS, %AX; { Sub last down count }
  1943. CMPW DOUBLEDELAY, %AX; { Greater than delay? }
  1944. JAE .L_MouseDown;
  1945. MOVB $1, %BH; { Double click }
  1946. .L_MouseDown:
  1947. MOVB %BL, DOWNBUTTONS; { Hold down buttons }
  1948. MOVW %CX, DOWNWHEREX; { Hold x down point }
  1949. MOVW %DX, DOWNWHEREY; { Hold y down point }
  1950. MOVW %DI, DOWNTICKS; { Hold tick value }
  1951. MOVW %DI, AUTOTICKS; { Hold tick value }
  1952. MOVW REPEATDELAY, %AX; { Load delay count }
  1953. MOVW %AX, AUTODELAY; { Set delay time }
  1954. MOVW $1, %AX; { Mouse down event }
  1955. JMP .L_UpdateValues; { Update, svae & exit }
  1956. .L_MouseUp:
  1957. MOVW $2, %AX; { Mouse button up }
  1958. JMP .L_UpdateValues; { Update, save & exit }
  1959. .L_MouseMove:
  1960. MOVW $4, %AX; { Mouse has moved }
  1961. JMP .L_UpdateValues; { Update, save & exit }
  1962. .L_MouseAuto:
  1963. MOVW $8, %AX; { Mouse auto event }
  1964. MOVW %DI, AUTOTICKS; { Reset auto ticks }
  1965. MOVW $1, AUTODELAY; { Reset delay count }
  1966. .L_UpdateValues:
  1967. MOVB %BL, LASTBUTTONS; { Save last buttons }
  1968. MOVB %BH, LASTDOUBLE; { Save double state }
  1969. MOVW %CX, LASTWHEREX; { Save x position }
  1970. MOVW %DX, LASTWHEREY; { Save y position }
  1971. JMP .L_StoreAndExit; { Now store and exit }
  1972. .L_NoEventExit:
  1973. XORW %AX, %AX; { Clear register }
  1974. MOVW %AX, %BX; { Clear register }
  1975. MOVW %AX, %CX; { Clear register }
  1976. MOVW %AX, %DX; { Clear register }
  1977. .L_StoreAndExit:
  1978. MOVL Event, %EDI; { Adress of event }
  1979. CLD; { Set direction fwd }
  1980. STOSW; { Save 1st word }
  1981. XCHGW %BX, %AX; { Transfer register }
  1982. STOSW; { Save 2nd word }
  1983. XCHGW %CX, %AX; { Transfer register }
  1984. STOSW; { Save 3rd word }
  1985. XCHGW %DX, %AX; { Transfer register }
  1986. STOSW; { Save 4th word }
  1987. END;
  1988. {$ENDIF}
  1989. {$ENDIF}
  1990. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  1991. VAR Msg: TMsg;
  1992. BEGIN
  1993. Event.What := evNothing; { Preset no event }
  1994. {$IFDEF PPC_FPC} { FPC WINDOWS COMPILER }
  1995. If PeekMessage(@Msg, 0, WM_MouseFirst,
  1996. WM_MouseLast, pm_Remove) Then Begin { Fetch mouse message }
  1997. {$ELSE} { OTHER COMPILERS }
  1998. If PeekMessage(Msg, 0, WM_MouseFirst,
  1999. WM_MouseLast, pm_Remove) Then Begin { Fetch mouse message }
  2000. {$ENDIF}
  2001. TranslateMessage(Msg); { Translate message }
  2002. DispatchMessage(Msg); { Dispatch message }
  2003. End;
  2004. END;
  2005. {$ENDIF}
  2006. {$IFDEF OS_OS2} { OS2 CODE }
  2007. VAR Msg: QMsg;
  2008. BEGIN
  2009. Event.What := evNothing; { Preset no event }
  2010. If WinPeekMsg(Anchor, Msg, 0, WM_MouseFirst,
  2011. WM_MouseLast, pm_Remove) Then Begin { Fetch mouse message }
  2012. WinDispatchMsg(Anchor, Msg); { Dispatch message }
  2013. End;
  2014. END;
  2015. {$ENDIF}
  2016. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2017. { EVENT HANDLER CONTROL ROUTINES }
  2018. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2019. {---------------------------------------------------------------------------}
  2020. { InitEvents -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 07Sep99 LdB }
  2021. {---------------------------------------------------------------------------}
  2022. PROCEDURE InitEvents;
  2023. BEGIN
  2024. If (ButtonCount <> 0) Then Begin { Mouse is available }
  2025. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2026. EventQHead := @EventQueue; { Initialize head }
  2027. EventQtail := @EventQueue; { Initialize tail }
  2028. LastDouble := False; { Clear last double }
  2029. LastButtons := 0; { Clear last buttons }
  2030. DownButtons := 0; { Clear down buttons }
  2031. HookMouse; { Hook the mouse }
  2032. GetMousePosition(MouseWhere.X, MouseWhere.Y); { Get mouse position }
  2033. LastWhereX := MouseWhere.X; { Set last x position }
  2034. LastWhereY := MouseWhere.Y; { Set last y position }
  2035. MouseEvents := True; { Set initialized flag }
  2036. ShowMouseCursor; { Show the mouse }
  2037. {$ENDIF}
  2038. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2039. MouseEvents := True; { Set initialized flag }
  2040. {$ENDIF}
  2041. {$IFDEF OS_OS2} { OS2 CODE }
  2042. If (Anchor=0) Then Anchor := WinInitialize(0); { Create anchor block }
  2043. If (MsgQue = 0) AND (Anchor <> 0) Then
  2044. MsgQue := WinCreateMsgQueue(Anchor, 0); { Initialize queue }
  2045. If (MsgQue = 0) Then Halt(254); { Check queue created }
  2046. MouseEvents := True; { Set initialized flag }
  2047. {$ENDIF}
  2048. End;
  2049. END;
  2050. {---------------------------------------------------------------------------}
  2051. { DoneEvents -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 30Jul99 LdB }
  2052. {---------------------------------------------------------------------------}
  2053. PROCEDURE DoneEvents;
  2054. BEGIN
  2055. If MouseEvents Then Begin { Initialized check }
  2056. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2057. HideMouseCursor; { Hide the mouse }
  2058. MouseEvents := False; { Clear event flag }
  2059. UnHookMouse; { Unhook the mouse }
  2060. {$ENDIF}
  2061. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2062. MouseEvents := False; { Clr initialized flag }
  2063. {$ENDIF}
  2064. {$IFDEF OS_OS2} { OS2 CODE }
  2065. If (MsgQue <> 0) Then WinDestroyMsgQueue(MsgQue);{ Destroy msg queue }
  2066. If (Anchor <> 0) Then WinTerminate(Anchor); { Destroy anchor block }
  2067. MsgQue := 0; { Zero msg queue handle }
  2068. Anchor := 0; { Zero anchor block }
  2069. MouseEvents := False; { Clr initialized flag }
  2070. {$ENDIF}
  2071. End;
  2072. END;
  2073. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2074. { VIDEO CONTROL ROUTINES }
  2075. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2076. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2077. {$IFDEF PPC_FPC} { FPC COMPILER ONLY }
  2078. { ******************************* REMARK ****************************** }
  2079. { This is purely temporary for FPC because the Graph is SuperVGA you }
  2080. { have no mouse pointer on screen because the mouse drivers don't go }
  2081. { up to supporting SVGA modes. This simply makes a cross hair so you }
  2082. { can see the mouse for now..will be fixed soon. }
  2083. { ****************************** END REMARK *** Leon de Boer, 04Nov99 * }
  2084. VAR LastX, LastY: Integer;
  2085. PROCEDURE ShowTheMouse; FAR;
  2086. BEGIN
  2087. If (MouseEvents = True) AND (HideCount = 0) { Mouse visible }
  2088. Then Begin
  2089. SetWriteMode(XORPut); { XOR write mode }
  2090. SetColor(15); { Set color to white }
  2091. Line(LastX-5, LastY, LastX+5, LastY); { Remove horz line }
  2092. Line(LastX, LastY-5, LastX, LastY+5); { Remove vert line }
  2093. LastX := MouseWhere.X; { Update x position }
  2094. LastY := MouseWHere.Y; { Update y position }
  2095. Line(LastX-5, LastY, LastX+5, LastY); { Draw horz line }
  2096. Line(LastX, LastY-5, LastX, LastY+5); { Draw vert line }
  2097. SetWriteMode(NormalPut); { Write mode to normal }
  2098. End;
  2099. END;
  2100. {$ENDIF}
  2101. {$ENDIF}
  2102. {---------------------------------------------------------------------------}
  2103. { InitVideo -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 26Nov99 LdB }
  2104. {---------------------------------------------------------------------------}
  2105. PROCEDURE InitVideo;
  2106. VAR {$IFDEF OS_DOS} I, J: Integer; Ts: TextSettingsType; {$ENDIF}
  2107. {$IFDEF OS_WINDOWS} Dc, Mem: HDc; TempFont: TLogFont; Tm: TTextmetric; {$ENDIF}
  2108. {$IFDEF OS_OS2} Ts, Fs: Integer; Ps: HPs; Tm: FontMetrics; {$ENDIF}
  2109. BEGIN
  2110. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2111. I := Detect; { Detect video card }
  2112. J := 0; { Zero select mode }
  2113. InitGraph(I, J, ''); { Initialize graphics }
  2114. I := GetMaxX; { Fetch max x size }
  2115. J := GetMaxY; { Fetch max y size }
  2116. {$IFDEF PPC_FPC} { FPC DOS COMPILER }
  2117. ASM
  2118. MOVW $7, %AX; { Set function id }
  2119. MOVW $0, %CX; { Clear register }
  2120. MOVW I, %DX; { Maximum x size }
  2121. INT $0x33; { Set mouse x movement }
  2122. MOVW $8, %AX; { Set function id }
  2123. MOVW $0, %CX; { Clear register }
  2124. MOVW J, %DX; { Maximum y size }
  2125. INT $0x33; { Set mouse y movement }
  2126. END;
  2127. Lock_Code(Pointer(@ShowTheMouse), 400); { Lock cursor code }
  2128. MouseMoveProc := ShowTheMouse; { Set move function }
  2129. ShowMouseProc := ShowTheMouse; { Set show function }
  2130. HideMouseProc := ShowTheMouse; { Set hide function }
  2131. {$ELSE} { OTHER DOS COMPILERS }
  2132. ASM
  2133. MOV AX, 7; { Set function id }
  2134. XOR CX, CX; { Clear register }
  2135. MOV DX, I; { Maximum x size }
  2136. INT 33H; { Set mouse x movement }
  2137. MOV AX, 8; { Set function id }
  2138. XOR CX, CX; { Clear register }
  2139. MOV DX, J; { Maximum y size }
  2140. INT 33H; { Set mouse y movement }
  2141. END;
  2142. {$ENDIF}
  2143. SysScreenWidth := GetMaxX+1; { Max screen width }
  2144. SysScreenHeight := GetMaxY+1; { Max screen height }
  2145. If (DefFontHeight = 0) Then { Font height not set }
  2146. J := SysScreenHeight DIV DefLineNum { Approx font height }
  2147. Else J := DefFontHeight; { Use set font height }
  2148. I := J DIV (TextHeight('H')+4); { Approx magnification }
  2149. If (I < 1) Then I := 1; { Must be 1 or above }
  2150. GetTextSettings(Ts); { Get text style }
  2151. SetTextStyle(Ts.Font, Ts.Direction, I); { Set new font settings }
  2152. SysFontWidth := TextWidth('H'); { Transfer font width }
  2153. SysFontHeight := TextHeight('H')+4; { Transfer font height }
  2154. {$ENDIF}
  2155. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2156. SysScreenWidth := GetSystemMetrics(
  2157. SM_CXFullScreen)-GetSystemMetrics(SM_CXFrame); { Max screen width }
  2158. SysScreenHeight := GetSystemMetrics(
  2159. SM_CYFullScreen); { Max screen height }
  2160. With TempFont Do Begin
  2161. If (DefFontHeight = 0) Then Begin { Font height not set }
  2162. lfHeight := SysScreenHeight DIV DefLineNum; { Best guess height }
  2163. End Else lfHeight := -DefFontHeight; { Specific font height }
  2164. lfWidth := 0; { No specific width }
  2165. lfEscapement := 0; { No specifics }
  2166. lfOrientation := 0; { Normal orientation }
  2167. lfWeight := DefFontWeight; { Default font weight }
  2168. lfItalic := 0; { No italics }
  2169. lfUnderline := 0; { No underlines }
  2170. lfStrikeOut := 0; { No strikeouts }
  2171. lfCharSet := ANSI_CharSet; { ANSI font set }
  2172. lfOutPrecision := Out_Default_Precis; { Default precision out }
  2173. lfClipPrecision := Clip_Default_Precis; { Default clip precision }
  2174. lfQuality := Proof_Quality; { Proof quality }
  2175. lfPitchAndFamily:= Variable_Pitch OR
  2176. Fixed_Pitch; { Either fitch format }
  2177. FillChar(lfFaceName, SizeOf(lfFaceName), #0); { Clear memory area }
  2178. Move(DefFontStyle[1], lfFacename,
  2179. Length(DefFontStyle)); { Transfer style name }
  2180. End;
  2181. DefGFVFont := CreateFontIndirect(TempFont); { Create a default font }
  2182. Dc := GetDc(0); { Get screen context }
  2183. Mem := CreateCompatibleDC(Dc); { Compatable context }
  2184. SelectObject(Mem, DefGFVFont); { Select the font }
  2185. {$IFDEF PPC_FPC} { FPC WINDOWS COMPILER }
  2186. GetTextMetrics(Mem, @Tm); { Get text metrics }
  2187. {$ELSE} { OTHER COMPILERS }
  2188. GetTextMetrics(Mem, Tm); { Get text metrics }
  2189. {$ENDIF}
  2190. SysFontWidth := Tm.tmaveCharWidth+1; { Ave char font width }
  2191. SysFontHeight := Tm.tmHeight; { Ave char font height }
  2192. DeleteDc(Mem); { Destroy context }
  2193. ReleaseDc(0, Dc); { Release context }
  2194. {$ENDIF}
  2195. {$IFDEF OS_OS2} { OS2 CODE }
  2196. Ts := WinQuerySysValue(HWND_Desktop,
  2197. SV_CYTitleBar) + 2*WinQuerySysValue(HWND_Desktop,
  2198. SV_CYSizeBorder); { Title size }
  2199. Fs := 2*WinQuerySysValue(HWND_DeskTop,
  2200. SV_CXSizeBorder); { Frame size }
  2201. SysScreenWidth := WinQuerySysValue(HWND_Desktop,
  2202. SV_CXFullScreen) - Fs; { Max screen width }
  2203. SysScreenHeight := WinQuerySysValue(HWND_Desktop,
  2204. SV_CYFullScreen) - Ts; { Max screen height }
  2205. (*With DefGFVFont Do Begin
  2206. usRecordLength := SizeOf(fAttrs); { Structure size }
  2207. fsSelection := $20; { Uses default selection }
  2208. lMatch := 0; { Does not force match }
  2209. idRegistry := 0; { Uses default registry }
  2210. usCodePage := 850; { Code-page 850 }
  2211. If (DefFontHeight = 0) Then Begin { Font height not set }
  2212. lMaxBaselineExt := SysScreenHeight DIV DefLineNum; { Best guess height }
  2213. End Else lMaxBaselineExt := DefFontHeight; { Specific font height }
  2214. lAveCharWidth := 0; { Req font default width }
  2215. fsType := 0; { Uses default type }
  2216. fsFontUse := fAttr_FontUse_Nomix; { Doesn't mix with graphics }
  2217. FillChar(szFaceName, SizeOf(szFaceName), #0); { Clear memory area }
  2218. Move(DefFontStyle[1], szFacename,
  2219. Length(DefFontStyle)); { Transfer style name }
  2220. End;*)
  2221. Ps := WinGetPS(HWND_Desktop); { Get desktop PS }
  2222. (*GpiCreateLogFont(Ps, Nil, 1, DefGFVFont);*) { Create the font }
  2223. GpiQueryFontMetrics(Ps, SizeOf(Tm), Tm); { Get text metrics }
  2224. SysFontWidth := Tm.lAveCharWidth+1; { Transfer font width }
  2225. SysFontHeight := Tm.lMaxBaselineExt; { Transfer font height }
  2226. { SysFontheight := SysScreenheight DIV DefLineNum;}
  2227. WinReleasePS(Ps); { Release desktop PS }
  2228. DefPointer := WinQuerySysPointer(HWND_DESKTOP,
  2229. SPTR_ARROW, False); { Hold default pointer }
  2230. {$ENDIF}
  2231. ScreenWidth := SysScreenWidth DIV SysFontWidth; { Calc screen width }
  2232. ScreenHeight := SysScreenHeight DIV SysFontHeight; { Calc screen height }
  2233. SysScreenWidth := ScreenWidth * SysFontWidth; { Actual width }
  2234. SysScreenHeight := ScreenHeight * SysFontHeight; { Actual height }
  2235. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2236. Inc(SysScreenWidth, 2*GetSystemMetrics(SM_CXFrame)); { Max screen width }
  2237. Inc(SysScreenHeight, GetSystemMetrics(SM_CYCaption)
  2238. + GetSystemMetrics(SM_CYFrame)); { Max screen height }
  2239. {$ENDIF}
  2240. {$IFDEF OS_OS2} { OS2 CODE }
  2241. Inc(SysScreenWidth, Fs); { Max screen width }
  2242. Inc(SysScreenHeight, Ts); { Max screen height }
  2243. {$ENDIF}
  2244. END;
  2245. {---------------------------------------------------------------------------}
  2246. { DoneVideo -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 19May98 LdB }
  2247. {---------------------------------------------------------------------------}
  2248. PROCEDURE DoneVideo;
  2249. BEGIN
  2250. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2251. {$IFDEF PPC_FPC}
  2252. MouseMoveProc := Nil; { Clr mouse move ptr }
  2253. ShowMouseProc := Nil; { Clr show mouse ptr }
  2254. HideMouseProc := Nil; { Clr hide mouse ptr }
  2255. UnLock_Code(Pointer(@ShowTheMouse), 400); { Unlock cursor code }
  2256. {$ENDIF}
  2257. CloseGraph; { Close down graphics }
  2258. {$ENDIF}
  2259. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2260. If (DefGFVFont <> 0) Then { Check font created }
  2261. DeleteObject(DefGFVFont); { Delete the font }
  2262. {$ENDIF}
  2263. END;
  2264. {---------------------------------------------------------------------------}
  2265. { ClearScreen -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 04Jan97 LdB }
  2266. {---------------------------------------------------------------------------}
  2267. PROCEDURE ClearScreen;
  2268. BEGIN
  2269. END;
  2270. {---------------------------------------------------------------------------}
  2271. { SetVideoMode -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 10Nov99 LdB }
  2272. {---------------------------------------------------------------------------}
  2273. PROCEDURE SetVideoMode (Mode: Word);
  2274. BEGIN
  2275. If (Mode > $100) Then DefLineNum := 50 { 50 line mode request }
  2276. Else DefLineNum := 24; { Normal 24 line mode }
  2277. END;
  2278. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2279. { ERROR CONTROL ROUTINES }
  2280. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2281. {---------------------------------------------------------------------------}
  2282. { InitSysError -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 20May98 LdB }
  2283. {---------------------------------------------------------------------------}
  2284. PROCEDURE InitSysError;
  2285. BEGIN
  2286. SysErrActive := True; { Set active flag }
  2287. END;
  2288. {---------------------------------------------------------------------------}
  2289. { DoneSysError -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 20May98 LdB }
  2290. {---------------------------------------------------------------------------}
  2291. PROCEDURE DoneSysError;
  2292. BEGIN
  2293. SysErrActive := False; { Clear active flag }
  2294. END;
  2295. {---------------------------------------------------------------------------}
  2296. { SystemError -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 20May98 LdB }
  2297. {---------------------------------------------------------------------------}
  2298. FUNCTION SystemError (ErrorCode: Integer; Drive: Byte): Integer;
  2299. BEGIN
  2300. If (FailSysErrors = False) Then Begin { Check error ignore }
  2301. End Else SystemError := 1; { Return 1 for ignored }
  2302. END;
  2303. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2304. { STRING FORMAT ROUTINES }
  2305. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2306. {---------------------------------------------------------------------------}
  2307. { PrintStr -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 18Feb99 LdB }
  2308. {---------------------------------------------------------------------------}
  2309. PROCEDURE PrintStr (CONST S: String);
  2310. {$IFNDEF OS_DOS} VAR Ts: String; {$ENDIF}
  2311. BEGIN
  2312. {$IFDEF OS_DOS} { DOS/DPMI CODE }
  2313. Write(S); { Write to screen }
  2314. {$ENDIF}
  2315. {$IFDEF OS_WINDOWS} { WIN/NT CODE }
  2316. Ts := S + #0; { Make asciiz }
  2317. {$IFNDEF PPC_SPEED} { NON SPEED COMPILER }
  2318. MessageBox(0, @Ts[1], Nil, mb_Ok OR mb_IconStop);{ Display to screen }
  2319. {$ELSE} { SYBIL 2+ COMPILER }
  2320. MessageBox(0, CString(@Ts[1]), Nil, mb_Ok OR
  2321. mb_IconStop); { Display to screen }
  2322. {$ENDIF}
  2323. {$ENDIF}
  2324. {$IFDEF OS_OS2} { OS2 CODE }
  2325. Ts := S + #0; { Make asciiz }
  2326. WinMessageBox(0, 0, @Ts[1], Nil, mb_Ok OR
  2327. 0, mb_IconHand); { Display to screen }
  2328. {$ENDIF}
  2329. END;
  2330. {---------------------------------------------------------------------------}
  2331. { FormatStr -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 13Jul99 LdB }
  2332. {---------------------------------------------------------------------------}
  2333. PROCEDURE FormatStr (Var Result: String; CONST Format: String; Var Params);
  2334. TYPE TLongArray = Array[0..0] Of LongInt;
  2335. VAR ResultLength, FormatIndex, Justify, Wth: Byte; Fill: Char; S: String;
  2336. FUNCTION LongToStr (L: Longint; Radix: Byte): String;
  2337. CONST HexChars: Array[0..15] Of Char =
  2338. ('0', '1', '2', '3', '4', '5', '6', '7',
  2339. '8', '9', 'A', 'B', 'C', 'D', 'E', 'F');
  2340. VAR I: LongInt; S: String; Sign: String[1];
  2341. BEGIN
  2342. LongToStr := ''; { Preset empty return }
  2343. If (L < 0) Then Begin { If L is negative }
  2344. Sign := '-'; { Sign is negative }
  2345. L := Abs(L); { Convert to positive }
  2346. End Else Sign := ''; { Sign is empty }
  2347. S := ''; { Preset empty string }
  2348. Repeat
  2349. I := L MOD Radix; { Radix mod of value }
  2350. S := HexChars[I] + S; { Add char to string }
  2351. L := L DIV Radix; { Divid by radix }
  2352. Until (L = 0); { Until no remainder }
  2353. LongToStr := Sign + S; { Return result }
  2354. END;
  2355. PROCEDURE HandleParameter (I : LongInt);
  2356. BEGIN
  2357. While (FormatIndex <= Length(Format)) Do Begin { While length valid }
  2358. While (Format[FormatIndex] <> '%') AND { Param char not found }
  2359. (FormatIndex <= Length(Format)) Do Begin { Length still valid }
  2360. Result[ResultLength+1] := Format[FormatIndex]; { Transfer character }
  2361. Inc(ResultLength); { One character added }
  2362. Inc(FormatIndex); { Next param char }
  2363. End;
  2364. If (FormatIndex < Length(Format)) AND { Not last char and }
  2365. (Format[FormatIndex] = '%') Then Begin { '%' char found }
  2366. Fill := ' '; { Default fill char }
  2367. Justify := 0; { Default justify }
  2368. Wth := 0; { Default 0=no width }
  2369. Inc(FormatIndex); { Next character }
  2370. If (Format[FormatIndex] = '0') Then
  2371. Fill := '0'; { Fill char to zero }
  2372. If (Format[FormatIndex] = '-') Then Begin { Optional just char }
  2373. Justify := 1; { Right justify }
  2374. Inc(FormatIndex); { Next character }
  2375. End;
  2376. While ((FormatIndex <= Length(Format)) AND { Length still valid }
  2377. (Format[FormatIndex] >= '0') AND
  2378. (Format[FormatIndex] <= '9')) Do Begin { Numeric character }
  2379. Wth := Wth * 10; { Multiply x10 }
  2380. Wth := Wth + Ord(Format[FormatIndex])-$30; { Add numeric value }
  2381. Inc(FormatIndex); { Next character }
  2382. End;
  2383. If ((FormatIndex <= Length(Format)) AND { Length still valid }
  2384. (Format[FormatIndex] = '#')) Then Begin { Parameter marker }
  2385. Inc(FormatIndex); { Next character }
  2386. HandleParameter(Wth); { Width is param idx }
  2387. End;
  2388. If (FormatIndex <= Length(Format)) Then Begin{ Length still valid }
  2389. Case Format[FormatIndex] Of
  2390. 'c': S := Char(TLongArray(Params)[I]); { Character parameter }
  2391. 'd': S := LongToStr(TLongArray(Params)[I],
  2392. 10); { Decimal parameter }
  2393. 's': S := PString(TLongArray(Params)[I])^;{ String parameter }
  2394. 'x': S := LongToStr(TLongArray(Params)[I],
  2395. 16); { Hex parameter }
  2396. '%': Begin { Literal % }
  2397. S := '%'; { Set string }
  2398. Inc(FormatIndex); { Next character }
  2399. Move(S[1], Result[ResultLength+1], 1); { '%' char to result }
  2400. Inc(ResultLength, Length(S)); { Inc result length }
  2401. Continue; { Now continue }
  2402. End;
  2403. End;
  2404. Inc(I); { Next parameter }
  2405. Inc(FormatIndex); { Next character }
  2406. If (Wth > 0) Then Begin { Width control active }
  2407. If (Length(S) > Wth) Then Begin { We must shorten S }
  2408. If (Justify=1) Then { Check right justify }
  2409. S := Copy(S, Length(S)-Wth+1, Wth) { Take right side data }
  2410. Else S := Copy(S, 1, Wth); { Take left side data }
  2411. End Else Begin { We must pad out S }
  2412. If (Justify=1) Then { Right justify }
  2413. While (Length(S) < Wth) Do
  2414. S := S+Fill Else { Right justify fill }
  2415. While (Length(S) < Wth) Do
  2416. S := Fill + S; { Left justify fill }
  2417. End;
  2418. End;
  2419. Move(S[1], Result[ResultLength+1],
  2420. Length(S)); { Move data to result }
  2421. ResultLength := ResultLength + Length(S); { Adj result length }
  2422. End;
  2423. End;
  2424. End;
  2425. END;
  2426. BEGIN
  2427. ResultLength := 0; { Zero result length }
  2428. FormatIndex := 1; { Format index to 1 }
  2429. HandleParameter(0); { Handle parameter }
  2430. {$IFDEF PPC_DELPHI3} { DELPHI 3+ COMPILER }
  2431. SetLength(Result, ResultLength); { Set string length }
  2432. {$ELSE} { OTHER COMPILERS }
  2433. Result[0] := Chr(ResultLength); { Set string length }
  2434. {$ENDIF}
  2435. END;
  2436. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2437. { NEW QUEUED EVENT HANDLER ROUTINES }
  2438. {+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++}
  2439. {---------------------------------------------------------------------------}
  2440. { PutEventInQueue -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 17Mar98 LdB }
  2441. {---------------------------------------------------------------------------}
  2442. FUNCTION PutEventInQueue (Var Event: TEvent): Boolean;
  2443. BEGIN
  2444. If (QueueCount < QueueMax) Then Begin { Check room in queue }
  2445. Queue[QueueHead] := Event; { Store event }
  2446. Inc(QueueHead); { Inc head position }
  2447. If (QueueHead = QueueMax) Then QueueHead := 0; { Roll to start check }
  2448. Inc(QueueCount); { Inc queue count }
  2449. PutEventInQueue := True; { Return successful }
  2450. End Else PutEventInQueue := False; { Return failure }
  2451. END;
  2452. {---------------------------------------------------------------------------}
  2453. { NextQueuedEvent -> Platforms DOS/DPMI/WIN/NT/OS2 - Updated 17Mar98 LdB }
  2454. {---------------------------------------------------------------------------}
  2455. PROCEDURE NextQueuedEvent(Var Event: TEvent);
  2456. BEGIN
  2457. If (QueueCount > 0) Then Begin { Check queued event }
  2458. Event := Queue[QueueTail]; { Fetch next event }
  2459. Inc(QueueTail); { Inc tail position }
  2460. If (QueueTail = QueueMax) Then QueueTail := 0; { Roll to start check }
  2461. Dec(QueueCount); { Dec queue count }
  2462. End Else Event.What := evNothing; { Return empty event }
  2463. END;
  2464. {***************************************************************************}
  2465. { UNIT INITIALIZATION ROUTINE }
  2466. {***************************************************************************}
  2467. BEGIN
  2468. ButtonCount := DetectMouse; { Detect mouse }
  2469. DetectVideo; { Detect video }
  2470. SaveExit := ExitProc; { Save old exit }
  2471. ExitProc := @ExitDrivers; { Set new exit }
  2472. END.
  2473. {
  2474. $Log$
  2475. Revision 1.2 2000-08-24 12:00:21 marco
  2476. * CVS log and ID tags
  2477. }