guiTextListCtrl.cpp 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881
  1. //-----------------------------------------------------------------------------
  2. // Copyright (c) 2012 GarageGames, LLC
  3. //
  4. // Permission is hereby granted, free of charge, to any person obtaining a copy
  5. // of this software and associated documentation files (the "Software"), to
  6. // deal in the Software without restriction, including without limitation the
  7. // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  8. // sell copies of the Software, and to permit persons to whom the Software is
  9. // furnished to do so, subject to the following conditions:
  10. //
  11. // The above copyright notice and this permission notice shall be included in
  12. // all copies or substantial portions of the Software.
  13. //
  14. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  19. // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
  20. // IN THE SOFTWARE.
  21. //-----------------------------------------------------------------------------
  22. #include "platform/platform.h"
  23. #include "gui/controls/guiTextListCtrl.h"
  24. #include "console/consoleTypes.h"
  25. #include "console/console.h"
  26. #include "gui/containers/guiScrollCtrl.h"
  27. #include "gui/core/guiDefaultControlRender.h"
  28. #include "gfx/gfxDrawUtil.h"
  29. #include "console/engineAPI.h"
  30. IMPLEMENT_CONOBJECT(GuiTextListCtrl);
  31. ConsoleDocClass( GuiTextListCtrl,
  32. "@brief GUI control that displays a list of text. Text items in the list can be individually selected.\n\n"
  33. "@tsexample\n"
  34. " new GuiTextListCtrl(EndGameGuiList)\n"
  35. " {\n"
  36. " columns = \"0 256\";\n"
  37. " fitParentWidth = \"1\";\n"
  38. " clipColumnText = \"0\";\n"
  39. " //Properties not specific to this control have been omitted from this example.\n"
  40. " };\n"
  41. "@endtsexample\n\n"
  42. "@see Reference\n\n"
  43. "@ingroup GuiControls\n"
  44. );
  45. IMPLEMENT_CALLBACK( GuiTextListCtrl, onSelect, void, (S32 cellid, const char* text),( cellid , text ),
  46. "@brief Called whenever an item in the list is selected.\n\n"
  47. "@param cellid The ID of the cell that was selected\n"
  48. "@param text The text in the selected cel\n\n"
  49. "@tsexample\n"
  50. "// A cel in the control was selected, causing the callback to occur\n"
  51. "GuiTextListCtrl::onSelect(%this,%callid,%text)\n"
  52. " {\n"
  53. " // Code to run when a cel item is selected\n"
  54. " }\n"
  55. "@endtsexample\n\n"
  56. "@see GuiControl\n\n"
  57. );
  58. IMPLEMENT_CALLBACK( GuiTextListCtrl, onDeleteKey, void, ( S32 id ),( id ),
  59. "@brief Called when the delete key has been pressed.\n\n"
  60. "@param id Id of the selected item in the list\n"
  61. "@tsexample\n"
  62. "// The delete key was pressed while the GuiTextListCtrl was in focus, causing the callback to occur.\n"
  63. "GuiTextListCtrl::onDeleteKey(%this,%id)\n"
  64. " {\n"
  65. " // Code to run when the delete key is pressed\n"
  66. " }\n"
  67. "@endtsexample\n\n"
  68. "@see GuiControl\n\n"
  69. );
  70. static S32 sortColumn;
  71. static bool sIncreasing;
  72. static const char *getColumn(const char *text)
  73. {
  74. S32 ct = sortColumn;
  75. while(ct--)
  76. {
  77. text = dStrchr(text, '\t');
  78. if(!text)
  79. return "";
  80. text++;
  81. }
  82. return text;
  83. }
  84. static S32 QSORT_CALLBACK textCompare( const void* a, const void* b )
  85. {
  86. GuiTextListCtrl::Entry *ea = (GuiTextListCtrl::Entry *) (a);
  87. GuiTextListCtrl::Entry *eb = (GuiTextListCtrl::Entry *) (b);
  88. S32 result = dStrnatcasecmp( getColumn( ea->text ), getColumn( eb->text ) );
  89. return ( sIncreasing ? result : -result );
  90. }
  91. static S32 QSORT_CALLBACK numCompare(const void *a,const void *b)
  92. {
  93. GuiTextListCtrl::Entry *ea = (GuiTextListCtrl::Entry *) (a);
  94. GuiTextListCtrl::Entry *eb = (GuiTextListCtrl::Entry *) (b);
  95. const char* aCol = getColumn( ea->text );
  96. const char* bCol = getColumn( eb->text );
  97. F32 result = dAtof(aCol) - dAtof(bCol);
  98. S32 res = result < 0 ? -1 : (result > 0 ? 1 : 0);
  99. return ( sIncreasing ? res : -res );
  100. }
  101. GuiTextListCtrl::GuiTextListCtrl()
  102. {
  103. VECTOR_SET_ASSOCIATION(mList);
  104. VECTOR_SET_ASSOCIATION(mColumnOffsets);
  105. mActive = true;
  106. mSize.set(1, 0);
  107. mColumnOffsets.push_back(0);
  108. mFitParentWidth = true;
  109. mClipColumnText = false;
  110. mRowHeightPadding = 2;
  111. }
  112. void GuiTextListCtrl::initPersistFields()
  113. {
  114. addField("columns", TypeS32Vector, Offset(mColumnOffsets, GuiTextListCtrl), "A vector of column offsets. The number of values determines the number of columns in the table.\n" );
  115. addField("fitParentWidth", TypeBool, Offset(mFitParentWidth, GuiTextListCtrl), "If true, the width of this control will match the width of its parent.\n");
  116. addField("clipColumnText", TypeBool, Offset(mClipColumnText, GuiTextListCtrl), "If true, text exceeding a column's given width will get clipped.\n" );
  117. addField("rowHeightPadding", TypeS32, Offset(mRowHeightPadding, GuiTextListCtrl), "Sets how much padding to add to the row heights on top of the font height");
  118. Parent::initPersistFields();
  119. }
  120. bool GuiTextListCtrl::onWake()
  121. {
  122. if(!Parent::onWake())
  123. return false;
  124. setSize(mSize);
  125. return true;
  126. }
  127. U32 GuiTextListCtrl::getSelectedId()
  128. {
  129. if (mSelectedCell.y == -1)
  130. return InvalidId;
  131. return mList[mSelectedCell.y].id;
  132. }
  133. U32 GuiTextListCtrl::getSelectedRow()
  134. {
  135. return mSelectedCell.y;
  136. }
  137. bool GuiTextListCtrl::cellSelected(Point2I cell)
  138. {
  139. // Is the selection being cleared?
  140. if( cell.x == -1 && cell.y == -1)
  141. return Parent::cellSelected(cell);
  142. // Do not allow selection of inactive cells
  143. if (cell.y >= 0 && cell.y < mSize.y && mList[cell.y].active)
  144. return Parent::cellSelected(cell);
  145. else
  146. return false;
  147. }
  148. void GuiTextListCtrl::onCellSelected(Point2I cell)
  149. {
  150. onSelect_callback(mList[cell.y].id, mList[cell.y].text);
  151. execConsoleCallback();
  152. }
  153. void GuiTextListCtrl::onRenderCell(Point2I offset, Point2I cell, bool selected, bool mouseOver)
  154. {
  155. if ( mList[cell.y].active )
  156. {
  157. if (selected || (mProfile->mMouseOverSelected && mouseOver))
  158. {
  159. RectI highlightRect = RectI(offset.x, offset.y, mCellSize.x, mCellSize.y);
  160. highlightRect.inset( 0, -1 );
  161. renderFilledBorder( highlightRect, mProfile->mBorderColorHL, mProfile->mFillColorHL);
  162. GFX->getDrawUtil()->setBitmapModulation(mProfile->mFontColorHL);
  163. }
  164. else
  165. GFX->getDrawUtil()->setBitmapModulation(mouseOver ? mProfile->mFontColorHL : mProfile->mFontColor);
  166. }
  167. else
  168. GFX->getDrawUtil()->setBitmapModulation( mProfile->mFontColorNA );
  169. const char *text = mList[cell.y].text;
  170. for(U32 index = 0; index < mColumnOffsets.size(); index++)
  171. {
  172. const char *nextCol = dStrchr(text, '\t');
  173. if(mColumnOffsets[index] >= 0)
  174. {
  175. dsize_t slen;
  176. if(nextCol)
  177. slen = nextCol - text;
  178. else
  179. slen = dStrlen(text);
  180. Point2I pos(offset.x + 4 + mColumnOffsets[index], offset.y + mRowHeightPadding / 2);
  181. RectI saveClipRect;
  182. bool clipped = false;
  183. if(mClipColumnText && (index != (mColumnOffsets.size() - 1)))
  184. {
  185. saveClipRect = GFX->getClipRect();
  186. RectI clipRect(pos, Point2I(mColumnOffsets[index+1] - mColumnOffsets[index] - 4, mCellSize.y));
  187. if(clipRect.intersect(saveClipRect))
  188. {
  189. clipped = true;
  190. GFX->setClipRect( clipRect );
  191. }
  192. }
  193. GFX->getDrawUtil()->drawTextN(mFont, pos, text, slen, mProfile->mFontColors);
  194. if(clipped)
  195. GFX->setClipRect( saveClipRect );
  196. }
  197. if(!nextCol)
  198. break;
  199. text = nextCol+1;
  200. }
  201. }
  202. U32 GuiTextListCtrl::getRowWidth(Entry *row)
  203. {
  204. U32 width = 1;
  205. const char *text = row->text;
  206. for(U32 index = 0; index < mColumnOffsets.size(); index++)
  207. {
  208. const char *nextCol = dStrchr(text, '\t');
  209. U32 textWidth;
  210. if(nextCol)
  211. textWidth = mFont->getStrNWidth((const UTF8*)text, nextCol - text);
  212. else
  213. textWidth = mFont->getStrWidth((const UTF8*)text);
  214. if(mColumnOffsets[index] >= 0)
  215. width = getMax(width, mColumnOffsets[index] + textWidth);
  216. if(!nextCol)
  217. break;
  218. text = nextCol+1;
  219. }
  220. return width;
  221. }
  222. void GuiTextListCtrl::insertEntry(U32 id, const char *text, S32 index)
  223. {
  224. Entry e;
  225. e.text = dStrdup(text);
  226. e.id = id;
  227. e.active = true;
  228. if(!mList.size())
  229. mList.push_back(e);
  230. else
  231. {
  232. if(index > mList.size())
  233. index = mList.size();
  234. mList.insert(index);
  235. mList[index] = e;
  236. }
  237. setSize(Point2I(1, mList.size()));
  238. }
  239. void GuiTextListCtrl::addEntry(U32 id, const char *text)
  240. {
  241. Entry e;
  242. e.text = dStrdup(text);
  243. e.id = id;
  244. e.active = true;
  245. mList.push_back(e);
  246. setSize(Point2I(1, mList.size()));
  247. }
  248. void GuiTextListCtrl::setEntry(U32 id, const char *text)
  249. {
  250. S32 e = findEntryById(id);
  251. if(e == -1)
  252. addEntry(id, text);
  253. else
  254. {
  255. dFree(mList[e].text);
  256. mList[e].text = dStrdup(text);
  257. // Still have to call this to make sure cells are wide enough for new values:
  258. setSize( Point2I( 1, mList.size() ) );
  259. }
  260. setUpdate();
  261. }
  262. void GuiTextListCtrl::setEntryActive(U32 id, bool active)
  263. {
  264. S32 index = findEntryById( id );
  265. if ( index == -1 )
  266. return;
  267. if ( mList[index].active != active )
  268. {
  269. mList[index].active = active;
  270. // You can't have an inactive entry selected...
  271. if ( !active && mSelectedCell.y >= 0 && mSelectedCell.y < mList.size()
  272. && mList[mSelectedCell.y].id == id )
  273. setSelectedCell( Point2I( -1, -1 ) );
  274. setUpdate();
  275. }
  276. }
  277. S32 GuiTextListCtrl::findEntryById(U32 id)
  278. {
  279. for(U32 i = 0; i < mList.size(); i++)
  280. if(mList[i].id == id)
  281. return i;
  282. return -1;
  283. }
  284. S32 GuiTextListCtrl::findEntryByText(const char *text)
  285. {
  286. for(U32 i = 0; i < mList.size(); i++)
  287. if(!dStricmp(mList[i].text, text))
  288. return i;
  289. return -1;
  290. }
  291. bool GuiTextListCtrl::isEntryActive(U32 id)
  292. {
  293. S32 index = findEntryById( id );
  294. if ( index == -1 )
  295. return( false );
  296. return( mList[index].active );
  297. }
  298. void GuiTextListCtrl::setSize(Point2I newSize)
  299. {
  300. mSize = newSize;
  301. if ( bool( mFont ) )
  302. {
  303. if ( mSize.x == 1 && mFitParentWidth )
  304. {
  305. GuiScrollCtrl* parent = dynamic_cast<GuiScrollCtrl *>(getParent());
  306. if ( parent )
  307. mCellSize.x = parent->getContentExtent().x;
  308. }
  309. else
  310. {
  311. // Find the maximum width cell:
  312. S32 maxWidth = 1;
  313. for ( U32 i = 0; i < mList.size(); i++ )
  314. {
  315. U32 rWidth = getRowWidth( &mList[i] );
  316. if ( rWidth > maxWidth )
  317. maxWidth = rWidth;
  318. }
  319. mCellSize.x = maxWidth + 8;
  320. }
  321. mCellSize.y = mFont->getHeight() + mRowHeightPadding;
  322. }
  323. Point2I newExtent( newSize.x * mCellSize.x + mHeaderDim.x, newSize.y * mCellSize.y + mHeaderDim.y );
  324. setExtent( newExtent );
  325. }
  326. void GuiTextListCtrl::clear()
  327. {
  328. while (mList.size())
  329. removeEntry(mList[0].id);
  330. mMouseOverCell.set( -1, -1 );
  331. setSelectedCell(Point2I(-1, -1));
  332. }
  333. void GuiTextListCtrl::sort(U32 column, bool increasing)
  334. {
  335. if (getNumEntries() < 2)
  336. return;
  337. sortColumn = column;
  338. sIncreasing = increasing;
  339. dQsort((void *)&(mList[0]), mList.size(), sizeof(Entry), textCompare);
  340. }
  341. void GuiTextListCtrl::sortNumerical( U32 column, bool increasing )
  342. {
  343. if ( getNumEntries() < 2 )
  344. return;
  345. sortColumn = column;
  346. sIncreasing = increasing;
  347. dQsort( (void*) &( mList[0] ), mList.size(), sizeof( Entry ), numCompare );
  348. }
  349. void GuiTextListCtrl::onRemove()
  350. {
  351. clear();
  352. Parent::onRemove();
  353. }
  354. U32 GuiTextListCtrl::getNumEntries()
  355. {
  356. return mList.size();
  357. }
  358. void GuiTextListCtrl::removeEntryByIndex(S32 index)
  359. {
  360. if(index < 0 || index >= mList.size())
  361. return;
  362. dFree(mList[index].text);
  363. mList.erase(index);
  364. setSize(Point2I( 1, mList.size()));
  365. setSelectedCell(Point2I(-1, -1));
  366. }
  367. void GuiTextListCtrl::removeEntry(U32 id)
  368. {
  369. S32 index = findEntryById(id);
  370. removeEntryByIndex(index);
  371. }
  372. const char *GuiTextListCtrl::getSelectedText()
  373. {
  374. if (mSelectedCell.y == -1)
  375. return NULL;
  376. return mList[mSelectedCell.y].text;
  377. }
  378. const char *GuiTextListCtrl::getScriptValue()
  379. {
  380. return getSelectedText();
  381. }
  382. void GuiTextListCtrl::setScriptValue(const char *val)
  383. {
  384. S32 e = findEntryByText(val);
  385. if(e == -1)
  386. setSelectedCell(Point2I(-1, -1));
  387. else
  388. setSelectedCell(Point2I(0, e));
  389. }
  390. bool GuiTextListCtrl::onKeyDown( const GuiEvent &event )
  391. {
  392. //if this control is a dead end, make sure the event stops here
  393. if ( !mVisible || !mActive || !mAwake )
  394. return true;
  395. S32 yDelta = 0;
  396. switch( event.keyCode )
  397. {
  398. case KEY_RETURN:
  399. execAltConsoleCallback();
  400. break;
  401. case KEY_LEFT:
  402. case KEY_UP:
  403. if ( mSelectedCell.y > 0 )
  404. {
  405. mSelectedCell.y--;
  406. yDelta = -mCellSize.y;
  407. }
  408. break;
  409. case KEY_DOWN:
  410. case KEY_RIGHT:
  411. if ( mSelectedCell.y < ( mList.size() - 1 ) )
  412. {
  413. mSelectedCell.y++;
  414. yDelta = mCellSize.y;
  415. }
  416. break;
  417. case KEY_HOME:
  418. if ( mList.size() )
  419. {
  420. mSelectedCell.y = 0;
  421. yDelta = -(mCellSize.y * mList.size() + 1 );
  422. }
  423. break;
  424. case KEY_END:
  425. if ( mList.size() )
  426. {
  427. mSelectedCell.y = mList.size() - 1;
  428. yDelta = (mCellSize.y * mList.size() + 1 );
  429. }
  430. break;
  431. case KEY_DELETE:
  432. if ( mSelectedCell.y >= 0 && mSelectedCell.y < mList.size() )
  433. onDeleteKey_callback( mList[mSelectedCell.y].id );
  434. break;
  435. default:
  436. return( Parent::onKeyDown( event ) );
  437. break;
  438. };
  439. GuiScrollCtrl* parent = dynamic_cast<GuiScrollCtrl *>(getParent());
  440. if ( parent )
  441. parent->scrollDelta( 0, yDelta );
  442. return ( true );
  443. }
  444. bool GuiTextListCtrl::onGamepadAxisUp(const GuiEvent& event)
  445. {
  446. if (mSelectedCell.y < (mList.size() - 1))
  447. {
  448. S32 yDelta = 0;
  449. mSelectedCell.y++;
  450. yDelta = mCellSize.y;
  451. GuiScrollCtrl* parent = dynamic_cast<GuiScrollCtrl*>(getParent());
  452. if (parent)
  453. parent->scrollDelta(0, yDelta);
  454. }
  455. return true;
  456. }
  457. bool GuiTextListCtrl::onGamepadAxisDown(const GuiEvent& event)
  458. {
  459. if (mSelectedCell.y > 0)
  460. {
  461. S32 yDelta = 0;
  462. mSelectedCell.y--;
  463. yDelta = -mCellSize.y;
  464. GuiScrollCtrl* parent = dynamic_cast<GuiScrollCtrl*>(getParent());
  465. if (parent)
  466. parent->scrollDelta(0, yDelta);
  467. }
  468. return true;
  469. }
  470. //-----------------------------------------------------------------------------
  471. // Console Methods
  472. //-----------------------------------------------------------------------------
  473. DefineEngineMethod( GuiTextListCtrl, getSelectedId, S32, (),,
  474. "@brief Get the ID of the currently selected item.\n\n"
  475. "@tsexample\n"
  476. "// Acquire the ID of the selected item in the list.\n"
  477. "%id = %thisGuiTextListCtrl.getSelectedId();\n"
  478. "@endtsexample\n\n"
  479. "@return The id of the selected item in the list.\n\n"
  480. "@see GuiControl")
  481. {
  482. return object->getSelectedId();
  483. }
  484. DefineEngineMethod( GuiTextListCtrl, setSelectedById, void, (S32 id),,
  485. "@brief Finds the specified entry by id, then marks its row as selected.\n\n"
  486. "@param id Entry within the text list to make selected.\n"
  487. "@tsexample\n"
  488. "// Define the id\n"
  489. "%id = \"5\";\n\n"
  490. "// Inform the GuiTextListCtrl control to set the defined id entry as selected\n"
  491. "%thisGuiTextListCtrl.setSelectedById(%id);\n"
  492. "@endtsexample\n\n"
  493. "@see GuiControl")
  494. {
  495. S32 index = object->findEntryById(id);
  496. if(index < 0)
  497. return ;
  498. object->setSelectedCell(Point2I(0, index));
  499. }
  500. DefineEngineMethod( GuiTextListCtrl, setSelectedRow, void, (S32 rowNum),,
  501. "@briefSelects the specified row.\n\n"
  502. "@param rowNum Row number to set selected.\n"
  503. "@tsexample\n"
  504. "// Define the row number to set selected\n"
  505. "%rowNum = \"4\";\n\n"
  506. "%guiTextListCtrl.setSelectedRow(%rowNum);\n"
  507. "@endtsexample\n\n"
  508. "@see GuiControl")
  509. {
  510. object->setSelectedCell( Point2I( 0, rowNum ) );
  511. }
  512. DefineEngineMethod( GuiTextListCtrl, getSelectedRow, S32, (),,
  513. "@brief Returns the selected row index (not the row ID).\n\n"
  514. "@tsexample\n"
  515. "// Acquire the selected row index\n"
  516. "%rowIndex = %thisGuiTextListCtrl.getSelectedRow();\n"
  517. "@endtsexample\n\n"
  518. "@return Index of the selected row\n\n"
  519. "@see GuiControl")
  520. {
  521. return object->getSelectedRow();
  522. }
  523. DefineEngineMethod( GuiTextListCtrl, clearSelection, void, (),,
  524. "@brief Set the selection to nothing.\n\n"
  525. "@tsexample\n"
  526. "// Deselect anything that is currently selected\n"
  527. "%thisGuiTextListCtrl.clearSelection();\n"
  528. "@endtsexample\n\n"
  529. "@see GuiControl")
  530. {
  531. object->setSelectedCell(Point2I(-1, -1));
  532. }
  533. DefineEngineMethod( GuiTextListCtrl, addRow, S32, (S32 id, const char* text, S32 index),(0,"",-1),
  534. "@brief Adds a new row at end of the list with the defined id and text.\n"
  535. "If index is used, then the new row is inserted at the row location of 'index'.\n\n"
  536. "@param id Id of the new row.\n"
  537. "@param text Text to display at the new row.\n"
  538. "@param index Index to insert the new row at. If not used, new row will be placed at the end of the list.\n"
  539. "@tsexample\n"
  540. "// Define the id\n"
  541. "%id = \"4\";\n\n"
  542. "// Define the text to display\n"
  543. "%text = \"Display Text\"\n\n"
  544. "// Define the index (optional)\n"
  545. "%index = \"2\"\n\n"
  546. "// Inform the GuiTextListCtrl control to add the new row with the defined information.\n"
  547. "%rowIndex = %thisGuiTextListCtrl.addRow(%id,%text,%index);\n"
  548. "@endtsexample\n\n"
  549. "@return Returns the row index of the new row. If 'index' was defined, then this just returns the number of rows in the list.\n\n"
  550. "@see References")
  551. {
  552. S32 ret = object->mList.size();
  553. if(index == -1)
  554. object->addEntry(id, text);
  555. else
  556. object->insertEntry(id, text, index);
  557. return ret;
  558. }
  559. DefineEngineMethod( GuiTextListCtrl, setRowById, void, (S32 id, const char* text),,
  560. "@brief Sets the text at the defined id.\n\n"
  561. "@param id Id to change.\n"
  562. "@param text Text to use at the Id.\n"
  563. "@tsexample\n"
  564. "// Define the id\n"
  565. "%id = \"4\";\n\n"
  566. "// Define the text\n"
  567. "%text = \"Text To Display\";\n\n"
  568. "// Inform the GuiTextListCtrl control to display the defined text at the defined id\n"
  569. "%thisGuiTextListCtrl.setRowById(%id,%text);\n"
  570. "@endtsexample\n\n"
  571. "@see GuiControl")
  572. {
  573. object->setEntry(id, text);
  574. }
  575. DefineEngineMethod( GuiTextListCtrl, sort, void, ( S32 columnId, bool increasing ), ( true ),
  576. "@brief Performs a standard (alphabetical) sort on the values in the specified column.\n\n"
  577. "@param columnId Column ID to perform the sort on.\n"
  578. "@param increasing If false, sort will be performed in reverse.\n"
  579. "@tsexample\n"
  580. "// Define the columnId\n"
  581. "%id = \"1\";\n\n"
  582. "// Define if we are increasing or not\n"
  583. "%increasing = \"false\";\n\n"
  584. "// Inform the GuiTextListCtrl to perform the sort operation\n"
  585. "%thisGuiTextListCtrl.sort(%id,%increasing);\n"
  586. "@endtsexample\n\n"
  587. "@see GuiControl")
  588. {
  589. object->sort( columnId, increasing );
  590. }
  591. DefineEngineMethod( GuiTextListCtrl, sortNumerical, void, (S32 columnID, bool increasing), ( true ),
  592. "@brief Perform a numerical sort on the values in the specified column.\n\n"
  593. "Detailed description\n\n"
  594. "@param columnId Column ID to perform the sort on.\n"
  595. "@param increasing If false, sort will be performed in reverse.\n"
  596. "@tsexample\n"
  597. "// Define the columnId\n"
  598. "%id = \"1\";\n\n"
  599. "// Define if we are increasing or not\n"
  600. "%increasing = \"false\";\n\n"
  601. "// Inform the GuiTextListCtrl to perform the sort operation\n"
  602. "%thisGuiTextListCtrl.sortNumerical(%id,%increasing);\n"
  603. "@endtsexample\n\n"
  604. "@see GuiControl")
  605. {
  606. object->sortNumerical( columnID, increasing );
  607. }
  608. DefineEngineMethod( GuiTextListCtrl, clear, void, (),,
  609. "@brief Clear the list.\n\n"
  610. "@tsexample\n"
  611. "// Inform the GuiTextListCtrl control to clear its contents\n"
  612. "%thisGuiTextListCtrl.clear();\n"
  613. "@endtsexample\n\n"
  614. "@see GuiControl")
  615. {
  616. object->clear();
  617. }
  618. DefineEngineMethod( GuiTextListCtrl, rowCount, S32, (),,
  619. "@brief Get the number of rows.\n\n"
  620. "@tsexample\n"
  621. "// Get the number of rows in the list\n"
  622. "%rowCount = %thisGuiTextListCtrl.rowCount();\n"
  623. "@endtsexample\n\n"
  624. "@return Number of rows in the list.\n\n"
  625. "@see GuiControl")
  626. {
  627. return object->getNumEntries();
  628. }
  629. DefineEngineMethod( GuiTextListCtrl, getRowId, S32, (S32 index),,
  630. "@brief Get the row ID for an index.\n\n"
  631. "@param index Index to get the RowID at\n"
  632. "@tsexample\n"
  633. "// Define the index\n"
  634. "%index = \"3\";\n\n"
  635. "// Request the row ID at the defined index\n"
  636. "%rowId = %thisGuiTextListCtrl.getRowId(%index);\n"
  637. "@endtsexample\n\n"
  638. "@return RowId at the defined index.\n\n"
  639. "@see GuiControl")
  640. {
  641. if(index >= object->getNumEntries())
  642. return -1;
  643. return object->mList[index].id;
  644. }
  645. DefineEngineMethod( GuiTextListCtrl, getRowTextById, const char*, (S32 id),,
  646. "@brief Get the text of a row with the specified id.\n\n"
  647. "@tsexample\n"
  648. "// Define the id\n"
  649. "%id = \"4\";\n\n"
  650. "// Inform the GuiTextListCtrl control to return the text at the defined row id\n"
  651. "%rowText = %thisGuiTextListCtrl.getRowTextById(%id);\n"
  652. "@endtsexample\n\n"
  653. "@return Row text at the requested row id.\n\n"
  654. "@see GuiControl")
  655. {
  656. S32 index = object->findEntryById(id);
  657. if(index < 0)
  658. return "";
  659. return object->mList[index].text;
  660. }
  661. DefineEngineMethod( GuiTextListCtrl, getRowNumById, S32, (S32 id),,
  662. "@brief Get the row number for a specified id.\n\n"
  663. "@param id Id to get the row number at\n"
  664. "@tsexample\n"
  665. "// Define the id\n"
  666. "%id = \"4\";\n\n"
  667. "// Request the row number from the GuiTextListCtrl control at the defined id.\n"
  668. "%rowNumber = %thisGuiTextListCtrl.getRowNumById(%id);\n"
  669. "@endtsexample\n\n"
  670. "@see GuiControl")
  671. {
  672. S32 index = object->findEntryById(id);
  673. if(index < 0)
  674. return -1;
  675. return index;
  676. }
  677. DefineEngineMethod( GuiTextListCtrl, getRowText, const char*, (S32 index),,
  678. "@brief Get the text of the row with the specified index.\n\n"
  679. "@param index Row index to acquire the text at.\n"
  680. "@tsexample\n"
  681. "// Define the row index\n"
  682. "%index = \"5\";\n\n"
  683. "// Request the text from the row at the defined index\n"
  684. "%rowText = %thisGuiTextListCtrl.getRowText(%index);\n"
  685. "@endtsexample\n\n"
  686. "@return Text at the defined row index.\n\n"
  687. "@see GuiControl")
  688. {
  689. if(index < 0 || index >= object->mList.size())
  690. return "";
  691. return object->mList[index].text;
  692. }
  693. DefineEngineMethod( GuiTextListCtrl, removeRowById, void, (S32 id),,
  694. "@brief Remove row with the specified id.\n\n"
  695. "@param id Id to remove the row entry at\n"
  696. "@tsexample\n"
  697. "// Define the id\n"
  698. "%id = \"4\";\n\n"
  699. "// Inform the GuiTextListCtrl control to remove the row at the defined id\n"
  700. "%thisGuiTextListCtrl.removeRowById(%id);\n"
  701. "@endtsexample\n\n"
  702. "@see GuiControl")
  703. {
  704. object->removeEntry(id);
  705. }
  706. DefineEngineMethod( GuiTextListCtrl, removeRow, void, (S32 index),,
  707. "@brief Remove a row from the table, based on its index.\n\n"
  708. "@param index Row index to remove from the list.\n"
  709. "@tsexample\n"
  710. "// Define the row index\n"
  711. "%index = \"4\";\n\n"
  712. "// Inform the GuiTextListCtrl control to remove the row at the defined row index\n"
  713. "%thisGuiTextListCtrl.removeRow(%index);\n"
  714. "@endtsexample\n\n"
  715. "@see GuiControl")
  716. {
  717. object->removeEntryByIndex(index);
  718. }
  719. DefineEngineMethod( GuiTextListCtrl, scrollVisible, void, (S32 rowNum),,
  720. "@brief Scroll so the specified row is visible\n\n"
  721. "@param rowNum Row number to make visible\n"
  722. "@tsexample\n"
  723. "// Define the row number to make visible\n"
  724. "%rowNum = \"4\";\n\n"
  725. "// Inform the GuiTextListCtrl control to scroll the list so the defined rowNum is visible.\n"
  726. "%thisGuiTextListCtrl.scrollVisible(%rowNum);\n"
  727. "@endtsexample\n\n"
  728. "@see GuiControl")
  729. {
  730. object->scrollCellVisible(Point2I(0, rowNum));
  731. }
  732. DefineEngineMethod( GuiTextListCtrl, findTextIndex, S32, (const char* needle),,
  733. "@brief Find needle in the list, and return the row number it was found in.\n\n"
  734. "@param needle Text to find in the list.\n"
  735. "@tsexample\n"
  736. "// Define the text to find in the list\n"
  737. "%needle = \"Text To Find\";\n\n"
  738. "// Request the row number that contains the defined text to find\n\n"
  739. "%rowNumber = %thisGuiTextListCtrl.findTextIndex(%needle);\n\n"
  740. "@endtsexample\n\n"
  741. "@return Row number that the defined text was found in,\n\n"
  742. "@see GuiControl")
  743. {
  744. return( object->findEntryByText(needle) );
  745. }
  746. DefineEngineMethod( GuiTextListCtrl, setRowActive, void, (S32 rowNum, bool active),,
  747. "@brief Mark a specified row as active/not.\n\n"
  748. "@param rowNum Row number to change the active state.\n"
  749. "@param active Boolean active state to set the row number.\n"
  750. "@tsexample\n"
  751. "// Define the row number\n"
  752. "%rowNum = \"4\";\n\n"
  753. "// Define the boolean active state\n"
  754. "%active = \"true\";\n\n"
  755. "// Informthe GuiTextListCtrl control to set the defined active state at the defined row number.\n"
  756. "%thisGuiTextListCtrl.setRowActive(%rowNum,%active);\n"
  757. "@endtsexample\n\n"
  758. "@see GuiControl")
  759. {
  760. object->setEntryActive( U32( rowNum ), active );
  761. }
  762. DefineEngineMethod( GuiTextListCtrl, isRowActive, bool, (S32 rowNum),,
  763. "@brief Check if the specified row is currently active or not.\n\n"
  764. "@param rowNum Row number to check the active state.\n"
  765. "@tsexample\n"
  766. "// Define the row number\n"
  767. "%rowNum = \"5\";\n\n"
  768. "// Request the active state of the defined row number from the GuiTextListCtrl control.\n"
  769. "%rowActiveState = %thisGuiTextListCtrl.isRowActive(%rowNum);\n"
  770. "@endtsexample\n\n"
  771. "@return Active state of the defined row number.\n\n"
  772. "@see GuiControl")
  773. {
  774. return( object->isEntryActive( U32( rowNum ) ) );
  775. }