griddemo.cpp 70 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369
  1. /////////////////////////////////////////////////////////////////////////////
  2. // Name: griddemo.cpp
  3. // Purpose: Grid control wxWidgets sample
  4. // Author: Michael Bedward
  5. // Modified by: Santiago Palacios
  6. // Copyright: (c) Michael Bedward, Julian Smart, Vadim Zeitlin
  7. // Licence: wxWindows licence
  8. /////////////////////////////////////////////////////////////////////////////
  9. // ============================================================================
  10. // declarations
  11. // ============================================================================
  12. // ----------------------------------------------------------------------------
  13. // headers
  14. // ----------------------------------------------------------------------------
  15. // For compilers that support precompilation, includes "wx/wx.h".
  16. #include "wx/wxprec.h"
  17. #ifdef __BORLANDC__
  18. #pragma hdrstop
  19. #endif
  20. #ifndef WX_PRECOMP
  21. #include "wx/wx.h"
  22. #endif
  23. #include "wx/colordlg.h"
  24. #include "wx/fontdlg.h"
  25. #include "wx/numdlg.h"
  26. #include "wx/aboutdlg.h"
  27. #include "wx/grid.h"
  28. #include "wx/headerctrl.h"
  29. #include "wx/generic/gridctrl.h"
  30. #include "wx/generic/grideditors.h"
  31. #include "griddemo.h"
  32. #ifndef wxHAS_IMAGES_IN_RESOURCES
  33. #include "../sample.xpm"
  34. #endif
  35. // Custom renderer that renders column header cells without borders and in
  36. // italic
  37. class CustomColumnHeaderRenderer : public wxGridColumnHeaderRenderer
  38. {
  39. public:
  40. CustomColumnHeaderRenderer(const wxColour& colFg, const wxColour& colBg)
  41. : m_colFg(colFg),
  42. m_colBg(colBg)
  43. {
  44. }
  45. virtual void DrawLabel(const wxGrid& WXUNUSED(grid),
  46. wxDC& dc,
  47. const wxString& value,
  48. const wxRect& rect,
  49. int horizAlign,
  50. int vertAlign,
  51. int WXUNUSED(textOrientation)) const
  52. {
  53. dc.SetTextForeground(m_colFg);
  54. dc.SetFont(wxITALIC_FONT->Bold());
  55. dc.DrawLabel(value, rect, horizAlign | vertAlign);
  56. }
  57. virtual void DrawBorder(const wxGrid& WXUNUSED(grid),
  58. wxDC& dc,
  59. wxRect& rect) const
  60. {
  61. dc.SetPen(*wxTRANSPARENT_PEN);
  62. dc.SetBrush(wxBrush(m_colBg));
  63. dc.DrawRectangle(rect);
  64. }
  65. private:
  66. const wxColour m_colFg, m_colBg;
  67. wxDECLARE_NO_COPY_CLASS(CustomColumnHeaderRenderer);
  68. };
  69. // And a custom attributes provider which uses custom column header renderer
  70. // defined above
  71. class CustomColumnHeadersProvider : public wxGridCellAttrProvider
  72. {
  73. public:
  74. // by default custom column renderer is not used, call
  75. // UseCustomColHeaders() to enable it
  76. CustomColumnHeadersProvider()
  77. : m_customOddRenderer(*wxYELLOW, *wxBLUE),
  78. m_customEvenRenderer(*wxWHITE, *wxBLACK),
  79. m_useCustom(false)
  80. {
  81. }
  82. // enable or disable the use of custom renderer for column headers
  83. void UseCustomColHeaders(bool use = true) { m_useCustom = use; }
  84. protected:
  85. virtual const wxGridColumnHeaderRenderer& GetColumnHeaderRenderer(int col)
  86. {
  87. // if enabled, use custom renderers
  88. if ( m_useCustom )
  89. {
  90. // and use different ones for odd and even columns -- just to show
  91. // that we can
  92. return col % 2 ? m_customOddRenderer : m_customEvenRenderer;
  93. }
  94. return wxGridCellAttrProvider::GetColumnHeaderRenderer(col);
  95. }
  96. private:
  97. CustomColumnHeaderRenderer m_customOddRenderer,
  98. m_customEvenRenderer;
  99. bool m_useCustom;
  100. wxDECLARE_NO_COPY_CLASS(CustomColumnHeadersProvider);
  101. };
  102. // ----------------------------------------------------------------------------
  103. // wxWin macros
  104. // ----------------------------------------------------------------------------
  105. IMPLEMENT_APP( GridApp )
  106. // ============================================================================
  107. // implementation
  108. // ============================================================================
  109. // ----------------------------------------------------------------------------
  110. // GridApp
  111. // ----------------------------------------------------------------------------
  112. bool GridApp::OnInit()
  113. {
  114. GridFrame *frame = new GridFrame;
  115. frame->Show(true);
  116. return true;
  117. }
  118. // ----------------------------------------------------------------------------
  119. // GridFrame
  120. // ----------------------------------------------------------------------------
  121. wxBEGIN_EVENT_TABLE( GridFrame, wxFrame )
  122. EVT_MENU( ID_TOGGLEROWLABELS, GridFrame::ToggleRowLabels )
  123. EVT_MENU( ID_TOGGLECOLLABELS, GridFrame::ToggleColLabels )
  124. EVT_MENU( ID_TOGGLEEDIT, GridFrame::ToggleEditing )
  125. EVT_MENU( ID_TOGGLEROWSIZING, GridFrame::ToggleRowSizing )
  126. EVT_MENU( ID_TOGGLECOLSIZING, GridFrame::ToggleColSizing )
  127. EVT_MENU( ID_TOGGLECOLMOVING, GridFrame::ToggleColMoving )
  128. EVT_MENU( ID_TOGGLEGRIDSIZING, GridFrame::ToggleGridSizing )
  129. EVT_MENU( ID_TOGGLEGRIDDRAGCELL, GridFrame::ToggleGridDragCell )
  130. EVT_MENU( ID_COLNATIVEHEADER, GridFrame::SetNativeColHeader )
  131. EVT_MENU( ID_COLDEFAULTHEADER, GridFrame::SetDefaultColHeader )
  132. EVT_MENU( ID_COLCUSTOMHEADER, GridFrame::SetCustomColHeader )
  133. EVT_MENU_RANGE( ID_TAB_STOP, ID_TAB_LEAVE, GridFrame::SetTabBehaviour )
  134. EVT_MENU( ID_TAB_CUSTOM, GridFrame::SetTabCustomHandler )
  135. EVT_MENU( ID_TOGGLEGRIDLINES, GridFrame::ToggleGridLines )
  136. EVT_MENU( ID_AUTOSIZECOLS, GridFrame::AutoSizeCols )
  137. EVT_MENU( ID_CELLOVERFLOW, GridFrame::CellOverflow )
  138. EVT_MENU( ID_RESIZECELL, GridFrame::ResizeCell )
  139. EVT_MENU( ID_SETLABELCOLOUR, GridFrame::SetLabelColour )
  140. EVT_MENU( ID_SETLABELTEXTCOLOUR, GridFrame::SetLabelTextColour )
  141. EVT_MENU( ID_SETLABEL_FONT, GridFrame::SetLabelFont )
  142. EVT_MENU( ID_ROWLABELHORIZALIGN, GridFrame::SetRowLabelHorizAlignment )
  143. EVT_MENU( ID_ROWLABELVERTALIGN, GridFrame::SetRowLabelVertAlignment )
  144. EVT_MENU( ID_COLLABELHORIZALIGN, GridFrame::SetColLabelHorizAlignment )
  145. EVT_MENU( ID_COLLABELVERTALIGN, GridFrame::SetColLabelVertAlignment )
  146. EVT_MENU( ID_GRIDLINECOLOUR, GridFrame::SetGridLineColour )
  147. EVT_MENU( ID_INSERTROW, GridFrame::InsertRow )
  148. EVT_MENU( ID_INSERTCOL, GridFrame::InsertCol )
  149. EVT_MENU( ID_DELETEROW, GridFrame::DeleteSelectedRows )
  150. EVT_MENU( ID_DELETECOL, GridFrame::DeleteSelectedCols )
  151. EVT_MENU( ID_CLEARGRID, GridFrame::ClearGrid )
  152. EVT_MENU( ID_SELCELLS, GridFrame::SelectCells )
  153. EVT_MENU( ID_SELROWS, GridFrame::SelectRows )
  154. EVT_MENU( ID_SELCOLS, GridFrame::SelectCols )
  155. EVT_MENU( ID_SELROWSORCOLS, GridFrame::SelectRowsOrCols )
  156. EVT_MENU( ID_SET_CELL_FG_COLOUR, GridFrame::SetCellFgColour )
  157. EVT_MENU( ID_SET_CELL_BG_COLOUR, GridFrame::SetCellBgColour )
  158. EVT_MENU( wxID_ABOUT, GridFrame::About )
  159. EVT_MENU( wxID_EXIT, GridFrame::OnQuit )
  160. EVT_MENU( ID_VTABLE, GridFrame::OnVTable)
  161. EVT_MENU( ID_BUGS_TABLE, GridFrame::OnBugsTable)
  162. EVT_MENU( ID_TABULAR_TABLE, GridFrame::OnTabularTable)
  163. EVT_MENU( ID_DESELECT_CELL, GridFrame::DeselectCell)
  164. EVT_MENU( ID_DESELECT_COL, GridFrame::DeselectCol)
  165. EVT_MENU( ID_DESELECT_ROW, GridFrame::DeselectRow)
  166. EVT_MENU( ID_DESELECT_ALL, GridFrame::DeselectAll)
  167. EVT_MENU( ID_SELECT_CELL, GridFrame::SelectCell)
  168. EVT_MENU( ID_SELECT_COL, GridFrame::SelectCol)
  169. EVT_MENU( ID_SELECT_ROW, GridFrame::SelectRow)
  170. EVT_MENU( ID_SELECT_ALL, GridFrame::SelectAll)
  171. EVT_MENU( ID_SELECT_UNSELECT, GridFrame::OnAddToSelectToggle)
  172. EVT_MENU( ID_SIZE_ROW, GridFrame::AutoSizeRow )
  173. EVT_MENU( ID_SIZE_COL, GridFrame::AutoSizeCol )
  174. EVT_MENU( ID_SIZE_ROW_LABEL, GridFrame::AutoSizeRowLabel )
  175. EVT_MENU( ID_SIZE_COL_LABEL, GridFrame::AutoSizeColLabel )
  176. EVT_MENU( ID_SIZE_LABELS_COL, GridFrame::AutoSizeLabelsCol )
  177. EVT_MENU( ID_SIZE_LABELS_ROW, GridFrame::AutoSizeLabelsRow )
  178. EVT_MENU( ID_SIZE_GRID, GridFrame::AutoSizeTable )
  179. EVT_MENU( ID_HIDECOL, GridFrame::HideCol )
  180. EVT_MENU( ID_SHOWCOL, GridFrame::ShowCol )
  181. EVT_MENU( ID_HIDEROW, GridFrame::HideRow )
  182. EVT_MENU( ID_SHOWROW, GridFrame::ShowRow )
  183. EVT_MENU( ID_SET_HIGHLIGHT_WIDTH, GridFrame::OnSetHighlightWidth)
  184. EVT_MENU( ID_SET_RO_HIGHLIGHT_WIDTH, GridFrame::OnSetROHighlightWidth)
  185. EVT_MENU( wxID_PRINT, GridFrame::OnGridRender )
  186. EVT_MENU( ID_RENDER_COORDS, GridFrame::OnGridRender )
  187. EVT_GRID_LABEL_LEFT_CLICK( GridFrame::OnLabelLeftClick )
  188. EVT_GRID_CELL_LEFT_CLICK( GridFrame::OnCellLeftClick )
  189. EVT_GRID_ROW_SIZE( GridFrame::OnRowSize )
  190. EVT_GRID_COL_SIZE( GridFrame::OnColSize )
  191. EVT_GRID_COL_AUTO_SIZE( GridFrame::OnColAutoSize )
  192. EVT_GRID_SELECT_CELL( GridFrame::OnSelectCell )
  193. EVT_GRID_RANGE_SELECT( GridFrame::OnRangeSelected )
  194. EVT_GRID_CELL_CHANGING( GridFrame::OnCellValueChanging )
  195. EVT_GRID_CELL_CHANGED( GridFrame::OnCellValueChanged )
  196. EVT_GRID_CELL_BEGIN_DRAG( GridFrame::OnCellBeginDrag )
  197. EVT_GRID_EDITOR_SHOWN( GridFrame::OnEditorShown )
  198. EVT_GRID_EDITOR_HIDDEN( GridFrame::OnEditorHidden )
  199. wxEND_EVENT_TABLE()
  200. GridFrame::GridFrame()
  201. : wxFrame( (wxFrame *)NULL, wxID_ANY, wxT("wxWidgets grid class demo"),
  202. wxDefaultPosition,
  203. wxDefaultSize )
  204. {
  205. SetIcon(wxICON(sample));
  206. wxMenu *fileMenu = new wxMenu;
  207. fileMenu->Append( ID_VTABLE, wxT("&Virtual table test\tCtrl-V"));
  208. fileMenu->Append( ID_BUGS_TABLE, wxT("&Bugs table test\tCtrl-B"));
  209. fileMenu->Append( ID_TABULAR_TABLE, wxT("&Tabular table test\tCtrl-T"));
  210. fileMenu->AppendSeparator();
  211. wxMenu* setupMenu = new wxMenu;
  212. wxMenuItem* item;
  213. item = setupMenu->AppendCheckItem( ID_RENDER_ROW_LABEL,
  214. "Render row labels" );
  215. item->Check();
  216. item = setupMenu->AppendCheckItem( ID_RENDER_COL_LABEL,
  217. "Render column labels" );
  218. item->Check();
  219. item = setupMenu->AppendCheckItem( ID_RENDER_GRID_LINES,
  220. "Render grid cell lines" );
  221. item->Check();
  222. item = setupMenu->AppendCheckItem( ID_RENDER_GRID_BORDER,
  223. "Render border" );
  224. item->Check();
  225. item = setupMenu->AppendCheckItem( ID_RENDER_SELECT_HLIGHT,
  226. "Render selection highlight" );
  227. setupMenu->AppendSeparator();
  228. setupMenu->AppendCheckItem( ID_RENDER_LOMETRIC,
  229. "Use LOMETRIC mapping mode" );
  230. setupMenu->AppendCheckItem( ID_RENDER_DEFAULT_SIZE,
  231. "Use wxDefaultSize" );
  232. setupMenu->AppendCheckItem( ID_RENDER_MARGIN,
  233. "Logical 50 unit margin" );
  234. setupMenu->AppendCheckItem( ID_RENDER_ZOOM,
  235. "Zoom 125%" );
  236. fileMenu->AppendSubMenu( setupMenu, "Render setup" );
  237. fileMenu->Append( wxID_PRINT, "Render" );
  238. fileMenu->Append( ID_RENDER_COORDS, "Render G5:P30" );
  239. fileMenu->AppendSeparator();
  240. fileMenu->Append( wxID_EXIT, wxT("E&xit\tAlt-X") );
  241. wxMenu *viewMenu = new wxMenu;
  242. viewMenu->AppendCheckItem(ID_TOGGLEROWLABELS, "&Row labels");
  243. viewMenu->AppendCheckItem(ID_TOGGLECOLLABELS, "&Col labels");
  244. viewMenu->AppendCheckItem(ID_TOGGLEEDIT,"&Editable");
  245. viewMenu->AppendCheckItem(ID_TOGGLEROWSIZING, "Ro&w drag-resize");
  246. viewMenu->AppendCheckItem(ID_TOGGLECOLSIZING, "C&ol drag-resize");
  247. viewMenu->AppendCheckItem(ID_TOGGLECOLMOVING, "Col drag-&move");
  248. viewMenu->AppendCheckItem(ID_TOGGLEGRIDSIZING, "&Grid drag-resize");
  249. viewMenu->AppendCheckItem(ID_TOGGLEGRIDDRAGCELL, "&Grid drag-cell");
  250. viewMenu->AppendCheckItem(ID_TOGGLEGRIDLINES, "&Grid Lines");
  251. viewMenu->AppendCheckItem(ID_SET_HIGHLIGHT_WIDTH, "&Set Cell Highlight Width...");
  252. viewMenu->AppendCheckItem(ID_SET_RO_HIGHLIGHT_WIDTH, "&Set Cell RO Highlight Width...");
  253. viewMenu->AppendCheckItem(ID_AUTOSIZECOLS, "&Auto-size cols");
  254. viewMenu->AppendCheckItem(ID_CELLOVERFLOW, "&Overflow cells");
  255. viewMenu->AppendCheckItem(ID_RESIZECELL, "&Resize cell (7,1)");
  256. viewMenu->Append(ID_HIDECOL, "&Hide column A");
  257. viewMenu->Append(ID_SHOWCOL, "&Show column A");
  258. viewMenu->Append(ID_HIDEROW, "&Hide row 2");
  259. viewMenu->Append(ID_SHOWROW, "&Show row 2");
  260. wxMenu *rowLabelMenu = new wxMenu;
  261. viewMenu->Append( ID_ROWLABELALIGN, wxT("R&ow label alignment"),
  262. rowLabelMenu,
  263. wxT("Change alignment of row labels") );
  264. rowLabelMenu->AppendRadioItem( ID_ROWLABELHORIZALIGN, wxT("&Horizontal") );
  265. rowLabelMenu->AppendRadioItem( ID_ROWLABELVERTALIGN, wxT("&Vertical") );
  266. wxMenu *colLabelMenu = new wxMenu;
  267. viewMenu->Append( ID_COLLABELALIGN, wxT("Col l&abel alignment"),
  268. colLabelMenu,
  269. wxT("Change alignment of col labels") );
  270. colLabelMenu->AppendRadioItem( ID_COLLABELHORIZALIGN, wxT("&Horizontal") );
  271. colLabelMenu->AppendRadioItem( ID_COLLABELVERTALIGN, wxT("&Vertical") );
  272. wxMenu *colHeaderMenu = new wxMenu;
  273. viewMenu->Append( ID_ROWLABELALIGN, wxT("Col header style"),
  274. colHeaderMenu,
  275. wxT("Change style of col header") );
  276. colHeaderMenu->AppendRadioItem( ID_COLDEFAULTHEADER, wxT("&Default") );
  277. colHeaderMenu->AppendRadioItem( ID_COLNATIVEHEADER, wxT("&Native") );
  278. colHeaderMenu->AppendRadioItem( ID_COLCUSTOMHEADER, wxT("&Custom") );
  279. wxMenu *tabBehaviourMenu = new wxMenu;
  280. tabBehaviourMenu->AppendRadioItem(ID_TAB_STOP, "&Stop at the boundary");
  281. tabBehaviourMenu->AppendRadioItem(ID_TAB_WRAP, "&Wrap at the boundary");
  282. tabBehaviourMenu->AppendRadioItem(ID_TAB_LEAVE, "&Leave the grid");
  283. tabBehaviourMenu->AppendRadioItem(ID_TAB_CUSTOM, "&Custom tab handler");
  284. viewMenu->AppendSubMenu(tabBehaviourMenu, "&Tab behaviour");
  285. wxMenu *colMenu = new wxMenu;
  286. colMenu->Append( ID_SETLABELCOLOUR, wxT("Set &label colour...") );
  287. colMenu->Append( ID_SETLABELTEXTCOLOUR, wxT("Set label &text colour...") );
  288. colMenu->Append( ID_SETLABEL_FONT, wxT("Set label fo&nt...") );
  289. colMenu->Append( ID_GRIDLINECOLOUR, wxT("&Grid line colour...") );
  290. colMenu->Append( ID_SET_CELL_FG_COLOUR, wxT("Set cell &foreground colour...") );
  291. colMenu->Append( ID_SET_CELL_BG_COLOUR, wxT("Set cell &background colour...") );
  292. wxMenu *editMenu = new wxMenu;
  293. editMenu->Append( ID_INSERTROW, wxT("Insert &row") );
  294. editMenu->Append( ID_INSERTCOL, wxT("Insert &column") );
  295. editMenu->Append( ID_DELETEROW, wxT("Delete selected ro&ws") );
  296. editMenu->Append( ID_DELETECOL, wxT("Delete selected co&ls") );
  297. editMenu->Append( ID_CLEARGRID, wxT("Cl&ear grid cell contents") );
  298. wxMenu *selectMenu = new wxMenu;
  299. selectMenu->Append( ID_SELECT_UNSELECT, wxT("Add new cells to the selection"),
  300. wxT("When off, old selection is deselected before ")
  301. wxT("selecting the new cells"), wxITEM_CHECK );
  302. selectMenu->AppendSeparator();
  303. selectMenu->Append( ID_SELECT_ALL, wxT("Select all"));
  304. selectMenu->Append( ID_SELECT_ROW, wxT("Select row 2"));
  305. selectMenu->Append( ID_SELECT_COL, wxT("Select col 2"));
  306. selectMenu->Append( ID_SELECT_CELL, wxT("Select cell (3, 1)"));
  307. selectMenu->AppendSeparator();
  308. selectMenu->Append( ID_DESELECT_ALL, wxT("Deselect all"));
  309. selectMenu->Append( ID_DESELECT_ROW, wxT("Deselect row 2"));
  310. selectMenu->Append( ID_DESELECT_COL, wxT("Deselect col 2"));
  311. selectMenu->Append( ID_DESELECT_CELL, wxT("Deselect cell (3, 1)"));
  312. wxMenu *selectionMenu = new wxMenu;
  313. selectMenu->Append( ID_CHANGESEL, wxT("Change &selection mode"),
  314. selectionMenu,
  315. wxT("Change selection mode") );
  316. selectionMenu->Append( ID_SELCELLS, wxT("Select &cells") );
  317. selectionMenu->Append( ID_SELROWS, wxT("Select &rows") );
  318. selectionMenu->Append( ID_SELCOLS, wxT("Select col&umns") );
  319. selectionMenu->Append( ID_SELROWSORCOLS, wxT("Select rows &or columns") );
  320. wxMenu *autosizeMenu = new wxMenu;
  321. autosizeMenu->Append( ID_SIZE_ROW, wxT("Selected &row data") );
  322. autosizeMenu->Append( ID_SIZE_COL, wxT("Selected &column data") );
  323. autosizeMenu->Append( ID_SIZE_ROW_LABEL, wxT("Selected row la&bel") );
  324. autosizeMenu->Append( ID_SIZE_COL_LABEL, wxT("Selected column &label") );
  325. autosizeMenu->Append( ID_SIZE_LABELS_COL, wxT("Column la&bels") );
  326. autosizeMenu->Append( ID_SIZE_LABELS_ROW, wxT("Row label&s") );
  327. autosizeMenu->Append( ID_SIZE_GRID, wxT("Entire &grid") );
  328. wxMenu *helpMenu = new wxMenu;
  329. helpMenu->Append( wxID_ABOUT, wxT("&About wxGrid demo") );
  330. wxMenuBar *menuBar = new wxMenuBar;
  331. menuBar->Append( fileMenu, wxT("&File") );
  332. menuBar->Append( viewMenu, wxT("&Grid") );
  333. menuBar->Append( colMenu, wxT("&Colours") );
  334. menuBar->Append( editMenu, wxT("&Edit") );
  335. menuBar->Append( selectMenu, wxT("&Select") );
  336. menuBar->Append( autosizeMenu, wxT("&Autosize") );
  337. menuBar->Append( helpMenu, wxT("&Help") );
  338. SetMenuBar( menuBar );
  339. m_addToSel = false;
  340. grid = new wxGrid( this,
  341. wxID_ANY,
  342. wxPoint( 0, 0 ),
  343. wxSize( 400, 300 ) );
  344. #if wxUSE_LOG
  345. int gridW = 600, gridH = 300;
  346. int logW = gridW, logH = 100;
  347. logWin = new wxTextCtrl( this,
  348. wxID_ANY,
  349. wxEmptyString,
  350. wxPoint( 0, gridH + 20 ),
  351. wxSize( logW, logH ),
  352. wxTE_MULTILINE );
  353. logger = new wxLogTextCtrl( logWin );
  354. m_logOld = wxLog::SetActiveTarget( logger );
  355. wxLog::DisableTimestamp();
  356. #endif // wxUSE_LOG
  357. // this will create a grid and, by default, an associated grid
  358. // table for strings
  359. grid->CreateGrid( 0, 0 );
  360. grid->GetTable()->SetAttrProvider(new CustomColumnHeadersProvider());
  361. grid->AppendRows(100);
  362. grid->AppendCols(100);
  363. int ir = grid->GetNumberRows();
  364. grid->DeleteRows(0, ir);
  365. grid->AppendRows(ir);
  366. grid->SetRowSize( 0, 60 );
  367. grid->SetCellValue( 0, 0, wxT("Ctrl+Home\nwill go to\nthis cell") );
  368. grid->SetCellValue( 0, 1, wxT("A long piece of text to demonstrate wrapping.") );
  369. grid->SetCellRenderer(0 , 1, new wxGridCellAutoWrapStringRenderer);
  370. grid->SetCellEditor( 0, 1 , new wxGridCellAutoWrapStringEditor);
  371. grid->SetCellValue( 0, 2, wxT("Blah") );
  372. grid->SetCellValue( 0, 3, wxT("Read only") );
  373. grid->SetReadOnly( 0, 3 );
  374. grid->SetCellValue( 0, 4, wxT("Can veto edit this cell") );
  375. grid->SetColSize(10, 150);
  376. wxString longtext = wxT("abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ\n\n");
  377. longtext += wxT("With tabs :\n");
  378. longtext += wxT("Home,\t\thome\t\t\tagain\n");
  379. longtext += wxT("Long word at start :\n");
  380. longtext += wxT("ILikeToBeHereWhen I can\n");
  381. longtext += wxT("Long word in the middle :\n");
  382. longtext += wxT("When IComeHome,ColdAnd tired\n");
  383. longtext += wxT("Long last word :\n");
  384. longtext += wxT("It's GoodToWarmMyBonesBesideTheFire");
  385. grid->SetCellValue( 0, 10, longtext );
  386. grid->SetCellRenderer(0 , 10, new wxGridCellAutoWrapStringRenderer);
  387. grid->SetCellEditor( 0, 10 , new wxGridCellAutoWrapStringEditor);
  388. grid->SetCellValue( 0, 11, wxT("K1 cell editor blocker") );
  389. grid->SetCellValue( 0, 5, wxT("Press\nCtrl+arrow\nto skip over\ncells") );
  390. grid->SetRowSize( 99, 60 );
  391. grid->SetCellValue(98, 98, "Test background colour setting");
  392. grid->SetCellBackgroundColour(98, 99, wxColour(255, 127, 127));
  393. grid->SetCellBackgroundColour(99, 98, wxColour(255, 127, 127));
  394. grid->SetCellValue( 99, 99, wxT("Ctrl+End\nwill go to\nthis cell") );
  395. grid->SetCellValue( 1, 0, wxT("This default cell will overflow into neighboring cells, but not if you turn overflow off."));
  396. grid->SetCellTextColour(1, 2, *wxRED);
  397. grid->SetCellBackgroundColour(1, 2, *wxGREEN);
  398. grid->SetCellValue( 1, 4, wxT("I'm in the middle"));
  399. grid->SetCellValue(2, 2, wxT("red"));
  400. grid->SetCellTextColour(2, 2, *wxRED);
  401. grid->SetCellValue(3, 3, wxT("green on grey"));
  402. grid->SetCellTextColour(3, 3, *wxGREEN);
  403. grid->SetCellBackgroundColour(3, 3, *wxLIGHT_GREY);
  404. grid->SetCellValue(4, 4, wxT("a weird looking cell"));
  405. grid->SetCellAlignment(4, 4, wxALIGN_CENTRE, wxALIGN_CENTRE);
  406. grid->SetCellRenderer(4, 4, new MyGridCellRenderer);
  407. grid->SetCellRenderer(3, 0, new wxGridCellBoolRenderer);
  408. grid->SetCellEditor(3, 0, new wxGridCellBoolEditor);
  409. grid->SetCellBackgroundColour(3, 0, wxColour(255, 127, 127));
  410. wxGridCellAttr *attr;
  411. attr = new wxGridCellAttr;
  412. attr->SetTextColour(*wxBLUE);
  413. grid->SetColAttr(5, attr);
  414. attr = new wxGridCellAttr;
  415. attr->SetBackgroundColour(*wxRED);
  416. grid->SetRowAttr(5, attr);
  417. grid->SetCellValue(2, 4, wxT("a wider column"));
  418. grid->SetColSize(4, 120);
  419. grid->SetColMinimalWidth(4, 120);
  420. grid->SetCellTextColour(5, 8, *wxGREEN);
  421. grid->SetCellValue(5, 8, wxT("Bg from row attr\nText col from cell attr"));
  422. grid->SetCellValue(5, 5, wxT("Bg from row attr Text col from col attr and this text is so long that it covers over many many empty cells but is broken by one that isn't"));
  423. // Some numeric columns with different formatting.
  424. grid->SetColFormatFloat(6);
  425. grid->SetCellValue(0, 6, "Default\nfloat format");
  426. grid->SetCellValue(1, 6, wxString::Format(wxT("%g"), 3.1415));
  427. grid->SetCellValue(2, 6, wxString::Format(wxT("%g"), 1415.0));
  428. grid->SetCellValue(3, 6, wxString::Format(wxT("%g"), 12345.67890));
  429. grid->SetColFormatFloat(7, 6, 2);
  430. grid->SetCellValue(0, 7, "Width 6\nprecision 2");
  431. grid->SetCellValue(1, 7, wxString::Format(wxT("%g"), 3.1415));
  432. grid->SetCellValue(2, 7, wxString::Format(wxT("%g"), 1415.0));
  433. grid->SetCellValue(3, 7, wxString::Format(wxT("%g"), 12345.67890));
  434. grid->SetColFormatCustom(8,
  435. wxString::Format("%s:%i,%i,%s", wxGRID_VALUE_FLOAT, -1, 4, "g"));
  436. grid->SetCellValue(0, 8, "Compact\nformat");
  437. grid->SetCellValue(1, 8, wxT("31415e-4"));
  438. grid->SetCellValue(2, 8, wxT("1415"));
  439. grid->SetCellValue(3, 8, wxT("123456789e-4"));
  440. grid->SetColFormatNumber(9);
  441. grid->SetCellValue(0, 9, "Integer\ncolumn");
  442. grid->SetCellValue(1, 9, "17");
  443. grid->SetCellValue(2, 9, "0");
  444. grid->SetCellValue(3, 9, "-666");
  445. grid->SetCellAlignment(3, 9, wxALIGN_CENTRE, wxALIGN_TOP);
  446. grid->SetCellValue(3, 10, "<- This numeric cell should be centred");
  447. const wxString choices[] =
  448. {
  449. wxT("Please select a choice"),
  450. wxT("This takes two cells"),
  451. wxT("Another choice"),
  452. };
  453. grid->SetCellEditor(4, 0, new wxGridCellChoiceEditor(WXSIZEOF(choices), choices));
  454. grid->SetCellSize(4, 0, 1, 2);
  455. grid->SetCellValue(4, 0, choices[0]);
  456. grid->SetCellOverflow(4, 0, false);
  457. grid->SetCellSize(7, 1, 3, 4);
  458. grid->SetCellAlignment(7, 1, wxALIGN_CENTRE, wxALIGN_CENTRE);
  459. grid->SetCellValue(7, 1, wxT("Big box!"));
  460. // create a separator-like row: it's grey and it's non-resizable
  461. grid->DisableRowResize(10);
  462. grid->SetRowSize(10, 30);
  463. attr = new wxGridCellAttr;
  464. attr->SetBackgroundColour(*wxLIGHT_GREY);
  465. grid->SetRowAttr(10, attr);
  466. grid->SetCellValue(10, 0, "You can't resize this row interactively -- try it");
  467. // this does exactly nothing except testing that SetAttr() handles NULL
  468. // attributes and does reference counting correctly
  469. grid->SetAttr(11, 11, NULL);
  470. grid->SetAttr(11, 11, new wxGridCellAttr);
  471. grid->SetAttr(11, 11, NULL);
  472. wxBoxSizer *topSizer = new wxBoxSizer( wxVERTICAL );
  473. topSizer->Add( grid,
  474. 1,
  475. wxEXPAND );
  476. #if wxUSE_LOG
  477. topSizer->Add( logWin,
  478. 0,
  479. wxEXPAND );
  480. #endif // wxUSE_LOG
  481. SetSizerAndFit( topSizer );
  482. Centre();
  483. SetDefaults();
  484. }
  485. GridFrame::~GridFrame()
  486. {
  487. #if wxUSE_LOG
  488. delete wxLog::SetActiveTarget(m_logOld);
  489. #endif // wxUSE_LOG
  490. }
  491. void GridFrame::SetDefaults()
  492. {
  493. GetMenuBar()->Check( ID_TOGGLEROWLABELS, true );
  494. GetMenuBar()->Check( ID_TOGGLECOLLABELS, true );
  495. GetMenuBar()->Check( ID_TOGGLEEDIT, true );
  496. GetMenuBar()->Check( ID_TOGGLEROWSIZING, true );
  497. GetMenuBar()->Check( ID_TOGGLECOLSIZING, true );
  498. GetMenuBar()->Check( ID_TOGGLECOLMOVING, false );
  499. GetMenuBar()->Check( ID_TOGGLEGRIDSIZING, true );
  500. GetMenuBar()->Check( ID_TOGGLEGRIDDRAGCELL, false );
  501. GetMenuBar()->Check( ID_TOGGLEGRIDLINES, true );
  502. GetMenuBar()->Check( ID_CELLOVERFLOW, true );
  503. }
  504. void GridFrame::ToggleRowLabels( wxCommandEvent& WXUNUSED(ev) )
  505. {
  506. if ( GetMenuBar()->IsChecked( ID_TOGGLEROWLABELS ) )
  507. {
  508. grid->SetRowLabelSize( grid->GetDefaultRowLabelSize() );
  509. }
  510. else
  511. {
  512. grid->SetRowLabelSize( 0 );
  513. }
  514. }
  515. void GridFrame::ToggleColLabels( wxCommandEvent& WXUNUSED(ev) )
  516. {
  517. if ( GetMenuBar()->IsChecked( ID_TOGGLECOLLABELS ) )
  518. {
  519. grid->SetColLabelSize( grid->GetDefaultColLabelSize() );
  520. }
  521. else
  522. {
  523. grid->SetColLabelSize( 0 );
  524. }
  525. }
  526. void GridFrame::ToggleEditing( wxCommandEvent& WXUNUSED(ev) )
  527. {
  528. grid->EnableEditing(
  529. GetMenuBar()->IsChecked( ID_TOGGLEEDIT ) );
  530. }
  531. void GridFrame::ToggleRowSizing( wxCommandEvent& WXUNUSED(ev) )
  532. {
  533. grid->EnableDragRowSize(
  534. GetMenuBar()->IsChecked( ID_TOGGLEROWSIZING ) );
  535. }
  536. void GridFrame::ToggleColSizing( wxCommandEvent& WXUNUSED(ev) )
  537. {
  538. grid->EnableDragColSize(
  539. GetMenuBar()->IsChecked( ID_TOGGLECOLSIZING ) );
  540. }
  541. void GridFrame::ToggleColMoving( wxCommandEvent& WXUNUSED(ev) )
  542. {
  543. grid->EnableDragColMove(
  544. GetMenuBar()->IsChecked( ID_TOGGLECOLMOVING ) );
  545. }
  546. void GridFrame::ToggleGridSizing( wxCommandEvent& WXUNUSED(ev) )
  547. {
  548. grid->EnableDragGridSize(
  549. GetMenuBar()->IsChecked( ID_TOGGLEGRIDSIZING ) );
  550. }
  551. void GridFrame::ToggleGridDragCell( wxCommandEvent& WXUNUSED(ev) )
  552. {
  553. grid->EnableDragCell(
  554. GetMenuBar()->IsChecked( ID_TOGGLEGRIDDRAGCELL ) );
  555. }
  556. void GridFrame::SetNativeColHeader( wxCommandEvent& WXUNUSED(ev) )
  557. {
  558. CustomColumnHeadersProvider* provider =
  559. static_cast<CustomColumnHeadersProvider*>(grid->GetTable()->GetAttrProvider());
  560. provider->UseCustomColHeaders(false);
  561. grid->SetUseNativeColLabels(true);
  562. }
  563. void GridFrame::SetCustomColHeader( wxCommandEvent& WXUNUSED(ev) )
  564. {
  565. CustomColumnHeadersProvider* provider =
  566. static_cast<CustomColumnHeadersProvider*>(grid->GetTable()->GetAttrProvider());
  567. provider->UseCustomColHeaders(true);
  568. grid->SetUseNativeColLabels(false);
  569. }
  570. void GridFrame::SetDefaultColHeader( wxCommandEvent& WXUNUSED(ev) )
  571. {
  572. CustomColumnHeadersProvider* provider =
  573. static_cast<CustomColumnHeadersProvider*>(grid->GetTable()->GetAttrProvider());
  574. provider->UseCustomColHeaders(false);
  575. grid->SetUseNativeColLabels(false);
  576. }
  577. void GridFrame::OnGridCustomTab(wxGridEvent& event)
  578. {
  579. // just for testing, make the cursor move up and down instead of the usual
  580. // left and right
  581. if ( event.ShiftDown() )
  582. {
  583. if ( grid->GetGridCursorRow() > 0 )
  584. grid->MoveCursorUp( false );
  585. }
  586. else
  587. {
  588. if ( grid->GetGridCursorRow() < grid->GetNumberRows() - 1 )
  589. grid->MoveCursorDown( false );
  590. }
  591. }
  592. void GridFrame::SetTabBehaviour(wxCommandEvent& event)
  593. {
  594. // To make any built-in behaviour work, we need to disable the custom TAB
  595. // handler, otherwise it would be overriding them.
  596. grid->Disconnect(wxEVT_GRID_TABBING,
  597. wxGridEventHandler(GridFrame::OnGridCustomTab));
  598. grid->SetTabBehaviour(
  599. static_cast<wxGrid::TabBehaviour>(event.GetId() - ID_TAB_STOP)
  600. );
  601. }
  602. void GridFrame::SetTabCustomHandler(wxCommandEvent&)
  603. {
  604. grid->Connect(wxEVT_GRID_TABBING,
  605. wxGridEventHandler(GridFrame::OnGridCustomTab),
  606. NULL, this);
  607. }
  608. void GridFrame::ToggleGridLines( wxCommandEvent& WXUNUSED(ev) )
  609. {
  610. grid->EnableGridLines(
  611. GetMenuBar()->IsChecked( ID_TOGGLEGRIDLINES ) );
  612. }
  613. void GridFrame::OnSetHighlightWidth( wxCommandEvent& WXUNUSED(ev) )
  614. {
  615. wxString choices[] = { wxT("0"), wxT("1"), wxT("2"), wxT("3"), wxT("4"), wxT("5"), wxT("6"), wxT("7"), wxT("8"), wxT("9"), wxT("10")};
  616. wxSingleChoiceDialog dlg(this, wxT("Choose the thickness of the highlight pen:"),
  617. wxT("Pen Width"), 11, choices);
  618. int current = grid->GetCellHighlightPenWidth();
  619. dlg.SetSelection(current);
  620. if (dlg.ShowModal() == wxID_OK) {
  621. grid->SetCellHighlightPenWidth(dlg.GetSelection());
  622. }
  623. }
  624. void GridFrame::OnSetROHighlightWidth( wxCommandEvent& WXUNUSED(ev) )
  625. {
  626. wxString choices[] = { wxT("0"), wxT("1"), wxT("2"), wxT("3"), wxT("4"), wxT("5"), wxT("6"), wxT("7"), wxT("8"), wxT("9"), wxT("10")};
  627. wxSingleChoiceDialog dlg(this, wxT("Choose the thickness of the highlight pen:"),
  628. wxT("Pen Width"), 11, choices);
  629. int current = grid->GetCellHighlightROPenWidth();
  630. dlg.SetSelection(current);
  631. if (dlg.ShowModal() == wxID_OK) {
  632. grid->SetCellHighlightROPenWidth(dlg.GetSelection());
  633. }
  634. }
  635. void GridFrame::AutoSizeCols( wxCommandEvent& WXUNUSED(ev) )
  636. {
  637. grid->AutoSizeColumns();
  638. grid->Refresh();
  639. }
  640. void GridFrame::CellOverflow( wxCommandEvent& ev )
  641. {
  642. grid->SetDefaultCellOverflow(ev.IsChecked());
  643. grid->Refresh();
  644. }
  645. void GridFrame::ResizeCell( wxCommandEvent& ev )
  646. {
  647. if (ev.IsChecked())
  648. grid->SetCellSize( 7, 1, 5, 5 );
  649. else
  650. grid->SetCellSize( 7, 1, 1, 5 );
  651. grid->Refresh();
  652. }
  653. void GridFrame::SetLabelColour( wxCommandEvent& WXUNUSED(ev) )
  654. {
  655. wxColourDialog dlg( NULL );
  656. if ( dlg.ShowModal() == wxID_OK )
  657. {
  658. wxColourData retData;
  659. retData = dlg.GetColourData();
  660. wxColour colour = retData.GetColour();
  661. grid->SetLabelBackgroundColour( colour );
  662. }
  663. }
  664. void GridFrame::SetLabelTextColour( wxCommandEvent& WXUNUSED(ev) )
  665. {
  666. wxColourDialog dlg( NULL );
  667. if ( dlg.ShowModal() == wxID_OK )
  668. {
  669. wxColourData retData;
  670. retData = dlg.GetColourData();
  671. wxColour colour = retData.GetColour();
  672. grid->SetLabelTextColour( colour );
  673. }
  674. }
  675. void GridFrame::SetLabelFont( wxCommandEvent& WXUNUSED(ev) )
  676. {
  677. wxFont font = wxGetFontFromUser(this);
  678. if ( font.IsOk() )
  679. {
  680. grid->SetLabelFont(font);
  681. }
  682. }
  683. void GridFrame::SetRowLabelHorizAlignment( wxCommandEvent& WXUNUSED(ev) )
  684. {
  685. int horiz, vert;
  686. grid->GetRowLabelAlignment( &horiz, &vert );
  687. switch ( horiz )
  688. {
  689. case wxALIGN_LEFT:
  690. horiz = wxALIGN_CENTRE;
  691. break;
  692. case wxALIGN_CENTRE:
  693. horiz = wxALIGN_RIGHT;
  694. break;
  695. case wxALIGN_RIGHT:
  696. horiz = wxALIGN_LEFT;
  697. break;
  698. }
  699. grid->SetRowLabelAlignment( horiz, vert );
  700. }
  701. void GridFrame::SetRowLabelVertAlignment( wxCommandEvent& WXUNUSED(ev) )
  702. {
  703. int horiz, vert;
  704. grid->GetRowLabelAlignment( &horiz, &vert );
  705. switch ( vert )
  706. {
  707. case wxALIGN_TOP:
  708. vert = wxALIGN_CENTRE;
  709. break;
  710. case wxALIGN_CENTRE:
  711. vert = wxALIGN_BOTTOM;
  712. break;
  713. case wxALIGN_BOTTOM:
  714. vert = wxALIGN_TOP;
  715. break;
  716. }
  717. grid->SetRowLabelAlignment( horiz, vert );
  718. }
  719. void GridFrame::SetColLabelHorizAlignment( wxCommandEvent& WXUNUSED(ev) )
  720. {
  721. int horiz, vert;
  722. grid->GetColLabelAlignment( &horiz, &vert );
  723. switch ( horiz )
  724. {
  725. case wxALIGN_LEFT:
  726. horiz = wxALIGN_CENTRE;
  727. break;
  728. case wxALIGN_CENTRE:
  729. horiz = wxALIGN_RIGHT;
  730. break;
  731. case wxALIGN_RIGHT:
  732. horiz = wxALIGN_LEFT;
  733. break;
  734. }
  735. grid->SetColLabelAlignment( horiz, vert );
  736. }
  737. void GridFrame::SetColLabelVertAlignment( wxCommandEvent& WXUNUSED(ev) )
  738. {
  739. int horiz, vert;
  740. grid->GetColLabelAlignment( &horiz, &vert );
  741. switch ( vert )
  742. {
  743. case wxALIGN_TOP:
  744. vert = wxALIGN_CENTRE;
  745. break;
  746. case wxALIGN_CENTRE:
  747. vert = wxALIGN_BOTTOM;
  748. break;
  749. case wxALIGN_BOTTOM:
  750. vert = wxALIGN_TOP;
  751. break;
  752. }
  753. grid->SetColLabelAlignment( horiz, vert );
  754. }
  755. void GridFrame::SetGridLineColour( wxCommandEvent& WXUNUSED(ev) )
  756. {
  757. wxColourDialog dlg( NULL );
  758. if ( dlg.ShowModal() == wxID_OK )
  759. {
  760. wxColourData retData;
  761. retData = dlg.GetColourData();
  762. wxColour colour = retData.GetColour();
  763. grid->SetGridLineColour( colour );
  764. }
  765. }
  766. void GridFrame::InsertRow( wxCommandEvent& WXUNUSED(ev) )
  767. {
  768. grid->InsertRows( grid->GetGridCursorRow(), 1 );
  769. }
  770. void GridFrame::InsertCol( wxCommandEvent& WXUNUSED(ev) )
  771. {
  772. grid->InsertCols( grid->GetGridCursorCol(), 1 );
  773. }
  774. void GridFrame::DeleteSelectedRows( wxCommandEvent& WXUNUSED(ev) )
  775. {
  776. if ( grid->IsSelection() )
  777. {
  778. wxGridUpdateLocker locker(grid);
  779. for ( int n = 0; n < grid->GetNumberRows(); )
  780. {
  781. if ( grid->IsInSelection( n , 0 ) )
  782. grid->DeleteRows( n, 1 );
  783. else
  784. n++;
  785. }
  786. }
  787. }
  788. void GridFrame::AutoSizeRow(wxCommandEvent& WXUNUSED(event))
  789. {
  790. wxGridUpdateLocker locker(grid);
  791. const wxArrayInt sels = grid->GetSelectedRows();
  792. for ( size_t n = 0, count = sels.size(); n < count; n++ )
  793. {
  794. grid->AutoSizeRow( sels[n], false );
  795. }
  796. }
  797. void GridFrame::AutoSizeCol(wxCommandEvent& WXUNUSED(event))
  798. {
  799. wxGridUpdateLocker locker(grid);
  800. const wxArrayInt sels = grid->GetSelectedCols();
  801. for ( size_t n = 0, count = sels.size(); n < count; n++ )
  802. {
  803. grid->AutoSizeColumn( sels[n], false );
  804. }
  805. }
  806. void GridFrame::AutoSizeRowLabel(wxCommandEvent& WXUNUSED(event))
  807. {
  808. wxGridUpdateLocker locker(grid);
  809. const wxArrayInt sels = grid->GetSelectedRows();
  810. for ( size_t n = 0, count = sels.size(); n < count; n++ )
  811. {
  812. grid->AutoSizeRowLabelSize( sels[n] );
  813. }
  814. }
  815. void GridFrame::AutoSizeColLabel(wxCommandEvent& WXUNUSED(event))
  816. {
  817. wxGridUpdateLocker locker(grid);
  818. const wxArrayInt sels = grid->GetSelectedCols();
  819. for ( size_t n = 0, count = sels.size(); n < count; n++ )
  820. {
  821. grid->AutoSizeColLabelSize( sels[n] );
  822. }
  823. }
  824. void GridFrame::AutoSizeLabelsCol(wxCommandEvent& WXUNUSED(event))
  825. {
  826. grid->SetColLabelSize( wxGRID_AUTOSIZE );
  827. }
  828. void GridFrame::AutoSizeLabelsRow(wxCommandEvent& WXUNUSED(event))
  829. {
  830. grid->SetRowLabelSize( wxGRID_AUTOSIZE );
  831. }
  832. void GridFrame::AutoSizeTable(wxCommandEvent& WXUNUSED(event))
  833. {
  834. grid->AutoSize();
  835. Layout();
  836. }
  837. void GridFrame::DeleteSelectedCols( wxCommandEvent& WXUNUSED(ev) )
  838. {
  839. if ( grid->IsSelection() )
  840. {
  841. wxGridUpdateLocker locker(grid);
  842. for ( int n = 0; n < grid->GetNumberCols(); )
  843. {
  844. if ( grid->IsInSelection( 0 , n ) )
  845. grid->DeleteCols( n, 1 );
  846. else
  847. n++;
  848. }
  849. }
  850. }
  851. void GridFrame::ClearGrid( wxCommandEvent& WXUNUSED(ev) )
  852. {
  853. grid->ClearGrid();
  854. }
  855. void GridFrame::SelectCells( wxCommandEvent& WXUNUSED(ev) )
  856. {
  857. grid->SetSelectionMode( wxGrid::wxGridSelectCells );
  858. }
  859. void GridFrame::SelectRows( wxCommandEvent& WXUNUSED(ev) )
  860. {
  861. grid->SetSelectionMode( wxGrid::wxGridSelectRows );
  862. }
  863. void GridFrame::SelectCols( wxCommandEvent& WXUNUSED(ev) )
  864. {
  865. grid->SetSelectionMode( wxGrid::wxGridSelectColumns );
  866. }
  867. void GridFrame::SelectRowsOrCols( wxCommandEvent& WXUNUSED(ev) )
  868. {
  869. grid->SetSelectionMode( wxGrid::wxGridSelectRowsOrColumns );
  870. }
  871. void GridFrame::SetCellFgColour( wxCommandEvent& WXUNUSED(ev) )
  872. {
  873. wxColour col = wxGetColourFromUser(this);
  874. if ( col.IsOk() )
  875. {
  876. grid->SetDefaultCellTextColour(col);
  877. grid->Refresh();
  878. }
  879. }
  880. void GridFrame::SetCellBgColour( wxCommandEvent& WXUNUSED(ev) )
  881. {
  882. wxColour col = wxGetColourFromUser(this);
  883. if ( col.IsOk() )
  884. {
  885. // Check the new Refresh function by passing it a rectangle
  886. // which exactly fits the grid.
  887. wxPoint pt(0, 0);
  888. wxRect r(pt, grid->GetSize());
  889. grid->SetDefaultCellBackgroundColour(col);
  890. grid->Refresh(true, &r);
  891. }
  892. }
  893. void GridFrame::DeselectCell(wxCommandEvent& WXUNUSED(event))
  894. {
  895. grid->DeselectCell(3, 1);
  896. }
  897. void GridFrame::DeselectCol(wxCommandEvent& WXUNUSED(event))
  898. {
  899. grid->DeselectCol(2);
  900. }
  901. void GridFrame::DeselectRow(wxCommandEvent& WXUNUSED(event))
  902. {
  903. grid->DeselectRow(2);
  904. }
  905. void GridFrame::DeselectAll(wxCommandEvent& WXUNUSED(event))
  906. {
  907. grid->ClearSelection();
  908. }
  909. void GridFrame::SelectCell(wxCommandEvent& WXUNUSED(event))
  910. {
  911. grid->SelectBlock(3, 1, 3, 1, m_addToSel);
  912. }
  913. void GridFrame::SelectCol(wxCommandEvent& WXUNUSED(event))
  914. {
  915. grid->SelectCol(2, m_addToSel);
  916. }
  917. void GridFrame::SelectRow(wxCommandEvent& WXUNUSED(event))
  918. {
  919. grid->SelectRow(2, m_addToSel);
  920. }
  921. void GridFrame::SelectAll(wxCommandEvent& WXUNUSED(event))
  922. {
  923. grid->SelectAll();
  924. }
  925. void GridFrame::OnAddToSelectToggle(wxCommandEvent& event)
  926. {
  927. m_addToSel = event.IsChecked();
  928. }
  929. void GridFrame::OnLabelLeftClick( wxGridEvent& ev )
  930. {
  931. wxString logBuf;
  932. if ( ev.GetRow() != -1 )
  933. {
  934. logBuf << wxT("Left click on row label ") << ev.GetRow();
  935. }
  936. else if ( ev.GetCol() != -1 )
  937. {
  938. logBuf << wxT("Left click on col label ") << ev.GetCol();
  939. }
  940. else
  941. {
  942. logBuf << wxT("Left click on corner label");
  943. }
  944. if ( ev.ShiftDown() )
  945. logBuf << wxT(" (shift down)");
  946. if ( ev.ControlDown() )
  947. logBuf << wxT(" (control down)");
  948. wxLogMessage( wxT("%s"), logBuf.c_str() );
  949. // you must call event skip if you want default grid processing
  950. //
  951. ev.Skip();
  952. }
  953. void GridFrame::OnCellLeftClick( wxGridEvent& ev )
  954. {
  955. wxLogMessage(wxT("Left click at row %d, col %d"), ev.GetRow(), ev.GetCol());
  956. // you must call event skip if you want default grid processing
  957. // (cell highlighting etc.)
  958. //
  959. ev.Skip();
  960. }
  961. void GridFrame::OnRowSize( wxGridSizeEvent& ev )
  962. {
  963. const int row = ev.GetRowOrCol();
  964. wxLogMessage("Resized row %d, new height = %d",
  965. row, grid->GetRowSize(row));
  966. ev.Skip();
  967. }
  968. void GridFrame::OnColSize( wxGridSizeEvent& ev )
  969. {
  970. const int col = ev.GetRowOrCol();
  971. wxLogMessage("Resized column %d, new width = %d",
  972. col, grid->GetColSize(col));
  973. ev.Skip();
  974. }
  975. void GridFrame::OnColAutoSize( wxGridSizeEvent &event )
  976. {
  977. // Fit even-numbered columns to their contents while using the default
  978. // behaviour for the odd-numbered ones to be able to see the difference.
  979. int col = event.GetRowOrCol();
  980. if ( col % 2 )
  981. {
  982. wxLogMessage("Auto-sizing column %d to fit its contents", col);
  983. grid->AutoSizeColumn(col);
  984. }
  985. else
  986. {
  987. event.Skip();
  988. }
  989. }
  990. void GridFrame::OnSelectCell( wxGridEvent& ev )
  991. {
  992. wxString logBuf;
  993. if ( ev.Selecting() )
  994. logBuf << wxT("Selected ");
  995. else
  996. logBuf << wxT("Deselected ");
  997. logBuf << wxT("cell at row ") << ev.GetRow()
  998. << wxT(" col ") << ev.GetCol()
  999. << wxT(" ( ControlDown: ")<< (ev.ControlDown() ? 'T':'F')
  1000. << wxT(", ShiftDown: ")<< (ev.ShiftDown() ? 'T':'F')
  1001. << wxT(", AltDown: ")<< (ev.AltDown() ? 'T':'F')
  1002. << wxT(", MetaDown: ")<< (ev.MetaDown() ? 'T':'F') << wxT(" )");
  1003. //Indicate whether this column was moved
  1004. if ( ((wxGrid *)ev.GetEventObject())->GetColPos( ev.GetCol() ) != ev.GetCol() )
  1005. logBuf << wxT(" *** Column moved, current position: ") << ((wxGrid *)ev.GetEventObject())->GetColPos( ev.GetCol() );
  1006. wxLogMessage( wxT("%s"), logBuf.c_str() );
  1007. // you must call Skip() if you want the default processing
  1008. // to occur in wxGrid
  1009. ev.Skip();
  1010. }
  1011. void GridFrame::OnRangeSelected( wxGridRangeSelectEvent& ev )
  1012. {
  1013. wxString logBuf;
  1014. if ( ev.Selecting() )
  1015. logBuf << wxT("Selected ");
  1016. else
  1017. logBuf << wxT("Deselected ");
  1018. logBuf << wxT("cells from row ") << ev.GetTopRow()
  1019. << wxT(" col ") << ev.GetLeftCol()
  1020. << wxT(" to row ") << ev.GetBottomRow()
  1021. << wxT(" col ") << ev.GetRightCol()
  1022. << wxT(" ( ControlDown: ")<< (ev.ControlDown() ? 'T':'F')
  1023. << wxT(", ShiftDown: ")<< (ev.ShiftDown() ? 'T':'F')
  1024. << wxT(", AltDown: ")<< (ev.AltDown() ? 'T':'F')
  1025. << wxT(", MetaDown: ")<< (ev.MetaDown() ? 'T':'F') << wxT(" )");
  1026. wxLogMessage( wxT("%s"), logBuf.c_str() );
  1027. ev.Skip();
  1028. }
  1029. void GridFrame::OnCellValueChanging( wxGridEvent& ev )
  1030. {
  1031. int row = ev.GetRow(),
  1032. col = ev.GetCol();
  1033. wxLogMessage("Value of cell at (%d, %d): about to change "
  1034. "from \"%s\" to \"%s\"",
  1035. row, col,
  1036. grid->GetCellValue(row, col), ev.GetString());
  1037. // test how vetoing works
  1038. if ( ev.GetString() == "42" )
  1039. {
  1040. wxLogMessage("Vetoing the change.");
  1041. ev.Veto();
  1042. return;
  1043. }
  1044. ev.Skip();
  1045. }
  1046. void GridFrame::OnCellValueChanged( wxGridEvent& ev )
  1047. {
  1048. int row = ev.GetRow(),
  1049. col = ev.GetCol();
  1050. wxLogMessage("Value of cell at (%d, %d) changed and is now \"%s\" "
  1051. "(was \"%s\")",
  1052. row, col,
  1053. grid->GetCellValue(row, col), ev.GetString());
  1054. ev.Skip();
  1055. }
  1056. void GridFrame::OnCellBeginDrag( wxGridEvent& ev )
  1057. {
  1058. wxLogMessage(wxT("Got request to drag cell at row %d, col %d"),
  1059. ev.GetRow(), ev.GetCol());
  1060. ev.Skip();
  1061. }
  1062. void GridFrame::OnEditorShown( wxGridEvent& ev )
  1063. {
  1064. if ( (ev.GetCol() == 4) &&
  1065. (ev.GetRow() == 0) &&
  1066. (wxMessageBox(wxT("Are you sure you wish to edit this cell"),
  1067. wxT("Checking"),wxYES_NO) == wxNO ) ) {
  1068. ev.Veto();
  1069. return;
  1070. }
  1071. wxLogMessage( wxT("Cell editor shown.") );
  1072. ev.Skip();
  1073. }
  1074. void GridFrame::OnEditorHidden( wxGridEvent& ev )
  1075. {
  1076. if ( (ev.GetCol() == 4) &&
  1077. (ev.GetRow() == 0) &&
  1078. (wxMessageBox(wxT("Are you sure you wish to finish editing this cell"),
  1079. wxT("Checking"),wxYES_NO) == wxNO ) ) {
  1080. ev.Veto();
  1081. return;
  1082. }
  1083. wxLogMessage( wxT("Cell editor hidden.") );
  1084. ev.Skip();
  1085. }
  1086. void GridFrame::About( wxCommandEvent& WXUNUSED(ev) )
  1087. {
  1088. wxAboutDialogInfo aboutInfo;
  1089. aboutInfo.SetName(wxT("wxGrid demo"));
  1090. aboutInfo.SetDescription(_("wxGrid sample program"));
  1091. aboutInfo.AddDeveloper(wxT("Michael Bedward"));
  1092. aboutInfo.AddDeveloper(wxT("Julian Smart"));
  1093. aboutInfo.AddDeveloper(wxT("Vadim Zeitlin"));
  1094. // this is just to force the generic version of the about
  1095. // dialog under wxMSW so that it's easy to test if the grid
  1096. // repaints correctly when it has lost focus and a dialog
  1097. // (different from the Windows standard message box -- it doesn't
  1098. // work with it for some reason) is moved over it.
  1099. aboutInfo.SetWebSite(wxT("http://www.wxwidgets.org"));
  1100. wxAboutBox(aboutInfo);
  1101. }
  1102. void GridFrame::OnQuit( wxCommandEvent& WXUNUSED(ev) )
  1103. {
  1104. Close( true );
  1105. }
  1106. void GridFrame::OnBugsTable(wxCommandEvent& )
  1107. {
  1108. BugsGridFrame *frame = new BugsGridFrame;
  1109. frame->Show(true);
  1110. }
  1111. // ----------------------------------------------------------------------------
  1112. // MyGridCellAttrProvider
  1113. // ----------------------------------------------------------------------------
  1114. MyGridCellAttrProvider::MyGridCellAttrProvider()
  1115. {
  1116. m_attrForOddRows = new wxGridCellAttr;
  1117. m_attrForOddRows->SetBackgroundColour(*wxLIGHT_GREY);
  1118. }
  1119. MyGridCellAttrProvider::~MyGridCellAttrProvider()
  1120. {
  1121. m_attrForOddRows->DecRef();
  1122. }
  1123. wxGridCellAttr *MyGridCellAttrProvider::GetAttr(int row, int col,
  1124. wxGridCellAttr::wxAttrKind kind /* = wxGridCellAttr::Any */) const
  1125. {
  1126. wxGridCellAttr *attr = wxGridCellAttrProvider::GetAttr(row, col, kind);
  1127. if ( row % 2 )
  1128. {
  1129. if ( !attr )
  1130. {
  1131. attr = m_attrForOddRows;
  1132. attr->IncRef();
  1133. }
  1134. else
  1135. {
  1136. if ( !attr->HasBackgroundColour() )
  1137. {
  1138. wxGridCellAttr *attrNew = attr->Clone();
  1139. attr->DecRef();
  1140. attr = attrNew;
  1141. attr->SetBackgroundColour(*wxLIGHT_GREY);
  1142. }
  1143. }
  1144. }
  1145. return attr;
  1146. }
  1147. void GridFrame::OnVTable(wxCommandEvent& )
  1148. {
  1149. static long s_sizeGrid = 10000;
  1150. s_sizeGrid = wxGetNumberFromUser(wxT("Size of the table to create"),
  1151. wxT("Size: "),
  1152. wxT("wxGridDemo question"),
  1153. s_sizeGrid,
  1154. 0, 32000, this);
  1155. if ( s_sizeGrid != -1 )
  1156. {
  1157. BigGridFrame* win = new BigGridFrame(s_sizeGrid);
  1158. win->Show(true);
  1159. }
  1160. }
  1161. // ----------------------------------------------------------------------------
  1162. // MyGridCellRenderer
  1163. // ----------------------------------------------------------------------------
  1164. // do something that the default renderer doesn't here just to show that it is
  1165. // possible to alter the appearance of the cell beyond what the attributes
  1166. // allow
  1167. void MyGridCellRenderer::Draw(wxGrid& grid,
  1168. wxGridCellAttr& attr,
  1169. wxDC& dc,
  1170. const wxRect& rect,
  1171. int row, int col,
  1172. bool isSelected)
  1173. {
  1174. wxGridCellStringRenderer::Draw(grid, attr, dc, rect, row, col, isSelected);
  1175. dc.SetPen(*wxGREEN_PEN);
  1176. dc.SetBrush(*wxTRANSPARENT_BRUSH);
  1177. dc.DrawEllipse(rect);
  1178. }
  1179. // ============================================================================
  1180. // BigGridFrame and BigGridTable: Sample of a non-standard table
  1181. // ============================================================================
  1182. BigGridFrame::BigGridFrame(long sizeGrid)
  1183. : wxFrame(NULL, wxID_ANY, wxT("Plugin Virtual Table"),
  1184. wxDefaultPosition, wxSize(500, 450))
  1185. {
  1186. m_grid = new wxGrid(this, wxID_ANY, wxDefaultPosition, wxDefaultSize);
  1187. m_table = new BigGridTable(sizeGrid);
  1188. // VZ: I don't understand why this slows down the display that much,
  1189. // must profile it...
  1190. //m_table->SetAttrProvider(new MyGridCellAttrProvider);
  1191. m_grid->SetTable(m_table, true);
  1192. #if defined __WXMOTIF__
  1193. // MB: the grid isn't getting a sensible default size under wxMotif
  1194. int cw, ch;
  1195. GetClientSize( &cw, &ch );
  1196. m_grid->SetSize( cw, ch );
  1197. #endif
  1198. }
  1199. // ============================================================================
  1200. // BugsGridFrame: a "realistic" table
  1201. // ============================================================================
  1202. // ----------------------------------------------------------------------------
  1203. // bugs table data
  1204. // ----------------------------------------------------------------------------
  1205. enum Columns
  1206. {
  1207. Col_Id,
  1208. Col_Summary,
  1209. Col_Severity,
  1210. Col_Priority,
  1211. Col_Platform,
  1212. Col_Opened,
  1213. Col_Max
  1214. };
  1215. enum Severity
  1216. {
  1217. Sev_Wish,
  1218. Sev_Minor,
  1219. Sev_Normal,
  1220. Sev_Major,
  1221. Sev_Critical,
  1222. Sev_Max
  1223. };
  1224. static const wxString severities[] =
  1225. {
  1226. wxT("wishlist"),
  1227. wxT("minor"),
  1228. wxT("normal"),
  1229. wxT("major"),
  1230. wxT("critical"),
  1231. };
  1232. static struct BugsGridData
  1233. {
  1234. int id;
  1235. wxChar summary[80];
  1236. Severity severity;
  1237. int prio;
  1238. wxChar platform[12];
  1239. bool opened;
  1240. } gs_dataBugsGrid [] =
  1241. {
  1242. { 18, wxT("foo doesn't work"), Sev_Major, 1, wxT("wxMSW"), true },
  1243. { 27, wxT("bar crashes"), Sev_Critical, 1, wxT("all"), false },
  1244. { 45, wxT("printing is slow"), Sev_Minor, 3, wxT("wxMSW"), true },
  1245. { 68, wxT("Rectangle() fails"), Sev_Normal, 1, wxT("wxMSW"), false },
  1246. };
  1247. static const wxChar *headers[Col_Max] =
  1248. {
  1249. wxT("Id"),
  1250. wxT("Summary"),
  1251. wxT("Severity"),
  1252. wxT("Priority"),
  1253. wxT("Platform"),
  1254. wxT("Opened?"),
  1255. };
  1256. // ----------------------------------------------------------------------------
  1257. // BugsGridTable
  1258. // ----------------------------------------------------------------------------
  1259. wxString BugsGridTable::GetTypeName(int WXUNUSED(row), int col)
  1260. {
  1261. switch ( col )
  1262. {
  1263. case Col_Id:
  1264. case Col_Priority:
  1265. return wxGRID_VALUE_NUMBER;;
  1266. case Col_Severity:
  1267. // fall thorugh (TODO should be a list)
  1268. case Col_Summary:
  1269. return wxString::Format(wxT("%s:80"), wxGRID_VALUE_STRING);
  1270. case Col_Platform:
  1271. return wxString::Format(wxT("%s:all,MSW,GTK,other"), wxGRID_VALUE_CHOICE);
  1272. case Col_Opened:
  1273. return wxGRID_VALUE_BOOL;
  1274. }
  1275. wxFAIL_MSG(wxT("unknown column"));
  1276. return wxEmptyString;
  1277. }
  1278. int BugsGridTable::GetNumberRows()
  1279. {
  1280. return WXSIZEOF(gs_dataBugsGrid);
  1281. }
  1282. int BugsGridTable::GetNumberCols()
  1283. {
  1284. return Col_Max;
  1285. }
  1286. bool BugsGridTable::IsEmptyCell( int WXUNUSED(row), int WXUNUSED(col) )
  1287. {
  1288. return false;
  1289. }
  1290. wxString BugsGridTable::GetValue( int row, int col )
  1291. {
  1292. const BugsGridData& gd = gs_dataBugsGrid[row];
  1293. switch ( col )
  1294. {
  1295. case Col_Id:
  1296. return wxString::Format(wxT("%d"), gd.id);
  1297. case Col_Priority:
  1298. return wxString::Format(wxT("%d"), gd.prio);
  1299. case Col_Opened:
  1300. return gd.opened ? wxT("1") : wxT("0");
  1301. case Col_Severity:
  1302. return severities[gd.severity];
  1303. case Col_Summary:
  1304. return gd.summary;
  1305. case Col_Platform:
  1306. return gd.platform;
  1307. }
  1308. return wxEmptyString;
  1309. }
  1310. void BugsGridTable::SetValue( int row, int col, const wxString& value )
  1311. {
  1312. BugsGridData& gd = gs_dataBugsGrid[row];
  1313. switch ( col )
  1314. {
  1315. case Col_Id:
  1316. case Col_Priority:
  1317. case Col_Opened:
  1318. wxFAIL_MSG(wxT("unexpected column"));
  1319. break;
  1320. case Col_Severity:
  1321. {
  1322. size_t n;
  1323. for ( n = 0; n < WXSIZEOF(severities); n++ )
  1324. {
  1325. if ( severities[n] == value )
  1326. {
  1327. gd.severity = (Severity)n;
  1328. break;
  1329. }
  1330. }
  1331. if ( n == WXSIZEOF(severities) )
  1332. {
  1333. wxLogWarning(wxT("Invalid severity value '%s'."),
  1334. value.c_str());
  1335. gd.severity = Sev_Normal;
  1336. }
  1337. }
  1338. break;
  1339. case Col_Summary:
  1340. wxStrncpy(gd.summary, value, WXSIZEOF(gd.summary));
  1341. break;
  1342. case Col_Platform:
  1343. wxStrncpy(gd.platform, value, WXSIZEOF(gd.platform));
  1344. break;
  1345. }
  1346. }
  1347. bool
  1348. BugsGridTable::CanGetValueAs(int WXUNUSED(row),
  1349. int col,
  1350. const wxString& typeName)
  1351. {
  1352. if ( typeName == wxGRID_VALUE_STRING )
  1353. {
  1354. return true;
  1355. }
  1356. else if ( typeName == wxGRID_VALUE_BOOL )
  1357. {
  1358. return col == Col_Opened;
  1359. }
  1360. else if ( typeName == wxGRID_VALUE_NUMBER )
  1361. {
  1362. return col == Col_Id || col == Col_Priority || col == Col_Severity;
  1363. }
  1364. else
  1365. {
  1366. return false;
  1367. }
  1368. }
  1369. bool BugsGridTable::CanSetValueAs( int row, int col, const wxString& typeName )
  1370. {
  1371. return CanGetValueAs(row, col, typeName);
  1372. }
  1373. long BugsGridTable::GetValueAsLong( int row, int col )
  1374. {
  1375. const BugsGridData& gd = gs_dataBugsGrid[row];
  1376. switch ( col )
  1377. {
  1378. case Col_Id:
  1379. return gd.id;
  1380. case Col_Priority:
  1381. return gd.prio;
  1382. case Col_Severity:
  1383. return gd.severity;
  1384. default:
  1385. wxFAIL_MSG(wxT("unexpected column"));
  1386. return -1;
  1387. }
  1388. }
  1389. bool BugsGridTable::GetValueAsBool( int row, int col )
  1390. {
  1391. if ( col == Col_Opened )
  1392. {
  1393. return gs_dataBugsGrid[row].opened;
  1394. }
  1395. else
  1396. {
  1397. wxFAIL_MSG(wxT("unexpected column"));
  1398. return false;
  1399. }
  1400. }
  1401. void BugsGridTable::SetValueAsLong( int row, int col, long value )
  1402. {
  1403. BugsGridData& gd = gs_dataBugsGrid[row];
  1404. switch ( col )
  1405. {
  1406. case Col_Priority:
  1407. gd.prio = value;
  1408. break;
  1409. default:
  1410. wxFAIL_MSG(wxT("unexpected column"));
  1411. }
  1412. }
  1413. void BugsGridTable::SetValueAsBool( int row, int col, bool value )
  1414. {
  1415. if ( col == Col_Opened )
  1416. {
  1417. gs_dataBugsGrid[row].opened = value;
  1418. }
  1419. else
  1420. {
  1421. wxFAIL_MSG(wxT("unexpected column"));
  1422. }
  1423. }
  1424. wxString BugsGridTable::GetColLabelValue( int col )
  1425. {
  1426. return headers[col];
  1427. }
  1428. // ----------------------------------------------------------------------------
  1429. // BugsGridFrame
  1430. // ----------------------------------------------------------------------------
  1431. BugsGridFrame::BugsGridFrame()
  1432. : wxFrame(NULL, wxID_ANY, wxT("Bugs table"))
  1433. {
  1434. wxGrid *grid = new wxGrid(this, wxID_ANY);
  1435. wxGridTableBase *table = new BugsGridTable();
  1436. table->SetAttrProvider(new MyGridCellAttrProvider);
  1437. grid->SetTable(table, true);
  1438. wxGridCellAttr *attrRO = new wxGridCellAttr,
  1439. *attrRangeEditor = new wxGridCellAttr,
  1440. *attrCombo = new wxGridCellAttr;
  1441. attrRO->SetReadOnly();
  1442. attrRangeEditor->SetEditor(new wxGridCellNumberEditor(1, 5));
  1443. attrCombo->SetEditor(new wxGridCellChoiceEditor(WXSIZEOF(severities),
  1444. severities));
  1445. grid->SetColAttr(Col_Id, attrRO);
  1446. grid->SetColAttr(Col_Priority, attrRangeEditor);
  1447. grid->SetColAttr(Col_Severity, attrCombo);
  1448. grid->Fit();
  1449. SetClientSize(grid->GetSize());
  1450. }
  1451. // ============================================================================
  1452. // TabularGrid: grid used for display of tabular data
  1453. // ============================================================================
  1454. class TabularGridTable : public wxGridTableBase
  1455. {
  1456. public:
  1457. enum
  1458. {
  1459. COL_NAME,
  1460. COL_EXT,
  1461. COL_SIZE,
  1462. COL_DATE,
  1463. COL_MAX
  1464. };
  1465. enum
  1466. {
  1467. ROW_MAX = 3
  1468. };
  1469. TabularGridTable() { m_sortOrder = NULL; }
  1470. virtual int GetNumberRows() { return ROW_MAX; }
  1471. virtual int GetNumberCols() { return COL_MAX; }
  1472. virtual wxString GetValue(int row, int col)
  1473. {
  1474. if ( m_sortOrder )
  1475. row = m_sortOrder[row];
  1476. switch ( col )
  1477. {
  1478. case COL_NAME:
  1479. case COL_EXT:
  1480. return GetNameOrExt(row, col);
  1481. case COL_SIZE:
  1482. return wxString::Format("%lu", GetSize(row));
  1483. case COL_DATE:
  1484. return GetDate(row).FormatDate();
  1485. case COL_MAX:
  1486. default:
  1487. wxFAIL_MSG( "unknown column" );
  1488. }
  1489. return wxString();
  1490. }
  1491. virtual void SetValue(int, int, const wxString&)
  1492. {
  1493. wxFAIL_MSG( "shouldn't be called" );
  1494. }
  1495. virtual wxString GetColLabelValue(int col)
  1496. {
  1497. // notice that column parameter here always refers to the internal
  1498. // column index, independently of its position on the screen
  1499. static const char *labels[] = { "Name", "Extension", "Size", "Date" };
  1500. wxCOMPILE_TIME_ASSERT( WXSIZEOF(labels) == COL_MAX, LabelsMismatch );
  1501. return labels[col];
  1502. }
  1503. virtual void SetColLabelValue(int, const wxString&)
  1504. {
  1505. wxFAIL_MSG( "shouldn't be called" );
  1506. }
  1507. void Sort(int col, bool ascending)
  1508. {
  1509. // we hardcode all sorting orders for simplicity here
  1510. static int sortOrders[COL_MAX][2][ROW_MAX] =
  1511. {
  1512. // descending ascending
  1513. { { 2, 1, 0 }, { 0, 1, 2 } },
  1514. { { 2, 1, 0 }, { 0, 1, 2 } },
  1515. { { 2, 1, 0 }, { 0, 1, 2 } },
  1516. { { 1, 0, 2 }, { 2, 0, 1 } },
  1517. };
  1518. m_sortOrder = col == wxNOT_FOUND ? NULL : sortOrders[col][ascending];
  1519. }
  1520. private:
  1521. wxString GetNameOrExt(int row, int col) const
  1522. {
  1523. static const char *
  1524. names[] = { "autoexec.bat", "boot.ini", "io.sys" };
  1525. wxCOMPILE_TIME_ASSERT( WXSIZEOF(names) == ROW_MAX, NamesMismatch );
  1526. const wxString s(names[row]);
  1527. return col == COL_NAME ? s.BeforeFirst('.') : s.AfterLast('.');
  1528. }
  1529. unsigned long GetSize(int row) const
  1530. {
  1531. static const unsigned long
  1532. sizes[] = { 412, 604, 40774 };
  1533. wxCOMPILE_TIME_ASSERT( WXSIZEOF(sizes) == ROW_MAX, SizesMismatch );
  1534. return sizes[row];
  1535. }
  1536. wxDateTime GetDate(int row) const
  1537. {
  1538. static const char *
  1539. dates[] = { "2004-04-17", "2006-05-27", "1994-05-31" };
  1540. wxCOMPILE_TIME_ASSERT( WXSIZEOF(dates) == ROW_MAX, DatesMismatch );
  1541. wxDateTime dt;
  1542. dt.ParseISODate(dates[row]);
  1543. return dt;
  1544. }
  1545. int *m_sortOrder;
  1546. };
  1547. // specialized text control for column indexes entry
  1548. class ColIndexEntry : public wxTextCtrl
  1549. {
  1550. public:
  1551. ColIndexEntry(wxWindow *parent)
  1552. : wxTextCtrl(parent, wxID_ANY, "")
  1553. {
  1554. SetValidator(wxTextValidator(wxFILTER_NUMERIC));
  1555. }
  1556. int GetCol()
  1557. {
  1558. unsigned long col;
  1559. if ( !GetValue().ToULong(&col) || col > TabularGridTable::COL_MAX )
  1560. {
  1561. SetFocus();
  1562. return -1;
  1563. }
  1564. return col;
  1565. }
  1566. protected:
  1567. virtual wxSize DoGetBestSize() const
  1568. {
  1569. wxSize size = wxTextCtrl::DoGetBestSize();
  1570. size.x = 3*GetCharWidth();
  1571. return size;
  1572. }
  1573. };
  1574. class TabularGridFrame : public wxFrame
  1575. {
  1576. public:
  1577. TabularGridFrame();
  1578. private:
  1579. enum // control ids
  1580. {
  1581. Id_Check_UseNativeHeader,
  1582. Id_Check_DrawNativeLabels,
  1583. Id_Check_ShowRowLabels,
  1584. Id_Check_EnableColMove
  1585. };
  1586. // event handlers
  1587. void OnToggleUseNativeHeader(wxCommandEvent&)
  1588. {
  1589. m_grid->UseNativeColHeader(m_chkUseNative->IsChecked());
  1590. }
  1591. void OnUpdateDrawNativeLabelsUI(wxUpdateUIEvent& event)
  1592. {
  1593. // we don't draw labels at all, native or otherwise, if we use the
  1594. // native header control
  1595. event.Enable( !m_chkUseNative->GetValue() );
  1596. }
  1597. void OnToggleDrawNativeLabels(wxCommandEvent&)
  1598. {
  1599. m_grid->SetUseNativeColLabels(m_chkDrawNative->IsChecked());
  1600. }
  1601. void OnToggleShowRowLabels(wxCommandEvent&)
  1602. {
  1603. m_grid->SetRowLabelSize(m_chkShowRowLabels->IsChecked()
  1604. ? wxGRID_AUTOSIZE
  1605. : 0);
  1606. }
  1607. void OnToggleColMove(wxCommandEvent&)
  1608. {
  1609. m_grid->EnableDragColMove(m_chkEnableColMove->IsChecked());
  1610. }
  1611. void OnShowHideColumn(wxCommandEvent& event)
  1612. {
  1613. int col = m_txtColShowHide->GetCol();
  1614. if ( col != -1 )
  1615. {
  1616. m_grid->SetColSize(col,
  1617. event.GetId() == wxID_ADD ? wxGRID_AUTOSIZE : 0);
  1618. UpdateOrderAndVisibility();
  1619. }
  1620. }
  1621. void OnMoveColumn(wxCommandEvent&)
  1622. {
  1623. int col = m_txtColIndex->GetCol();
  1624. int pos = m_txtColPos->GetCol();
  1625. if ( col == -1 || pos == -1 )
  1626. return;
  1627. m_grid->SetColPos(col, pos);
  1628. UpdateOrderAndVisibility();
  1629. }
  1630. void OnResetColumnOrder(wxCommandEvent&)
  1631. {
  1632. m_grid->ResetColPos();
  1633. UpdateOrderAndVisibility();
  1634. }
  1635. void OnGridColSort(wxGridEvent& event)
  1636. {
  1637. const int col = event.GetCol();
  1638. m_table->Sort(col, !(m_grid->IsSortingBy(col) &&
  1639. m_grid->IsSortOrderAscending()));
  1640. }
  1641. void OnGridColMove(wxGridEvent& event)
  1642. {
  1643. // can't update it yet as the order hasn't been changed, so do it a bit
  1644. // later
  1645. m_shouldUpdateOrder = true;
  1646. event.Skip();
  1647. }
  1648. void OnGridColSize(wxGridSizeEvent& event)
  1649. {
  1650. // we only catch this event to react to the user showing or hiding this
  1651. // column using the header control menu and not because we're
  1652. // interested in column resizing
  1653. UpdateOrderAndVisibility();
  1654. event.Skip();
  1655. }
  1656. void OnIdle(wxIdleEvent& event)
  1657. {
  1658. if ( m_shouldUpdateOrder )
  1659. {
  1660. m_shouldUpdateOrder = false;
  1661. UpdateOrderAndVisibility();
  1662. }
  1663. event.Skip();
  1664. }
  1665. void UpdateOrderAndVisibility()
  1666. {
  1667. wxString s;
  1668. for ( int pos = 0; pos < TabularGridTable::COL_MAX; pos++ )
  1669. {
  1670. const int col = m_grid->GetColAt(pos);
  1671. const bool isHidden = m_grid->GetColSize(col) == 0;
  1672. if ( isHidden )
  1673. s << '[';
  1674. s << col;
  1675. if ( isHidden )
  1676. s << ']';
  1677. s << ' ';
  1678. }
  1679. m_statOrder->SetLabel(s);
  1680. }
  1681. // controls
  1682. wxGrid *m_grid;
  1683. TabularGridTable *m_table;
  1684. wxCheckBox *m_chkUseNative,
  1685. *m_chkDrawNative,
  1686. *m_chkShowRowLabels,
  1687. *m_chkEnableColMove;
  1688. ColIndexEntry *m_txtColIndex,
  1689. *m_txtColPos,
  1690. *m_txtColShowHide;
  1691. wxStaticText *m_statOrder;
  1692. // fla for EVT_IDLE handler
  1693. bool m_shouldUpdateOrder;
  1694. wxDECLARE_NO_COPY_CLASS(TabularGridFrame);
  1695. wxDECLARE_EVENT_TABLE();
  1696. };
  1697. wxBEGIN_EVENT_TABLE(TabularGridFrame, wxFrame)
  1698. EVT_CHECKBOX(Id_Check_UseNativeHeader,
  1699. TabularGridFrame::OnToggleUseNativeHeader)
  1700. EVT_CHECKBOX(Id_Check_DrawNativeLabels,
  1701. TabularGridFrame::OnToggleDrawNativeLabels)
  1702. EVT_CHECKBOX(Id_Check_ShowRowLabels,
  1703. TabularGridFrame::OnToggleShowRowLabels)
  1704. EVT_CHECKBOX(Id_Check_EnableColMove,
  1705. TabularGridFrame::OnToggleColMove)
  1706. EVT_UPDATE_UI(Id_Check_DrawNativeLabels,
  1707. TabularGridFrame::OnUpdateDrawNativeLabelsUI)
  1708. EVT_BUTTON(wxID_APPLY, TabularGridFrame::OnMoveColumn)
  1709. EVT_BUTTON(wxID_RESET, TabularGridFrame::OnResetColumnOrder)
  1710. EVT_BUTTON(wxID_ADD, TabularGridFrame::OnShowHideColumn)
  1711. EVT_BUTTON(wxID_DELETE, TabularGridFrame::OnShowHideColumn)
  1712. EVT_GRID_COL_SORT(TabularGridFrame::OnGridColSort)
  1713. EVT_GRID_COL_MOVE(TabularGridFrame::OnGridColMove)
  1714. EVT_GRID_COL_SIZE(TabularGridFrame::OnGridColSize)
  1715. EVT_IDLE(TabularGridFrame::OnIdle)
  1716. wxEND_EVENT_TABLE()
  1717. TabularGridFrame::TabularGridFrame()
  1718. : wxFrame(NULL, wxID_ANY, "Tabular table")
  1719. {
  1720. m_shouldUpdateOrder = false;
  1721. wxPanel * const panel = new wxPanel(this);
  1722. // create and initialize the grid with the specified data
  1723. m_table = new TabularGridTable;
  1724. m_grid = new wxGrid(panel, wxID_ANY,
  1725. wxDefaultPosition, wxDefaultSize,
  1726. wxBORDER_STATIC | wxWANTS_CHARS);
  1727. m_grid->SetTable(m_table, true, wxGrid::wxGridSelectRows);
  1728. m_grid->EnableDragColMove();
  1729. m_grid->UseNativeColHeader();
  1730. m_grid->HideRowLabels();
  1731. // add it and the other controls to the frame
  1732. wxSizer * const sizerTop = new wxBoxSizer(wxVERTICAL);
  1733. sizerTop->Add(m_grid, wxSizerFlags(1).Expand().Border());
  1734. wxSizer * const sizerControls = new wxBoxSizer(wxHORIZONTAL);
  1735. wxSizer * const sizerStyles = new wxBoxSizer(wxVERTICAL);
  1736. m_chkUseNative = new wxCheckBox(panel, Id_Check_UseNativeHeader,
  1737. "&Use native header");
  1738. m_chkUseNative->SetValue(true);
  1739. sizerStyles->Add(m_chkUseNative, wxSizerFlags().Border());
  1740. m_chkDrawNative = new wxCheckBox(panel, Id_Check_DrawNativeLabels,
  1741. "&Draw native column labels");
  1742. sizerStyles->Add(m_chkDrawNative, wxSizerFlags().Border());
  1743. m_chkShowRowLabels = new wxCheckBox(panel, Id_Check_ShowRowLabels,
  1744. "Show &row labels");
  1745. sizerStyles->Add(m_chkShowRowLabels, wxSizerFlags().Border());
  1746. m_chkEnableColMove = new wxCheckBox(panel, Id_Check_EnableColMove,
  1747. "Allow column re&ordering");
  1748. m_chkEnableColMove->SetValue(true);
  1749. sizerStyles->Add(m_chkEnableColMove, wxSizerFlags().Border());
  1750. sizerControls->Add(sizerStyles);
  1751. sizerControls->AddSpacer(10);
  1752. wxSizer * const sizerColumns = new wxBoxSizer(wxVERTICAL);
  1753. wxSizer * const sizerMoveCols = new wxBoxSizer(wxHORIZONTAL);
  1754. const wxSizerFlags
  1755. flagsHorz(wxSizerFlags().Border(wxLEFT | wxRIGHT).Centre());
  1756. sizerMoveCols->Add(new wxStaticText(panel, wxID_ANY, "&Move column"),
  1757. flagsHorz);
  1758. m_txtColIndex = new ColIndexEntry(panel);
  1759. sizerMoveCols->Add(m_txtColIndex, flagsHorz);
  1760. sizerMoveCols->Add(new wxStaticText(panel, wxID_ANY, "&to"), flagsHorz);
  1761. m_txtColPos = new ColIndexEntry(panel);
  1762. sizerMoveCols->Add(m_txtColPos, flagsHorz);
  1763. sizerMoveCols->Add(new wxButton(panel, wxID_APPLY), flagsHorz);
  1764. sizerColumns->Add(sizerMoveCols, wxSizerFlags().Expand().Border(wxBOTTOM));
  1765. wxSizer * const sizerShowCols = new wxBoxSizer(wxHORIZONTAL);
  1766. sizerShowCols->Add(new wxStaticText(panel, wxID_ANY, "Current order:"),
  1767. flagsHorz);
  1768. m_statOrder = new wxStaticText(panel, wxID_ANY, "<<< default >>>");
  1769. sizerShowCols->Add(m_statOrder, flagsHorz);
  1770. sizerShowCols->Add(new wxButton(panel, wxID_RESET, "&Reset order"));
  1771. sizerColumns->Add(sizerShowCols, wxSizerFlags().Expand().Border(wxTOP));
  1772. wxSizer * const sizerShowHide = new wxBoxSizer(wxHORIZONTAL);
  1773. sizerShowHide->Add(new wxStaticText(panel, wxID_ANY, "Show/hide column:"),
  1774. flagsHorz);
  1775. m_txtColShowHide = new ColIndexEntry(panel);
  1776. sizerShowHide->Add(m_txtColShowHide, flagsHorz);
  1777. sizerShowHide->Add(new wxButton(panel, wxID_ADD, "&Show"), flagsHorz);
  1778. sizerShowHide->Add(new wxButton(panel, wxID_DELETE, "&Hide"), flagsHorz);
  1779. sizerColumns->Add(sizerShowHide, wxSizerFlags().Expand().Border(wxTOP));
  1780. sizerControls->Add(sizerColumns, wxSizerFlags(1).Expand().Border());
  1781. sizerTop->Add(sizerControls, wxSizerFlags().Expand().Border());
  1782. panel->SetSizer(sizerTop);
  1783. SetClientSize(panel->GetBestSize());
  1784. SetSizeHints(GetSize());
  1785. Show();
  1786. }
  1787. void GridFrame::OnTabularTable(wxCommandEvent&)
  1788. {
  1789. new TabularGridFrame;
  1790. }
  1791. // Example using wxGrid::Render
  1792. // Displays a preset selection or, if it exists, a selection block
  1793. // Draws the selection to a wxBitmap and displays the bitmap
  1794. void GridFrame::OnGridRender( wxCommandEvent& event )
  1795. {
  1796. int styleRender = 0, i;
  1797. bool useLometric = false, defSize = false;
  1798. double zoom = 1;
  1799. wxSize sizeMargin( 0, 0 );
  1800. wxPoint pointOrigin( 0, 0 );
  1801. wxMenu* menu = GetMenuBar()->GetMenu( 0 );
  1802. wxMenuItem* menuItem = menu->FindItem( ID_RENDER_ROW_LABEL );
  1803. menu = menuItem->GetMenu();
  1804. if ( menu->FindItem( ID_RENDER_ROW_LABEL )->IsChecked() )
  1805. styleRender |= wxGRID_DRAW_ROWS_HEADER;
  1806. if ( menu->FindItem( ID_RENDER_COL_LABEL )->IsChecked() )
  1807. styleRender |= wxGRID_DRAW_COLS_HEADER;
  1808. if ( menu->FindItem( ID_RENDER_GRID_LINES )->IsChecked() )
  1809. styleRender |= wxGRID_DRAW_CELL_LINES;
  1810. if ( menu->FindItem( ID_RENDER_GRID_BORDER )->IsChecked() )
  1811. styleRender |= wxGRID_DRAW_BOX_RECT;
  1812. if ( menu->FindItem( ID_RENDER_SELECT_HLIGHT )->IsChecked() )
  1813. styleRender |= wxGRID_DRAW_SELECTION;
  1814. if ( menu->FindItem( ID_RENDER_LOMETRIC )->IsChecked() )
  1815. useLometric = true;
  1816. if ( menu->FindItem( ID_RENDER_MARGIN )->IsChecked() )
  1817. {
  1818. pointOrigin.x += 50;
  1819. pointOrigin.y += 50;
  1820. sizeMargin.IncBy( 50 );
  1821. }
  1822. if ( menu->FindItem( ID_RENDER_ZOOM )->IsChecked() )
  1823. zoom = 1.25;
  1824. if ( menu->FindItem( ID_RENDER_DEFAULT_SIZE )->IsChecked() )
  1825. defSize = true;
  1826. // init render area coords with a default row and col selection
  1827. wxGridCellCoords topLeft( 0, 0 ), bottomRight( 8, 6 );
  1828. // check whether we are printing a block selection
  1829. // other selection types not catered for here
  1830. if ( event.GetId() == ID_RENDER_COORDS )
  1831. {
  1832. topLeft.SetCol( 6 );
  1833. topLeft.SetRow( 4 );
  1834. bottomRight.SetCol( 15 );
  1835. bottomRight.SetRow( 29 );
  1836. }
  1837. else if ( grid->IsSelection() && grid->GetSelectionBlockTopLeft().Count() )
  1838. {
  1839. wxGridCellCoordsArray cells = grid->GetSelectionBlockTopLeft();
  1840. if ( grid->GetSelectionBlockBottomRight().Count() )
  1841. {
  1842. cells.Add( grid->GetSelectionBlockBottomRight()[ 0 ] );
  1843. topLeft.Set( cells[ 0 ].GetRow(),
  1844. cells[ 0 ].GetCol() );
  1845. bottomRight.Set( cells[ 1 ].GetRow(),
  1846. cells[ 1 ].GetCol() );
  1847. }
  1848. }
  1849. // sum col widths
  1850. wxSize sizeRender( 0, 0 );
  1851. wxGridSizesInfo sizeinfo = grid->GetColSizes();
  1852. for ( i = topLeft.GetCol(); i <= bottomRight.GetCol(); i++ )
  1853. {
  1854. sizeRender.x += sizeinfo.GetSize( i );
  1855. }
  1856. // sum row heights
  1857. sizeinfo = grid->GetRowSizes();
  1858. for ( i = topLeft.GetRow(); i <= bottomRight.GetRow(); i++ )
  1859. {
  1860. sizeRender.y += sizeinfo.GetSize( i );
  1861. }
  1862. if ( styleRender & wxGRID_DRAW_ROWS_HEADER )
  1863. sizeRender.x += grid->GetRowLabelSize();
  1864. if ( styleRender & wxGRID_DRAW_COLS_HEADER )
  1865. sizeRender.y += grid->GetColLabelSize();
  1866. sizeRender.x *= zoom;
  1867. sizeRender.y *= zoom;
  1868. // delete any existing render frame and create new one
  1869. wxWindow* win = FindWindow( "frameRender" );
  1870. if ( win )
  1871. win->Destroy();
  1872. wxFrame* frame = new wxFrame( this, wxID_ANY, "Grid Render" );
  1873. frame->SetClientSize( 780, 400 );
  1874. frame->SetName( "frameRender" );
  1875. wxPanel* canvas = new wxPanel( frame, wxID_ANY );
  1876. // make bitmap large enough for margins if any
  1877. if ( !defSize )
  1878. sizeRender.IncBy( sizeMargin * 2 );
  1879. else
  1880. sizeRender.IncBy( sizeMargin );
  1881. wxBitmap bmp( sizeRender );
  1882. // don't leave it larger or drawing will be scaled
  1883. sizeRender.DecBy( sizeMargin * 2 );
  1884. wxMemoryDC memDc(bmp);
  1885. // default row labels have no background colour so set background
  1886. memDc.SetBackground( wxBrush( canvas->GetBackgroundColour() ) );
  1887. memDc.Clear();
  1888. // convert sizeRender to mapping mode units if necessary
  1889. if ( useLometric )
  1890. {
  1891. memDc.SetMapMode( wxMM_LOMETRIC );
  1892. sizeRender.x = memDc.DeviceToLogicalXRel( sizeRender.x );
  1893. sizeRender.y = memDc.DeviceToLogicalYRel( sizeRender.y );
  1894. }
  1895. // pass wxDefaultSize if menu item is checked
  1896. if ( defSize )
  1897. sizeRender = wxDefaultSize;
  1898. grid->Render( memDc,
  1899. pointOrigin,
  1900. sizeRender,
  1901. topLeft, bottomRight,
  1902. wxGridRenderStyle( styleRender ) );
  1903. m_gridBitmap = bmp;
  1904. canvas->Connect( wxEVT_PAINT,
  1905. wxPaintEventHandler(GridFrame::OnRenderPaint),
  1906. NULL,
  1907. this );
  1908. frame->Show();
  1909. }
  1910. void GridFrame::OnRenderPaint( wxPaintEvent& event )
  1911. {
  1912. wxPanel* canvas = ( wxPanel* )event.GetEventObject();
  1913. wxPaintDC dc( canvas );
  1914. canvas->PrepareDC( dc );
  1915. if ( !m_gridBitmap.IsOk() )
  1916. return;;
  1917. wxMemoryDC memDc( m_gridBitmap );
  1918. dc.Blit( 0, 0,
  1919. m_gridBitmap.GetWidth(),
  1920. m_gridBitmap.GetHeight(),
  1921. &memDc, 0, 0 );
  1922. }
  1923. void GridFrame::HideCol( wxCommandEvent& WXUNUSED(event) )
  1924. {
  1925. grid->HideCol(0);
  1926. }
  1927. void GridFrame::ShowCol( wxCommandEvent& WXUNUSED(event) )
  1928. {
  1929. grid->ShowCol(0);
  1930. }
  1931. void GridFrame::HideRow( wxCommandEvent& WXUNUSED(event) )
  1932. {
  1933. grid->HideRow(1);
  1934. }
  1935. void GridFrame::ShowRow( wxCommandEvent& WXUNUSED(event) )
  1936. {
  1937. grid->ShowRow(1);
  1938. }