Fixed bugs in, and added operators and copy constructors to, style
[wxWidgets.git] / samples / richtext / richtext.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: samples/richtext/richtext.cpp
3 // Purpose: wxWidgets rich text editor sample
4 // Author: Julian Smart
5 // Modified by:
6 // Created: 2005-10-02
7 // RCS-ID: $Id$
8 // Copyright: (c) Julian Smart
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 // For compilers that support precompilation, includes "wx/wx.h".
21 #include "wx/wxprec.h"
22
23 #ifdef __BORLANDC__
24 #pragma hdrstop
25 #endif
26
27 // for all others, include the necessary headers (this file is usually all you
28 // need because it includes almost all "standard" wxWidgets headers)
29 #ifndef WX_PRECOMP
30 #include "wx/wx.h"
31 #endif
32
33 #include "wx/fontdlg.h"
34 #include "wx/splitter.h"
35 #include "wx/sstream.h"
36 #include "wx/html/htmlwin.h"
37
38 #ifndef __WXMSW__
39 #include "../sample.xpm"
40 #endif
41
42 #include "bitmaps/smiley.xpm"
43 // #include "bitmaps/idea.xpm"
44 #include "bitmaps/zebra.xpm"
45
46 #include "bitmaps/open.xpm"
47 #include "bitmaps/save.xpm"
48 #include "bitmaps/copy.xpm"
49 #include "bitmaps/cut.xpm"
50 #include "bitmaps/paste.xpm"
51 #include "bitmaps/undo.xpm"
52 #include "bitmaps/redo.xpm"
53 #include "bitmaps/bold.xpm"
54 #include "bitmaps/italic.xpm"
55 #include "bitmaps/underline.xpm"
56
57 #include "bitmaps/alignleft.xpm"
58 #include "bitmaps/alignright.xpm"
59 #include "bitmaps/centre.xpm"
60 #include "bitmaps/font.xpm"
61 #include "bitmaps/indentless.xpm"
62 #include "bitmaps/indentmore.xpm"
63
64 #include "wx/richtext/richtextctrl.h"
65 #include "wx/richtext/richtextstyles.h"
66 #include "wx/richtext/richtextxml.h"
67 #include "wx/richtext/richtexthtml.h"
68
69 // ----------------------------------------------------------------------------
70 // resources
71 // ----------------------------------------------------------------------------
72
73 // ----------------------------------------------------------------------------
74 // private classes
75 // ----------------------------------------------------------------------------
76
77 // Define a new application type, each program should derive a class from wxApp
78 class MyApp : public wxApp
79 {
80 public:
81 // override base class virtuals
82 // ----------------------------
83
84 // this one is called on application startup and is a good place for the app
85 // initialization (doing it here and not in the ctor allows to have an error
86 // return: if OnInit() returns false, the application terminates)
87 virtual bool OnInit();
88 virtual int OnExit();
89
90 void CreateStyles();
91
92 wxRichTextStyleSheet* GetStyleSheet() const { return m_styleSheet; }
93
94 wxRichTextStyleSheet* m_styleSheet;
95 };
96
97 // Define a new frame type: this is going to be our main frame
98 class MyFrame : public wxFrame
99 {
100 public:
101 // ctor(s)
102 MyFrame(const wxString& title, wxWindowID id, const wxPoint& pos = wxDefaultPosition,
103 const wxSize& size = wxDefaultSize, long style = wxDEFAULT_FRAME_STYLE);
104
105 // event handlers (these functions should _not_ be virtual)
106 void OnQuit(wxCommandEvent& event);
107 void OnAbout(wxCommandEvent& event);
108
109 void OnOpen(wxCommandEvent& event);
110 void OnSave(wxCommandEvent& event);
111 void OnSaveAs(wxCommandEvent& event);
112
113 void OnBold(wxCommandEvent& event);
114 void OnItalic(wxCommandEvent& event);
115 void OnUnderline(wxCommandEvent& event);
116
117 void OnUpdateBold(wxUpdateUIEvent& event);
118 void OnUpdateItalic(wxUpdateUIEvent& event);
119 void OnUpdateUnderline(wxUpdateUIEvent& event);
120
121 void OnAlignLeft(wxCommandEvent& event);
122 void OnAlignCentre(wxCommandEvent& event);
123 void OnAlignRight(wxCommandEvent& event);
124
125 void OnUpdateAlignLeft(wxUpdateUIEvent& event);
126 void OnUpdateAlignCentre(wxUpdateUIEvent& event);
127 void OnUpdateAlignRight(wxUpdateUIEvent& event);
128
129 void OnFont(wxCommandEvent& event);
130 void OnIndentMore(wxCommandEvent& event);
131 void OnIndentLess(wxCommandEvent& event);
132
133 void OnLineSpacingHalf(wxCommandEvent& event);
134 void OnLineSpacingDouble(wxCommandEvent& event);
135 void OnLineSpacingSingle(wxCommandEvent& event);
136
137 void OnParagraphSpacingMore(wxCommandEvent& event);
138 void OnParagraphSpacingLess(wxCommandEvent& event);
139
140 void OnViewHTML(wxCommandEvent& event);
141
142 void OnSwitchStyleSheets(wxCommandEvent& event);
143
144 // Forward command events to the current rich text control, if any
145 bool ProcessEvent(wxEvent& event);
146
147 private:
148 // any class wishing to process wxWidgets events must use this macro
149 DECLARE_EVENT_TABLE()
150
151 wxRichTextCtrl* m_richTextCtrl;
152 };
153
154 // ----------------------------------------------------------------------------
155 // constants
156 // ----------------------------------------------------------------------------
157
158 // IDs for the controls and the menu commands
159 enum
160 {
161 // menu items
162 ID_Quit = wxID_EXIT,
163 ID_About = wxID_ABOUT,
164
165 ID_FORMAT_BOLD = 100,
166 ID_FORMAT_ITALIC,
167 ID_FORMAT_UNDERLINE,
168 ID_FORMAT_FONT,
169
170 ID_FORMAT_ALIGN_LEFT,
171 ID_FORMAT_ALIGN_CENTRE,
172 ID_FORMAT_ALIGN_RIGHT,
173
174 ID_FORMAT_INDENT_MORE,
175 ID_FORMAT_INDENT_LESS,
176
177 ID_FORMAT_PARAGRAPH_SPACING_MORE,
178 ID_FORMAT_PARAGRAPH_SPACING_LESS,
179
180 ID_FORMAT_LINE_SPACING_HALF,
181 ID_FORMAT_LINE_SPACING_DOUBLE,
182 ID_FORMAT_LINE_SPACING_SINGLE,
183
184 ID_VIEW_HTML,
185 ID_SWITCH_STYLE_SHEETS,
186
187 ID_RICHTEXT_CTRL,
188 ID_RICHTEXT_STYLE_LIST,
189 ID_RICHTEXT_STYLE_COMBO
190 };
191
192 // ----------------------------------------------------------------------------
193 // event tables and other macros for wxWidgets
194 // ----------------------------------------------------------------------------
195
196 // the event tables connect the wxWidgets events with the functions (event
197 // handlers) which process them. It can be also done at run-time, but for the
198 // simple menu events like this the static method is much simpler.
199 BEGIN_EVENT_TABLE(MyFrame, wxFrame)
200 EVT_MENU(ID_Quit, MyFrame::OnQuit)
201 EVT_MENU(ID_About, MyFrame::OnAbout)
202
203 EVT_MENU(wxID_OPEN, MyFrame::OnOpen)
204 EVT_MENU(wxID_SAVE, MyFrame::OnSave)
205 EVT_MENU(wxID_SAVEAS, MyFrame::OnSaveAs)
206
207 EVT_MENU(ID_FORMAT_BOLD, MyFrame::OnBold)
208 EVT_MENU(ID_FORMAT_ITALIC, MyFrame::OnItalic)
209 EVT_MENU(ID_FORMAT_UNDERLINE, MyFrame::OnUnderline)
210
211 EVT_UPDATE_UI(ID_FORMAT_BOLD, MyFrame::OnUpdateBold)
212 EVT_UPDATE_UI(ID_FORMAT_ITALIC, MyFrame::OnUpdateItalic)
213 EVT_UPDATE_UI(ID_FORMAT_UNDERLINE, MyFrame::OnUpdateUnderline)
214
215 EVT_MENU(ID_FORMAT_ALIGN_LEFT, MyFrame::OnAlignLeft)
216 EVT_MENU(ID_FORMAT_ALIGN_CENTRE, MyFrame::OnAlignCentre)
217 EVT_MENU(ID_FORMAT_ALIGN_RIGHT, MyFrame::OnAlignRight)
218
219 EVT_UPDATE_UI(ID_FORMAT_ALIGN_LEFT, MyFrame::OnUpdateAlignLeft)
220 EVT_UPDATE_UI(ID_FORMAT_ALIGN_CENTRE, MyFrame::OnUpdateAlignCentre)
221 EVT_UPDATE_UI(ID_FORMAT_ALIGN_RIGHT, MyFrame::OnUpdateAlignRight)
222
223 EVT_MENU(ID_FORMAT_FONT, MyFrame::OnFont)
224 EVT_MENU(ID_FORMAT_INDENT_MORE, MyFrame::OnIndentMore)
225 EVT_MENU(ID_FORMAT_INDENT_LESS, MyFrame::OnIndentLess)
226
227 EVT_MENU(ID_FORMAT_LINE_SPACING_HALF, MyFrame::OnLineSpacingHalf)
228 EVT_MENU(ID_FORMAT_LINE_SPACING_SINGLE, MyFrame::OnLineSpacingSingle)
229 EVT_MENU(ID_FORMAT_LINE_SPACING_DOUBLE, MyFrame::OnLineSpacingDouble)
230
231 EVT_MENU(ID_FORMAT_PARAGRAPH_SPACING_MORE, MyFrame::OnParagraphSpacingMore)
232 EVT_MENU(ID_FORMAT_PARAGRAPH_SPACING_LESS, MyFrame::OnParagraphSpacingLess)
233
234 EVT_MENU(ID_VIEW_HTML, MyFrame::OnViewHTML)
235 EVT_MENU(ID_SWITCH_STYLE_SHEETS, MyFrame::OnSwitchStyleSheets)
236 END_EVENT_TABLE()
237
238 // Create a new application object: this macro will allow wxWidgets to create
239 // the application object during program execution (it's better than using a
240 // static object for many reasons) and also implements the accessor function
241 // wxGetApp() which will return the reference of the right type (i.e. MyApp and
242 // not wxApp)
243 IMPLEMENT_APP(MyApp)
244
245 // ============================================================================
246 // implementation
247 // ============================================================================
248
249 // ----------------------------------------------------------------------------
250 // the application class
251 // ----------------------------------------------------------------------------
252
253 // 'Main program' equivalent: the program execution "starts" here
254 bool MyApp::OnInit()
255 {
256 m_styleSheet = new wxRichTextStyleSheet;
257
258 CreateStyles();
259
260 // Add extra handlers (plain text is automatically added)
261 wxRichTextBuffer::AddHandler(new wxRichTextXMLHandler);
262 wxRichTextBuffer::AddHandler(new wxRichTextHTMLHandler);
263
264 // Add image handlers
265 #if wxUSE_LIBPNG
266 wxImage::AddHandler( new wxPNGHandler );
267 #endif
268
269 #if wxUSE_LIBJPEG
270 wxImage::AddHandler( new wxJPEGHandler );
271 #endif
272
273 #if wxUSE_GIF
274 wxImage::AddHandler( new wxGIFHandler );
275 #endif
276
277 // create the main application window
278 MyFrame *frame = new MyFrame(_T("wxRichTextCtrl Sample"), wxID_ANY, wxDefaultPosition, wxSize(700, 600));
279
280 // and show it (the frames, unlike simple controls, are not shown when
281 // created initially)
282 frame->Show(true);
283
284 // success: wxApp::OnRun() will be called which will enter the main message
285 // loop and the application will run. If we returned false here, the
286 // application would exit immediately.
287 return true;
288 }
289
290 int MyApp::OnExit()
291 {
292 delete m_styleSheet;
293 return 0;
294 }
295
296 void MyApp::CreateStyles()
297 {
298 // Paragraph styles
299
300 wxFont romanFont(12, wxROMAN, wxNORMAL, wxNORMAL);
301 wxFont swissFont(12, wxSWISS, wxNORMAL, wxNORMAL);
302
303 wxRichTextParagraphStyleDefinition* normalPara = new wxRichTextParagraphStyleDefinition(wxT("Normal"));
304 wxRichTextAttr normalAttr;
305 normalAttr.SetFontFaceName(romanFont.GetFaceName());
306 normalAttr.SetFontSize(12);
307 // Let's set all attributes for this style
308 normalAttr.SetFlags(wxTEXT_ATTR_FONT | wxTEXT_ATTR_BACKGROUND_COLOUR | wxTEXT_ATTR_TEXT_COLOUR|wxTEXT_ATTR_ALIGNMENT|wxTEXT_ATTR_LEFT_INDENT|wxTEXT_ATTR_RIGHT_INDENT|wxTEXT_ATTR_TABS|
309 wxTEXT_ATTR_PARA_SPACING_BEFORE|wxTEXT_ATTR_PARA_SPACING_AFTER|wxTEXT_ATTR_LINE_SPACING|
310 wxTEXT_ATTR_BULLET_STYLE|wxTEXT_ATTR_BULLET_NUMBER);
311 normalPara->SetStyle(normalAttr);
312
313 m_styleSheet->AddParagraphStyle(normalPara);
314
315 wxRichTextParagraphStyleDefinition* indentedPara = new wxRichTextParagraphStyleDefinition(wxT("Indented"));
316 wxRichTextAttr indentedAttr;
317 indentedAttr.SetFontFaceName(romanFont.GetFaceName());
318 indentedAttr.SetFontSize(12);
319 indentedAttr.SetLeftIndent(100, 0);
320 // We only want to affect indentation
321 indentedAttr.SetFlags(wxTEXT_ATTR_LEFT_INDENT|wxTEXT_ATTR_RIGHT_INDENT);
322 indentedPara->SetStyle(indentedAttr);
323
324 m_styleSheet->AddParagraphStyle(indentedPara);
325
326 wxRichTextParagraphStyleDefinition* indentedPara2 = new wxRichTextParagraphStyleDefinition(wxT("Red Bold Indented"));
327 wxRichTextAttr indentedAttr2;
328 indentedAttr2.SetFontFaceName(romanFont.GetFaceName());
329 indentedAttr2.SetFontSize(12);
330 indentedAttr2.SetFontWeight(wxBOLD);
331 indentedAttr2.SetTextColour(*wxRED);
332 indentedAttr2.SetFontSize(12);
333 indentedAttr2.SetLeftIndent(100, 0);
334 // We want to affect indentation, font and text colour
335 indentedAttr2.SetFlags(wxTEXT_ATTR_LEFT_INDENT|wxTEXT_ATTR_RIGHT_INDENT|wxTEXT_ATTR_FONT|wxTEXT_ATTR_TEXT_COLOUR);
336 indentedPara2->SetStyle(indentedAttr2);
337
338 m_styleSheet->AddParagraphStyle(indentedPara2);
339
340 wxRichTextParagraphStyleDefinition* flIndentedPara = new wxRichTextParagraphStyleDefinition(wxT("First Line Indented"));
341 wxRichTextAttr flIndentedAttr;
342 flIndentedAttr.SetFontFaceName(swissFont.GetFaceName());
343 flIndentedAttr.SetFontSize(12);
344 flIndentedAttr.SetLeftIndent(100, -100);
345 // We only want to affect indentation
346 flIndentedAttr.SetFlags(wxTEXT_ATTR_LEFT_INDENT|wxTEXT_ATTR_RIGHT_INDENT);
347 flIndentedPara->SetStyle(flIndentedAttr);
348
349 m_styleSheet->AddParagraphStyle(flIndentedPara);
350
351 // Character styles
352
353 wxRichTextCharacterStyleDefinition* boldDef = new wxRichTextCharacterStyleDefinition(wxT("Bold"));
354 wxRichTextAttr boldAttr;
355 boldAttr.SetFontFaceName(romanFont.GetFaceName());
356 boldAttr.SetFontSize(12);
357 boldAttr.SetFontWeight(wxBOLD);
358 // We only want to affect boldness
359 boldAttr.SetFlags(wxTEXT_ATTR_FONT_WEIGHT);
360 boldDef->SetStyle(boldAttr);
361
362 m_styleSheet->AddCharacterStyle(boldDef);
363
364 wxRichTextCharacterStyleDefinition* italicDef = new wxRichTextCharacterStyleDefinition(wxT("Italic"));
365 wxRichTextAttr italicAttr;
366 italicAttr.SetFontFaceName(romanFont.GetFaceName());
367 italicAttr.SetFontSize(12);
368 italicAttr.SetFontStyle(wxITALIC);
369 // We only want to affect italics
370 italicAttr.SetFlags(wxTEXT_ATTR_FONT_ITALIC);
371 italicDef->SetStyle(italicAttr);
372
373 m_styleSheet->AddCharacterStyle(italicDef);
374
375 wxRichTextCharacterStyleDefinition* redDef = new wxRichTextCharacterStyleDefinition(wxT("Red Bold"));
376 wxRichTextAttr redAttr;
377 redAttr.SetFontFaceName(romanFont.GetFaceName());
378 redAttr.SetFontSize(12);
379 redAttr.SetFontWeight(wxBOLD);
380 redAttr.SetTextColour(*wxRED);
381 // We only want to affect colour, weight and face
382 redAttr.SetFlags(wxTEXT_ATTR_FONT_FACE|wxTEXT_ATTR_FONT_WEIGHT|wxTEXT_ATTR_TEXT_COLOUR);
383 redDef->SetStyle(redAttr);
384
385 m_styleSheet->AddCharacterStyle(redDef);
386 }
387
388 // ----------------------------------------------------------------------------
389 // main frame
390 // ----------------------------------------------------------------------------
391
392 // frame constructor
393 MyFrame::MyFrame(const wxString& title, wxWindowID id, const wxPoint& pos,
394 const wxSize& size, long style)
395 : wxFrame(NULL, id, title, pos, size, style)
396 {
397 // set the frame icon
398 SetIcon(wxICON(sample));
399
400 // create a menu bar
401 wxMenu *fileMenu = new wxMenu;
402
403 // the "About" item should be in the help menu
404 wxMenu *helpMenu = new wxMenu;
405 helpMenu->Append(ID_About, _T("&About...\tF1"), _T("Show about dialog"));
406
407 fileMenu->Append(wxID_OPEN, _T("&Open\tCtrl+O"), _T("Open a file"));
408 fileMenu->Append(wxID_SAVE, _T("&Save\tCtrl+S"), _T("Save a file"));
409 fileMenu->Append(wxID_SAVEAS, _T("&Save As...\tF12"), _T("Save to a new file"));
410 fileMenu->AppendSeparator();
411 fileMenu->Append(ID_VIEW_HTML, _T("&View as HTML"), _T("View HTML"));
412 fileMenu->AppendSeparator();
413 fileMenu->Append(ID_Quit, _T("E&xit\tAlt+X"), _T("Quit this program"));
414
415 wxMenu* editMenu = new wxMenu;
416 editMenu->Append(wxID_UNDO, _("&Undo\tCtrl+Z"));
417 editMenu->Append(wxID_REDO, _("&Redo\tCtrl+Y"));
418 editMenu->AppendSeparator();
419 editMenu->Append(wxID_CUT, _("Cu&t\tCtrl+X"));
420 editMenu->Append(wxID_COPY, _("&Copy\tCtrl+C"));
421 editMenu->Append(wxID_PASTE, _("&Paste\tCtrl+V"));
422
423 editMenu->Append(wxID_CLEAR, _("&Delete\tDel"));
424
425 editMenu->AppendSeparator();
426 editMenu->Append(wxID_SELECTALL, _("Select A&ll\tCtrl+A"));
427 #if 0
428 editMenu->AppendSeparator();
429 editMenu->Append(wxID_FIND, _("&Find...\tCtrl+F"));
430 editMenu->Append(stID_FIND_REPLACE, _("&Replace...\tCtrl+R"));
431 #endif
432
433 wxMenu* formatMenu = new wxMenu;
434 formatMenu->AppendCheckItem(ID_FORMAT_BOLD, _("&Bold\tCtrl+B"));
435 formatMenu->AppendCheckItem(ID_FORMAT_ITALIC, _("&Italic\tCtrl+I"));
436 formatMenu->AppendCheckItem(ID_FORMAT_UNDERLINE, _("&Underline\tCtrl+U"));
437 formatMenu->AppendSeparator();
438 formatMenu->AppendCheckItem(ID_FORMAT_ALIGN_LEFT, _("L&eft Align"));
439 formatMenu->AppendCheckItem(ID_FORMAT_ALIGN_RIGHT, _("&Right Align"));
440 formatMenu->AppendCheckItem(ID_FORMAT_ALIGN_CENTRE, _("&Centre"));
441 formatMenu->AppendSeparator();
442 formatMenu->Append(ID_FORMAT_INDENT_MORE, _("Indent &More"));
443 formatMenu->Append(ID_FORMAT_INDENT_LESS, _("Indent &Less"));
444 formatMenu->AppendSeparator();
445 formatMenu->Append(ID_FORMAT_PARAGRAPH_SPACING_MORE, _("Increase Paragraph &Spacing"));
446 formatMenu->Append(ID_FORMAT_PARAGRAPH_SPACING_LESS, _("Decrease &Paragraph Spacing"));
447 formatMenu->AppendSeparator();
448 formatMenu->Append(ID_FORMAT_LINE_SPACING_SINGLE, _("Normal Line Spacing"));
449 formatMenu->Append(ID_FORMAT_LINE_SPACING_HALF, _("1.5 Line Spacing"));
450 formatMenu->Append(ID_FORMAT_LINE_SPACING_DOUBLE, _("Double Line Spacing"));
451 formatMenu->AppendSeparator();
452 formatMenu->Append(ID_FORMAT_FONT, _("&Font..."));
453 formatMenu->AppendSeparator();
454 formatMenu->Append(ID_SWITCH_STYLE_SHEETS, _("&Switch Style Sheets"));
455
456 // now append the freshly created menu to the menu bar...
457 wxMenuBar *menuBar = new wxMenuBar();
458 menuBar->Append(fileMenu, _T("&File"));
459 menuBar->Append(editMenu, _T("&Edit"));
460 menuBar->Append(formatMenu, _T("F&ormat"));
461 menuBar->Append(helpMenu, _T("&Help"));
462
463 // ... and attach this menu bar to the frame
464 SetMenuBar(menuBar);
465
466 // create a status bar just for fun (by default with 1 pane only)
467 // but don't create it on limited screen space (WinCE)
468 bool is_pda = wxSystemSettings::GetScreenType() <= wxSYS_SCREEN_PDA;
469
470 #if wxUSE_STATUSBAR
471 if ( !is_pda )
472 {
473 CreateStatusBar(2);
474 SetStatusText(_T("Welcome to wxRichTextCtrl!"));
475 }
476 #endif
477
478 wxToolBar* toolBar = CreateToolBar();
479
480 toolBar->AddTool(wxID_OPEN, wxBitmap(open_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Open"));
481 toolBar->AddTool(wxID_SAVEAS, wxBitmap(save_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Save"));
482 toolBar->AddSeparator();
483 toolBar->AddTool(wxID_CUT, wxBitmap(cut_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Cut"));
484 toolBar->AddTool(wxID_COPY, wxBitmap(copy_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Copy"));
485 toolBar->AddTool(wxID_PASTE, wxBitmap(paste_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Paste"));
486 toolBar->AddSeparator();
487 toolBar->AddTool(wxID_UNDO, wxBitmap(undo_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Undo"));
488 toolBar->AddTool(wxID_REDO, wxBitmap(redo_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Redo"));
489 toolBar->AddSeparator();
490 toolBar->AddTool(ID_FORMAT_BOLD, wxBitmap(bold_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Bold"));
491 toolBar->AddTool(ID_FORMAT_ITALIC, wxBitmap(italic_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Italic"));
492 toolBar->AddTool(ID_FORMAT_UNDERLINE, wxBitmap(underline_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Underline"));
493 toolBar->AddSeparator();
494 toolBar->AddTool(ID_FORMAT_ALIGN_LEFT, wxBitmap(alignleft_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Align Left"));
495 toolBar->AddTool(ID_FORMAT_ALIGN_CENTRE, wxBitmap(centre_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Centre"));
496 toolBar->AddTool(ID_FORMAT_ALIGN_RIGHT, wxBitmap(alignright_xpm), wxNullBitmap, true, -1, -1, (wxObject *) NULL, _("Align Right"));
497 toolBar->AddSeparator();
498 toolBar->AddTool(ID_FORMAT_INDENT_LESS, wxBitmap(indentless_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Indent Less"));
499 toolBar->AddTool(ID_FORMAT_INDENT_MORE, wxBitmap(indentmore_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Indent More"));
500 toolBar->AddSeparator();
501 toolBar->AddTool(ID_FORMAT_FONT, wxBitmap(font_xpm), wxNullBitmap, false, -1, -1, (wxObject *) NULL, _("Font"));
502
503 wxRichTextStyleComboCtrl* combo = new wxRichTextStyleComboCtrl(toolBar, ID_RICHTEXT_STYLE_COMBO, wxDefaultPosition, wxSize(200, -1));
504 toolBar->AddControl(combo);
505
506 toolBar->Realize();
507
508 wxSplitterWindow* splitter = new wxSplitterWindow(this, wxID_ANY, wxDefaultPosition, GetClientSize(), wxSP_NO_XP_THEME|wxSP_3D|wxSP_LIVE_UPDATE);
509
510 wxFont textFont = wxFont(12, wxROMAN, wxNORMAL, wxNORMAL);
511 wxFont boldFont = wxFont(12, wxROMAN, wxNORMAL, wxBOLD);
512 wxFont italicFont = wxFont(12, wxROMAN, wxITALIC, wxNORMAL);
513
514 m_richTextCtrl = new wxRichTextCtrl(splitter, ID_RICHTEXT_CTRL, wxEmptyString, wxDefaultPosition, wxSize(200, 200), wxVSCROLL|wxHSCROLL|wxNO_BORDER|wxWANTS_CHARS);
515 wxFont font(12, wxROMAN, wxNORMAL, wxNORMAL);
516
517 m_richTextCtrl->SetFont(font);
518
519 m_richTextCtrl->SetStyleSheet(wxGetApp().GetStyleSheet());
520
521 combo->SetStyleSheet(wxGetApp().GetStyleSheet());
522 combo->SetRichTextCtrl(m_richTextCtrl);
523 combo->UpdateStyles();
524
525 wxRichTextStyleListBox* styleListBox = new wxRichTextStyleListBox(splitter, ID_RICHTEXT_STYLE_LIST);
526
527 wxSize display = wxGetDisplaySize();
528 if ( is_pda && ( display.GetWidth() < display.GetHeight() ) )
529 {
530 splitter->SplitHorizontally(m_richTextCtrl, styleListBox);
531 }
532 else
533 {
534 splitter->SplitVertically(m_richTextCtrl, styleListBox, 500);
535 }
536
537 splitter->UpdateSize();
538
539 styleListBox->SetStyleSheet(wxGetApp().GetStyleSheet());
540 styleListBox->SetRichTextCtrl(m_richTextCtrl);
541 styleListBox->UpdateStyles();
542
543 wxRichTextCtrl& r = *m_richTextCtrl;
544
545 r.BeginSuppressUndo();
546
547 r.BeginParagraphSpacing(0, 20);
548
549 r.BeginAlignment(wxTEXT_ALIGNMENT_CENTRE);
550 r.BeginBold();
551
552 r.BeginFontSize(14);
553 r.WriteText(wxT("Welcome to wxRichTextCtrl, a wxWidgets control for editing and presenting styled text and images"));
554 r.EndFontSize();
555 r.Newline();
556
557 r.BeginItalic();
558 r.WriteText(wxT("by Julian Smart"));
559 r.EndItalic();
560
561 r.EndBold();
562
563 r.Newline();
564 r.WriteImage(wxBitmap(zebra_xpm));
565
566 r.EndAlignment();
567
568 r.Newline();
569 r.Newline();
570
571 r.WriteText(wxT("What can you do with this thing? "));
572 r.WriteImage(wxBitmap(smiley_xpm));
573 r.WriteText(wxT(" Well, you can change text "));
574
575 r.BeginTextColour(wxColour(255, 0, 0));
576 r.WriteText(wxT("colour, like this red bit."));
577 r.EndTextColour();
578
579 r.BeginTextColour(wxColour(0, 0, 255));
580 r.WriteText(wxT(" And this blue bit."));
581 r.EndTextColour();
582
583 r.WriteText(wxT(" Naturally you can make things "));
584 r.BeginBold();
585 r.WriteText(wxT("bold "));
586 r.EndBold();
587 r.BeginItalic();
588 r.WriteText(wxT("or italic "));
589 r.EndItalic();
590 r.BeginUnderline();
591 r.WriteText(wxT("or underlined."));
592 r.EndUnderline();
593
594 r.BeginFontSize(14);
595 r.WriteText(wxT(" Different font sizes on the same line is allowed, too."));
596 r.EndFontSize();
597
598 r.WriteText(wxT(" Next we'll show an indented paragraph."));
599
600 r.BeginLeftIndent(60);
601 r.Newline();
602
603 r.WriteText(wxT("It was in January, the most down-trodden month of an Edinburgh winter. An attractive woman came into the cafe, which is nothing remarkable."));
604 r.EndLeftIndent();
605
606 r.Newline();
607
608 r.WriteText(wxT("Next, we'll show a first-line indent, achieved using BeginLeftIndent(100, -40)."));
609
610 r.BeginLeftIndent(100, -40);
611 r.Newline();
612
613 r.WriteText(wxT("It was in January, the most down-trodden month of an Edinburgh winter. An attractive woman came into the cafe, which is nothing remarkable."));
614 r.EndLeftIndent();
615
616 r.Newline();
617
618 r.WriteText(wxT("Numbered bullets are possible, again using subindents:"));
619
620 r.BeginNumberedBullet(1, 100, 60);
621 r.Newline();
622
623 r.WriteText(wxT("This is my first item. Note that wxRichTextCtrl doesn't automatically do numbering, but this will be added later."));
624 r.EndNumberedBullet();
625
626 r.BeginNumberedBullet(2, 100, 60);
627 r.Newline();
628
629 r.WriteText(wxT("This is my second item."));
630 r.EndNumberedBullet();
631
632 r.Newline();
633
634 r.WriteText(wxT("The following paragraph is right-indented:"));
635
636 r.BeginRightIndent(200);
637 r.Newline();
638
639 r.WriteText(wxT("It was in January, the most down-trodden month of an Edinburgh winter. An attractive woman came into the cafe, which is nothing remarkable."));
640 r.EndRightIndent();
641
642 r.Newline();
643
644 r.WriteText(wxT("The following paragraph is right-aligned with 1.5 line spacing:"));
645
646 r.BeginAlignment(wxTEXT_ALIGNMENT_RIGHT);
647 r.BeginLineSpacing(wxTEXT_ATTR_LINE_SPACING_HALF);
648 r.Newline();
649
650 r.WriteText(wxT("It was in January, the most down-trodden month of an Edinburgh winter. An attractive woman came into the cafe, which is nothing remarkable."));
651 r.EndLineSpacing();
652 r.EndAlignment();
653
654 wxArrayInt tabs;
655 tabs.Add(400);
656 tabs.Add(600);
657 tabs.Add(800);
658 tabs.Add(1000);
659 wxTextAttrEx attr;
660 attr.SetFlags(wxTEXT_ATTR_TABS);
661 attr.SetTabs(tabs);
662 r.SetDefaultStyle(attr);
663
664 r.Newline();
665 r.WriteText(wxT("This line contains tabs:\tFirst tab\tSecond tab\tThird tab"));
666
667 r.Newline();
668 r.WriteText(wxT("Other notable features of wxRichTextCtrl include:"));
669
670 r.BeginSymbolBullet(wxT('*'), 100, 60);
671 r.Newline();
672 r.WriteText(wxT("Compatibility with wxTextCtrl API"));
673 r.EndSymbolBullet();
674
675 r.BeginSymbolBullet(wxT('*'), 100, 60);
676 r.Newline();
677 r.WriteText(wxT("Easy stack-based BeginXXX()...EndXXX() style setting in addition to SetStyle()"));
678 r.EndSymbolBullet();
679
680 r.BeginSymbolBullet(wxT('*'), 100, 60);
681 r.Newline();
682 r.WriteText(wxT("XML loading and saving"));
683 r.EndSymbolBullet();
684
685 r.BeginSymbolBullet(wxT('*'), 100, 60);
686 r.Newline();
687 r.WriteText(wxT("Undo/Redo, with batching option and Undo suppressing"));
688 r.EndSymbolBullet();
689
690 r.BeginSymbolBullet(wxT('*'), 100, 60);
691 r.Newline();
692 r.WriteText(wxT("Clipboard copy and paste"));
693 r.EndSymbolBullet();
694
695 r.BeginSymbolBullet(wxT('*'), 100, 60);
696 r.Newline();
697 r.WriteText(wxT("wxRichTextStyleSheet with named character and paragraph styles, and control for applying named styles"));
698 r.EndSymbolBullet();
699
700 r.BeginSymbolBullet(wxT('*'), 100, 60);
701 r.Newline();
702 r.WriteText(wxT("A design that can easily be extended to other content types, ultimately with text boxes, tables, controls, and so on"));
703 r.EndSymbolBullet();
704
705 r.Newline();
706
707 r.WriteText(wxT("Note: this sample content was generated programmatically from within the MyFrame constructor in the demo. The images were loaded from inline XPMs. Enjoy wxRichTextCtrl!"));
708
709 r.EndParagraphSpacing();
710
711 r.EndSuppressUndo();
712 }
713
714
715 // event handlers
716
717 void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event))
718 {
719 // true is to force the frame to close
720 Close(true);
721 }
722
723 void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
724 {
725 wxString msg;
726 msg.Printf( _T("This is a demo for wxRichTextCtrl, a control for editing styled text.\n(c) Julian Smart, 2005"));
727 wxMessageBox(msg, _T("About wxRichTextCtrl Sample"), wxOK | wxICON_INFORMATION, this);
728 }
729
730 // Forward command events to the current rich text control, if any
731 bool MyFrame::ProcessEvent(wxEvent& event)
732 {
733 if (event.IsCommandEvent() && !event.IsKindOf(CLASSINFO(wxChildFocusEvent)))
734 {
735 // Problem: we can get infinite recursion because the events
736 // climb back up to this frame, and repeat.
737 // Assume that command events don't cause another command event
738 // to be called, so we can rely on inCommand not being overwritten
739
740 static int s_eventType = 0;
741 static wxWindowID s_id = 0;
742
743 if (s_id != event.GetId() && s_eventType != event.GetEventType())
744 {
745 s_eventType = event.GetEventType();
746 s_id = event.GetId();
747
748 wxWindow* focusWin = wxFindFocusDescendant(this);
749 if (focusWin && focusWin->ProcessEvent(event))
750 {
751 //s_command = NULL;
752 s_eventType = 0;
753 s_id = 0;
754 return true;
755 }
756
757 s_eventType = 0;
758 s_id = 0;
759 }
760 else
761 {
762 return false;
763 }
764 }
765
766 return wxFrame::ProcessEvent(event);
767 }
768
769 void MyFrame::OnOpen(wxCommandEvent& WXUNUSED(event))
770 {
771 wxString path;
772 wxString filename;
773 wxArrayInt fileTypes;
774
775 wxString filter = wxRichTextBuffer::GetExtWildcard(false, false, & fileTypes);
776 if (!filter.empty())
777 filter += wxT("|");
778 filter += wxT("All files (*.*)|*.*");
779
780 wxFileDialog dialog(this,
781 _("Choose a filename"),
782 path,
783 filename,
784 filter,
785 wxFD_OPEN);
786
787 if (dialog.ShowModal() == wxID_OK)
788 {
789 wxString path = dialog.GetPath();
790
791 if (!path.empty())
792 {
793 int filterIndex = dialog.GetFilterIndex();
794 int fileType = (filterIndex < (int) fileTypes.GetCount())
795 ? fileTypes[filterIndex]
796 : wxRICHTEXT_TYPE_TEXT;
797 m_richTextCtrl->LoadFile(path, fileType);
798 }
799 }
800 }
801
802 void MyFrame::OnSave(wxCommandEvent& event)
803 {
804 if (m_richTextCtrl->GetFilename().empty())
805 {
806 OnSaveAs(event);
807 return;
808 }
809 m_richTextCtrl->SaveFile();
810 }
811
812 void MyFrame::OnSaveAs(wxCommandEvent& WXUNUSED(event))
813 {
814 wxString filter = wxRichTextBuffer::GetExtWildcard(false, true);
815 wxString path;
816 wxString filename;
817
818 wxFileDialog dialog(this,
819 _("Choose a filename"),
820 path,
821 filename,
822 filter,
823 wxFD_SAVE);
824
825 if (dialog.ShowModal() == wxID_OK)
826 {
827 wxString path = dialog.GetPath();
828
829 if (!path.empty())
830 {
831 m_richTextCtrl->SaveFile(path);
832 }
833 }
834 }
835
836 void MyFrame::OnBold(wxCommandEvent& WXUNUSED(event))
837 {
838 m_richTextCtrl->ApplyBoldToSelection();
839 }
840
841 void MyFrame::OnItalic(wxCommandEvent& WXUNUSED(event))
842 {
843 m_richTextCtrl->ApplyItalicToSelection();
844 }
845
846 void MyFrame::OnUnderline(wxCommandEvent& WXUNUSED(event))
847 {
848 m_richTextCtrl->ApplyUnderlineToSelection();
849 }
850
851
852 void MyFrame::OnUpdateBold(wxUpdateUIEvent& event)
853 {
854 event.Check(m_richTextCtrl->IsSelectionBold());
855 }
856
857 void MyFrame::OnUpdateItalic(wxUpdateUIEvent& event)
858 {
859 event.Check(m_richTextCtrl->IsSelectionItalics());
860 }
861
862 void MyFrame::OnUpdateUnderline(wxUpdateUIEvent& event)
863 {
864 event.Check(m_richTextCtrl->IsSelectionUnderlined());
865 }
866
867 void MyFrame::OnAlignLeft(wxCommandEvent& WXUNUSED(event))
868 {
869 m_richTextCtrl->ApplyAlignmentToSelection(wxTEXT_ALIGNMENT_LEFT);
870 }
871
872 void MyFrame::OnAlignCentre(wxCommandEvent& WXUNUSED(event))
873 {
874 m_richTextCtrl->ApplyAlignmentToSelection(wxTEXT_ALIGNMENT_CENTRE);
875 }
876
877 void MyFrame::OnAlignRight(wxCommandEvent& WXUNUSED(event))
878 {
879 m_richTextCtrl->ApplyAlignmentToSelection(wxTEXT_ALIGNMENT_RIGHT);
880 }
881
882 void MyFrame::OnUpdateAlignLeft(wxUpdateUIEvent& event)
883 {
884 event.Check(m_richTextCtrl->IsSelectionAligned(wxTEXT_ALIGNMENT_LEFT));
885 }
886
887 void MyFrame::OnUpdateAlignCentre(wxUpdateUIEvent& event)
888 {
889 event.Check(m_richTextCtrl->IsSelectionAligned(wxTEXT_ALIGNMENT_CENTRE));
890 }
891
892 void MyFrame::OnUpdateAlignRight(wxUpdateUIEvent& event)
893 {
894 event.Check(m_richTextCtrl->IsSelectionAligned(wxTEXT_ALIGNMENT_RIGHT));
895 }
896
897 void MyFrame::OnFont(wxCommandEvent& WXUNUSED(event))
898 {
899 if (!m_richTextCtrl->HasSelection())
900 return;
901
902 wxRichTextRange range = m_richTextCtrl->GetSelectionRange();
903 wxFontData fontData;
904
905 wxTextAttrEx attr;
906 attr.SetFlags(wxTEXT_ATTR_FONT);
907
908 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
909 fontData.SetInitialFont(attr.GetFont());
910
911 wxFontDialog dialog(this, fontData);
912 if (dialog.ShowModal() == wxID_OK)
913 {
914 fontData = dialog.GetFontData();
915 attr.SetFlags(wxTEXT_ATTR_FONT);
916 attr.SetFont(fontData.GetChosenFont());
917 if (attr.GetFont().Ok())
918 {
919 m_richTextCtrl->SetStyle(range, attr);
920 }
921 }
922 }
923
924 void MyFrame::OnIndentMore(wxCommandEvent& WXUNUSED(event))
925 {
926 wxTextAttrEx attr;
927 attr.SetFlags(wxTEXT_ATTR_LEFT_INDENT);
928
929 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
930 {
931 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
932 if (m_richTextCtrl->HasSelection())
933 range = m_richTextCtrl->GetSelectionRange();
934
935 wxFontData fontData;
936 attr.SetLeftIndent(attr.GetLeftIndent() + 100);
937
938 attr.SetFlags(wxTEXT_ATTR_LEFT_INDENT);
939 m_richTextCtrl->SetStyle(range, attr);
940 }
941 }
942
943 void MyFrame::OnIndentLess(wxCommandEvent& WXUNUSED(event))
944 {
945 wxTextAttrEx attr;
946 attr.SetFlags(wxTEXT_ATTR_LEFT_INDENT);
947
948 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
949 {
950 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
951 if (m_richTextCtrl->HasSelection())
952 range = m_richTextCtrl->GetSelectionRange();
953
954 if (attr.GetLeftIndent() >= 100)
955 {
956 wxFontData fontData;
957 attr.SetLeftIndent(attr.GetLeftIndent() - 100);
958
959 m_richTextCtrl->SetStyle(range, attr);
960 }
961 }
962 }
963
964 void MyFrame::OnLineSpacingHalf(wxCommandEvent& WXUNUSED(event))
965 {
966 wxTextAttrEx attr;
967 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
968
969 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
970 {
971 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
972 if (m_richTextCtrl->HasSelection())
973 range = m_richTextCtrl->GetSelectionRange();
974
975 wxFontData fontData;
976 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
977 attr.SetLineSpacing(15);
978
979 m_richTextCtrl->SetStyle(range, attr);
980 }
981 }
982
983 void MyFrame::OnLineSpacingDouble(wxCommandEvent& WXUNUSED(event))
984 {
985 wxTextAttrEx attr;
986 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
987
988 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
989 {
990 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
991 if (m_richTextCtrl->HasSelection())
992 range = m_richTextCtrl->GetSelectionRange();
993
994 wxFontData fontData;
995 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
996 attr.SetLineSpacing(20);
997
998 m_richTextCtrl->SetStyle(range, attr);
999 }
1000 }
1001
1002 void MyFrame::OnLineSpacingSingle(wxCommandEvent& WXUNUSED(event))
1003 {
1004 wxTextAttrEx attr;
1005 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
1006
1007 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
1008 {
1009 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
1010 if (m_richTextCtrl->HasSelection())
1011 range = m_richTextCtrl->GetSelectionRange();
1012
1013 wxFontData fontData;
1014 attr.SetFlags(wxTEXT_ATTR_LINE_SPACING);
1015 attr.SetLineSpacing(0); // Can also use 10
1016
1017 m_richTextCtrl->SetStyle(range, attr);
1018 }
1019 }
1020
1021 void MyFrame::OnParagraphSpacingMore(wxCommandEvent& WXUNUSED(event))
1022 {
1023 wxTextAttrEx attr;
1024 attr.SetFlags(wxTEXT_ATTR_PARA_SPACING_AFTER);
1025
1026 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
1027 {
1028 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
1029 if (m_richTextCtrl->HasSelection())
1030 range = m_richTextCtrl->GetSelectionRange();
1031
1032 wxFontData fontData;
1033 attr.SetParagraphSpacingAfter(attr.GetParagraphSpacingAfter() + 20);
1034
1035 attr.SetFlags(wxTEXT_ATTR_PARA_SPACING_AFTER);
1036 m_richTextCtrl->SetStyle(range, attr);
1037 }
1038 }
1039
1040 void MyFrame::OnParagraphSpacingLess(wxCommandEvent& WXUNUSED(event))
1041 {
1042 wxTextAttrEx attr;
1043 attr.SetFlags(wxTEXT_ATTR_PARA_SPACING_AFTER);
1044
1045 if (m_richTextCtrl->GetStyle(m_richTextCtrl->GetInsertionPoint(), attr))
1046 {
1047 wxRichTextRange range(m_richTextCtrl->GetInsertionPoint(), m_richTextCtrl->GetInsertionPoint());
1048 if (m_richTextCtrl->HasSelection())
1049 range = m_richTextCtrl->GetSelectionRange();
1050
1051 if (attr.GetParagraphSpacingAfter() >= 20)
1052 {
1053 wxFontData fontData;
1054 attr.SetParagraphSpacingAfter(attr.GetParagraphSpacingAfter() - 20);
1055
1056 attr.SetFlags(wxTEXT_ATTR_PARA_SPACING_AFTER);
1057 m_richTextCtrl->SetStyle(range, attr);
1058 }
1059 }
1060 }
1061
1062 void MyFrame::OnViewHTML(wxCommandEvent& WXUNUSED(event))
1063 {
1064 wxDialog dialog(this, wxID_ANY, _("HTML"), wxDefaultPosition, wxSize(500, 400), wxDEFAULT_DIALOG_STYLE);
1065
1066 wxBoxSizer* boxSizer = new wxBoxSizer(wxVERTICAL);
1067 dialog.SetSizer(boxSizer);
1068
1069 wxHtmlWindow* win = new wxHtmlWindow(& dialog, wxID_ANY, wxDefaultPosition, wxSize(500, 400), wxSUNKEN_BORDER);
1070 boxSizer->Add(win, 1, wxALL, 5);
1071
1072 wxButton* cancelButton = new wxButton(& dialog, wxID_CANCEL, wxT("&Close"));
1073 boxSizer->Add(cancelButton, 0, wxALL|wxCENTRE, 5);
1074
1075 wxString text;
1076 wxStringOutputStream strStream(& text);
1077
1078 wxRichTextHTMLHandler htmlHandler;
1079 if (htmlHandler.SaveFile(& m_richTextCtrl->GetBuffer(), strStream))
1080 {
1081 win->SetPage(text);
1082 }
1083
1084 boxSizer->Fit(& dialog);
1085
1086 dialog.ShowModal();
1087 }
1088
1089 // Demonstrates how you can change the style sheets and have the changes
1090 // reflected in the control content without wiping out character formatting.
1091
1092 void MyFrame::OnSwitchStyleSheets(wxCommandEvent& WXUNUSED(event))
1093 {
1094 static wxRichTextStyleSheet* gs_AlternateStyleSheet = NULL;
1095
1096 wxRichTextCtrl* ctrl = (wxRichTextCtrl*) FindWindow(ID_RICHTEXT_CTRL);
1097 wxRichTextStyleListBox* styleList = (wxRichTextStyleListBox*) FindWindow(ID_RICHTEXT_STYLE_LIST);
1098 wxRichTextStyleComboCtrl* styleCombo = (wxRichTextStyleComboCtrl*) FindWindow(ID_RICHTEXT_STYLE_COMBO);
1099
1100 wxRichTextStyleSheet* sheet = ctrl->GetStyleSheet();
1101
1102 // One-time creation of an alternate style sheet
1103 if (!gs_AlternateStyleSheet)
1104 {
1105 gs_AlternateStyleSheet = new wxRichTextStyleSheet(*sheet);
1106
1107 // Make some modifications
1108 for (int i = 0; i < (int) gs_AlternateStyleSheet->GetParagraphStyleCount(); i++)
1109 {
1110 wxRichTextParagraphStyleDefinition* def = gs_AlternateStyleSheet->GetParagraphStyle(i);
1111
1112 if (def->GetStyle().HasTextColour())
1113 def->GetStyle().SetTextColour(*wxBLUE);
1114
1115 if (def->GetStyle().HasAlignment())
1116 {
1117 if (def->GetStyle().GetAlignment() == wxTEXT_ALIGNMENT_CENTRE)
1118 def->GetStyle().SetAlignment(wxTEXT_ALIGNMENT_RIGHT);
1119 else if (def->GetStyle().GetAlignment() == wxTEXT_ALIGNMENT_LEFT)
1120 def->GetStyle().SetAlignment(wxTEXT_ALIGNMENT_CENTRE);
1121 }
1122 if (def->GetStyle().HasLeftIndent())
1123 {
1124 def->GetStyle().SetLeftIndent(def->GetStyle().GetLeftIndent() * 2);
1125 }
1126 }
1127 }
1128
1129 // Switch sheets
1130 wxRichTextStyleSheet* tmp = gs_AlternateStyleSheet;
1131 gs_AlternateStyleSheet = sheet;
1132 sheet = tmp;
1133
1134 ctrl->SetStyleSheet(sheet);
1135 ctrl->ApplyStyleSheet(sheet); // Makes the control reflect the new style definitions
1136
1137 styleList->SetStyleSheet(sheet);
1138 styleList->UpdateStyles();
1139
1140 styleCombo->SetStyleSheet(sheet);
1141 styleCombo->UpdateStyles();
1142 }