]> git.saurik.com Git - wxWidgets.git/blob - src/common/resource.cpp
Don't complain under MicroWindows if a wxDC's HDC is NULL - it happens
[wxWidgets.git] / src / common / resource.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: resource.cpp
3 // Purpose: Resource system
4 // Author: Julian Smart
5 // Modified by:
6 // Created: 04/01/98
7 // RCS-ID: $Id$
8 // Copyright: (c) Julian Smart and Markus Holzem
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifdef __GNUG__
13 #pragma implementation "resource.h"
14 #endif
15
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
18
19 #ifdef __BORLANDC__
20 #pragma hdrstop
21 #endif
22
23 #if wxUSE_WX_RESOURCES
24
25 #ifdef __VISUALC__
26 #pragma warning(disable:4706) // assignment within conditional expression
27 #endif // VC++
28
29 #ifndef WX_PRECOMP
30 #include "wx/defs.h"
31 #include "wx/setup.h"
32 #include "wx/list.h"
33 #include "wx/hash.h"
34 #include "wx/gdicmn.h"
35 #include "wx/utils.h"
36 #include "wx/types.h"
37 #include "wx/menu.h"
38 #include "wx/stattext.h"
39 #include "wx/button.h"
40 #include "wx/bmpbuttn.h"
41 #include "wx/radiobox.h"
42 #include "wx/listbox.h"
43 #include "wx/choice.h"
44 #include "wx/checkbox.h"
45 #include "wx/settings.h"
46 #include "wx/slider.h"
47 #include "wx/icon.h"
48 #include "wx/statbox.h"
49 #include "wx/statbmp.h"
50 #include "wx/gauge.h"
51 #include "wx/textctrl.h"
52 #include "wx/msgdlg.h"
53 #include "wx/intl.h"
54 #endif
55
56 #if wxUSE_RADIOBTN
57 #include "wx/radiobut.h"
58 #endif
59
60 #if wxUSE_SCROLLBAR
61 #include "wx/scrolbar.h"
62 #endif
63
64 #if wxUSE_COMBOBOX
65 #include "wx/combobox.h"
66 #endif
67
68 #include "wx/validate.h"
69
70 #include "wx/log.h"
71
72 #include <ctype.h>
73 #include <math.h>
74 #include <stdlib.h>
75 #include <string.h>
76
77 #include "wx/resource.h"
78 #include "wx/string.h"
79 #include "wx/wxexpr.h"
80
81 #include "wx/settings.h"
82 #include "wx/stream.h"
83
84 // Forward (private) declarations
85 bool wxResourceInterpretResources(wxResourceTable& table, wxExprDatabase& db);
86 wxItemResource *wxResourceInterpretDialog(wxResourceTable& table, wxExpr *expr, bool isPanel = FALSE);
87 wxItemResource *wxResourceInterpretControl(wxResourceTable& table, wxExpr *expr);
88 wxItemResource *wxResourceInterpretMenu(wxResourceTable& table, wxExpr *expr);
89 wxItemResource *wxResourceInterpretMenuBar(wxResourceTable& table, wxExpr *expr);
90 wxItemResource *wxResourceInterpretString(wxResourceTable& table, wxExpr *expr);
91 wxItemResource *wxResourceInterpretBitmap(wxResourceTable& table, wxExpr *expr);
92 wxItemResource *wxResourceInterpretIcon(wxResourceTable& table, wxExpr *expr);
93 // Interpret list expression
94 wxFont wxResourceInterpretFontSpec(wxExpr *expr);
95
96 bool wxResourceReadOneResource(FILE *fd, wxExprDatabase& db, bool *eof, wxResourceTable *table = (wxResourceTable *) NULL);
97 bool wxResourceReadOneResource(wxInputStream *fd, wxExprDatabase& db, bool *eof, wxResourceTable *table) ;
98 bool wxResourceParseIncludeFile(const wxString& f, wxResourceTable *table = (wxResourceTable *) NULL);
99
100 wxResourceTable *wxDefaultResourceTable = (wxResourceTable *) NULL;
101
102 char *wxResourceBuffer = (char *) NULL;
103 long wxResourceBufferSize = 0;
104 long wxResourceBufferCount = 0;
105 int wxResourceStringPtr = 0;
106
107 void wxInitializeResourceSystem()
108 {
109 wxDefaultResourceTable = new wxResourceTable;
110 }
111
112 void wxCleanUpResourceSystem()
113 {
114 delete wxDefaultResourceTable;
115 if (wxResourceBuffer)
116 delete[] wxResourceBuffer;
117 }
118
119 void wxLogWarning(char *msg)
120 {
121 wxMessageBox(msg, _("Warning"), wxOK);
122 }
123
124 IMPLEMENT_DYNAMIC_CLASS(wxItemResource, wxObject)
125 IMPLEMENT_DYNAMIC_CLASS(wxResourceTable, wxHashTable)
126
127 wxItemResource::wxItemResource()
128 {
129 m_itemType = "";
130 m_title = "";
131 m_name = "";
132 m_windowStyle = 0;
133 m_x = m_y = m_width = m_height = 0;
134 m_value1 = m_value2 = m_value3 = m_value5 = 0;
135 m_value4 = "";
136 m_windowId = 0;
137 m_exStyle = 0;
138 }
139
140 wxItemResource::~wxItemResource()
141 {
142 wxNode *node = m_children.First();
143 while (node)
144 {
145 wxItemResource *item = (wxItemResource *)node->Data();
146 delete item;
147 delete node;
148 node = m_children.First();
149 }
150 }
151
152 /*
153 * Resource table
154 */
155
156 wxResourceTable::wxResourceTable():wxHashTable(wxKEY_STRING), identifiers(wxKEY_STRING)
157 {
158 }
159
160 wxResourceTable::~wxResourceTable()
161 {
162 ClearTable();
163 }
164
165 wxItemResource *wxResourceTable::FindResource(const wxString& name) const
166 {
167 wxItemResource *item = (wxItemResource *)Get(WXSTRINGCAST name);
168 return item;
169 }
170
171 void wxResourceTable::AddResource(wxItemResource *item)
172 {
173 wxString name = item->GetName();
174 if (name == wxT(""))
175 name = item->GetTitle();
176 if (name == wxT(""))
177 name = wxT("no name");
178
179 // Delete existing resource, if any.
180 Delete(name);
181
182 Put(name, item);
183 }
184
185 bool wxResourceTable::DeleteResource(const wxString& name)
186 {
187 wxItemResource *item = (wxItemResource *)Delete(WXSTRINGCAST name);
188 if (item)
189 {
190 // See if any resource has this as its child; if so, delete from
191 // parent's child list.
192 BeginFind();
193 wxNode *node = (wxNode *) NULL;
194 node = Next();
195 while (node != NULL)
196 {
197 wxItemResource *parent = (wxItemResource *)node->Data();
198 if (parent->GetChildren().Member(item))
199 {
200 parent->GetChildren().DeleteObject(item);
201 break;
202 }
203 node = Next();
204 }
205
206 delete item;
207 return TRUE;
208 }
209 else
210 return FALSE;
211 }
212
213 bool wxResourceTable::ParseResourceFile( wxInputStream *is )
214 {
215 wxExprDatabase db;
216 int len = is->StreamSize() ;
217
218 bool eof = FALSE;
219 while ( is->TellI() + 10 < len) // it's a hack because the streams dont support EOF
220 {
221 wxResourceReadOneResource(is, db, &eof, this) ;
222 }
223 return wxResourceInterpretResources(*this, db);
224 }
225
226 bool wxResourceTable::ParseResourceFile(const wxString& filename)
227 {
228 wxExprDatabase db;
229
230 FILE *fd = wxFopen(filename, _T("r"));
231 if (!fd)
232 return FALSE;
233 bool eof = FALSE;
234 while (wxResourceReadOneResource(fd, db, &eof, this) && !eof)
235 {
236 // Loop
237 }
238 fclose(fd);
239 return wxResourceInterpretResources(*this, db);
240 }
241
242 bool wxResourceTable::ParseResourceData(const wxString& data)
243 {
244 wxExprDatabase db;
245 if (!db.ReadFromString(data))
246 {
247 wxLogWarning(_("Ill-formed resource file syntax."));
248 return FALSE;
249 }
250
251 return wxResourceInterpretResources(*this, db);
252 }
253
254 bool wxResourceTable::RegisterResourceBitmapData(const wxString& name, char bits[], int width, int height)
255 {
256 // Register pre-loaded bitmap data
257 wxItemResource *item = new wxItemResource;
258 // item->SetType(wxRESOURCE_TYPE_XBM_DATA);
259 item->SetType(wxT("wxXBMData"));
260 item->SetName(name);
261 item->SetValue1((long)bits);
262 item->SetValue2((long)width);
263 item->SetValue3((long)height);
264 AddResource(item);
265 return TRUE;
266 }
267
268 bool wxResourceTable::RegisterResourceBitmapData(const wxString& name, char **data)
269 {
270 // Register pre-loaded bitmap data
271 wxItemResource *item = new wxItemResource;
272 // item->SetType(wxRESOURCE_TYPE_XPM_DATA);
273 item->SetType(wxT("wxXPMData"));
274 item->SetName(name);
275 item->SetValue1((long)data);
276 AddResource(item);
277 return TRUE;
278 }
279
280 bool wxResourceTable::SaveResource(const wxString& WXUNUSED(filename))
281 {
282 return FALSE;
283 }
284
285 void wxResourceTable::ClearTable()
286 {
287 BeginFind();
288 wxNode *node = Next();
289 while (node)
290 {
291 wxNode *next = Next();
292 wxItemResource *item = (wxItemResource *)node->Data();
293 delete item;
294 delete node;
295 node = next;
296 }
297 }
298
299 wxControl *wxResourceTable::CreateItem(wxWindow *parent, const wxItemResource* childResource, const wxItemResource* parentResource) const
300 {
301 int id = childResource->GetId();
302 if ( id == 0 )
303 id = -1;
304
305 bool dlgUnits = ((parentResource->GetResourceStyle() & wxRESOURCE_DIALOG_UNITS) != 0);
306
307 wxControl *control = (wxControl *) NULL;
308 wxString itemType(childResource->GetType());
309
310 wxPoint pos;
311 wxSize size;
312 if (dlgUnits)
313 {
314 pos = parent->ConvertDialogToPixels(wxPoint(childResource->GetX(), childResource->GetY()));
315 size = parent->ConvertDialogToPixels(wxSize(childResource->GetWidth(), childResource->GetHeight()));
316 }
317 else
318 {
319 pos = wxPoint(childResource->GetX(), childResource->GetY());
320 size = wxSize(childResource->GetWidth(), childResource->GetHeight());
321 }
322
323 if (itemType == wxString(wxT("wxButton")) || itemType == wxString(wxT("wxBitmapButton")))
324 {
325 if (childResource->GetValue4() != wxT(""))
326 {
327 // Bitmap button
328 wxBitmap bitmap = childResource->GetBitmap();
329 if (!bitmap.Ok())
330 {
331 bitmap = wxResourceCreateBitmap(childResource->GetValue4(), (wxResourceTable *)this);
332 ((wxItemResource*) childResource)->SetBitmap(bitmap);
333 }
334 if (!bitmap.Ok())
335 bitmap.LoadFile("cross_bmp", wxBITMAP_TYPE_BMP_RESOURCE);
336 control = new wxBitmapButton(parent, id, bitmap, pos, size,
337 childResource->GetStyle() | wxBU_AUTODRAW, wxDefaultValidator, childResource->GetName());
338 }
339 else
340 // Normal, text button
341 control = new wxButton(parent, id, childResource->GetTitle(), pos, size,
342 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
343 }
344 else if (itemType == wxString(wxT("wxMessage")) || itemType == wxString(wxT("wxStaticText")) ||
345 itemType == wxString(wxT("wxStaticBitmap")))
346 {
347 if (childResource->GetValue4() != wxT("") || itemType == wxString(wxT("wxStaticBitmap")) )
348 {
349 // Bitmap message
350 wxBitmap bitmap = childResource->GetBitmap();
351 if (!bitmap.Ok())
352 {
353 bitmap = wxResourceCreateBitmap(childResource->GetValue4(), (wxResourceTable *)this);
354 ((wxItemResource*) childResource)->SetBitmap(bitmap);
355 }
356 #if wxUSE_BITMAP_MESSAGE
357 #ifdef __WXMSW__
358 // Use a default bitmap
359 if (!bitmap.Ok())
360 bitmap.LoadFile("cross_bmp", wxBITMAP_TYPE_BMP_RESOURCE);
361 #endif
362
363 if (bitmap.Ok())
364 control = new wxStaticBitmap(parent, id, bitmap, pos, size,
365 childResource->GetStyle(), childResource->GetName());
366 #endif
367 }
368 else
369 {
370 control = new wxStaticText(parent, id, childResource->GetTitle(), pos, size,
371 childResource->GetStyle(), childResource->GetName());
372 }
373 }
374 else if (itemType == wxString(wxT("wxText")) || itemType == wxString(wxT("wxTextCtrl")) || itemType == wxString(wxT("wxMultiText")))
375 {
376 control = new wxTextCtrl(parent, id, childResource->GetValue4(), pos, size,
377 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
378 }
379 else if (itemType == wxString(wxT("wxCheckBox")))
380 {
381 control = new wxCheckBox(parent, id, childResource->GetTitle(), pos, size,
382 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
383
384 ((wxCheckBox *)control)->SetValue((childResource->GetValue1() != 0));
385 }
386 #if wxUSE_GAUGE
387 else if (itemType == wxString(wxT("wxGauge")))
388 {
389 control = new wxGauge(parent, id, (int)childResource->GetValue2(), pos, size,
390 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
391
392 ((wxGauge *)control)->SetValue((int)childResource->GetValue1());
393 }
394 #endif
395 #if wxUSE_RADIOBTN
396 else if (itemType == wxString(wxT("wxRadioButton")))
397 {
398 control = new wxRadioButton(parent, id, childResource->GetTitle(), // (int)childResource->GetValue1(),
399 pos, size,
400 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
401 }
402 #endif
403 #if wxUSE_SCROLLBAR
404 else if (itemType == wxString(wxT("wxScrollBar")))
405 {
406 control = new wxScrollBar(parent, id, pos, size,
407 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
408 /*
409 ((wxScrollBar *)control)->SetValue((int)childResource->GetValue1());
410 ((wxScrollBar *)control)->SetPageSize((int)childResource->GetValue2());
411 ((wxScrollBar *)control)->SetObjectLength((int)childResource->GetValue3());
412 ((wxScrollBar *)control)->SetViewLength((int)(long)childResource->GetValue5());
413 */
414 ((wxScrollBar *)control)->SetScrollbar((int)childResource->GetValue1(),(int)childResource->GetValue2(),
415 (int)childResource->GetValue3(),(int)(long)childResource->GetValue5(),FALSE);
416
417 }
418 #endif
419 else if (itemType == wxString(wxT("wxSlider")))
420 {
421 control = new wxSlider(parent, id, (int)childResource->GetValue1(),
422 (int)childResource->GetValue2(), (int)childResource->GetValue3(), pos, size,
423 childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
424 }
425 else if (itemType == wxString(wxT("wxGroupBox")) || itemType == wxString(wxT("wxStaticBox")))
426 {
427 control = new wxStaticBox(parent, id, childResource->GetTitle(), pos, size,
428 childResource->GetStyle(), childResource->GetName());
429 }
430 else if (itemType == wxString(wxT("wxListBox")))
431 {
432 wxStringList& stringList = childResource->GetStringValues();
433 wxString *strings = (wxString *) NULL;
434 int noStrings = 0;
435 if (stringList.Number() > 0)
436 {
437 noStrings = stringList.Number();
438 strings = new wxString[noStrings];
439 wxNode *node = stringList.First();
440 int i = 0;
441 while (node)
442 {
443 strings[i] = (wxChar *)node->Data();
444 i ++;
445 node = node->Next();
446 }
447 }
448 control = new wxListBox(parent, id, pos, size,
449 noStrings, strings, childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
450
451 if (strings)
452 delete[] strings;
453 }
454 else if (itemType == wxString(wxT("wxChoice")))
455 {
456 wxStringList& stringList = childResource->GetStringValues();
457 wxString *strings = (wxString *) NULL;
458 int noStrings = 0;
459 if (stringList.Number() > 0)
460 {
461 noStrings = stringList.Number();
462 strings = new wxString[noStrings];
463 wxNode *node = stringList.First();
464 int i = 0;
465 while (node)
466 {
467 strings[i] = (wxChar *)node->Data();
468 i ++;
469 node = node->Next();
470 }
471 }
472 control = new wxChoice(parent, id, pos, size,
473 noStrings, strings, childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
474
475 if (strings)
476 delete[] strings;
477 }
478 #if wxUSE_COMBOBOX
479 else if (itemType == wxString(wxT("wxComboBox")))
480 {
481 wxStringList& stringList = childResource->GetStringValues();
482 wxString *strings = (wxString *) NULL;
483 int noStrings = 0;
484 if (stringList.Number() > 0)
485 {
486 noStrings = stringList.Number();
487 strings = new wxString[noStrings];
488 wxNode *node = stringList.First();
489 int i = 0;
490 while (node)
491 {
492 strings[i] = (wxChar *)node->Data();
493 i ++;
494 node = node->Next();
495 }
496 }
497 control = new wxComboBox(parent, id, childResource->GetValue4(), pos, size,
498 noStrings, strings, childResource->GetStyle(), wxDefaultValidator, childResource->GetName());
499
500 if (strings)
501 delete[] strings;
502 }
503 #endif
504 else if (itemType == wxString(wxT("wxRadioBox")))
505 {
506 wxStringList& stringList = childResource->GetStringValues();
507 wxString *strings = (wxString *) NULL;
508 int noStrings = 0;
509 if (stringList.Number() > 0)
510 {
511 noStrings = stringList.Number();
512 strings = new wxString[noStrings];
513 wxNode *node = stringList.First();
514 int i = 0;
515 while (node)
516 {
517 strings[i] = (wxChar *)node->Data();
518 i ++;
519 node = node->Next();
520 }
521 }
522 control = new wxRadioBox(parent, (wxWindowID) id, wxString(childResource->GetTitle()), pos, size,
523 noStrings, strings, (int)childResource->GetValue1(), childResource->GetStyle(), wxDefaultValidator,
524 childResource->GetName());
525
526 if (strings)
527 delete[] strings;
528 }
529
530 if ((parentResource->GetResourceStyle() & wxRESOURCE_USE_DEFAULTS) != 0)
531 {
532 // Don't set font; will be inherited from parent.
533 }
534 else
535 {
536 if (control && childResource->GetFont().Ok())
537 {
538 control->SetFont(childResource->GetFont());
539
540 #ifdef __WXMSW__
541 // Force the layout algorithm since the size changes the layout
542 if (control->IsKindOf(CLASSINFO(wxRadioBox)))
543 {
544 control->SetSize(-1, -1, -1, -1, wxSIZE_AUTO_WIDTH|wxSIZE_AUTO_HEIGHT);
545 }
546 #endif
547 }
548 }
549 return control;
550 }
551
552 /*
553 * Interpret database as a series of resources
554 */
555
556 bool wxResourceInterpretResources(wxResourceTable& table, wxExprDatabase& db)
557 {
558 wxNode *node = db.First();
559 while (node)
560 {
561 wxExpr *clause = (wxExpr *)node->Data();
562 wxString functor(clause->Functor());
563
564 wxItemResource *item = (wxItemResource *) NULL;
565 if (functor == wxT("dialog"))
566 item = wxResourceInterpretDialog(table, clause);
567 else if (functor == wxT("panel"))
568 item = wxResourceInterpretDialog(table, clause, TRUE);
569 else if (functor == wxT("menubar"))
570 item = wxResourceInterpretMenuBar(table, clause);
571 else if (functor == wxT("menu"))
572 item = wxResourceInterpretMenu(table, clause);
573 else if (functor == wxT("string"))
574 item = wxResourceInterpretString(table, clause);
575 else if (functor == wxT("bitmap"))
576 item = wxResourceInterpretBitmap(table, clause);
577 else if (functor == wxT("icon"))
578 item = wxResourceInterpretIcon(table, clause);
579
580 if (item)
581 {
582 // Remove any existing resource of same name
583 if (item->GetName() != wxT(""))
584 table.DeleteResource(item->GetName());
585 table.AddResource(item);
586 }
587 node = node->Next();
588 }
589 return TRUE;
590 }
591
592 static const wxChar *g_ValidControlClasses[] =
593 {
594 wxT("wxButton"),
595 wxT("wxBitmapButton"),
596 wxT("wxMessage"),
597 wxT("wxStaticText"),
598 wxT("wxStaticBitmap"),
599 wxT("wxText"),
600 wxT("wxTextCtrl"),
601 wxT("wxMultiText"),
602 wxT("wxListBox"),
603 wxT("wxRadioBox"),
604 wxT("wxRadioButton"),
605 wxT("wxCheckBox"),
606 wxT("wxBitmapCheckBox"),
607 wxT("wxGroupBox"),
608 wxT("wxStaticBox"),
609 wxT("wxSlider"),
610 wxT("wxGauge"),
611 wxT("wxScrollBar"),
612 wxT("wxChoice"),
613 wxT("wxComboBox")
614 };
615
616 static bool wxIsValidControlClass(const wxString& c)
617 {
618 for ( size_t i = 0; i < WXSIZEOF(g_ValidControlClasses); i++ )
619 {
620 if ( c == g_ValidControlClasses[i] )
621 return TRUE;
622 }
623 return FALSE;
624 }
625
626 wxItemResource *wxResourceInterpretDialog(wxResourceTable& table, wxExpr *expr, bool isPanel)
627 {
628 wxItemResource *dialogItem = new wxItemResource;
629 if (isPanel)
630 dialogItem->SetType(wxT("wxPanel"));
631 else
632 dialogItem->SetType(wxT("wxDialog"));
633 wxString style = wxT("");
634 wxString title = wxT("");
635 wxString name = wxT("");
636 wxString backColourHex = wxT("");
637 wxString labelColourHex = wxT("");
638 wxString buttonColourHex = wxT("");
639
640 long windowStyle = wxDEFAULT_DIALOG_STYLE;
641 if (isPanel)
642 windowStyle = 0;
643
644 int x = 0; int y = 0; int width = -1; int height = -1;
645 int isModal = 0;
646 wxExpr *labelFontExpr = (wxExpr *) NULL;
647 wxExpr *buttonFontExpr = (wxExpr *) NULL;
648 wxExpr *fontExpr = (wxExpr *) NULL;
649 expr->GetAttributeValue(wxT("style"), style);
650 expr->GetAttributeValue(wxT("name"), name);
651 expr->GetAttributeValue(wxT("title"), title);
652 expr->GetAttributeValue(wxT("x"), x);
653 expr->GetAttributeValue(wxT("y"), y);
654 expr->GetAttributeValue(wxT("width"), width);
655 expr->GetAttributeValue(wxT("height"), height);
656 expr->GetAttributeValue(wxT("modal"), isModal);
657 expr->GetAttributeValue(wxT("label_font"), &labelFontExpr);
658 expr->GetAttributeValue(wxT("button_font"), &buttonFontExpr);
659 expr->GetAttributeValue(wxT("font"), &fontExpr);
660 expr->GetAttributeValue(wxT("background_colour"), backColourHex);
661 expr->GetAttributeValue(wxT("label_colour"), labelColourHex);
662 expr->GetAttributeValue(wxT("button_colour"), buttonColourHex);
663
664 int useDialogUnits = 0;
665 expr->GetAttributeValue(wxT("use_dialog_units"), useDialogUnits);
666 if (useDialogUnits != 0)
667 dialogItem->SetResourceStyle(dialogItem->GetResourceStyle() | wxRESOURCE_DIALOG_UNITS);
668
669 int useDefaults = 0;
670 expr->GetAttributeValue(wxT("use_system_defaults"), useDefaults);
671 if (useDefaults != 0)
672 dialogItem->SetResourceStyle(dialogItem->GetResourceStyle() | wxRESOURCE_USE_DEFAULTS);
673
674 int id = 0;
675 expr->GetAttributeValue(wxT("id"), id);
676 dialogItem->SetId(id);
677
678 if (style != wxT(""))
679 {
680 windowStyle = wxParseWindowStyle(style);
681 }
682 dialogItem->SetStyle(windowStyle);
683 dialogItem->SetValue1(isModal);
684 if (windowStyle & wxDIALOG_MODAL) // Uses style in wxWin 2
685 dialogItem->SetValue1(TRUE);
686
687 dialogItem->SetName(name);
688 dialogItem->SetTitle(title);
689 dialogItem->SetSize(x, y, width, height);
690
691 // Check for wxWin 1.68-style specifications
692 if (style.Find(wxT("VERTICAL_LABEL")) != -1)
693 dialogItem->SetResourceStyle(dialogItem->GetResourceStyle() | wxRESOURCE_VERTICAL_LABEL);
694 else if (style.Find(wxT("HORIZONTAL_LABEL")) != -1)
695 dialogItem->SetResourceStyle(dialogItem->GetResourceStyle() | wxRESOURCE_HORIZONTAL_LABEL);
696
697 if (backColourHex != wxT(""))
698 {
699 int r = 0;
700 int g = 0;
701 int b = 0;
702 r = wxHexToDec(backColourHex.Mid(0, 2));
703 g = wxHexToDec(backColourHex.Mid(2, 2));
704 b = wxHexToDec(backColourHex.Mid(4, 2));
705 dialogItem->SetBackgroundColour(wxColour((unsigned char)r,(unsigned char)g,(unsigned char)b));
706 }
707 if (labelColourHex != wxT(""))
708 {
709 int r = 0;
710 int g = 0;
711 int b = 0;
712 r = wxHexToDec(labelColourHex.Mid(0, 2));
713 g = wxHexToDec(labelColourHex.Mid(2, 2));
714 b = wxHexToDec(labelColourHex.Mid(4, 2));
715 dialogItem->SetLabelColour(wxColour((unsigned char)r,(unsigned char)g,(unsigned char)b));
716 }
717 if (buttonColourHex != wxT(""))
718 {
719 int r = 0;
720 int g = 0;
721 int b = 0;
722 r = wxHexToDec(buttonColourHex.Mid(0, 2));
723 g = wxHexToDec(buttonColourHex.Mid(2, 2));
724 b = wxHexToDec(buttonColourHex.Mid(4, 2));
725 dialogItem->SetButtonColour(wxColour((unsigned char)r,(unsigned char)g,(unsigned char)b));
726 }
727
728 if (fontExpr)
729 dialogItem->SetFont(wxResourceInterpretFontSpec(fontExpr));
730 else if (buttonFontExpr)
731 dialogItem->SetFont(wxResourceInterpretFontSpec(buttonFontExpr));
732 else if (labelFontExpr)
733 dialogItem->SetFont(wxResourceInterpretFontSpec(labelFontExpr));
734
735 // Now parse all controls
736 wxExpr *controlExpr = expr->GetFirst();
737 while (controlExpr)
738 {
739 if (controlExpr->Number() == 3)
740 {
741 wxString controlKeyword(controlExpr->Nth(1)->StringValue());
742 if (controlKeyword != wxT("") && controlKeyword == wxT("control"))
743 {
744 // The value part: always a list.
745 wxExpr *listExpr = controlExpr->Nth(2);
746 if (listExpr->Type() == PrologList)
747 {
748 wxItemResource *controlItem = wxResourceInterpretControl(table, listExpr);
749 if (controlItem)
750 {
751 dialogItem->GetChildren().Append(controlItem);
752 }
753 }
754 }
755 }
756 controlExpr = controlExpr->GetNext();
757 }
758 return dialogItem;
759 }
760
761 wxItemResource *wxResourceInterpretControl(wxResourceTable& table, wxExpr *expr)
762 {
763 wxItemResource *controlItem = new wxItemResource;
764
765 // First, find the standard features of a control definition:
766 // [optional integer/string id], control name, title, style, name, x, y, width, height
767
768 wxString controlType;
769 wxString style;
770 wxString title;
771 wxString name;
772 int id = 0;
773 long windowStyle = 0;
774 int x = 0; int y = 0; int width = -1; int height = -1;
775 int count = 0;
776
777 wxExpr *expr1 = expr->Nth(0);
778
779 if ( expr1->Type() == PrologString || expr1->Type() == PrologWord )
780 {
781 if ( wxIsValidControlClass(expr1->StringValue()) )
782 {
783 count = 1;
784 controlType = expr1->StringValue();
785 }
786 else
787 {
788 wxString str(expr1->StringValue());
789 id = wxResourceGetIdentifier(str, &table);
790 if (id == 0)
791 {
792 wxLogWarning(_("Could not resolve control class or id '%s'. Use (non-zero) integer instead\n or provide #define (see manual for caveats)"),
793 (const wxChar*) expr1->StringValue());
794 delete controlItem;
795 return (wxItemResource *) NULL;
796 }
797 else
798 {
799 // Success - we have an id, so the 2nd element must be the control class.
800 controlType = expr->Nth(1)->StringValue();
801 count = 2;
802 }
803 }
804 }
805 else if (expr1->Type() == PrologInteger)
806 {
807 id = (int)expr1->IntegerValue();
808 // Success - we have an id, so the 2nd element must be the control class.
809 controlType = expr->Nth(1)->StringValue();
810 count = 2;
811 }
812
813 expr1 = expr->Nth(count);
814 count ++;
815 if ( expr1 )
816 title = expr1->StringValue();
817
818 expr1 = expr->Nth(count);
819 count ++;
820 if (expr1)
821 {
822 style = expr1->StringValue();
823 windowStyle = wxParseWindowStyle(style);
824 }
825
826 expr1 = expr->Nth(count);
827 count ++;
828 if (expr1)
829 name = expr1->StringValue();
830
831 expr1 = expr->Nth(count);
832 count ++;
833 if (expr1)
834 x = (int)expr1->IntegerValue();
835
836 expr1 = expr->Nth(count);
837 count ++;
838 if (expr1)
839 y = (int)expr1->IntegerValue();
840
841 expr1 = expr->Nth(count);
842 count ++;
843 if (expr1)
844 width = (int)expr1->IntegerValue();
845
846 expr1 = expr->Nth(count);
847 count ++;
848 if (expr1)
849 height = (int)expr1->IntegerValue();
850
851 controlItem->SetStyle(windowStyle);
852 controlItem->SetName(name);
853 controlItem->SetTitle(title);
854 controlItem->SetSize(x, y, width, height);
855 controlItem->SetType(controlType);
856 controlItem->SetId(id);
857
858 // Check for wxWin 1.68-style specifications
859 if (style.Find(wxT("VERTICAL_LABEL")) != -1)
860 controlItem->SetResourceStyle(controlItem->GetResourceStyle() | wxRESOURCE_VERTICAL_LABEL);
861 else if (style.Find(wxT("HORIZONTAL_LABEL")) != -1)
862 controlItem->SetResourceStyle(controlItem->GetResourceStyle() | wxRESOURCE_HORIZONTAL_LABEL);
863
864 if (controlType == wxT("wxButton"))
865 {
866 // Check for bitmap resource name (in case loading old-style resource file)
867 if (expr->Nth(count) && ((expr->Nth(count)->Type() == PrologString) || (expr->Nth(count)->Type() == PrologWord)))
868 {
869 wxString str(expr->Nth(count)->StringValue());
870 count ++;
871
872 if (str != wxT(""))
873 {
874 controlItem->SetValue4(str);
875 controlItem->SetType(wxT("wxBitmapButton"));
876 }
877 }
878 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
879 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
880 }
881 else if (controlType == wxT("wxBitmapButton"))
882 {
883 // Check for bitmap resource name
884 if (expr->Nth(count) && ((expr->Nth(count)->Type() == PrologString) || (expr->Nth(count)->Type() == PrologWord)))
885 {
886 wxString str(expr->Nth(count)->StringValue());
887 controlItem->SetValue4(str);
888 count ++;
889 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
890 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
891 }
892 }
893 else if (controlType == wxT("wxCheckBox"))
894 {
895 // Check for default value
896 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
897 {
898 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
899 count ++;
900 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
901 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
902 }
903 }
904 #if wxUSE_RADIOBTN
905 else if (controlType == wxT("wxRadioButton"))
906 {
907 // Check for default value
908 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
909 {
910 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
911 count ++;
912 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
913 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
914 }
915 }
916 #endif
917 else if (controlType == wxT("wxText") || controlType == wxT("wxTextCtrl") || controlType == wxT("wxMultiText"))
918 {
919 // Check for default value
920 if (expr->Nth(count) && ((expr->Nth(count)->Type() == PrologString) || (expr->Nth(count)->Type() == PrologWord)))
921 {
922 wxString str(expr->Nth(count)->StringValue());
923 controlItem->SetValue4(str);
924 count ++;
925
926 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
927 {
928 // controlItem->SetLabelFont(wxResourceInterpretFontSpec(expr->Nth(count)));
929 // Skip past the obsolete label font spec if there are two consecutive specs
930 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
931 count ++;
932 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
933 }
934 }
935 }
936 else if (controlType == wxT("wxMessage") || controlType == wxT("wxStaticText"))
937 {
938 // Check for bitmap resource name (in case it's an old-style .wxr file)
939 if (expr->Nth(count) && ((expr->Nth(count)->Type() == PrologString) || (expr->Nth(count)->Type() == PrologWord)))
940 {
941 wxString str(expr->Nth(count)->StringValue());
942 controlItem->SetValue4(str);
943 count ++;
944 controlItem->SetType(wxT("wxStaticText"));
945 }
946 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
947 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
948 }
949 else if (controlType == wxT("wxStaticBitmap"))
950 {
951 // Check for bitmap resource name
952 if (expr->Nth(count) && ((expr->Nth(count)->Type() == PrologString) || (expr->Nth(count)->Type() == PrologWord)))
953 {
954 wxString str(expr->Nth(count)->StringValue());
955 controlItem->SetValue4(str);
956 count ++;
957 }
958 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
959 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
960 }
961 else if (controlType == wxT("wxGroupBox") || controlType == wxT("wxStaticBox"))
962 {
963 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
964 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
965 }
966 else if (controlType == wxT("wxGauge"))
967 {
968 // Check for default value
969 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
970 {
971 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
972 count ++;
973
974 // Check for range
975 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
976 {
977 controlItem->SetValue2(expr->Nth(count)->IntegerValue());
978 count ++;
979
980 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
981 {
982 // Skip past the obsolete label font spec if there are two consecutive specs
983 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
984 count ++;
985 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
986 }
987 }
988 }
989 }
990 else if (controlType == wxT("wxSlider"))
991 {
992 // Check for default value
993 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
994 {
995 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
996 count ++;
997
998 // Check for min
999 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1000 {
1001 controlItem->SetValue2(expr->Nth(count)->IntegerValue());
1002 count ++;
1003
1004 // Check for max
1005 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1006 {
1007 controlItem->SetValue3(expr->Nth(count)->IntegerValue());
1008 count ++;
1009
1010 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1011 {
1012 // controlItem->SetLabelFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1013 // do nothing
1014 count ++;
1015
1016 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1017 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1018 }
1019 }
1020 }
1021 }
1022 }
1023 else if (controlType == wxT("wxScrollBar"))
1024 {
1025 // DEFAULT VALUE
1026 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1027 {
1028 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
1029 count ++;
1030
1031 // PAGE LENGTH
1032 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1033 {
1034 controlItem->SetValue2(expr->Nth(count)->IntegerValue());
1035 count ++;
1036
1037 // OBJECT LENGTH
1038 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1039 {
1040 controlItem->SetValue3(expr->Nth(count)->IntegerValue());
1041 count ++;
1042
1043 // VIEW LENGTH
1044 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1045 controlItem->SetValue5(expr->Nth(count)->IntegerValue());
1046 }
1047 }
1048 }
1049 }
1050 else if (controlType == wxT("wxListBox"))
1051 {
1052 wxExpr *valueList = (wxExpr *) NULL;
1053
1054 if (((valueList = expr->Nth(count)) != 0) && (valueList->Type() == PrologList))
1055 {
1056 wxStringList stringList;
1057 wxExpr *stringExpr = valueList->GetFirst();
1058 while (stringExpr)
1059 {
1060 stringList.Add(stringExpr->StringValue());
1061 stringExpr = stringExpr->GetNext();
1062 }
1063 controlItem->SetStringValues(stringList);
1064 count ++;
1065 // This is now obsolete: it's in the window style.
1066 // Check for wxSINGLE/wxMULTIPLE
1067 wxExpr *mult = (wxExpr *) NULL;
1068 /*
1069 controlItem->SetValue1(wxLB_SINGLE);
1070 */
1071 if (((mult = expr->Nth(count)) != 0) && ((mult->Type() == PrologString)||(mult->Type() == PrologWord)))
1072 {
1073 /*
1074 wxString m(mult->StringValue());
1075 if (m == "wxLB_MULTIPLE")
1076 controlItem->SetValue1(wxLB_MULTIPLE);
1077 else if (m == "wxLB_EXTENDED")
1078 controlItem->SetValue1(wxLB_EXTENDED);
1079 */
1080 // Ignore the value
1081 count ++;
1082 }
1083 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1084 {
1085 // Skip past the obsolete label font spec if there are two consecutive specs
1086 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
1087 count ++;
1088 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1089 }
1090 }
1091 }
1092 else if (controlType == wxT("wxChoice"))
1093 {
1094 wxExpr *valueList = (wxExpr *) NULL;
1095 // Check for default value list
1096 if (((valueList = expr->Nth(count)) != 0) && (valueList->Type() == PrologList))
1097 {
1098 wxStringList stringList;
1099 wxExpr *stringExpr = valueList->GetFirst();
1100 while (stringExpr)
1101 {
1102 stringList.Add(stringExpr->StringValue());
1103 stringExpr = stringExpr->GetNext();
1104 }
1105 controlItem->SetStringValues(stringList);
1106
1107 count ++;
1108
1109 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1110 {
1111 // Skip past the obsolete label font spec if there are two consecutive specs
1112 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
1113 count ++;
1114 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1115 }
1116 }
1117 }
1118 #if wxUSE_COMBOBOX
1119 else if (controlType == wxT("wxComboBox"))
1120 {
1121 wxExpr *textValue = expr->Nth(count);
1122 if (textValue && (textValue->Type() == PrologString || textValue->Type() == PrologWord))
1123 {
1124 wxString str(textValue->StringValue());
1125 controlItem->SetValue4(str);
1126
1127 count ++;
1128
1129 wxExpr *valueList = (wxExpr *) NULL;
1130 // Check for default value list
1131 if (((valueList = expr->Nth(count)) != 0) && (valueList->Type() == PrologList))
1132 {
1133 wxStringList stringList;
1134 wxExpr *stringExpr = valueList->GetFirst();
1135 while (stringExpr)
1136 {
1137 stringList.Add(stringExpr->StringValue());
1138 stringExpr = stringExpr->GetNext();
1139 }
1140 controlItem->SetStringValues(stringList);
1141
1142 count ++;
1143
1144 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1145 {
1146 // Skip past the obsolete label font spec if there are two consecutive specs
1147 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
1148 count ++;
1149 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1150 }
1151 }
1152 }
1153 }
1154 #endif
1155 #if 1
1156 else if (controlType == wxT("wxRadioBox"))
1157 {
1158 wxExpr *valueList = (wxExpr *) NULL;
1159 // Check for default value list
1160 if (((valueList = expr->Nth(count)) != 0) && (valueList->Type() == PrologList))
1161 {
1162 wxStringList stringList;
1163 wxExpr *stringExpr = valueList->GetFirst();
1164 while (stringExpr)
1165 {
1166 stringList.Add(stringExpr->StringValue());
1167 stringExpr = stringExpr->GetNext();
1168 }
1169 controlItem->SetStringValues(stringList);
1170 count ++;
1171
1172 // majorDim (number of rows or cols)
1173 if (expr->Nth(count) && (expr->Nth(count)->Type() == PrologInteger))
1174 {
1175 controlItem->SetValue1(expr->Nth(count)->IntegerValue());
1176 count ++;
1177 }
1178 else
1179 controlItem->SetValue1(0);
1180
1181 if (expr->Nth(count) && expr->Nth(count)->Type() == PrologList)
1182 {
1183 // Skip past the obsolete label font spec if there are two consecutive specs
1184 if (expr->Nth(count+1) && expr->Nth(count+1)->Type() == PrologList)
1185 count ++;
1186 controlItem->SetFont(wxResourceInterpretFontSpec(expr->Nth(count)));
1187 }
1188 }
1189 }
1190 #endif
1191 else
1192 {
1193 delete controlItem;
1194 return (wxItemResource *) NULL;
1195 }
1196 return controlItem;
1197 }
1198
1199 // Forward declaration
1200 wxItemResource *wxResourceInterpretMenu1(wxResourceTable& table, wxExpr *expr);
1201
1202 /*
1203 * Interpet a menu item
1204 */
1205
1206 wxItemResource *wxResourceInterpretMenuItem(wxResourceTable& table, wxExpr *expr)
1207 {
1208 wxItemResource *item = new wxItemResource;
1209
1210 wxExpr *labelExpr = expr->Nth(0);
1211 wxExpr *idExpr = expr->Nth(1);
1212 wxExpr *helpExpr = expr->Nth(2);
1213 wxExpr *checkableExpr = expr->Nth(3);
1214
1215 // Further keywords/attributes to follow sometime...
1216 if (expr->Number() == 0)
1217 {
1218 // item->SetType(wxRESOURCE_TYPE_SEPARATOR);
1219 item->SetType(wxT("wxMenuSeparator"));
1220 return item;
1221 }
1222 else
1223 {
1224 // item->SetType(wxTYPE_MENU); // Well, menu item, but doesn't matter.
1225 item->SetType(wxT("wxMenu")); // Well, menu item, but doesn't matter.
1226 if (labelExpr)
1227 {
1228 wxString str(labelExpr->StringValue());
1229 item->SetTitle(str);
1230 }
1231 if (idExpr)
1232 {
1233 int id = 0;
1234 // If a string or word, must look up in identifier table.
1235 if ((idExpr->Type() == PrologString) || (idExpr->Type() == PrologWord))
1236 {
1237 wxString str(idExpr->StringValue());
1238 id = wxResourceGetIdentifier(str, &table);
1239 if (id == 0)
1240 {
1241 wxLogWarning(_("Could not resolve menu id '%s'. Use (non-zero) integer instead\nor provide #define (see manual for caveats)"),
1242 (const wxChar*) idExpr->StringValue());
1243 }
1244 }
1245 else if (idExpr->Type() == PrologInteger)
1246 id = (int)idExpr->IntegerValue();
1247 item->SetValue1(id);
1248 }
1249 if (helpExpr)
1250 {
1251 wxString str(helpExpr->StringValue());
1252 item->SetValue4(str);
1253 }
1254 if (checkableExpr)
1255 item->SetValue2(checkableExpr->IntegerValue());
1256
1257 // Find the first expression that's a list, for submenu
1258 wxExpr *subMenuExpr = expr->GetFirst();
1259 while (subMenuExpr && (subMenuExpr->Type() != PrologList))
1260 subMenuExpr = subMenuExpr->GetNext();
1261
1262 while (subMenuExpr)
1263 {
1264 wxItemResource *child = wxResourceInterpretMenuItem(table, subMenuExpr);
1265 item->GetChildren().Append(child);
1266 subMenuExpr = subMenuExpr->GetNext();
1267 }
1268 }
1269 return item;
1270 }
1271
1272 /*
1273 * Interpret a nested list as a menu
1274 */
1275 /*
1276 wxItemResource *wxResourceInterpretMenu1(wxResourceTable& table, wxExpr *expr)
1277 {
1278 wxItemResource *menu = new wxItemResource;
1279 // menu->SetType(wxTYPE_MENU);
1280 menu->SetType("wxMenu");
1281 wxExpr *element = expr->GetFirst();
1282 while (element)
1283 {
1284 wxItemResource *item = wxResourceInterpretMenuItem(table, element);
1285 if (item)
1286 menu->GetChildren().Append(item);
1287 element = element->GetNext();
1288 }
1289 return menu;
1290 }
1291 */
1292
1293 wxItemResource *wxResourceInterpretMenu(wxResourceTable& table, wxExpr *expr)
1294 {
1295 wxExpr *listExpr = (wxExpr *) NULL;
1296 expr->GetAttributeValue(wxT("menu"), &listExpr);
1297 if (!listExpr)
1298 return (wxItemResource *) NULL;
1299
1300 wxItemResource *menuResource = wxResourceInterpretMenuItem(table, listExpr);
1301
1302 if (!menuResource)
1303 return (wxItemResource *) NULL;
1304
1305 wxString name;
1306 if (expr->GetAttributeValue(wxT("name"), name))
1307 {
1308 menuResource->SetName(name);
1309 }
1310
1311 return menuResource;
1312 }
1313
1314 wxItemResource *wxResourceInterpretMenuBar(wxResourceTable& table, wxExpr *expr)
1315 {
1316 wxExpr *listExpr = (wxExpr *) NULL;
1317 expr->GetAttributeValue(wxT("menu"), &listExpr);
1318 if (!listExpr)
1319 return (wxItemResource *) NULL;
1320
1321 wxItemResource *resource = new wxItemResource;
1322 resource->SetType(wxT("wxMenu"));
1323 // resource->SetType(wxTYPE_MENU);
1324
1325 wxExpr *element = listExpr->GetFirst();
1326 while (element)
1327 {
1328 wxItemResource *menuResource = wxResourceInterpretMenuItem(table, listExpr);
1329 resource->GetChildren().Append(menuResource);
1330 element = element->GetNext();
1331 }
1332
1333 wxString name;
1334 if (expr->GetAttributeValue(wxT("name"), name))
1335 {
1336 resource->SetName(name);
1337 }
1338
1339 return resource;
1340 }
1341
1342 wxItemResource *wxResourceInterpretString(wxResourceTable& WXUNUSED(table), wxExpr *WXUNUSED(expr))
1343 {
1344 return (wxItemResource *) NULL;
1345 }
1346
1347 wxItemResource *wxResourceInterpretBitmap(wxResourceTable& WXUNUSED(table), wxExpr *expr)
1348 {
1349 wxItemResource *bitmapItem = new wxItemResource;
1350 // bitmapItem->SetType(wxTYPE_BITMAP);
1351 bitmapItem->SetType(wxT("wxBitmap"));
1352 wxString name;
1353 if (expr->GetAttributeValue(wxT("name"), name))
1354 {
1355 bitmapItem->SetName(name);
1356 }
1357 // Now parse all bitmap specifications
1358 wxExpr *bitmapExpr = expr->GetFirst();
1359 while (bitmapExpr)
1360 {
1361 if (bitmapExpr->Number() == 3)
1362 {
1363 wxString bitmapKeyword(bitmapExpr->Nth(1)->StringValue());
1364 if (bitmapKeyword == wxT("bitmap") || bitmapKeyword == wxT("icon"))
1365 {
1366 // The value part: always a list.
1367 wxExpr *listExpr = bitmapExpr->Nth(2);
1368 if (listExpr->Type() == PrologList)
1369 {
1370 wxItemResource *bitmapSpec = new wxItemResource;
1371 // bitmapSpec->SetType(wxTYPE_BITMAP);
1372 bitmapSpec->SetType(wxT("wxBitmap"));
1373
1374 // List is of form: [filename, bitmaptype, platform, colours, xresolution, yresolution]
1375 // where everything after 'filename' is optional.
1376 wxExpr *nameExpr = listExpr->Nth(0);
1377 wxExpr *typeExpr = listExpr->Nth(1);
1378 wxExpr *platformExpr = listExpr->Nth(2);
1379 wxExpr *coloursExpr = listExpr->Nth(3);
1380 wxExpr *xresExpr = listExpr->Nth(4);
1381 wxExpr *yresExpr = listExpr->Nth(5);
1382 if (nameExpr && nameExpr->StringValue() != wxT(""))
1383 {
1384 bitmapSpec->SetName(nameExpr->StringValue());
1385 }
1386 if (typeExpr && typeExpr->StringValue() != wxT(""))
1387 {
1388 bitmapSpec->SetValue1(wxParseWindowStyle(typeExpr->StringValue()));
1389 }
1390 else
1391 bitmapSpec->SetValue1(0);
1392
1393 if (platformExpr && platformExpr->StringValue() != wxT(""))
1394 {
1395 wxString plat(platformExpr->StringValue());
1396 if (plat == wxT("windows") || plat == wxT("WINDOWS"))
1397 bitmapSpec->SetValue2(RESOURCE_PLATFORM_WINDOWS);
1398 else if (plat == wxT("x") || plat == wxT("X"))
1399 bitmapSpec->SetValue2(RESOURCE_PLATFORM_X);
1400 else if (plat == wxT("mac") || plat == wxT("MAC"))
1401 bitmapSpec->SetValue2(RESOURCE_PLATFORM_MAC);
1402 else
1403 bitmapSpec->SetValue2(RESOURCE_PLATFORM_ANY);
1404 }
1405 else
1406 bitmapSpec->SetValue2(RESOURCE_PLATFORM_ANY);
1407
1408 if (coloursExpr)
1409 bitmapSpec->SetValue3(coloursExpr->IntegerValue());
1410 int xres = 0;
1411 int yres = 0;
1412 if (xresExpr)
1413 xres = (int)xresExpr->IntegerValue();
1414 if (yresExpr)
1415 yres = (int)yresExpr->IntegerValue();
1416 bitmapSpec->SetSize(0, 0, xres, yres);
1417
1418 bitmapItem->GetChildren().Append(bitmapSpec);
1419 }
1420 }
1421 }
1422 bitmapExpr = bitmapExpr->GetNext();
1423 }
1424
1425 return bitmapItem;
1426 }
1427
1428 wxItemResource *wxResourceInterpretIcon(wxResourceTable& table, wxExpr *expr)
1429 {
1430 wxItemResource *item = wxResourceInterpretBitmap(table, expr);
1431 if (item)
1432 {
1433 // item->SetType(wxTYPE_ICON);
1434 item->SetType(wxT("wxIcon"));
1435 return item;
1436 }
1437 else
1438 return (wxItemResource *) NULL;
1439 }
1440
1441 // Interpret list expression as a font
1442 wxFont wxResourceInterpretFontSpec(wxExpr *expr)
1443 {
1444 if (expr->Type() != PrologList)
1445 return wxNullFont;
1446
1447 int point = 10;
1448 int family = wxSWISS;
1449 int style = wxNORMAL;
1450 int weight = wxNORMAL;
1451 int underline = 0;
1452 wxString faceName(wxT(""));
1453
1454 wxExpr *pointExpr = expr->Nth(0);
1455 wxExpr *familyExpr = expr->Nth(1);
1456 wxExpr *styleExpr = expr->Nth(2);
1457 wxExpr *weightExpr = expr->Nth(3);
1458 wxExpr *underlineExpr = expr->Nth(4);
1459 wxExpr *faceNameExpr = expr->Nth(5);
1460 if (pointExpr)
1461 point = (int)pointExpr->IntegerValue();
1462
1463 wxString str;
1464 if (familyExpr)
1465 {
1466 str = familyExpr->StringValue();
1467 family = (int)wxParseWindowStyle(str);
1468 }
1469 if (styleExpr)
1470 {
1471 str = styleExpr->StringValue();
1472 style = (int)wxParseWindowStyle(str);
1473 }
1474 if (weightExpr)
1475 {
1476 str = weightExpr->StringValue();
1477 weight = (int)wxParseWindowStyle(str);
1478 }
1479 if (underlineExpr)
1480 underline = (int)underlineExpr->IntegerValue();
1481 if (faceNameExpr)
1482 faceName = faceNameExpr->StringValue();
1483
1484 wxFont font(point, family, style, weight, (underline != 0), faceName);
1485 return font;
1486 }
1487
1488 // Separate file for the remainder of this, for BC++/Win16
1489
1490 #if !((defined(__BORLANDC__) || defined(__SC__)) && defined(__WIN16__))
1491 /*
1492 * (Re)allocate buffer for reading in from resource file
1493 */
1494
1495 bool wxReallocateResourceBuffer()
1496 {
1497 if (!wxResourceBuffer)
1498 {
1499 wxResourceBufferSize = 1000;
1500 wxResourceBuffer = new char[wxResourceBufferSize];
1501 return TRUE;
1502 }
1503 if (wxResourceBuffer)
1504 {
1505 long newSize = wxResourceBufferSize + 1000;
1506 char *tmp = new char[(int)newSize];
1507 strncpy(tmp, wxResourceBuffer, (int)wxResourceBufferCount);
1508 delete[] wxResourceBuffer;
1509 wxResourceBuffer = tmp;
1510 wxResourceBufferSize = newSize;
1511 }
1512 return TRUE;
1513 }
1514
1515 static bool wxEatWhiteSpace(FILE *fd)
1516 {
1517 int ch = 0;
1518
1519 while ((ch = getc(fd)) != EOF)
1520 {
1521 switch (ch)
1522 {
1523 case ' ':
1524 case 0x0a:
1525 case 0x0d:
1526 case 0x09:
1527 break;
1528 case '/':
1529 {
1530 int prev_ch = ch;
1531 ch = getc(fd);
1532 if (ch == EOF)
1533 {
1534 ungetc(prev_ch, fd);
1535 return TRUE;
1536 }
1537
1538 if (ch == '*')
1539 {
1540 // Eat C comment
1541 prev_ch = 0;
1542 while ((ch = getc(fd)) != EOF)
1543 {
1544 if (ch == '/' && prev_ch == '*')
1545 break;
1546 prev_ch = ch;
1547 }
1548 }
1549 else if (ch == '/')
1550 {
1551 // Eat C++ comment
1552 static char buffer[255];
1553 fgets(buffer, 255, fd);
1554 }
1555 else
1556 {
1557 ungetc(prev_ch, fd);
1558 ungetc(ch, fd);
1559 return TRUE;
1560 }
1561 }
1562 break;
1563 default:
1564 ungetc(ch, fd);
1565 return TRUE;
1566
1567 }
1568 }
1569 return FALSE;
1570 }
1571 static bool wxEatWhiteSpace(wxInputStream *is)
1572 {
1573 int ch = is->GetC() ;
1574 if ((ch != ' ') && (ch != '/') && (ch != ' ') && (ch != 10) && (ch != 13) && (ch != 9))
1575 {
1576 is->Ungetch(ch);
1577 return TRUE;
1578 }
1579
1580 // Eat whitespace
1581 while (ch == ' ' || ch == 10 || ch == 13 || ch == 9)
1582 ch = is->GetC();
1583 // Check for comment
1584 if (ch == '/')
1585 {
1586 ch = is->GetC();
1587 if (ch == '*')
1588 {
1589 bool finished = FALSE;
1590 while (!finished)
1591 {
1592 ch = is->GetC();
1593 if (ch == EOF)
1594 return FALSE;
1595 if (ch == '*')
1596 {
1597 int newCh = is->GetC();
1598 if (newCh == '/')
1599 finished = TRUE;
1600 else
1601 {
1602 is->Ungetch(ch);
1603 }
1604 }
1605 }
1606 }
1607 else // False alarm
1608 return FALSE;
1609 }
1610 else
1611 is->Ungetch(ch);
1612 return wxEatWhiteSpace(is);
1613 }
1614
1615 bool wxGetResourceToken(FILE *fd)
1616 {
1617 if (!wxResourceBuffer)
1618 wxReallocateResourceBuffer();
1619 wxResourceBuffer[0] = 0;
1620 wxEatWhiteSpace(fd);
1621
1622 int ch = getc(fd);
1623 if (ch == '"')
1624 {
1625 // Get string
1626 wxResourceBufferCount = 0;
1627 ch = getc(fd);
1628 while (ch != '"')
1629 {
1630 int actualCh = ch;
1631 if (ch == EOF)
1632 {
1633 wxResourceBuffer[wxResourceBufferCount] = 0;
1634 return FALSE;
1635 }
1636 // Escaped characters
1637 else if (ch == '\\')
1638 {
1639 int newCh = getc(fd);
1640 if (newCh == '"')
1641 actualCh = '"';
1642 else if (newCh == 10)
1643 actualCh = 10;
1644 else
1645 {
1646 ungetc(newCh, fd);
1647 }
1648 }
1649
1650 if (wxResourceBufferCount >= wxResourceBufferSize-1)
1651 wxReallocateResourceBuffer();
1652 wxResourceBuffer[wxResourceBufferCount] = (char)actualCh;
1653 wxResourceBufferCount ++;
1654 ch = getc(fd);
1655 }
1656 wxResourceBuffer[wxResourceBufferCount] = 0;
1657 }
1658 else
1659 {
1660 wxResourceBufferCount = 0;
1661 // Any other token
1662 while (ch != ' ' && ch != EOF && ch != ' ' && ch != 13 && ch != 9 && ch != 10)
1663 {
1664 if (wxResourceBufferCount >= wxResourceBufferSize-1)
1665 wxReallocateResourceBuffer();
1666 wxResourceBuffer[wxResourceBufferCount] = (char)ch;
1667 wxResourceBufferCount ++;
1668
1669 ch = getc(fd);
1670 }
1671 wxResourceBuffer[wxResourceBufferCount] = 0;
1672 if (ch == EOF)
1673 return FALSE;
1674 }
1675 return TRUE;
1676 }
1677
1678 bool wxGetResourceToken(wxInputStream *is)
1679 {
1680 if (!wxResourceBuffer)
1681 wxReallocateResourceBuffer();
1682 wxResourceBuffer[0] = 0;
1683 wxEatWhiteSpace(is);
1684
1685 int ch = is->GetC() ;
1686 if (ch == '"')
1687 {
1688 // Get string
1689 wxResourceBufferCount = 0;
1690 ch = is->GetC();
1691 while (ch != '"')
1692 {
1693 int actualCh = ch;
1694 if (ch == EOF)
1695 {
1696 wxResourceBuffer[wxResourceBufferCount] = 0;
1697 return FALSE;
1698 }
1699 // Escaped characters
1700 else if (ch == '\\')
1701 {
1702 int newCh = is->GetC();
1703 if (newCh == '"')
1704 actualCh = '"';
1705 else if (newCh == 10)
1706 actualCh = 10;
1707 else if (newCh == 13) // mac
1708 actualCh = 10;
1709 else
1710 {
1711 is->Ungetch(newCh);
1712 }
1713 }
1714
1715 if (wxResourceBufferCount >= wxResourceBufferSize-1)
1716 wxReallocateResourceBuffer();
1717 wxResourceBuffer[wxResourceBufferCount] = (char)actualCh;
1718 wxResourceBufferCount ++;
1719 ch = is->GetC();
1720 }
1721 wxResourceBuffer[wxResourceBufferCount] = 0;
1722 }
1723 else
1724 {
1725 wxResourceBufferCount = 0;
1726 // Any other token
1727 while (ch != ' ' && ch != EOF && ch != ' ' && ch != 13 && ch != 9 && ch != 10)
1728 {
1729 if (wxResourceBufferCount >= wxResourceBufferSize-1)
1730 wxReallocateResourceBuffer();
1731 wxResourceBuffer[wxResourceBufferCount] = (char)ch;
1732 wxResourceBufferCount ++;
1733
1734 ch = is->GetC();
1735 }
1736 wxResourceBuffer[wxResourceBufferCount] = 0;
1737 if (ch == EOF)
1738 return FALSE;
1739 }
1740 return TRUE;
1741 }
1742
1743 /*
1744 * Files are in form:
1745 static char *name = "....";
1746 with possible comments.
1747 */
1748
1749 bool wxResourceReadOneResource(FILE *fd, wxExprDatabase& db, bool *eof, wxResourceTable *table)
1750 {
1751 if (!table)
1752 table = wxDefaultResourceTable;
1753
1754 // static or #define
1755 if (!wxGetResourceToken(fd))
1756 {
1757 *eof = TRUE;
1758 return FALSE;
1759 }
1760
1761 if (strcmp(wxResourceBuffer, "#define") == 0)
1762 {
1763 wxGetResourceToken(fd);
1764 wxChar *name = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
1765 wxGetResourceToken(fd);
1766 wxChar *value = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
1767 if (wxIsdigit(value[0]))
1768 {
1769 int val = (int)wxAtol(value);
1770 wxResourceAddIdentifier(name, val, table);
1771 }
1772 else
1773 {
1774 wxLogWarning(_("#define %s must be an integer."), name);
1775 delete[] name;
1776 delete[] value;
1777 return FALSE;
1778 }
1779 delete[] name;
1780 delete[] value;
1781
1782 return TRUE;
1783 }
1784 else if (strcmp(wxResourceBuffer, "#include") == 0)
1785 {
1786 wxGetResourceToken(fd);
1787 wxChar *name = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
1788 wxChar *actualName = name;
1789 if (name[0] == wxT('"'))
1790 actualName = name + 1;
1791 int len = wxStrlen(name);
1792 if ((len > 0) && (name[len-1] == wxT('"')))
1793 name[len-1] = 0;
1794 if (!wxResourceParseIncludeFile(actualName, table))
1795 {
1796 wxLogWarning(_("Could not find resource include file %s."), actualName);
1797 }
1798 delete[] name;
1799 return TRUE;
1800 }
1801 else if (strcmp(wxResourceBuffer, "static") != 0)
1802 {
1803 wxChar buf[300];
1804 wxStrcpy(buf, _("Found "));
1805 wxStrncat(buf, wxConvCurrent->cMB2WX(wxResourceBuffer), 30);
1806 wxStrcat(buf, _(", expected static, #include or #define\nwhilst parsing resource."));
1807 wxLogWarning(buf);
1808 return FALSE;
1809 }
1810
1811 // char
1812 if (!wxGetResourceToken(fd))
1813 {
1814 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1815 *eof = TRUE;
1816 return FALSE;
1817 }
1818
1819 if (strcmp(wxResourceBuffer, "char") != 0)
1820 {
1821 wxLogWarning(_("Expected 'char' whilst parsing resource."));
1822 return FALSE;
1823 }
1824
1825 // *name
1826 if (!wxGetResourceToken(fd))
1827 {
1828 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1829 *eof = TRUE;
1830 return FALSE;
1831 }
1832
1833 if (wxResourceBuffer[0] != '*')
1834 {
1835 wxLogWarning(_("Expected '*' whilst parsing resource."));
1836 return FALSE;
1837 }
1838 wxChar nameBuf[100];
1839 wxMB2WX(nameBuf, wxResourceBuffer+1, 99);
1840 nameBuf[99] = 0;
1841
1842 // =
1843 if (!wxGetResourceToken(fd))
1844 {
1845 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1846 *eof = TRUE;
1847 return FALSE;
1848 }
1849
1850 if (strcmp(wxResourceBuffer, "=") != 0)
1851 {
1852 wxLogWarning(_("Expected '=' whilst parsing resource."));
1853 return FALSE;
1854 }
1855
1856 // String
1857 if (!wxGetResourceToken(fd))
1858 {
1859 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1860 *eof = TRUE;
1861 return FALSE;
1862 }
1863 else
1864 {
1865 if (!db.ReadPrologFromString(wxResourceBuffer))
1866 {
1867 wxLogWarning(_("%s: ill-formed resource file syntax."), nameBuf);
1868 return FALSE;
1869 }
1870 }
1871 // Semicolon
1872 if (!wxGetResourceToken(fd))
1873 {
1874 *eof = TRUE;
1875 }
1876 return TRUE;
1877 }
1878
1879 bool wxResourceReadOneResource(wxInputStream *fd, wxExprDatabase& db, bool *eof, wxResourceTable *table)
1880 {
1881 if (!table)
1882 table = wxDefaultResourceTable;
1883
1884 // static or #define
1885 if (!wxGetResourceToken(fd))
1886 {
1887 *eof = TRUE;
1888 return FALSE;
1889 }
1890
1891 if (strcmp(wxResourceBuffer, "#define") == 0)
1892 {
1893 wxGetResourceToken(fd);
1894 wxChar *name = copystring(wxConvLibc.cMB2WX(wxResourceBuffer));
1895 wxGetResourceToken(fd);
1896 wxChar *value = copystring(wxConvLibc.cMB2WX(wxResourceBuffer));
1897 if (wxIsalpha(value[0]))
1898 {
1899 int val = (int)wxAtol(value);
1900 wxResourceAddIdentifier(name, val, table);
1901 }
1902 else
1903 {
1904 wxLogWarning(_("#define %s must be an integer."), name);
1905 delete[] name;
1906 delete[] value;
1907 return FALSE;
1908 }
1909 delete[] name;
1910 delete[] value;
1911
1912 return TRUE;
1913 }
1914 else if (strcmp(wxResourceBuffer, "#include") == 0)
1915 {
1916 wxGetResourceToken(fd);
1917 wxChar *name = copystring(wxConvLibc.cMB2WX(wxResourceBuffer));
1918 wxChar *actualName = name;
1919 if (name[0] == wxT('"'))
1920 actualName = name + 1;
1921 int len = wxStrlen(name);
1922 if ((len > 0) && (name[len-1] == wxT('"')))
1923 name[len-1] = 0;
1924 if (!wxResourceParseIncludeFile(actualName, table))
1925 {
1926 wxLogWarning(_("Could not find resource include file %s."), actualName);
1927 }
1928 delete[] name;
1929 return TRUE;
1930 }
1931 else if (strcmp(wxResourceBuffer, "static") != 0)
1932 {
1933 wxChar buf[300];
1934 wxStrcpy(buf, _("Found "));
1935 wxStrncat(buf, wxConvLibc.cMB2WX(wxResourceBuffer), 30);
1936 wxStrcat(buf, _(", expected static, #include or #define\nwhilst parsing resource."));
1937 wxLogWarning(buf);
1938 return FALSE;
1939 }
1940
1941 // char
1942 if (!wxGetResourceToken(fd))
1943 {
1944 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1945 *eof = TRUE;
1946 return FALSE;
1947 }
1948
1949 if (strcmp(wxResourceBuffer, "char") != 0)
1950 {
1951 wxLogWarning(_("Expected 'char' whilst parsing resource."));
1952 return FALSE;
1953 }
1954
1955 // *name
1956 if (!wxGetResourceToken(fd))
1957 {
1958 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1959 *eof = TRUE;
1960 return FALSE;
1961 }
1962
1963 if (wxResourceBuffer[0] != '*')
1964 {
1965 wxLogWarning(_("Expected '*' whilst parsing resource."));
1966 return FALSE;
1967 }
1968 char nameBuf[100];
1969 strncpy(nameBuf, wxResourceBuffer+1, 99);
1970
1971 // =
1972 if (!wxGetResourceToken(fd))
1973 {
1974 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1975 *eof = TRUE;
1976 return FALSE;
1977 }
1978
1979 if (strcmp(wxResourceBuffer, "=") != 0)
1980 {
1981 wxLogWarning(_("Expected '=' whilst parsing resource."));
1982 return FALSE;
1983 }
1984
1985 // String
1986 if (!wxGetResourceToken(fd))
1987 {
1988 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
1989 *eof = TRUE;
1990 return FALSE;
1991 }
1992 else
1993 {
1994 if (!db.ReadPrologFromString(wxResourceBuffer))
1995 {
1996 wxLogWarning(_("%s: ill-formed resource file syntax."), nameBuf);
1997 return FALSE;
1998 }
1999 }
2000 // Semicolon
2001 if (!wxGetResourceToken(fd))
2002 {
2003 *eof = TRUE;
2004 }
2005 return TRUE;
2006 }
2007
2008 /*
2009 * Parses string window style into integer window style
2010 */
2011
2012 /*
2013 * Style flag parsing, e.g.
2014 * "wxSYSTEM_MENU | wxBORDER" -> integer
2015 */
2016
2017 wxChar* wxResourceParseWord(wxChar*s, int *i)
2018 {
2019 if (!s)
2020 return (wxChar*) NULL;
2021
2022 static wxChar buf[150];
2023 int len = wxStrlen(s);
2024 int j = 0;
2025 int ii = *i;
2026 while ((ii < len) && (wxIsalpha(s[ii]) || (s[ii] == wxT('_'))))
2027 {
2028 buf[j] = s[ii];
2029 j ++;
2030 ii ++;
2031 }
2032 buf[j] = 0;
2033
2034 // Eat whitespace and conjunction characters
2035 while ((ii < len) &&
2036 ((s[ii] == wxT(' ')) || (s[ii] == wxT('|')) || (s[ii] == wxT(','))))
2037 {
2038 ii ++;
2039 }
2040 *i = ii;
2041 if (j == 0)
2042 return (wxChar*) NULL;
2043 else
2044 return buf;
2045 }
2046
2047 struct wxResourceBitListStruct
2048 {
2049 wxChar *word;
2050 long bits;
2051 };
2052
2053 static wxResourceBitListStruct wxResourceBitListTable[] =
2054 {
2055 /* wxListBox */
2056 { wxT("wxSINGLE"), wxLB_SINGLE },
2057 { wxT("wxMULTIPLE"), wxLB_MULTIPLE },
2058 { wxT("wxEXTENDED"), wxLB_EXTENDED },
2059 { wxT("wxLB_SINGLE"), wxLB_SINGLE },
2060 { wxT("wxLB_MULTIPLE"), wxLB_MULTIPLE },
2061 { wxT("wxLB_EXTENDED"), wxLB_EXTENDED },
2062 { wxT("wxLB_NEEDED_SB"), wxLB_NEEDED_SB },
2063 { wxT("wxLB_ALWAYS_SB"), wxLB_ALWAYS_SB },
2064 { wxT("wxLB_SORT"), wxLB_SORT },
2065 { wxT("wxLB_OWNERDRAW"), wxLB_OWNERDRAW },
2066 { wxT("wxLB_HSCROLL"), wxLB_HSCROLL },
2067
2068 /* wxComboxBox */
2069 { wxT("wxCB_SIMPLE"), wxCB_SIMPLE },
2070 { wxT("wxCB_DROPDOWN"), wxCB_DROPDOWN },
2071 { wxT("wxCB_READONLY"), wxCB_READONLY },
2072 { wxT("wxCB_SORT"), wxCB_SORT },
2073
2074 /* wxGauge */
2075 { wxT("wxGA_PROGRESSBAR"), wxGA_PROGRESSBAR },
2076 { wxT("wxGA_HORIZONTAL"), wxGA_HORIZONTAL },
2077 { wxT("wxGA_VERTICAL"), wxGA_VERTICAL },
2078
2079 /* wxTextCtrl */
2080 { wxT("wxPASSWORD"), wxPASSWORD},
2081 { wxT("wxPROCESS_ENTER"), wxPROCESS_ENTER},
2082 { wxT("wxTE_PASSWORD"), wxTE_PASSWORD},
2083 { wxT("wxTE_READONLY"), wxTE_READONLY},
2084 { wxT("wxTE_PROCESS_ENTER"), wxTE_PROCESS_ENTER},
2085 { wxT("wxTE_MULTILINE"), wxTE_MULTILINE},
2086 { wxT("wxTE_NO_VSCROLL"), wxTE_NO_VSCROLL},
2087
2088 /* wxRadioBox/wxRadioButton */
2089 { wxT("wxRB_GROUP"), wxRB_GROUP },
2090 { wxT("wxRA_SPECIFY_COLS"), wxRA_SPECIFY_COLS },
2091 { wxT("wxRA_SPECIFY_ROWS"), wxRA_SPECIFY_ROWS },
2092 { wxT("wxRA_HORIZONTAL"), wxRA_HORIZONTAL },
2093 { wxT("wxRA_VERTICAL"), wxRA_VERTICAL },
2094
2095 /* wxSlider */
2096 { wxT("wxSL_HORIZONTAL"), wxSL_HORIZONTAL },
2097 { wxT("wxSL_VERTICAL"), wxSL_VERTICAL },
2098 { wxT("wxSL_AUTOTICKS"), wxSL_AUTOTICKS },
2099 { wxT("wxSL_LABELS"), wxSL_LABELS },
2100 { wxT("wxSL_LEFT"), wxSL_LEFT },
2101 { wxT("wxSL_TOP"), wxSL_TOP },
2102 { wxT("wxSL_RIGHT"), wxSL_RIGHT },
2103 { wxT("wxSL_BOTTOM"), wxSL_BOTTOM },
2104 { wxT("wxSL_BOTH"), wxSL_BOTH },
2105 { wxT("wxSL_SELRANGE"), wxSL_SELRANGE },
2106
2107 /* wxScrollBar */
2108 { wxT("wxSB_HORIZONTAL"), wxSB_HORIZONTAL },
2109 { wxT("wxSB_VERTICAL"), wxSB_VERTICAL },
2110
2111 /* wxButton */
2112 { wxT("wxBU_AUTODRAW"), wxBU_AUTODRAW },
2113 { wxT("wxBU_NOAUTODRAW"), wxBU_NOAUTODRAW },
2114
2115 /* wxTreeCtrl */
2116 { wxT("wxTR_HAS_BUTTONS"), wxTR_HAS_BUTTONS },
2117 { wxT("wxTR_EDIT_LABELS"), wxTR_EDIT_LABELS },
2118 { wxT("wxTR_LINES_AT_ROOT"), wxTR_LINES_AT_ROOT },
2119
2120 /* wxListCtrl */
2121 { wxT("wxLC_ICON"), wxLC_ICON },
2122 { wxT("wxLC_SMALL_ICON"), wxLC_SMALL_ICON },
2123 { wxT("wxLC_LIST"), wxLC_LIST },
2124 { wxT("wxLC_REPORT"), wxLC_REPORT },
2125 { wxT("wxLC_ALIGN_TOP"), wxLC_ALIGN_TOP },
2126 { wxT("wxLC_ALIGN_LEFT"), wxLC_ALIGN_LEFT },
2127 { wxT("wxLC_AUTOARRANGE"), wxLC_AUTOARRANGE },
2128 { wxT("wxLC_USER_TEXT"), wxLC_USER_TEXT },
2129 { wxT("wxLC_EDIT_LABELS"), wxLC_EDIT_LABELS },
2130 { wxT("wxLC_NO_HEADER"), wxLC_NO_HEADER },
2131 { wxT("wxLC_NO_SORT_HEADER"), wxLC_NO_SORT_HEADER },
2132 { wxT("wxLC_SINGLE_SEL"), wxLC_SINGLE_SEL },
2133 { wxT("wxLC_SORT_ASCENDING"), wxLC_SORT_ASCENDING },
2134 { wxT("wxLC_SORT_DESCENDING"), wxLC_SORT_DESCENDING },
2135
2136 /* wxSpinButton */
2137 { wxT("wxSP_VERTICAL"), wxSP_VERTICAL},
2138 { wxT("wxSP_HORIZONTAL"), wxSP_HORIZONTAL},
2139 { wxT("wxSP_ARROW_KEYS"), wxSP_ARROW_KEYS},
2140 { wxT("wxSP_WRAP"), wxSP_WRAP},
2141
2142 /* wxSplitterWnd */
2143 { wxT("wxSP_NOBORDER"), wxSP_NOBORDER},
2144 { wxT("wxSP_3D"), wxSP_3D},
2145 { wxT("wxSP_BORDER"), wxSP_BORDER},
2146
2147 /* wxTabCtrl */
2148 { wxT("wxTC_MULTILINE"), wxTC_MULTILINE},
2149 { wxT("wxTC_RIGHTJUSTIFY"), wxTC_RIGHTJUSTIFY},
2150 { wxT("wxTC_FIXEDWIDTH"), wxTC_FIXEDWIDTH},
2151 { wxT("wxTC_OWNERDRAW"), wxTC_OWNERDRAW},
2152
2153 /* wxStatusBar95 */
2154 { wxT("wxST_SIZEGRIP"), wxST_SIZEGRIP},
2155
2156 /* wxControl */
2157 { wxT("wxFIXED_LENGTH"), wxFIXED_LENGTH},
2158 { wxT("wxALIGN_LEFT"), wxALIGN_LEFT},
2159 { wxT("wxALIGN_CENTER"), wxALIGN_CENTER},
2160 { wxT("wxALIGN_CENTRE"), wxALIGN_CENTRE},
2161 { wxT("wxALIGN_RIGHT"), wxALIGN_RIGHT},
2162 { wxT("wxCOLOURED"), wxCOLOURED},
2163
2164 /* wxToolBar */
2165 { wxT("wxTB_3DBUTTONS"), wxTB_3DBUTTONS},
2166 { wxT("wxTB_HORIZONTAL"), wxTB_HORIZONTAL},
2167 { wxT("wxTB_VERTICAL"), wxTB_VERTICAL},
2168 { wxT("wxTB_FLAT"), wxTB_FLAT},
2169
2170 /* wxDialog */
2171 { wxT("wxDIALOG_MODAL"), wxDIALOG_MODAL },
2172
2173 /* Generic */
2174 { wxT("wxVSCROLL"), wxVSCROLL },
2175 { wxT("wxHSCROLL"), wxHSCROLL },
2176 { wxT("wxCAPTION"), wxCAPTION },
2177 { wxT("wxSTAY_ON_TOP"), wxSTAY_ON_TOP},
2178 { wxT("wxICONIZE"), wxICONIZE},
2179 { wxT("wxMINIMIZE"), wxICONIZE},
2180 { wxT("wxMAXIMIZE"), wxMAXIMIZE},
2181 { wxT("wxSDI"), 0},
2182 { wxT("wxMDI_PARENT"), 0},
2183 { wxT("wxMDI_CHILD"), 0},
2184 { wxT("wxTHICK_FRAME"), wxTHICK_FRAME},
2185 { wxT("wxRESIZE_BORDER"), wxRESIZE_BORDER},
2186 { wxT("wxSYSTEM_MENU"), wxSYSTEM_MENU},
2187 { wxT("wxMINIMIZE_BOX"), wxMINIMIZE_BOX},
2188 { wxT("wxMAXIMIZE_BOX"), wxMAXIMIZE_BOX},
2189 { wxT("wxRESIZE_BOX"), wxRESIZE_BOX},
2190 { wxT("wxDEFAULT_FRAME_STYLE"), wxDEFAULT_FRAME_STYLE},
2191 { wxT("wxDEFAULT_FRAME"), wxDEFAULT_FRAME_STYLE},
2192 { wxT("wxDEFAULT_DIALOG_STYLE"), wxDEFAULT_DIALOG_STYLE},
2193 { wxT("wxBORDER"), wxBORDER},
2194 { wxT("wxRETAINED"), wxRETAINED},
2195 { wxT("wxNATIVE_IMPL"), 0},
2196 { wxT("wxEXTENDED_IMPL"), 0},
2197 { wxT("wxBACKINGSTORE"), wxBACKINGSTORE},
2198 // { wxT("wxFLAT"), wxFLAT},
2199 // { wxT("wxMOTIF_RESIZE"), wxMOTIF_RESIZE},
2200 { wxT("wxFIXED_LENGTH"), 0},
2201 { wxT("wxDOUBLE_BORDER"), wxDOUBLE_BORDER},
2202 { wxT("wxSUNKEN_BORDER"), wxSUNKEN_BORDER},
2203 { wxT("wxRAISED_BORDER"), wxRAISED_BORDER},
2204 { wxT("wxSIMPLE_BORDER"), wxSIMPLE_BORDER},
2205 { wxT("wxSTATIC_BORDER"), wxSTATIC_BORDER},
2206 { wxT("wxTRANSPARENT_WINDOW"), wxTRANSPARENT_WINDOW},
2207 { wxT("wxNO_BORDER"), wxNO_BORDER},
2208 { wxT("wxCLIP_CHILDREN"), wxCLIP_CHILDREN},
2209 { wxT("wxCLIP_SIBLINGS"), wxCLIP_SIBLINGS},
2210 { wxT("wxTAB_TRAVERSAL"), 0}, // Compatibility only
2211
2212 { wxT("wxTINY_CAPTION_HORIZ"), wxTINY_CAPTION_HORIZ},
2213 { wxT("wxTINY_CAPTION_VERT"), wxTINY_CAPTION_VERT},
2214
2215 // Text font families
2216 { wxT("wxDEFAULT"), wxDEFAULT},
2217 { wxT("wxDECORATIVE"), wxDECORATIVE},
2218 { wxT("wxROMAN"), wxROMAN},
2219 { wxT("wxSCRIPT"), wxSCRIPT},
2220 { wxT("wxSWISS"), wxSWISS},
2221 { wxT("wxMODERN"), wxMODERN},
2222 { wxT("wxTELETYPE"), wxTELETYPE},
2223 { wxT("wxVARIABLE"), wxVARIABLE},
2224 { wxT("wxFIXED"), wxFIXED},
2225 { wxT("wxNORMAL"), wxNORMAL},
2226 { wxT("wxLIGHT"), wxLIGHT},
2227 { wxT("wxBOLD"), wxBOLD},
2228 { wxT("wxITALIC"), wxITALIC},
2229 { wxT("wxSLANT"), wxSLANT},
2230 { wxT("wxSOLID"), wxSOLID},
2231 { wxT("wxDOT"), wxDOT},
2232 { wxT("wxLONG_DASH"), wxLONG_DASH},
2233 { wxT("wxSHORT_DASH"), wxSHORT_DASH},
2234 { wxT("wxDOT_DASH"), wxDOT_DASH},
2235 { wxT("wxUSER_DASH"), wxUSER_DASH},
2236 { wxT("wxTRANSPARENT"), wxTRANSPARENT},
2237 { wxT("wxSTIPPLE"), wxSTIPPLE},
2238 { wxT("wxBDIAGONAL_HATCH"), wxBDIAGONAL_HATCH},
2239 { wxT("wxCROSSDIAG_HATCH"), wxCROSSDIAG_HATCH},
2240 { wxT("wxFDIAGONAL_HATCH"), wxFDIAGONAL_HATCH},
2241 { wxT("wxCROSS_HATCH"), wxCROSS_HATCH},
2242 { wxT("wxHORIZONTAL_HATCH"), wxHORIZONTAL_HATCH},
2243 { wxT("wxVERTICAL_HATCH"), wxVERTICAL_HATCH},
2244 { wxT("wxJOIN_BEVEL"), wxJOIN_BEVEL},
2245 { wxT("wxJOIN_MITER"), wxJOIN_MITER},
2246 { wxT("wxJOIN_ROUND"), wxJOIN_ROUND},
2247 { wxT("wxCAP_ROUND"), wxCAP_ROUND},
2248 { wxT("wxCAP_PROJECTING"), wxCAP_PROJECTING},
2249 { wxT("wxCAP_BUTT"), wxCAP_BUTT},
2250
2251 // Logical ops
2252 { wxT("wxCLEAR"), wxCLEAR},
2253 { wxT("wxXOR"), wxXOR},
2254 { wxT("wxINVERT"), wxINVERT},
2255 { wxT("wxOR_REVERSE"), wxOR_REVERSE},
2256 { wxT("wxAND_REVERSE"), wxAND_REVERSE},
2257 { wxT("wxCOPY"), wxCOPY},
2258 { wxT("wxAND"), wxAND},
2259 { wxT("wxAND_INVERT"), wxAND_INVERT},
2260 { wxT("wxNO_OP"), wxNO_OP},
2261 { wxT("wxNOR"), wxNOR},
2262 { wxT("wxEQUIV"), wxEQUIV},
2263 { wxT("wxSRC_INVERT"), wxSRC_INVERT},
2264 { wxT("wxOR_INVERT"), wxOR_INVERT},
2265 { wxT("wxNAND"), wxNAND},
2266 { wxT("wxOR"), wxOR},
2267 { wxT("wxSET"), wxSET},
2268
2269 { wxT("wxFLOOD_SURFACE"), wxFLOOD_SURFACE},
2270 { wxT("wxFLOOD_BORDER"), wxFLOOD_BORDER},
2271 { wxT("wxODDEVEN_RULE"), wxODDEVEN_RULE},
2272 { wxT("wxWINDING_RULE"), wxWINDING_RULE},
2273 { wxT("wxHORIZONTAL"), wxHORIZONTAL},
2274 { wxT("wxVERTICAL"), wxVERTICAL},
2275 { wxT("wxBOTH"), wxBOTH},
2276 { wxT("wxCENTER_FRAME"), wxCENTER_FRAME},
2277 { wxT("wxOK"), wxOK},
2278 { wxT("wxYES_NO"), wxYES_NO},
2279 { wxT("wxCANCEL"), wxCANCEL},
2280 { wxT("wxYES"), wxYES},
2281 { wxT("wxNO"), wxNO},
2282 { wxT("wxICON_EXCLAMATION"), wxICON_EXCLAMATION},
2283 { wxT("wxICON_HAND"), wxICON_HAND},
2284 { wxT("wxICON_QUESTION"), wxICON_QUESTION},
2285 { wxT("wxICON_INFORMATION"), wxICON_INFORMATION},
2286 { wxT("wxICON_STOP"), wxICON_STOP},
2287 { wxT("wxICON_ASTERISK"), wxICON_ASTERISK},
2288 { wxT("wxICON_MASK"), wxICON_MASK},
2289 { wxT("wxCENTRE"), wxCENTRE},
2290 { wxT("wxCENTER"), wxCENTRE},
2291 { wxT("wxUSER_COLOURS"), wxUSER_COLOURS},
2292 { wxT("wxVERTICAL_LABEL"), 0},
2293 { wxT("wxHORIZONTAL_LABEL"), 0},
2294
2295 // Bitmap types (not strictly styles)
2296 { wxT("wxBITMAP_TYPE_XPM"), wxBITMAP_TYPE_XPM},
2297 { wxT("wxBITMAP_TYPE_XBM"), wxBITMAP_TYPE_XBM},
2298 { wxT("wxBITMAP_TYPE_BMP"), wxBITMAP_TYPE_BMP},
2299 { wxT("wxBITMAP_TYPE_RESOURCE"), wxBITMAP_TYPE_BMP_RESOURCE},
2300 { wxT("wxBITMAP_TYPE_BMP_RESOURCE"), wxBITMAP_TYPE_BMP_RESOURCE},
2301 { wxT("wxBITMAP_TYPE_GIF"), wxBITMAP_TYPE_GIF},
2302 { wxT("wxBITMAP_TYPE_TIF"), wxBITMAP_TYPE_TIF},
2303 { wxT("wxBITMAP_TYPE_ICO"), wxBITMAP_TYPE_ICO},
2304 { wxT("wxBITMAP_TYPE_ICO_RESOURCE"), wxBITMAP_TYPE_ICO_RESOURCE},
2305 { wxT("wxBITMAP_TYPE_CUR"), wxBITMAP_TYPE_CUR},
2306 { wxT("wxBITMAP_TYPE_CUR_RESOURCE"), wxBITMAP_TYPE_CUR_RESOURCE},
2307 { wxT("wxBITMAP_TYPE_XBM_DATA"), wxBITMAP_TYPE_XBM_DATA},
2308 { wxT("wxBITMAP_TYPE_XPM_DATA"), wxBITMAP_TYPE_XPM_DATA},
2309 { wxT("wxBITMAP_TYPE_ANY"), wxBITMAP_TYPE_ANY}
2310 };
2311
2312 static int wxResourceBitListCount = (sizeof(wxResourceBitListTable)/sizeof(wxResourceBitListStruct));
2313
2314 long wxParseWindowStyle(const wxString& bitListString)
2315 {
2316 int i = 0;
2317 wxChar *word;
2318 long bitList = 0;
2319 word = wxResourceParseWord(WXSTRINGCAST bitListString, &i);
2320 while (word != NULL)
2321 {
2322 bool found = FALSE;
2323 int j;
2324 for (j = 0; j < wxResourceBitListCount; j++)
2325 if (wxStrcmp(wxResourceBitListTable[j].word, word) == 0)
2326 {
2327 bitList |= wxResourceBitListTable[j].bits;
2328 found = TRUE;
2329 break;
2330 }
2331 if (!found)
2332 {
2333 wxLogWarning(_("Unrecognized style %s whilst parsing resource."), word);
2334 return 0;
2335 }
2336 word = wxResourceParseWord(WXSTRINGCAST bitListString, &i);
2337 }
2338 return bitList;
2339 }
2340
2341 /*
2342 * Load a bitmap from a wxWindows resource, choosing an optimum
2343 * depth and appropriate type.
2344 */
2345
2346 wxBitmap wxResourceCreateBitmap(const wxString& resource, wxResourceTable *table)
2347 {
2348 if (!table)
2349 table = wxDefaultResourceTable;
2350
2351 wxItemResource *item = table->FindResource(resource);
2352 if (item)
2353 {
2354 if ((item->GetType() == wxT("")) || (item->GetType() != wxT("wxBitmap")))
2355 {
2356 wxLogWarning(_("%s not a bitmap resource specification."), (const wxChar*) resource);
2357 return wxNullBitmap;
2358 }
2359 int thisDepth = wxDisplayDepth();
2360 long thisNoColours = (long)pow(2.0, (double)thisDepth);
2361
2362 wxItemResource *optResource = (wxItemResource *) NULL;
2363
2364 // Try to find optimum bitmap for this platform/colour depth
2365 wxNode *node = item->GetChildren().First();
2366 while (node)
2367 {
2368 wxItemResource *child = (wxItemResource *)node->Data();
2369 int platform = (int)child->GetValue2();
2370 int noColours = (int)child->GetValue3();
2371 /*
2372 char *name = child->GetName();
2373 int bitmapType = (int)child->GetValue1();
2374 int xRes = child->GetWidth();
2375 int yRes = child->GetHeight();
2376 */
2377
2378 switch (platform)
2379 {
2380 case RESOURCE_PLATFORM_ANY:
2381 {
2382 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2383 optResource = child;
2384 else
2385 {
2386 // Maximise the number of colours.
2387 // If noColours is zero (unspecified), then assume this
2388 // is the right one.
2389 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2390 optResource = child;
2391 }
2392 break;
2393 }
2394 #ifdef __WXMSW__
2395 case RESOURCE_PLATFORM_WINDOWS:
2396 {
2397 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2398 optResource = child;
2399 else
2400 {
2401 // Maximise the number of colours
2402 if ((noColours > 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2403 optResource = child;
2404 }
2405 break;
2406 }
2407 #endif
2408 #ifdef __WXGTK__
2409 case RESOURCE_PLATFORM_X:
2410 {
2411 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2412 optResource = child;
2413 else
2414 {
2415 // Maximise the number of colours
2416 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2417 optResource = child;
2418 }
2419 break;
2420 }
2421 #endif
2422 #ifdef wx_max
2423 case RESOURCE_PLATFORM_MAC:
2424 {
2425 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2426 optResource = child;
2427 else
2428 {
2429 // Maximise the number of colours
2430 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2431 optResource = child;
2432 }
2433 break;
2434 }
2435 #endif
2436 default:
2437 break;
2438 }
2439 node = node->Next();
2440 }
2441 // If no matching resource, fail.
2442 if (!optResource)
2443 return wxNullBitmap;
2444
2445 wxString name = optResource->GetName();
2446 int bitmapType = (int)optResource->GetValue1();
2447 switch (bitmapType)
2448 {
2449 case wxBITMAP_TYPE_XBM_DATA:
2450 {
2451 #ifdef __WXGTK__
2452 wxItemResource *item = table->FindResource(name);
2453 if (!item)
2454 {
2455 wxLogWarning(_("Failed to find XBM resource %s.\n"
2456 "Forgot to use wxResourceLoadBitmapData?"), (const wxChar*) name);
2457 return wxNullBitmap;
2458 }
2459 return wxBitmap(item->GetValue1(), (int)item->GetValue2(), (int)item->GetValue3()) ;
2460 #else
2461 wxLogWarning(_("No XBM facility available!"));
2462 break;
2463 #endif
2464 }
2465 case wxBITMAP_TYPE_XPM_DATA:
2466 {
2467 wxItemResource *item = table->FindResource(name);
2468 if (!item)
2469 {
2470 wxLogWarning(_("Failed to find XPM resource %s.\nForgot to use wxResourceLoadBitmapData?"), (const wxChar*) name);
2471 return wxNullBitmap;
2472 }
2473 return wxBitmap((char **)item->GetValue1());
2474 }
2475 default:
2476 {
2477 return wxBitmap(name, (wxBitmapType)bitmapType);
2478 }
2479 }
2480 #ifndef __WXGTK__
2481 return wxNullBitmap;
2482 #endif
2483 }
2484 else
2485 {
2486 wxLogWarning(_("Bitmap resource specification %s not found."), (const wxChar*) resource);
2487 return wxNullBitmap;
2488 }
2489 }
2490
2491 /*
2492 * Load an icon from a wxWindows resource, choosing an optimum
2493 * depth and appropriate type.
2494 */
2495
2496 wxIcon wxResourceCreateIcon(const wxString& resource, wxResourceTable *table)
2497 {
2498 if (!table)
2499 table = wxDefaultResourceTable;
2500
2501 wxItemResource *item = table->FindResource(resource);
2502 if (item)
2503 {
2504 if ((item->GetType() == wxT("")) || wxStrcmp(item->GetType(), wxT("wxIcon")) != 0)
2505 {
2506 wxLogWarning(_("%s not an icon resource specification."), (const wxChar*) resource);
2507 return wxNullIcon;
2508 }
2509 int thisDepth = wxDisplayDepth();
2510 long thisNoColours = (long)pow(2.0, (double)thisDepth);
2511
2512 wxItemResource *optResource = (wxItemResource *) NULL;
2513
2514 // Try to find optimum icon for this platform/colour depth
2515 wxNode *node = item->GetChildren().First();
2516 while (node)
2517 {
2518 wxItemResource *child = (wxItemResource *)node->Data();
2519 int platform = (int)child->GetValue2();
2520 int noColours = (int)child->GetValue3();
2521 /*
2522 char *name = child->GetName();
2523 int bitmapType = (int)child->GetValue1();
2524 int xRes = child->GetWidth();
2525 int yRes = child->GetHeight();
2526 */
2527
2528 switch (platform)
2529 {
2530 case RESOURCE_PLATFORM_ANY:
2531 {
2532 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2533 optResource = child;
2534 else
2535 {
2536 // Maximise the number of colours.
2537 // If noColours is zero (unspecified), then assume this
2538 // is the right one.
2539 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2540 optResource = child;
2541 }
2542 break;
2543 }
2544 #ifdef __WXMSW__
2545 case RESOURCE_PLATFORM_WINDOWS:
2546 {
2547 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2548 optResource = child;
2549 else
2550 {
2551 // Maximise the number of colours
2552 if ((noColours > 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2553 optResource = child;
2554 }
2555 break;
2556 }
2557 #endif
2558 #ifdef __WXGTK__
2559 case RESOURCE_PLATFORM_X:
2560 {
2561 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2562 optResource = child;
2563 else
2564 {
2565 // Maximise the number of colours
2566 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2567 optResource = child;
2568 }
2569 break;
2570 }
2571 #endif
2572 #ifdef wx_max
2573 case RESOURCE_PLATFORM_MAC:
2574 {
2575 if (!optResource && ((noColours == 0) || (noColours <= thisNoColours)))
2576 optResource = child;
2577 else
2578 {
2579 // Maximise the number of colours
2580 if ((noColours == 0) || ((noColours <= thisNoColours) && (noColours > optResource->GetValue3())))
2581 optResource = child;
2582 }
2583 break;
2584 }
2585 #endif
2586 default:
2587 break;
2588 }
2589 node = node->Next();
2590 }
2591 // If no matching resource, fail.
2592 if (!optResource)
2593 return wxNullIcon;
2594
2595 wxString name = optResource->GetName();
2596 int bitmapType = (int)optResource->GetValue1();
2597 switch (bitmapType)
2598 {
2599 case wxBITMAP_TYPE_XBM_DATA:
2600 {
2601 #ifdef __WXGTK__
2602 wxItemResource *item = table->FindResource(name);
2603 if (!item)
2604 {
2605 wxLogWarning(_("Failed to find XBM resource %s.\n"
2606 "Forgot to use wxResourceLoadIconData?"), (const wxChar*) name);
2607 return wxNullIcon;
2608 }
2609 return wxIcon((const char **)item->GetValue1(), (int)item->GetValue2(), (int)item->GetValue3());
2610 #else
2611 wxLogWarning(_("No XBM facility available!"));
2612 break;
2613 #endif
2614 }
2615 case wxBITMAP_TYPE_XPM_DATA:
2616 {
2617 // *** XPM ICON NOT YET IMPLEMENTED IN WXWINDOWS ***
2618 /*
2619 wxItemResource *item = table->FindResource(name);
2620 if (!item)
2621 {
2622 char buf[400];
2623 sprintf(buf, _("Failed to find XPM resource %s.\nForgot to use wxResourceLoadIconData?"), name);
2624 wxLogWarning(buf);
2625 return NULL;
2626 }
2627 return wxIcon((char **)item->GetValue1());
2628 */
2629 wxLogWarning(_("No XPM icon facility available!"));
2630 break;
2631 }
2632 default:
2633 {
2634 #ifdef __WXGTK__
2635 wxLogWarning(_("Icon resource specification %s not found."), (const wxChar*) resource);
2636 break;
2637 #else
2638 return wxIcon(name, bitmapType);
2639 #endif
2640 }
2641 }
2642 return wxNullIcon;
2643 }
2644 else
2645 {
2646 wxLogWarning(_("Icon resource specification %s not found."), (const wxChar*) resource);
2647 return wxNullIcon;
2648 }
2649 }
2650
2651 #if wxUSE_MENUS
2652
2653 wxMenu *wxResourceCreateMenu(wxItemResource *item)
2654 {
2655 wxMenu *menu = new wxMenu;
2656 wxNode *node = item->GetChildren().First();
2657 while (node)
2658 {
2659 wxItemResource *child = (wxItemResource *)node->Data();
2660 if ((child->GetType() != wxT("")) && (child->GetType() == wxT("wxMenuSeparator")))
2661 menu->AppendSeparator();
2662 else if (child->GetChildren().Number() > 0)
2663 {
2664 wxMenu *subMenu = wxResourceCreateMenu(child);
2665 if (subMenu)
2666 menu->Append((int)child->GetValue1(), child->GetTitle(), subMenu, child->GetValue4());
2667 }
2668 else
2669 {
2670 menu->Append((int)child->GetValue1(), child->GetTitle(), child->GetValue4(), (child->GetValue2() != 0));
2671 }
2672 node = node->Next();
2673 }
2674 return menu;
2675 }
2676
2677 wxMenuBar *wxResourceCreateMenuBar(const wxString& resource, wxResourceTable *table, wxMenuBar *menuBar)
2678 {
2679 if (!table)
2680 table = wxDefaultResourceTable;
2681
2682 wxItemResource *menuResource = table->FindResource(resource);
2683 if (menuResource && (menuResource->GetType() != wxT("")) && (menuResource->GetType() == wxT("wxMenu")))
2684 {
2685 if (!menuBar)
2686 menuBar = new wxMenuBar;
2687 wxNode *node = menuResource->GetChildren().First();
2688 while (node)
2689 {
2690 wxItemResource *child = (wxItemResource *)node->Data();
2691 wxMenu *menu = wxResourceCreateMenu(child);
2692 if (menu)
2693 menuBar->Append(menu, child->GetTitle());
2694 node = node->Next();
2695 }
2696 return menuBar;
2697 }
2698 return (wxMenuBar *) NULL;
2699 }
2700
2701 wxMenu *wxResourceCreateMenu(const wxString& resource, wxResourceTable *table)
2702 {
2703 if (!table)
2704 table = wxDefaultResourceTable;
2705
2706 wxItemResource *menuResource = table->FindResource(resource);
2707 if (menuResource && (menuResource->GetType() != wxT("")) && (menuResource->GetType() == wxT("wxMenu")))
2708 // if (menuResource && (menuResource->GetType() == wxTYPE_MENU))
2709 return wxResourceCreateMenu(menuResource);
2710 return (wxMenu *) NULL;
2711 }
2712
2713 #endif // wxUSE_MENUS
2714
2715 // Global equivalents (so don't have to refer to default table explicitly)
2716 bool wxResourceParseData(const wxString& resource, wxResourceTable *table)
2717 {
2718 if (!table)
2719 table = wxDefaultResourceTable;
2720
2721 return table->ParseResourceData(resource);
2722 }
2723
2724 bool wxResourceParseFile(const wxString& filename, wxResourceTable *table)
2725 {
2726 if (!table)
2727 table = wxDefaultResourceTable;
2728
2729 return table->ParseResourceFile(filename);
2730 }
2731
2732 // Register XBM/XPM data
2733 bool wxResourceRegisterBitmapData(const wxString& name, char bits[], int width, int height, wxResourceTable *table)
2734 {
2735 if (!table)
2736 table = wxDefaultResourceTable;
2737
2738 return table->RegisterResourceBitmapData(name, bits, width, height);
2739 }
2740
2741 bool wxResourceRegisterBitmapData(const wxString& name, char **data, wxResourceTable *table)
2742 {
2743 if (!table)
2744 table = wxDefaultResourceTable;
2745
2746 return table->RegisterResourceBitmapData(name, data);
2747 }
2748
2749 void wxResourceClear(wxResourceTable *table)
2750 {
2751 if (!table)
2752 table = wxDefaultResourceTable;
2753
2754 table->ClearTable();
2755 }
2756
2757 /*
2758 * Identifiers
2759 */
2760
2761 bool wxResourceAddIdentifier(const wxString& name, int value, wxResourceTable *table)
2762 {
2763 if (!table)
2764 table = wxDefaultResourceTable;
2765
2766 table->identifiers.Put(name, (wxObject *)(long)value);
2767 return TRUE;
2768 }
2769
2770 int wxResourceGetIdentifier(const wxString& name, wxResourceTable *table)
2771 {
2772 if (!table)
2773 table = wxDefaultResourceTable;
2774
2775 return (int)(long)table->identifiers.Get(name);
2776 }
2777
2778 /*
2779 * Parse #include file for #defines (only)
2780 */
2781
2782 bool wxResourceParseIncludeFile(const wxString& f, wxResourceTable *table)
2783 {
2784 if (!table)
2785 table = wxDefaultResourceTable;
2786
2787 FILE *fd = wxFopen(f, _T("r"));
2788 if (!fd)
2789 {
2790 return FALSE;
2791 }
2792 while (wxGetResourceToken(fd))
2793 {
2794 if (strcmp(wxResourceBuffer, "#define") == 0)
2795 {
2796 wxGetResourceToken(fd);
2797 wxChar *name = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
2798 wxGetResourceToken(fd);
2799 wxChar *value = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
2800 if (wxIsdigit(value[0]))
2801 {
2802 int val = (int)wxAtol(value);
2803 wxResourceAddIdentifier(name, val, table);
2804 }
2805 delete[] name;
2806 delete[] value;
2807 }
2808 }
2809 fclose(fd);
2810 return TRUE;
2811 }
2812
2813 /*
2814 * Reading strings as if they were .wxr files
2815 */
2816
2817 static int getc_string(char *s)
2818 {
2819 int ch = s[wxResourceStringPtr];
2820 if (ch == 0)
2821 return EOF;
2822 else
2823 {
2824 wxResourceStringPtr ++;
2825 return ch;
2826 }
2827 }
2828
2829 static int ungetc_string()
2830 {
2831 wxResourceStringPtr --;
2832 return 0;
2833 }
2834
2835 bool wxEatWhiteSpaceString(char *s)
2836 {
2837 int ch = 0;
2838
2839 while ((ch = getc_string(s)) != EOF)
2840 {
2841 switch (ch)
2842 {
2843 case ' ':
2844 case 0x0a:
2845 case 0x0d:
2846 case 0x09:
2847 break;
2848 case '/':
2849 {
2850 int prev_ch = ch;
2851 ch = getc_string(s);
2852 if (ch == EOF)
2853 {
2854 ungetc_string();
2855 return TRUE;
2856 }
2857
2858 if (ch == '*')
2859 {
2860 // Eat C comment
2861 prev_ch = 0;
2862 while ((ch = getc_string(s)) != EOF)
2863 {
2864 if (ch == '/' && prev_ch == '*')
2865 break;
2866 prev_ch = ch;
2867 }
2868 }
2869 else
2870 {
2871 ungetc_string();
2872 ungetc_string();
2873 return TRUE;
2874 }
2875 }
2876 break;
2877 default:
2878 ungetc_string();
2879 return TRUE;
2880
2881 }
2882 }
2883 return FALSE;
2884 }
2885
2886 bool wxGetResourceTokenString(char *s)
2887 {
2888 if (!wxResourceBuffer)
2889 wxReallocateResourceBuffer();
2890 wxResourceBuffer[0] = 0;
2891 wxEatWhiteSpaceString(s);
2892
2893 int ch = getc_string(s);
2894 if (ch == '"')
2895 {
2896 // Get string
2897 wxResourceBufferCount = 0;
2898 ch = getc_string(s);
2899 while (ch != '"')
2900 {
2901 int actualCh = ch;
2902 if (ch == EOF)
2903 {
2904 wxResourceBuffer[wxResourceBufferCount] = 0;
2905 return FALSE;
2906 }
2907 // Escaped characters
2908 else if (ch == '\\')
2909 {
2910 int newCh = getc_string(s);
2911 if (newCh == '"')
2912 actualCh = '"';
2913 else if (newCh == 10)
2914 actualCh = 10;
2915 else
2916 {
2917 ungetc_string();
2918 }
2919 }
2920
2921 if (wxResourceBufferCount >= wxResourceBufferSize-1)
2922 wxReallocateResourceBuffer();
2923 wxResourceBuffer[wxResourceBufferCount] = (char)actualCh;
2924 wxResourceBufferCount ++;
2925 ch = getc_string(s);
2926 }
2927 wxResourceBuffer[wxResourceBufferCount] = 0;
2928 }
2929 else
2930 {
2931 wxResourceBufferCount = 0;
2932 // Any other token
2933 while (ch != ' ' && ch != EOF && ch != ' ' && ch != 13 && ch != 9 && ch != 10)
2934 {
2935 if (wxResourceBufferCount >= wxResourceBufferSize-1)
2936 wxReallocateResourceBuffer();
2937 wxResourceBuffer[wxResourceBufferCount] = (char)ch;
2938 wxResourceBufferCount ++;
2939
2940 ch = getc_string(s);
2941 }
2942 wxResourceBuffer[wxResourceBufferCount] = 0;
2943 if (ch == EOF)
2944 return FALSE;
2945 }
2946 return TRUE;
2947 }
2948
2949 /*
2950 * Files are in form:
2951 static char *name = "....";
2952 with possible comments.
2953 */
2954
2955 bool wxResourceReadOneResourceString(char *s, wxExprDatabase& db, bool *eof, wxResourceTable *table)
2956 {
2957 if (!table)
2958 table = wxDefaultResourceTable;
2959
2960 // static or #define
2961 if (!wxGetResourceTokenString(s))
2962 {
2963 *eof = TRUE;
2964 return FALSE;
2965 }
2966
2967 if (strcmp(wxResourceBuffer, "#define") == 0)
2968 {
2969 wxGetResourceTokenString(s);
2970 wxChar *name = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
2971 wxGetResourceTokenString(s);
2972 wxChar *value = copystring(wxConvCurrent->cMB2WX(wxResourceBuffer));
2973 if (wxIsdigit(value[0]))
2974 {
2975 int val = (int)wxAtol(value);
2976 wxResourceAddIdentifier(name, val, table);
2977 }
2978 else
2979 {
2980 wxLogWarning(_("#define %s must be an integer."), name);
2981 delete[] name;
2982 delete[] value;
2983 return FALSE;
2984 }
2985 delete[] name;
2986 delete[] value;
2987
2988 return TRUE;
2989 }
2990 /*
2991 else if (strcmp(wxResourceBuffer, "#include") == 0)
2992 {
2993 wxGetResourceTokenString(s);
2994 char *name = copystring(wxResourceBuffer);
2995 char *actualName = name;
2996 if (name[0] == '"')
2997 actualName = name + 1;
2998 int len = strlen(name);
2999 if ((len > 0) && (name[len-1] == '"'))
3000 name[len-1] = 0;
3001 if (!wxResourceParseIncludeFile(actualName, table))
3002 {
3003 char buf[400];
3004 sprintf(buf, _("Could not find resource include file %s."), actualName);
3005 wxLogWarning(buf);
3006 }
3007 delete[] name;
3008 return TRUE;
3009 }
3010 */
3011 else if (strcmp(wxResourceBuffer, "static") != 0)
3012 {
3013 wxChar buf[300];
3014 wxStrcpy(buf, _("Found "));
3015 wxStrncat(buf, wxConvCurrent->cMB2WX(wxResourceBuffer), 30);
3016 wxStrcat(buf, _(", expected static, #include or #define\nwhilst parsing resource."));
3017 wxLogWarning(buf);
3018 return FALSE;
3019 }
3020
3021 // char
3022 if (!wxGetResourceTokenString(s))
3023 {
3024 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
3025 *eof = TRUE;
3026 return FALSE;
3027 }
3028
3029 if (strcmp(wxResourceBuffer, "char") != 0)
3030 {
3031 wxLogWarning(_("Expected 'char' whilst parsing resource."));
3032 return FALSE;
3033 }
3034
3035 // *name
3036 if (!wxGetResourceTokenString(s))
3037 {
3038 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
3039 *eof = TRUE;
3040 return FALSE;
3041 }
3042
3043 if (wxResourceBuffer[0] != '*')
3044 {
3045 wxLogWarning(_("Expected '*' whilst parsing resource."));
3046 return FALSE;
3047 }
3048 wxChar nameBuf[100];
3049 wxMB2WX(nameBuf, wxResourceBuffer+1, 99);
3050 nameBuf[99] = 0;
3051
3052 // =
3053 if (!wxGetResourceTokenString(s))
3054 {
3055 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
3056 *eof = TRUE;
3057 return FALSE;
3058 }
3059
3060 if (strcmp(wxResourceBuffer, "=") != 0)
3061 {
3062 wxLogWarning(_("Expected '=' whilst parsing resource."));
3063 return FALSE;
3064 }
3065
3066 // String
3067 if (!wxGetResourceTokenString(s))
3068 {
3069 wxLogWarning(_("Unexpected end of file whilst parsing resource."));
3070 *eof = TRUE;
3071 return FALSE;
3072 }
3073 else
3074 {
3075 if (!db.ReadPrologFromString(wxResourceBuffer))
3076 {
3077 wxLogWarning(_("%s: ill-formed resource file syntax."), nameBuf);
3078 return FALSE;
3079 }
3080 }
3081 // Semicolon
3082 if (!wxGetResourceTokenString(s))
3083 {
3084 *eof = TRUE;
3085 }
3086 return TRUE;
3087 }
3088
3089 bool wxResourceParseString(char *s, wxResourceTable *table)
3090 {
3091 if (!table)
3092 table = wxDefaultResourceTable;
3093
3094 if (!s)
3095 return FALSE;
3096
3097 // Turn backslashes into spaces
3098 if (s)
3099 {
3100 int len = strlen(s);
3101 int i;
3102 for (i = 0; i < len; i++)
3103 if (s[i] == 92 && s[i+1] == 13)
3104 {
3105 s[i] = ' ';
3106 s[i+1] = ' ';
3107 }
3108 }
3109
3110 wxExprDatabase db;
3111 wxResourceStringPtr = 0;
3112
3113 bool eof = FALSE;
3114 while (wxResourceReadOneResourceString(s, db, &eof, table) && !eof)
3115 {
3116 // Loop
3117 }
3118 return wxResourceInterpretResources(*table, db);
3119 }
3120
3121 /*
3122 * resource loading facility
3123 */
3124
3125 bool wxWindowBase::LoadFromResource(wxWindow *parent, const wxString& resourceName, const wxResourceTable *table)
3126 {
3127 if (!table)
3128 table = wxDefaultResourceTable;
3129
3130 wxItemResource *resource = table->FindResource((const wxChar *)resourceName);
3131 // if (!resource || (resource->GetType() != wxTYPE_DIALOG_BOX))
3132 if (!resource || (resource->GetType() == wxT("")) ||
3133 ! ((resource->GetType() == wxT("wxDialog")) || (resource->GetType() == wxT("wxPanel"))))
3134 return FALSE;
3135
3136 wxString title(resource->GetTitle());
3137 long theWindowStyle = resource->GetStyle();
3138 bool isModal = (resource->GetValue1() != 0) ;
3139 int x = resource->GetX();
3140 int y = resource->GetY();
3141 int width = resource->GetWidth();
3142 int height = resource->GetHeight();
3143 wxString name = resource->GetName();
3144
3145 if (IsKindOf(CLASSINFO(wxDialog)))
3146 {
3147 wxDialog *dialogBox = (wxDialog *)this;
3148 long modalStyle = isModal ? wxDIALOG_MODAL : 0;
3149 if (!dialogBox->Create(parent, -1, title, wxPoint(x, y), wxSize(width, height), theWindowStyle|modalStyle, name))
3150 return FALSE;
3151
3152 // Only reset the client size if we know we're not going to do it again below.
3153 if ((resource->GetResourceStyle() & wxRESOURCE_DIALOG_UNITS) == 0)
3154 dialogBox->SetClientSize(width, height);
3155 }
3156 else if (IsKindOf(CLASSINFO(wxPanel)))
3157 {
3158 wxPanel* panel = (wxPanel *)this;
3159 if (!panel->Create(parent, -1, wxPoint(x, y), wxSize(width, height), theWindowStyle | wxTAB_TRAVERSAL, name))
3160 return FALSE;
3161 }
3162 else
3163 {
3164 if (!((wxWindow *)this)->Create(parent, -1, wxPoint(x, y), wxSize(width, height), theWindowStyle, name))
3165 return FALSE;
3166 }
3167
3168 if ((resource->GetResourceStyle() & wxRESOURCE_USE_DEFAULTS) != 0)
3169 {
3170 // No need to do this since it's done in wxPanel or wxDialog constructor.
3171 // SetFont(wxSystemSettings::GetSystemFont(wxSYS_DEFAULT_GUI_FONT));
3172 }
3173 else
3174 {
3175 if (resource->GetFont().Ok())
3176 SetFont(resource->GetFont());
3177 if (resource->GetBackgroundColour().Ok())
3178 SetBackgroundColour(resource->GetBackgroundColour());
3179 }
3180
3181 // Should have some kind of font at this point
3182 if (!GetFont().Ok())
3183 SetFont(wxSystemSettings::GetSystemFont(wxSYS_DEFAULT_GUI_FONT));
3184 if (!GetBackgroundColour().Ok())
3185 SetBackgroundColour(wxSystemSettings::GetSystemColour(wxSYS_COLOUR_3DFACE));
3186
3187 // Only when we've created the window and set the font can we set the correct size,
3188 // if based on dialog units.
3189 if ((resource->GetResourceStyle() & wxRESOURCE_DIALOG_UNITS) != 0)
3190 {
3191 wxSize sz = ConvertDialogToPixels(wxSize(width, height));
3192 SetClientSize(sz.x, sz.y);
3193
3194 wxPoint pt = ConvertDialogToPixels(wxPoint(x, y));
3195 Move(pt.x, pt.y);
3196 }
3197
3198 // Now create children
3199 wxNode *node = resource->GetChildren().First();
3200 while (node)
3201 {
3202 wxItemResource *childResource = (wxItemResource *)node->Data();
3203
3204 (void) CreateItem(childResource, resource, table);
3205
3206 node = node->Next();
3207 }
3208 return TRUE;
3209 }
3210
3211 wxControl *wxWindowBase::CreateItem(const wxItemResource *resource, const wxItemResource* parentResource, const wxResourceTable *table)
3212 {
3213 if (!table)
3214 table = wxDefaultResourceTable;
3215 return table->CreateItem((wxWindow *)this, resource, parentResource);
3216 }
3217
3218 #ifdef __VISUALC__
3219 #pragma warning(default:4706) // assignment within conditional expression
3220 #endif // VC++
3221
3222 #endif
3223 // BC++/Win16
3224
3225 #endif // wxUSE_WX_RESOURCES