Lua_VCL.pas 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720
  1. // ATTENZIONE
  2. // Obsoleta, lasciata per compatibilità finchè non si conclude Lua_Object etc...
  3. //******************************************************************************
  4. //*** LUA SCRIPT FUNCTIONS ***
  5. //*** ***
  6. //*** (c) Massimo Magnano 2005 ***
  7. //*** ***
  8. //*** ***
  9. //******************************************************************************
  10. //*** ***
  11. //*** Unit : Lua_VCL.pas ***
  12. //*** ***
  13. //*** Functions to Get\Set Properties of a Component from Lua Scripts. ***
  14. //*** Register component that can be public using AddPublicComponent, ***
  15. //*** you can add as public "Application" but i think is not a good idea.***
  16. //*** ***
  17. //******************************************************************************
  18. // Exported functions :
  19. //
  20. // GetVCLObject {Name=string} return TObject object.
  21. // TObject:GetProp(string PropName) return Property Value as Variant.
  22. // TObject:SetProp(string PropName, variant Value) set Property Value.
  23. //
  24. // CreateVCLObject {ClassName=string} Create a new TObject object. not yet implemented
  25. // TObject:Free() Free a TObject created with CreateComponent. not yet implemented
  26. //
  27. // GetProp(string FullPropName) return Property Value as Variant.
  28. // SetProp(string FullPropName, variant Value) set Property Value.
  29. unit Lua_VCL;
  30. interface
  31. uses Lua, LuaUtils, Classes;
  32. const
  33. LUAVCL_ACCESS_DENY = 0;
  34. LUAVCL_ACCESS_READ = 1;
  35. LUAVCL_ACCESS_WRITE = 2;
  36. LUAVCL_ACCESS_READWRITE = LUAVCL_ACCESS_READ or LUAVCL_ACCESS_WRITE;
  37. type
  38. TLuaVCLAccess = Integer; //LUAVCL_ACCESS_XXXX Constants
  39. procedure RegisterFunctions(L: Plua_State);
  40. procedure AddPublicComponent(AComponent :TObject;
  41. ALuaName :String;
  42. AccessRights :TLuaVclAccess=LUAVCL_ACCESS_READ);
  43. procedure DelPublicComponent(AComponent :TObject); overload;
  44. procedure DelPublicComponent(ALuaName :String); overload;
  45. procedure AddPublicProperty(AComponent :TObject; APropName :String;
  46. ALuaName :String; AccessRights :TLuaVclAccess);
  47. procedure DelPublicProperty(AComponent :TObject; APropName :String); overload;
  48. procedure DelPublicProperty(ALuaName :String); overload;
  49. function GetPublicPropertyAccess(AComponent :TObject; APropName :String) :TLuaVCLAccess;
  50. procedure SetPublicPropertyAccess(AComponent :TObject; APropName :String;
  51. AccessRights :TLuaVclAccess);
  52. implementation
  53. uses MGList, SysUtils, TypInfo;
  54. const
  55. HandleVCLObjectStr = 'HandleVCLObject';
  56. ERR_Script = 'Script Error : ';
  57. ERR_ACCESS_DENIED = 'Access Denied Property %s.%s';
  58. ERR_UNKNOWN_OBJECT = 'Unknown VCLObject %s';
  59. ERR_UNKNOWN_PROP = 'Unknown Property';
  60. Type
  61. //Classe che mantiene la lista delle associazioni Lua->TObject
  62. TObjectNameData = record
  63. LuaName :String;
  64. AccessRights :TLuaVclAccess;
  65. Component :TObject;
  66. end;
  67. PComponentNameData =^TObjectNameData;
  68. TObjectNameList = class(TMGList)
  69. protected
  70. function allocData :Pointer; override;
  71. procedure deallocData(pData :Pointer); override;
  72. function CompByComponent(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  73. function CompByLuaName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  74. public
  75. function Add(AComponent :TObject;
  76. ALuaName :String; AccessRights :TLuaVclAccess) :PComponentNameData; overload;
  77. function Find(AComponent :TObject): Integer; overload;
  78. function ExtFind(AComponent :TObject): PComponentNameData; overload;
  79. procedure GetAccessRights(AComponent :TObject;
  80. var AccessRights: TLuaVclAccess);
  81. function Find(ALuaName :String): TObject; overload;
  82. function ExtFind(ALuaName :String): PComponentNameData; overload;
  83. function Delete(ALuaName :String) :Boolean; overload;
  84. function Delete(AComponent :TObject) :Boolean; overload;
  85. end;
  86. //Classe che mantiene la lista delle associazioni Lua-> (Component Property)
  87. TPropertyNameData = record
  88. LuaName :String;
  89. AccessRights :TLuaVclAccess;
  90. Component :TObject;
  91. PropName :String;
  92. end;
  93. PPropertyNameData =^TPropertyNameData;
  94. TPropertyNameList = class(TMGList)
  95. protected
  96. function allocData :Pointer; override;
  97. procedure deallocData(pData :Pointer); override;
  98. function CompByCompPropName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  99. function CompByLuaName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  100. public
  101. function Add(AComponent :TObject; APropName :String;
  102. ALuaName :String; AccessRights :TLuaVclAccess) :PPropertyNameData; overload;
  103. function ExtFind(AComponent :TObject; APropName :String): PPropertyNameData; overload;
  104. function ExtFind(ALuaName :String): PPropertyNameData; overload;
  105. function Delete(ALuaName :String) :Boolean; overload;
  106. function Delete(AComponent :TObject; APropName :String) :Boolean; overload;
  107. end;
  108. Var
  109. ComponentNameList : TObjectNameList =Nil;
  110. PropertyNameList : TPropertyNameList =Nil;
  111. procedure ProcessDot(var xFullName, ChildName :String);
  112. Var
  113. xPos :Integer;
  114. begin
  115. xPos :=Pos('.', xFullName);
  116. if (xPos>0)
  117. then begin
  118. ChildName :=Copy(xFullName, 1, xPos-1);
  119. Delete(xFullname, 1, xPos);
  120. end
  121. else begin
  122. ChildName :=xFullName;
  123. xFullName :='';
  124. end;
  125. end;
  126. //==============================================================================
  127. // TObjectNameList Class
  128. //==============================================================================
  129. function TObjectNameList.allocData :Pointer;
  130. begin
  131. GetMem(Result, SizeOf(TObjectNameData));
  132. FillChar(PComponentNameData(Result)^, SizeOf(TObjectNameData), 0);
  133. PComponentNameData(Result)^.LuaName :='';
  134. end;
  135. procedure TObjectNameList.deallocData(pData :Pointer);
  136. begin
  137. PComponentNameData(pData)^.LuaName :='';
  138. FreeMem(pData, SizeOf(TObjectNameData));
  139. end;
  140. function TObjectNameList.CompByComponent(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  141. begin
  142. Result := (TObject(ptData1)=PComponentNameData(ptData2)^.Component);
  143. end;
  144. function TObjectNameList.CompByLuaName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  145. begin
  146. Result := (PChar(ptData1)=PComponentNameData(ptData2)^.LuaName);
  147. end;
  148. function TObjectNameList.Add(AComponent :TObject;
  149. ALuaName :String; AccessRights :TLuaVclAccess) :PComponentNameData;
  150. begin
  151. if (ALuaName<>'')
  152. then Result :=ExtFind(ALuaName)
  153. else Result :=ExtFind(AComponent);
  154. if (Result=Nil)
  155. then Result :=Add;
  156. if (Result<>Nil)
  157. then begin
  158. Result^.Component :=AComponent;
  159. if (ALuaName<>'')
  160. then Result^.LuaName :=Uppercase(ALuaName);
  161. Result^.AccessRights :=AccessRights;
  162. end;
  163. end;
  164. function TObjectNameList.Find(AComponent :TObject): Integer;
  165. begin
  166. Result :=Find(Pointer(AComponent), 0, CompByComponent);
  167. end;
  168. function TObjectNameList.ExtFind(AComponent :TObject): PComponentNameData;
  169. begin
  170. if (AComponent<>Nil)
  171. then Result :=ExtFind(Pointer(AComponent), 0, CompByComponent)
  172. else Result :=Nil;
  173. end;
  174. function TObjectNameList.Find(ALuaName :String): TObject;
  175. Var
  176. theComp :PComponentNameData;
  177. begin
  178. Result := Nil;
  179. theComp := ExtFind(ALuaName);
  180. if (theComp<>Nil)
  181. then Result := theComp^.Component;
  182. end;
  183. function TObjectNameList.ExtFind(ALuaName :String): PComponentNameData;
  184. begin
  185. Result :=ExtFind(PChar(Uppercase(ALuaName)), 0, CompByLuaName);
  186. end;
  187. function TObjectNameList.Delete(AComponent :TObject) :Boolean;
  188. begin
  189. Result :=Delete(Pointer(AComponent), 0, CompByComponent);
  190. end;
  191. function TObjectNameList.Delete(ALuaName :String) :Boolean;
  192. begin
  193. Result :=Delete(PChar(Uppercase(ALuaName)), 0, CompByLuaName);
  194. end;
  195. procedure TObjectNameList.GetAccessRights(AComponent :TObject;
  196. var AccessRights: TLuaVclAccess);
  197. Var
  198. xCompAccess :PComponentNameData;
  199. begin
  200. xCompAccess :=Self.ExtFind(AComponent);
  201. if (xCompAccess<>Nil)
  202. then AccessRights :=xCompAccess^.AccessRights;
  203. end;
  204. //==============================================================================
  205. // Components Registration\Deregistration
  206. //==============================================================================
  207. procedure AddPublicComponent(AComponent :TObject;
  208. ALuaName :String;
  209. AccessRights :TLuaVclAccess=LUAVCL_ACCESS_READ);
  210. begin
  211. if (ComponentNameList=Nil)
  212. then ComponentNameList := TObjectNameList.Create;
  213. ComponentNameList.Add(AComponent, ALuaName, AccessRights);
  214. end;
  215. procedure DelPublicComponent(AComponent :TObject);
  216. begin
  217. if (ComponentNameList<>Nil)
  218. then begin
  219. ComponentNameList.Delete(AComponent);
  220. if (ComponentNameList.Count=0)
  221. then begin
  222. ComponentNameList.Free;
  223. ComponentNameList :=Nil;
  224. end;
  225. end;
  226. end;
  227. procedure DelPublicComponent(ALuaName :String); overload;
  228. begin
  229. if (ComponentNameList<>Nil)
  230. then begin
  231. ComponentNameList.Delete(ALuaName);
  232. if (ComponentNameList.Count=0)
  233. then begin
  234. ComponentNameList.Free;
  235. ComponentNameList :=Nil;
  236. end;
  237. end;
  238. end;
  239. //==============================================================================
  240. // TPropertyNameList Class
  241. //==============================================================================
  242. function TPropertyNameList.allocData :Pointer;
  243. begin
  244. GetMem(Result, SizeOf(TPropertyNameData));
  245. FillChar(PPropertyNameData(Result)^, SizeOf(TPropertyNameData), 0);
  246. PPropertyNameData(Result)^.PropName :='';
  247. PPropertyNameData(Result)^.LuaName :='';
  248. end;
  249. procedure TPropertyNameList.deallocData(pData :Pointer);
  250. begin
  251. PPropertyNameData(pData)^.PropName :='';
  252. PPropertyNameData(pData)^.LuaName :='';
  253. FreeMem(pData, SizeOf(TPropertyNameData));
  254. end;
  255. function TPropertyNameList.CompByCompPropName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  256. begin
  257. Result := (PPropertyNameData(ptData1)^.Component=PPropertyNameData(ptData2)^.Component) and
  258. (PPropertyNameData(ptData1)^.PropName=PPropertyNameData(ptData2)^.PropName);
  259. end;
  260. function TPropertyNameList.CompByLuaName(Tag :Integer; ptData1, ptData2 :Pointer) :Boolean;
  261. begin
  262. Result := (PChar(ptData1)=PPropertyNameData(ptData2)^.LuaName);
  263. end;
  264. function TPropertyNameList.Add(AComponent :TObject; APropName :String;
  265. ALuaName :String; AccessRights :TLuaVclAccess) :PPropertyNameData;
  266. begin
  267. Result :=ExtFind(AComponent, APropName);
  268. if (Result=Nil)
  269. then Result :=Add;
  270. if (Result<>Nil)
  271. then begin
  272. Result^.Component :=AComponent;
  273. Result^.PropName :=Uppercase(APropName);
  274. Result^.LuaName :=Uppercase(ALuaName);
  275. Result^.AccessRights :=AccessRights;
  276. end;
  277. end;
  278. function TPropertyNameList.ExtFind(AComponent :TObject; APropName :String): PPropertyNameData;
  279. Var
  280. aux :PPropertyNameData;
  281. begin
  282. if (AComponent<>Nil)
  283. then begin
  284. aux :=allocData;
  285. aux^.Component :=AComponent;
  286. aux^.PropName :=Uppercase(APropName);
  287. Result :=ExtFind(aux, 0, CompByCompPropName);
  288. deallocData(aux);
  289. end
  290. else Result :=Nil;
  291. end;
  292. function TPropertyNameList.ExtFind(ALuaName :String): PPropertyNameData;
  293. begin
  294. Result :=ExtFind(PChar(Uppercase(ALuaName)), 0, CompByLuaName);
  295. end;
  296. function TPropertyNameList.Delete(ALuaName :String) :Boolean;
  297. begin
  298. Result :=Delete(PChar(Uppercase(ALuaName)), 0, CompByLuaName);
  299. end;
  300. function TPropertyNameList.Delete(AComponent :TObject; APropName :String) :Boolean;
  301. Var
  302. aux :PPropertyNameData;
  303. begin
  304. aux :=allocData;
  305. aux^.Component :=AComponent;
  306. aux^.PropName :=Uppercase(APropName);
  307. Result :=Delete(aux, 0, CompByCompPropName);
  308. deallocData(aux);
  309. end;
  310. //==============================================================================
  311. // Properties Registration\Deregistration, AccessRights
  312. //==============================================================================
  313. procedure AddPublicProperty(AComponent :TObject; APropName :String;
  314. ALuaName :String; AccessRights :TLuaVclAccess);
  315. begin
  316. if (PropertyNameList=Nil)
  317. then PropertyNameList := TPropertyNameList.Create;
  318. PropertyNameList.Add(AComponent, APropName, ALuaName, AccessRights);
  319. end;
  320. procedure DelPublicProperty(AComponent :TObject; APropName :String); overload;
  321. begin
  322. if (PropertyNameList<>Nil)
  323. then begin
  324. PropertyNameList.Delete(AComponent, APropName);
  325. if (PropertyNameList.Count=0)
  326. then begin
  327. PropertyNameList.Free;
  328. PropertyNameList :=Nil;
  329. end;
  330. end;
  331. end;
  332. procedure DelPublicProperty(ALuaName :String); overload;
  333. begin
  334. if (PropertyNameList<>Nil)
  335. then begin
  336. PropertyNameList.Delete(ALuaName);
  337. if (PropertyNameList.Count=0)
  338. then begin
  339. PropertyNameList.Free;
  340. PropertyNameList :=Nil;
  341. end;
  342. end;
  343. end;
  344. function GetPublicPropertyAccess(AComponent :TObject; APropName :String) :TLuaVCLAccess;
  345. Var
  346. xProp :PPropertyNameData;
  347. xComp :PComponentNameData;
  348. begin
  349. Result :=LUAVCL_ACCESS_DENY;
  350. xProp :=Nil;
  351. if (AComponent=Nil)
  352. then Exit;
  353. //Find Property AccessRights for this property
  354. if (APropName<>'') and (PropertyNameList<>Nil)
  355. then begin
  356. xProp :=PropertyNameList.ExtFind(AComponent, APropName);
  357. if (xProp<>Nil)
  358. then Result :=xProp^.AccessRights;
  359. end;
  360. if (xProp=Nil) and (ComponentNameList<>Nil)
  361. then begin
  362. //If not Find Property AccessRights for this property, Try with it's component
  363. xComp :=ComponentNameList.ExtFind(AComponent);
  364. if (xComp<>Nil)
  365. then Result :=xComp^.AccessRights;
  366. end;
  367. end;
  368. procedure SetPublicPropertyAccess(AComponent :TObject; APropName :String;
  369. AccessRights :TLuaVclAccess);
  370. begin
  371. AddPublicProperty(AComponent, APropName, APropName, AccessRights);
  372. end;
  373. //==============================================================================
  374. // Lua Interface : Components Property
  375. //==============================================================================
  376. function GetComponentByFullPath(FullCompName: String;
  377. var AccessRights :TLuaVCLAccess):TObject;
  378. Var
  379. xNewParent :TObject;
  380. xParent :TObject;
  381. xFullName,
  382. ChildName :String;
  383. xCompAccess :PComponentNameData;
  384. begin
  385. xFullName :=FullCompName;
  386. AccessRights :=LUAVCL_ACCESS_DENY;
  387. ProcessDot(xFullName, ChildName);
  388. xCompAccess :=ComponentNameList.ExtFind(ChildName);
  389. if (xCompAccess<>Nil)
  390. then begin
  391. xParent :=xCompAccess^.Component;
  392. AccessRights :=xCompAccess^.AccessRights;
  393. end
  394. else xParent :=Nil;
  395. while (xParent<>Nil) and (xFullName<>'') do
  396. begin
  397. try
  398. xNewParent :=Nil;
  399. ProcessDot(xFullName, ChildName);
  400. //Try find in Components
  401. if (xParent is TComponent)
  402. then xNewParent :=TComponent(xParent).FindComponent(ChildName);
  403. if (xNewParent=Nil)
  404. then begin //Try find in Class Properties
  405. if (PropType(xParent, ChildName)=tkClass)
  406. then xNewParent :=TObject(GetOrdProp(xParent, ChildName));
  407. end;
  408. xCompAccess :=ComponentNameList.ExtFind(xNewParent);
  409. if (xCompAccess<>Nil)
  410. then AccessRights :=xCompAccess^.AccessRights;
  411. xParent :=xNewParent;
  412. except
  413. xParent :=Nil;
  414. end;
  415. end;
  416. Result :=xParent;
  417. end;
  418. function GetPropertyByFullPath(FullPropName: String;
  419. var ResultComponent :TObject;
  420. var AccessRights :TLuaVCLAccess):String;
  421. Var
  422. xNewParent :TObject;
  423. xPropType :TTypeKind;
  424. xFullName,
  425. ChildName :String;
  426. xCompAccess :PComponentNameData;
  427. xPropAccess :PPropertyNameData;
  428. begin
  429. Result :='';
  430. xFullName :=FullPropName;
  431. xPropType :=tkUnknown;
  432. if (ResultComponent=Nil)
  433. then begin
  434. //No Parent Object specified, Find from Name
  435. ProcessDot(xFullName, ChildName);
  436. xCompAccess :=ComponentNameList.ExtFind(ChildName);
  437. if (xCompAccess<>Nil)
  438. then begin
  439. ResultComponent :=xCompAccess^.Component; //Convert possible Alias
  440. if (ResultComponent<>Nil)
  441. then xPropType :=tkClass;
  442. AccessRights :=xCompAccess^.AccessRights;
  443. end;
  444. end
  445. else xPropType :=tkClass; //If Parent specified AccessRights is controlled by GetVCLObject
  446. while (ResultComponent<>Nil) and (xPropType=tkClass) do
  447. begin
  448. try
  449. xNewParent :=Nil;
  450. ProcessDot(xFullName, ChildName);
  451. //Try find in Components
  452. if (ResultComponent is TComponent)
  453. then begin
  454. xNewParent :=TComponent(ResultComponent).FindComponent(ChildName);
  455. if (xNewParent<>Nil)
  456. then xPropType :=tkClass;
  457. end;
  458. if (xNewParent=Nil)
  459. then begin //Try find in Class Properties
  460. xPropType :=PropType(ResultComponent, ChildName);
  461. if (xPropType=tkClass)
  462. then xNewParent :=TObject(GetOrdProp(ResultComponent, ChildName));
  463. end;
  464. if (xPropType=tkClass)
  465. then begin
  466. //Search if exists AccessRights for this Class
  467. xCompAccess :=ComponentNameList.ExtFind(xNewParent);
  468. if (xCompAccess<>Nil)
  469. then AccessRights :=xCompAccess^.AccessRights;
  470. ResultComponent :=xNewParent;
  471. end;
  472. except
  473. ResultComponent :=Nil;
  474. end;
  475. end;
  476. if (ResultComponent<>Nil) and (xPropType<>tkClass) and (Pos('.', ChildName)=0)
  477. then begin
  478. Result :=ChildName;
  479. //Get Property AccessRights if Any
  480. xPropAccess :=PropertyNameList.ExtFind(ResultComponent, ChildName);
  481. if (xPropAccess<>Nil)
  482. then AccessRights :=xPropAccess^.AccessRights;
  483. end
  484. else begin
  485. Result :='';
  486. ResultComponent :=Nil;
  487. end;
  488. end;
  489. function LuaToTObject(L: Plua_State; Index: Integer): TObject;
  490. begin
  491. try
  492. Result :=TObject(LuaGetTableLightUserData(L, Index, HandleVCLObjectStr));
  493. except
  494. Result :=Nil;
  495. end;
  496. end;
  497. function LuaToPropertyName(L: Plua_State;
  498. var Index: Integer;
  499. var ResultComponent :TObject;
  500. var AccessRights :TLuaVCLAccess):String;
  501. begin
  502. Result :='';
  503. ResultComponent :=Nil;
  504. AccessRights :=LUAVCL_ACCESS_DENY;
  505. Index :=1;
  506. if lua_istable(L, Index)
  507. then begin
  508. //The First parameter is a TObject Table,
  509. // Property specified in the 2nd parameter start from this Class
  510. ResultComponent := LuaToTObject(L, Index);
  511. ComponentNameList.GetAccessRights(ResultComponent, AccessRights);
  512. Inc(Index); //Property is the 2nd parameter
  513. if (ResultComponent=Nil) or
  514. (AccessRights=LUAVCL_ACCESS_DENY)
  515. then Exit; //Invalid Object or no Access
  516. end;
  517. if (lua_isString(L, Index)<>0)
  518. then begin
  519. Result := GetPropertyByFullPath(LuaToString(L, Index),
  520. ResultComponent,
  521. AccessRights);
  522. Inc(Index);
  523. end;
  524. end;
  525. // TObject:GetProp(string PropName) return Property Value as Variant.
  526. // GetProp(string FullPropName) return Property Value as Variant.
  527. function LuaGetProp(L: Plua_State): Integer; cdecl;
  528. Var
  529. curComponent :TObject;
  530. PropName :String;
  531. PropValue :Variant;
  532. PropRights :TLuaVCLAccess;
  533. Index :Integer;
  534. begin
  535. Result := 1;
  536. try
  537. PropName := LuaToPropertyName(L, Index, curComponent, PropRights);
  538. if (PropName='') or (curComponent=Nil)
  539. then raise Exception.Create(ERR_UNKNOWN_PROP);
  540. if ((PropRights and LUAVCL_ACCESS_READ)<>0)
  541. then begin
  542. PropValue :=GetPropValue(curComponent, PropName);
  543. LuaPushVariant(L, PropValue);
  544. end
  545. else raise Exception.CreateFmt(ERR_ACCESS_DENIED, [curComponent.ClassName, PropName]);
  546. except
  547. On E:Exception do begin
  548. LuaError(L, ERR_Script+E.Message);
  549. Result :=0;
  550. end;
  551. end;
  552. end;
  553. // TObject:SetProp(string PropName, variant Value) set Property Value.
  554. // SetProp(string FullPropName, variant Value) set Property Value.
  555. function LuaSetProp(L: Plua_State): Integer; cdecl;
  556. Var
  557. curComponent :TObject;
  558. PropName :String;
  559. PropValue :Variant;
  560. PropRights :TLuaVCLAccess;
  561. Index :Integer;
  562. begin
  563. Result := 0;
  564. try
  565. PropName := LuaToPropertyName(L, Index, curComponent, PropRights);
  566. if (PropName='') or (curComponent=Nil)
  567. then raise Exception.Create(ERR_UNKNOWN_PROP);
  568. if ((PropRights and LUAVCL_ACCESS_WRITE)<>0)
  569. then begin
  570. PropValue :=LuaToVariant(L, Index);
  571. SetPropValue(curComponent, PropName, PropValue);
  572. end
  573. else raise Exception.CreateFmt(ERR_ACCESS_DENIED, [curComponent.ClassName, PropName]);
  574. except
  575. On E:Exception do begin
  576. LuaError(L, ERR_Script+E.Message);
  577. Result :=0;
  578. end;
  579. end;
  580. end;
  581. function LuaGetVCLObject(L: Plua_State): Integer; cdecl;
  582. Var
  583. ComponentName :String;
  584. xResult :TObject;
  585. AccessRights :TLuaVCLAccess;
  586. begin
  587. Result := 1;
  588. try
  589. ComponentName :=LuaGetTableString(L, 1, 'Name');
  590. LuaSetTableNil(L, 1, 'Name');
  591. xResult := GetComponentByFullPath(ComponentName, AccessRights);
  592. if (xResult=Nil) or (AccessRights=0)
  593. then raise Exception.CreateFmt(ERR_UNKNOWN_OBJECT, [ComponentName]);
  594. LuaSetTableLightUserData(L, 1, HandleVCLObjectStr, xResult);
  595. LuaSetTableFunction(L, 1, 'GetProp', LuaGetProp);
  596. LuaSetTableFunction(L, 1, 'SetProp', LuaSetProp);
  597. except
  598. On E:Exception do begin
  599. LuaError(L, ERR_Script+E.Message);
  600. Result :=0;
  601. end;
  602. end;
  603. end;
  604. procedure RegisterFunctions(L: plua_State);
  605. begin
  606. LuaRegister(L, 'GetVCLObject', LuaGetVCLObject);
  607. LuaRegister(L, 'GetProp', LuaGetProp);
  608. LuaRegister(L, 'SetProp', LuaSetProp);
  609. end;
  610. end.