Element.cpp 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619
  1. #include "LuaType.h"
  2. #include "precompiled.h"
  3. #include "Element.h"
  4. #include <ElementStyle.h>
  5. #include "LuaEventListener.h"
  6. namespace Rocket {
  7. namespace Core {
  8. namespace Lua {
  9. typedef ElementDocument Document;
  10. //methods
  11. int ElementAddEventListener(lua_State* L, Element* obj)
  12. {
  13. int top = lua_gettop(L);
  14. bool capture;
  15. //default false if they didn't pass it in
  16. if (top < 3) capture = false;
  17. else capture = CHECK_BOOL(L,3);
  18. const char* event = luaL_checkstring(L,1);
  19. LuaEventListener* listener = NULL;
  20. int type = lua_type(L,2);
  21. if(type == LUA_TFUNCTION)
  22. {
  23. lua_pushvalue(L,2);
  24. int ref = lua_ref(L,true);
  25. listener = new LuaEventListener(ref,obj);
  26. }
  27. else if(type == LUA_TSTRING)
  28. {
  29. const char* code = luaL_checkstring(L,2);
  30. listener = new LuaEventListener(code,obj);
  31. }
  32. if(listener != NULL)
  33. {
  34. obj->AddEventListener(event,listener,capture);
  35. }
  36. return 0;
  37. }
  38. int ElementAppendChild(lua_State* L, Element* obj)
  39. {
  40. Element* ele = LuaType<Element>::check(L,1);
  41. obj->AppendChild(ele);
  42. return 0;
  43. }
  44. int ElementBlur(lua_State* L, Element* obj)
  45. {
  46. obj->Blur();
  47. return 0;
  48. }
  49. int ElementClick(lua_State* L, Element* obj)
  50. {
  51. obj->Click();
  52. return 0;
  53. }
  54. int ElementDispatchEvent(lua_State* L, Element* obj)
  55. {
  56. const char* event = luaL_checkstring(L,1);
  57. Dictionary params;
  58. lua_pushnil(L); //becauase lua_next pops a key from the stack first, we don't want to pop the table
  59. while(lua_next(L,2) != 0)
  60. {
  61. //[-1] is value, [-2] is key
  62. int type = lua_type(L,-1);
  63. const char* key = luaL_checkstring(L,-2); //key HAS to be a string, or things will go bad
  64. switch(type)
  65. {
  66. case LUA_TNUMBER:
  67. params.Set(key,(float)lua_tonumber(L,-1));
  68. break;
  69. case LUA_TBOOLEAN:
  70. params.Set(key,CHECK_BOOL(L,-1));
  71. break;
  72. case LUA_TSTRING:
  73. params.Set(key,luaL_checkstring(L,-1));
  74. break;
  75. case LUA_TUSERDATA:
  76. case LUA_TLIGHTUSERDATA:
  77. params.Set(key,lua_touserdata(L,-1));
  78. break;
  79. default:
  80. break;
  81. }
  82. }
  83. obj->DispatchEvent(event,params,false);
  84. return 0;
  85. }
  86. int ElementFocus(lua_State* L, Element* obj)
  87. {
  88. obj->Focus();
  89. return 0;
  90. }
  91. int ElementGetAttribute(lua_State* L, Element* obj)
  92. {
  93. const char* name = luaL_checkstring(L,1);
  94. Variant* var = obj->GetAttribute(name);
  95. Variant::Type type = var->GetType();
  96. switch(type)
  97. {
  98. case Variant::BYTE:
  99. case Variant::CHAR:
  100. case Variant::INT:
  101. lua_pushinteger(L,*(int*)var);
  102. break;
  103. case Variant::FLOAT:
  104. lua_pushnumber(L,*(float*)var);
  105. break;
  106. case Variant::COLOURB:
  107. LuaType<Colourb>::push(L,(Colourb*)var,false);
  108. break;
  109. case Variant::COLOURF:
  110. LuaType<Colourf>::push(L,(Colourf*)var,false);
  111. break;
  112. case Variant::STRING:
  113. lua_pushstring(L,((String*)var)->CString());
  114. break;
  115. case Variant::VECTOR2:
  116. //according to Variant.inl, it is going to be a Vector2f
  117. LuaType<Vector2f>::push(L,((Vector2f*)var),false);
  118. break;
  119. case Variant::VOIDPTR:
  120. lua_pushlightuserdata(L,(void*)var);
  121. break;
  122. default:
  123. lua_pushnil(L);
  124. break;
  125. }
  126. return 1;
  127. }
  128. int ElementGetElementById(lua_State* L, Element* obj)
  129. {
  130. const char* id = luaL_checkstring(L,1);
  131. Element* ele = obj->GetElementById(id);
  132. LuaType<Element>::push(L,ele,false);
  133. return 1;
  134. }
  135. int ElementGetElementsByTagName(lua_State* L, Element* obj)
  136. {
  137. const char* tag = luaL_checkstring(L,1);
  138. ElementList list;
  139. obj->GetElementsByTagName(list,tag);
  140. lua_newtable(L);
  141. for(unsigned int i = 0; i < list.size(); i++)
  142. {
  143. lua_pushinteger(L,i);
  144. LuaType<Element>::push(L,list[i],false);
  145. lua_settable(L,-3); //-3 is the table
  146. }
  147. return 1;
  148. }
  149. int ElementHasAttribute(lua_State* L, Element* obj)
  150. {
  151. const char* name = luaL_checkstring(L,1);
  152. lua_pushboolean(L,obj->HasAttribute(name));
  153. return 1;
  154. }
  155. int ElementHasChildNodes(lua_State* L, Element* obj)
  156. {
  157. lua_pushboolean(L,obj->HasChildNodes());
  158. return 1;
  159. }
  160. int ElementInsertBefore(lua_State* L, Element* obj)
  161. {
  162. Element* element = LuaType<Element>::check(L,1);
  163. Element* adjacent = LuaType<Element>::check(L,2);
  164. obj->InsertBefore(element,adjacent);
  165. return 0;
  166. }
  167. int ElementIsClassSet(lua_State* L, Element* obj)
  168. {
  169. const char* name = luaL_checkstring(L,1);
  170. lua_pushboolean(L,obj->IsClassSet(name));
  171. return 1;
  172. }
  173. int ElementRemoveAttribute(lua_State* L, Element* obj)
  174. {
  175. const char* name = luaL_checkstring(L,1);
  176. obj->RemoveAttribute(name);
  177. return 0;
  178. }
  179. int ElementRemoveChild(lua_State* L, Element* obj)
  180. {
  181. Element* element = LuaType<Element>::check(L,1);
  182. lua_pushboolean(L,obj->RemoveChild(element));
  183. return 1;
  184. }
  185. int ElementReplaceChild(lua_State* L, Element* obj)
  186. {
  187. Element* inserted = LuaType<Element>::check(L,1);
  188. Element* replaced = LuaType<Element>::check(L,2);
  189. lua_pushboolean(L,obj->ReplaceChild(inserted,replaced));
  190. return 1;
  191. }
  192. int ElementScrollIntoView(lua_State* L, Element* obj)
  193. {
  194. bool align = CHECK_BOOL(L,1);
  195. obj->ScrollIntoView(align);
  196. return 0;
  197. }
  198. int ElementSetAttribute(lua_State* L, Element* obj)
  199. {
  200. LUACHECKOBJ(obj);
  201. const char* name = luaL_checkstring(L,1);
  202. const char* value = luaL_checkstring(L,2);
  203. obj->SetAttribute(name,String(value));
  204. return 0;
  205. }
  206. int ElementSetClass(lua_State* L, Element* obj)
  207. {
  208. const char* name = luaL_checkstring(L,1);
  209. bool value = CHECK_BOOL(L,2);
  210. obj->SetClass(name,value);
  211. return 0;
  212. }
  213. //getters
  214. int ElementGetAttrattributes(lua_State* L)
  215. {
  216. Element* ele = LuaType<Element>::check(L,1);
  217. int index;
  218. String key;
  219. Variant* var;
  220. Variant::Type type;
  221. lua_newtable(L);
  222. while(ele->IterateAttributes(index,key,var))
  223. {
  224. lua_pushstring(L,key.CString());
  225. type = var->GetType();
  226. switch(type)
  227. {
  228. case Variant::BYTE:
  229. case Variant::CHAR:
  230. case Variant::INT:
  231. lua_pushinteger(L,*(int*)var);
  232. break;
  233. case Variant::FLOAT:
  234. lua_pushnumber(L,*(float*)var);
  235. break;
  236. case Variant::COLOURB:
  237. LuaType<Colourb>::push(L,(Colourb*)var,false);
  238. break;
  239. case Variant::COLOURF:
  240. LuaType<Colourf>::push(L,(Colourf*)var,false);
  241. break;
  242. case Variant::STRING:
  243. lua_pushstring(L,((String*)var)->CString());
  244. break;
  245. case Variant::VECTOR2:
  246. //according to Variant.inl, it is going to be a Vector2f
  247. LuaType<Vector2f>::push(L,((Vector2f*)var),false);
  248. break;
  249. case Variant::VOIDPTR:
  250. lua_pushlightuserdata(L,(void*)var);
  251. break;
  252. default:
  253. lua_pushnil(L);
  254. break;
  255. }
  256. lua_settable(L,-3);
  257. }
  258. return 1;
  259. }
  260. int ElementGetAttrchild_nodes(lua_State* L)
  261. {
  262. Element* ele = LuaType<Element>::check(L,1);
  263. if(!ele->HasChildNodes())
  264. lua_pushnil(L);
  265. else
  266. {
  267. lua_newtable(L);
  268. int index = 0;
  269. int num_of_children = ele->GetNumChildren();
  270. while(index < num_of_children)
  271. {
  272. lua_pushinteger(L,index);
  273. LuaType<Element>::push(L,ele->GetChild(index),false);
  274. lua_settable(L,-3);
  275. ++index;
  276. }
  277. }
  278. return 1;
  279. }
  280. int ElementGetAttrclass_name(lua_State* L)
  281. {
  282. Element* ele = LuaType<Element>::check(L,1);
  283. const char* classnames = ele->GetClassNames().CString();
  284. lua_pushstring(L,classnames);
  285. return 1;
  286. }
  287. int ElementGetAttrclient_left(lua_State* L)
  288. {
  289. Element* ele = LuaType<Element>::check(L,1);
  290. lua_pushnumber(L,ele->GetClientLeft());
  291. return 1;
  292. }
  293. int ElementGetAttrclient_height(lua_State* L)
  294. {
  295. Element* ele = LuaType<Element>::check(L,1);
  296. lua_pushnumber(L,ele->GetClientHeight());
  297. return 1;
  298. }
  299. int ElementGetAttrclient_top(lua_State* L)
  300. {
  301. Element* ele = LuaType<Element>::check(L,1);
  302. lua_pushnumber(L,ele->GetClientTop());
  303. return 1;
  304. }
  305. int ElementGetAttrclient_width(lua_State* L)
  306. {
  307. Element* ele = LuaType<Element>::check(L,1);
  308. lua_pushnumber(L,ele->GetClientWidth());
  309. return 1;
  310. }
  311. int ElementGetAttrfirst_child(lua_State* L)
  312. {
  313. Element* ele = LuaType<Element>::check(L,1);
  314. Element* child = ele->GetFirstChild();
  315. if(child == NULL)
  316. lua_pushnil(L);
  317. else
  318. LuaType<Element>::push(L,child,false);
  319. return 1;
  320. }
  321. int ElementGetAttrid(lua_State* L)
  322. {
  323. Element* ele = LuaType<Element>::check(L,1);
  324. lua_pushstring(L,ele->GetId().CString());
  325. return 1;
  326. }
  327. int ElementGetAttrinner_rml(lua_State* L)
  328. {
  329. Element* ele = LuaType<Element>::check(L,1);
  330. lua_pushstring(L,ele->GetInnerRML().CString());
  331. return 1;
  332. }
  333. int ElementGetAttrlast_child(lua_State* L)
  334. {
  335. Element* ele = LuaType<Element>::check(L,1);
  336. Element* child = ele->GetLastChild();
  337. if(child == NULL)
  338. lua_pushnil(L);
  339. else
  340. LuaType<Element>::push(L,child,false);
  341. return 1;
  342. }
  343. int ElementGetAttrnext_sibling(lua_State* L)
  344. {
  345. Element* ele = LuaType<Element>::check(L,1);
  346. Element* sibling = ele->GetNextSibling();
  347. if(sibling == NULL)
  348. lua_pushnil(L);
  349. else
  350. LuaType<Element>::push(L,sibling,false);
  351. return 1;
  352. }
  353. int ElementGetAttroffset_height(lua_State* L)
  354. {
  355. Element* ele = LuaType<Element>::check(L,1);
  356. lua_pushnumber(L,ele->GetOffsetHeight());
  357. return 1;
  358. }
  359. int ElementGetAttroffset_left(lua_State* L)
  360. {
  361. Element* ele = LuaType<Element>::check(L,1);
  362. lua_pushnumber(L,ele->GetOffsetLeft());
  363. return 1;
  364. }
  365. int ElementGetAttroffset_parent(lua_State* L)
  366. {
  367. Element* ele = LuaType<Element>::check(L,1);
  368. Element* parent = ele->GetOffsetParent();
  369. LuaType<Element>::push(L,parent,false);
  370. return 1;
  371. }
  372. int ElementGetAttroffset_top(lua_State* L)
  373. {
  374. Element* ele = LuaType<Element>::check(L,1);
  375. lua_pushnumber(L, ele->GetOffsetTop());
  376. return 1;
  377. }
  378. int ElementGetAttroffset_width(lua_State* L)
  379. {
  380. Element* ele = LuaType<Element>::check(L,1);
  381. lua_pushnumber(L,ele->GetOffsetWidth());
  382. return 1;
  383. }
  384. int ElementGetAttrowner_document(lua_State* L)
  385. {
  386. Element* ele = LuaType<Element>::check(L,1);
  387. Document* doc = ele->GetOwnerDocument();
  388. LuaType<Document>::push(L,doc,false);
  389. return 1;
  390. }
  391. int ElementGetAttrparent_node(lua_State* L)
  392. {
  393. Element* ele = LuaType<Element>::check(L,1);
  394. Element* parent = ele->GetParentNode();
  395. if(parent == NULL)
  396. lua_pushnil(L);
  397. else
  398. LuaType<Element>::push(L,parent,false);
  399. return 1;
  400. }
  401. int ElementGetAttrprevious_sibling(lua_State* L)
  402. {
  403. Element* ele = LuaType<Element>::check(L,1);
  404. Element* sibling = ele->GetPreviousSibling();
  405. if(sibling == NULL)
  406. lua_pushnil(L);
  407. else
  408. LuaType<Element>::push(L,sibling,false);
  409. return 1;
  410. }
  411. int ElementGetAttrscroll_height(lua_State* L)
  412. {
  413. Element* ele = LuaType<Element>::check(L,1);
  414. lua_pushnumber(L,ele->GetScrollHeight());
  415. return 1;
  416. }
  417. int ElementGetAttrscroll_left(lua_State* L)
  418. {
  419. Element* ele = LuaType<Element>::check(L,1);
  420. lua_pushnumber(L,ele->GetScrollLeft());
  421. return 1;
  422. }
  423. int ElementGetAttrscroll_top(lua_State* L)
  424. {
  425. Element* ele = LuaType<Element>::check(L,1);
  426. lua_pushnumber(L,ele->GetScrollTop());
  427. return 1;
  428. }
  429. int ElementGetAttrscroll_width(lua_State* L)
  430. {
  431. Element* ele = LuaType<Element>::check(L,1);
  432. lua_pushnumber(L,ele->GetScrollWidth());
  433. return 1;
  434. }
  435. int ElementGetAttrstyle(lua_State* L)
  436. {
  437. Element* ele = LuaType<Element>::check(L,1);
  438. LuaType<ElementStyle>::push(L,ele->GetStyle(),false);
  439. return 1;
  440. }
  441. int ElementGetAttrtag_name(lua_State* L)
  442. {
  443. Element* ele = LuaType<Element>::check(L,1);
  444. lua_pushstring(L,ele->GetTagName().CString());
  445. return 0;
  446. }
  447. //setters
  448. int ElementSetAttrclass_name(lua_State* L)
  449. {
  450. Element* ele = LuaType<Element>::check(L,1);
  451. const char* name = luaL_checkstring(L,2);
  452. ele->SetClassNames(name);
  453. return 0;
  454. }
  455. int ElementSetAttrid(lua_State* L)
  456. {
  457. Element* ele = LuaType<Element>::check(L,1);
  458. const char* id = luaL_checkstring(L,2);
  459. ele->SetId(id);
  460. return 0;
  461. }
  462. int ElementSetAttrinner_rml(lua_State* L)
  463. {
  464. Element* ele = LuaType<Element>::check(L,1);
  465. const char* rml = luaL_checkstring(L,2);
  466. ele->SetInnerRML(rml);
  467. return 0;
  468. }
  469. int ElementSetAttrscroll_left(lua_State* L)
  470. {
  471. Element* ele = LuaType<Element>::check(L,1);
  472. float scroll = (float)luaL_checknumber(L,2);
  473. ele->SetScrollLeft(scroll);
  474. return 0;
  475. }
  476. int ElementSetAttrscroll_top(lua_State* L)
  477. {
  478. Element* ele = LuaType<Element>::check(L,1);
  479. float scroll = (float)luaL_checknumber(L,2);
  480. ele->SetScrollTop(scroll);
  481. return 0;
  482. }
  483. RegType<Element> ElementMethods[] =
  484. {
  485. LUAMETHOD(Element,AddEventListener)
  486. LUAMETHOD(Element,AppendChild)
  487. LUAMETHOD(Element,Blur)
  488. LUAMETHOD(Element,Click)
  489. LUAMETHOD(Element,DispatchEvent)
  490. LUAMETHOD(Element,Focus)
  491. LUAMETHOD(Element,GetAttribute)
  492. LUAMETHOD(Element,GetElementById)
  493. LUAMETHOD(Element,GetElementsByTagName)
  494. LUAMETHOD(Element,HasAttribute)
  495. LUAMETHOD(Element,HasChildNodes)
  496. LUAMETHOD(Element,InsertBefore)
  497. LUAMETHOD(Element,IsClassSet)
  498. LUAMETHOD(Element,RemoveAttribute)
  499. LUAMETHOD(Element,RemoveChild)
  500. LUAMETHOD(Element,ReplaceChild)
  501. LUAMETHOD(Element,ScrollIntoView)
  502. LUAMETHOD(Element,SetAttribute)
  503. LUAMETHOD(Element,SetClass)
  504. { NULL, NULL },
  505. };
  506. luaL_reg ElementGetters[] =
  507. {
  508. LUAGETTER(Element,attributes)
  509. LUAGETTER(Element,child_nodes)
  510. LUAGETTER(Element,class_name)
  511. LUAGETTER(Element,client_left)
  512. LUAGETTER(Element,client_height)
  513. LUAGETTER(Element,client_top)
  514. LUAGETTER(Element,client_width)
  515. LUAGETTER(Element,first_child)
  516. LUAGETTER(Element,id)
  517. LUAGETTER(Element,inner_rml)
  518. LUAGETTER(Element,last_child)
  519. LUAGETTER(Element,next_sibling)
  520. LUAGETTER(Element,offset_height)
  521. LUAGETTER(Element,offset_left)
  522. LUAGETTER(Element,offset_parent)
  523. LUAGETTER(Element,offset_top)
  524. LUAGETTER(Element,offset_width)
  525. LUAGETTER(Element,owner_document)
  526. LUAGETTER(Element,parent_node)
  527. LUAGETTER(Element,previous_sibling)
  528. LUAGETTER(Element,scroll_height)
  529. LUAGETTER(Element,scroll_left)
  530. LUAGETTER(Element,scroll_top)
  531. LUAGETTER(Element,scroll_width)
  532. LUAGETTER(Element,style)
  533. LUAGETTER(Element,tag_name)
  534. { NULL, NULL },
  535. };
  536. luaL_reg ElementSetters[] =
  537. {
  538. LUASETTER(Element,class_name)
  539. LUASETTER(Element,id)
  540. LUASETTER(Element,inner_rml)
  541. LUASETTER(Element,scroll_left)
  542. LUASETTER(Element,scroll_top)
  543. { NULL, NULL },
  544. };
  545. template<> const char* GetTClassName<Element>() { return "Element"; }
  546. template<> RegType<Element>* GetMethodTable<Element>() { return ElementMethods; }
  547. template<> luaL_reg* GetAttrTable<Element>() { return ElementGetters; }
  548. template<> luaL_reg* SetAttrTable<Element>() { return ElementSetters; }
  549. }
  550. }
  551. }