1 /*
2 Copyright (C) 2019-2021, Dirk Krause
3 SPDX-License-Identifier: BSD-3-Clause
4 */
5 
6 /*
7 	WARNING: This file was generated by the dkct program (see
8 	http://dktools.sourceforge.net/ for details).
9 	Changes you make here will be lost if dkct is run again!
10 	You should modify the original source and run dkct on it.
11 	Original source: WximgszFrame.wxc
12 */
13 
14 /**	@file WximgszFrame.cpp The WximgszFrame module.
15 */
16 
17 
18 #include <wximgsz/wximgsz.h>
19 
20 
21 #if !defined(__WXMSW__)
22 #include "gui-img/icons/dkicon.xpm"
23 #endif
24 
25 
26 #include "gui-img/shared/toolbar/run-conversion.xpm"
27 
28 
29 
30 
31 
32 
33 /*	__CHANGE__ 017: Add further events. */
34 
35 /*	Hint: Window IDs for main frame members are defined in an enum
36 	in the frame class.
37 	IDs defined in this enum should have WximgszFrame:: prepended
38 	for an optical distinction from predefined window IDs (i.e. from
39 	wxWidgets).
40 */
41 
42 /*	__CHANGE__ 008: Remove OnIdle if no idle processing required.
43 	When removing the table entry here, remove the entire OnIdle() method.
44 */
45 
46 #if wxCHECK_VERSION(3,0,0)
47 wxBEGIN_EVENT_TABLE(WximgszFrame,wxFrame)
48 #else
49 BEGIN_EVENT_TABLE(WximgszFrame,wxFrame)
50 #endif
51 	EVT_MENU(\
52 		wxID_OPEN,\
53 		WximgszFrame::OnFileOpen\
54 	)
55 	EVT_MENU(\
56 		wxID_EXIT,\
57 		WximgszFrame::OnQuit\
58 	)
59 	EVT_MENU(\
60 		WximgszFrame::ID_HELP_ABOUT,\
61 		WximgszFrame::OnAbout\
62 	)
63 	EVT_MENU(\
64 		WximgszFrame::ID_HELP_TOC,\
65 		WximgszFrame::OnHelpContents\
66 	)
67 	EVT_BUTTON(\
68 		WximgszFrame::ID_BUTTON_RUN,\
69 		WximgszFrame::OnButtonRun\
70 	)
71 	EVT_CHOICE(\
72 		WximgszFrame::ID_CHOICE_OP,\
73 		WximgszFrame::OnChoiceOperation\
74 	)
75 	EVT_IDLE(\
76 		WximgszFrame::OnIdle\
77 	)
78 #if wxCHECK_VERSION(3,0,0)
79 wxEND_EVENT_TABLE()
80 #else
81 END_EVENT_TABLE()
82 #endif
83 
84 
85 
86 /**	Image file types we can handle.
87 */
88 static wxChar const image_files_to_open[] = {
89 	wxT("All files (*.*)|*.*")
90 #if	wxUSE_LIBPNG
91 	wxT("|PNG files (*.png)|*.png")
92 #endif
93 #if	wxUSE_LIBJPEG
94 	wxT("|JPEG files (*.jpeg)|*.jpeg")
95 	wxT("|JPEG files (*.jpg)|*.jpg")
96 #endif
97 #if	wxUSE_LIBTIFF
98 	wxT("|TIFF files (*.tiff)|*.tiff")
99 	wxT("|TIFF files (*.tif)|*.tif")
100 #endif
101 #if	wxUSE_GIF
102 	wxT("|GIF files (*.gif)|*.gif")
103 #endif
104 #if	wxUSE_PCX
105 	wxT("|PCX files (*.pcx)|*.pcx")
106 #endif
107 	wxT("|BMP files (*.bmp)|*.bmp")
108 #if	wxUSE_ICO_CUR
109 	wxT("|ICO files (*.ico)|*.ico")
110 	wxT("|CUR files (*.cur)|*.cur")
111 #endif
112 #if	wxUSE_XPM
113 	wxT("|XPM files (*.xpm)|*.xpm")
114 	wxT("|XBM files (*.xbm)|*.xbm")
115 #endif
116 #if	wxUSE_TGA
117 	wxT("|TGA files (*.tga)|*.tga")
118 #endif
119 #if	wxUSE_IFF
120 	wxT("|IFF files (*.iff)|*.iff")
121 #endif
122 	wxT("|ANI files (*.ani)|*.ani")
123 #if	wxUSE_PNM
124 	wxT("|NetPBM files (*.pam)|*.pam")
125 	wxT("|NetPBM files (*.pnm)|*.pnm")
126 	wxT("|NetPBM files (*.ppm)|*.ppm")
127 	wxT("|NetPBM files (*.pgm)|*.pgm")
128 	wxT("|NetPBM files (*.pbm)|*.pbm")
129 #endif
130 };
131 
132 
133 /**	Suffix and bitmap type relationship.
134 */
135 typedef struct {
136 	wxChar const	*s;	/**< File name suffix. */
137 	wxBitmapType	 t;	/**< Bitmap type. */
138 } Suffix_and_type_t;
139 
140 
141 
142 /**	Array to assign file name suffixes to file types.
143 */
144 Suffix_and_type_t	suffix_and_type[] = {
145 #if	wxUSE_LIBPNG
146 	{ wxT(".png"),		wxBITMAP_TYPE_PNG },
147 #endif
148 #if	wxUSE_LIBJPEG
149 	{ wxT(".jpeg"),		wxBITMAP_TYPE_JPEG },
150 	{ wxT(".jpg"),		wxBITMAP_TYPE_JPEG },
151 #endif
152 #if	wxUSE_LIBTIFF
153 	{ wxT(".tiff"),		wxBITMAP_TYPE_TIFF },
154 	{ wxT(".tif"),		wxBITMAP_TYPE_TIF },
155 #endif
156 #if	wxUSE_PNM
157 	{ wxT(".pam"),		wxBITMAP_TYPE_PNM },
158 	{ wxT(".pnm"),		wxBITMAP_TYPE_PNM },
159 	{ wxT(".ppm"),		wxBITMAP_TYPE_PNM },
160 	{ wxT(".pgm"),		wxBITMAP_TYPE_PNM },
161 	{ wxT(".pbm"),		wxBITMAP_TYPE_PNM },
162 #endif
163 #if	wxUSE_XPM
164 	{ wxT(".xpm"),		wxBITMAP_TYPE_XPM },
165 	{ wxT(".xbm"),		wxBITMAP_TYPE_XBM },
166 #endif
167 #if	wxUSE_ICO_CUR
168 	{ wxT(".ico"),		wxBITMAP_TYPE_ICO },
169 	{ wxT(".cur"),		wxBITMAP_TYPE_CUR },
170 #endif
171 #if	wxUSE_GIF
172 	{ wxT(".gif"),		wxBITMAP_TYPE_GIF },
173 #endif
174 #if	wxUSE_PCX
175 	{ wxT(".pcx"),		wxBITMAP_TYPE_PCX },
176 #endif
177 	{ wxT(".bmp"),		wxBITMAP_TYPE_BMP },
178 #if	wxUSE_TGA
179 	{ wxT(".tga"),		wxBITMAP_TYPE_TGA },
180 #endif
181 #if	wxUSE_IFF
182 	{ wxT(".iff"),		wxBITMAP_TYPE_IFF },
183 #endif
184 	{ wxT(".ani"),		wxBITMAP_TYPE_ANI },
185 	{ NULL,				wxBITMAP_TYPE_INVALID }
186 };
187 
188 
189 
190 static
191 wxBitmapType
bitmap_type_for_name(wxString & fn)192 bitmap_type_for_name(wxString & fn)
193 {
194 	wxChar const		*ptr		= NULL;
195 	Suffix_and_type_t	*sat		= NULL;
196 	wxBitmapType		 back		= wxBITMAP_TYPE_INVALID;
197 	wxCStrData			 strdata	= fn.c_str();
198 	ptr = (wxChar const *)strdata;
199 	if (NULL != ptr) {
200 		ptr = dk4strx_get_path_suffix(ptr, NULL);
201 		if (NULL != ptr) {
202 			sat = suffix_and_type;
203 			while((NULL != sat->s) && (wxBITMAP_TYPE_INVALID == back)) {
204 				if (0 == dk4strx_casecmp(sat->s, ptr)) {
205 					back = sat->t;
206 				}
207 				else {
208 					sat++;
209 				}
210 			}
211 		}
212 	}
213 	return back;
214 }
215 
216 
217 
WximgszFrame(int wxid,Dk4WxApplicationHelper * applicationHelper,Dk4WxHelpController * hc,int argc,wxChar ** argv,wxChar const * const * localizedTexts,wxChar const * const * nlWx,dkChar const * const * nlDk)218 WximgszFrame::WximgszFrame(
219 	int						  wxid,
220 	Dk4WxApplicationHelper	 *applicationHelper,
221 	Dk4WxHelpController		 *hc,
222 	int						  argc,
223 	wxChar					**argv,
224 	wxChar const * const	 *localizedTexts,
225 	wxChar const * const	 *nlWx,
226 	dkChar const * const	 *nlDk
227 ) : Dk4WxFrame(nlWx[0], applicationHelper, hc, wxid),
228 	cas(),
229 	cLabelRed(127, 0, 0),
230 	cRed(255, 91, 91),
231 	cGreen(127, 255, 127),
232 	cYellow(255, 255, 0),
233 	cBlack(0, 0, 0),
234 	sImageFileName((1 < argc)?(argv[1]):(wxT(""))),
235 	sDirectory(wxEmptyString)
236 {
237 	wxString saOperation[] = {
238 		wxString(localizedTexts[21]),
239 		wxString(localizedTexts[22]),
240 		wxString(localizedTexts[23])
241 	};
242 
243 	/*	__CHANGE__ 012:	Add further local variables.
244 	*/
245 
246 	/*	__CHANGE__ 012: Initialize further local variables.
247 	*/
248 
249 	sTexts = localizedTexts;
250 	sNlWx  = nlWx;
251 	sNlDk  = nlDk;
252 #if defined(__WXMSW__)
253 	wxIcon	wximgsz_icon(sNlWx[4]);
254 #else
255 	wxIcon	wximgsz_icon(xpm_dkicon);
256 #endif
257 
258 	/*	__CHANGE__ 011:	Initialize further class members.
259 	*/
260 	maxpass = MAXPASS;
261 	bActive = false;
262 	bImageFileName = false;
263 	if (1 < argc) {
264 		bImageFileName = true;
265 		cas.SetAutoStart();
266 	}
267 
268   dkctGUILayoutOK = false;
269   dkctGUIContentsPanel = NULL;
270   mainSizer = NULL;
271   mbMain = NULL;
272   menuFile = NULL;
273   menuHelp = NULL;
274   miFileOpen = NULL;
275   miFileExit = NULL;
276   miHelpAbout = NULL;
277   miHelpContents = NULL;
278   verticalSizer = NULL;
279   contentsSizer = NULL;
280   inputSizer = NULL;
281   runButtonSizer = NULL;
282   resultSizer = NULL;
283   lInput = NULL;
284   lInputWidth = NULL;
285   spInputWidth = NULL;
286   lInputHeight = NULL;
287   spInputHeight = NULL;
288   lChange = NULL;
289   lOperation = NULL;
290   cbOperation = NULL;
291   lOperationMin = NULL;
292   spOperationMin = NULL;
293   lOperationMax = NULL;
294   spOperationMax = NULL;
295   bRun = NULL;
296   lResults = NULL;
297   tResult = NULL;
298   dkctGUIContentsPanel = new wxPanel(this);
299   if(!(dkctGUIContentsPanel)) {
300     goto dkctGUILayoutFinished;
301   }
302 #if wxUSE_MENUS
303   mbMain = new wxMenuBar(
304   );
305   if(!(mbMain)) {
306     goto dkctGUILayoutFinished;
307   }
308   menuFile = new wxMenu(
309   );
310   if(!(menuFile)) {
311     goto dkctGUILayoutFinished;
312   }
313   miFileOpen = menuFile->Append(
314     wxID_OPEN,
315     sTexts[40],
316     sTexts[41]
317   );
318   if(!(miFileOpen)) {
319     goto dkctGUILayoutFinished;
320   }
321   miFileExit = menuFile->Append(
322     wxID_EXIT,
323     sTexts[1],
324     sTexts[2]
325   );
326   if(!(miFileExit)) {
327     goto dkctGUILayoutFinished;
328   }
329   mbMain->Append(menuFile, sTexts[0]);
330   menuHelp = new wxMenu(
331   );
332   if(!(menuHelp)) {
333     goto dkctGUILayoutFinished;
334   }
335   miHelpAbout = menuHelp->Append(
336     WximgszFrame::ID_HELP_ABOUT,
337     sTexts[4],
338     sTexts[5]
339   );
340   if(!(miHelpAbout)) {
341     goto dkctGUILayoutFinished;
342   }
343   miHelpContents = menuHelp->Append(
344     WximgszFrame::ID_HELP_TOC,
345     sTexts[6],
346     sTexts[7]
347   );
348   if(!(miHelpContents)) {
349     goto dkctGUILayoutFinished;
350   }
351   mbMain->Append(menuHelp, sTexts[3]);
352   SetMenuBar(mbMain);
353 #endif
354   mainSizer = new wxBoxSizer(
355     wxHORIZONTAL
356   );
357   if(!(mainSizer)) {
358     goto dkctGUILayoutFinished;
359   }
360   mainSizer->Add(10, 10, 0);
361   verticalSizer = new wxBoxSizer(
362     wxVERTICAL
363   );
364   if(!(verticalSizer)) {
365     goto dkctGUILayoutFinished;
366   }
367   verticalSizer->Add(10, 10, 0);
368   contentsSizer = new wxBoxSizer(
369     wxHORIZONTAL
370   );
371   if(!(contentsSizer)) {
372     goto dkctGUILayoutFinished;
373   }
374   inputSizer = new wxGridBagSizer(
375     5, 5
376   );
377   if(!(inputSizer)) {
378     goto dkctGUILayoutFinished;
379   }
380   lInput = new wxStaticText(
381     dkctGUIContentsPanel,
382     wxID_ANY,
383     sTexts[13]
384   );
385   if(!(lInput)) {
386     goto dkctGUILayoutFinished;
387   }
388   inputSizer->Add(
389     lInput,
390     wxGBPosition(0, 0),
391     wxGBSpan(1, 2),
392     wxALIGN_LEFT
393   );
394   lInputWidth = new wxStaticText(
395     dkctGUIContentsPanel,
396     wxID_ANY,
397     sTexts[14]
398   );
399   if(!(lInputWidth)) {
400     goto dkctGUILayoutFinished;
401   }
402   inputSizer->Add(
403     lInputWidth,
404     wxGBPosition(1, 0),
405     wxGBSpan(1, 1),
406     wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL
407   );
408   spInputWidth = new wxSpinCtrl(
409     dkctGUIContentsPanel,
410     wxID_ANY,
411     wxEmptyString,
412     wxDefaultPosition,
413     wxDefaultSize,
414     0,
415     1,
416     65535,
417     1
418   );
419   if(!(spInputWidth)) {
420     goto dkctGUILayoutFinished;
421   }
422   spInputWidth->SetToolTip(sTexts[16]);
423   inputSizer->Add(
424     spInputWidth,
425     wxGBPosition(1, 1),
426     wxGBSpan(1, 1),
427     wxALIGN_CENTER_VERTICAL
428   );
429   lInputHeight = new wxStaticText(
430     dkctGUIContentsPanel,
431     wxID_ANY,
432     sTexts[15]
433   );
434   if(!(lInputHeight)) {
435     goto dkctGUILayoutFinished;
436   }
437   inputSizer->Add(
438     lInputHeight,
439     wxGBPosition(2, 0),
440     wxGBSpan(1, 1),
441     wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL
442   );
443   spInputHeight = new wxSpinCtrl(
444     dkctGUIContentsPanel,
445     wxID_ANY,
446     wxEmptyString,
447     wxDefaultPosition,
448     wxDefaultSize,
449     0,
450     1,
451     65535,
452     1
453   );
454   if(!(spInputHeight)) {
455     goto dkctGUILayoutFinished;
456   }
457   spInputHeight->SetToolTip(sTexts[17]);
458   inputSizer->Add(
459     spInputHeight,
460     wxGBPosition(2, 1),
461     wxGBSpan(1, 1),
462     wxALIGN_CENTER_VERTICAL
463   );
464   inputSizer->Add(10, 10, wxGBPosition(3, 0), wxGBSpan(1, 1));
465   lChange = new wxStaticText(
466     dkctGUIContentsPanel,
467     wxID_ANY,
468     sTexts[18]
469   );
470   if(!(lChange)) {
471     goto dkctGUILayoutFinished;
472   }
473   inputSizer->Add(
474     lChange,
475     wxGBPosition(4, 0),
476     wxGBSpan(1, 2),
477     wxALIGN_LEFT
478   );
479   lOperation = new wxStaticText(
480     dkctGUIContentsPanel,
481     wxID_ANY,
482     sTexts[19]
483   );
484   if(!(lOperation)) {
485     goto dkctGUILayoutFinished;
486   }
487   inputSizer->Add(
488     lOperation,
489     wxGBPosition(5, 0),
490     wxGBSpan(1, 1),
491     wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL
492   );
493   cbOperation = new wxChoice(
494     dkctGUIContentsPanel,
495     ID_CHOICE_OP,
496     wxDefaultPosition,
497     wxDefaultSize,
498     3,
499     saOperation
500   );
501   if(!(cbOperation)) {
502     goto dkctGUILayoutFinished;
503   }
504   cbOperation->SetToolTip(sTexts[20]);
505   inputSizer->Add(
506     cbOperation,
507     wxGBPosition(5, 1),
508     wxGBSpan(1, 1),
509     wxALIGN_LEFT|wxALIGN_CENTER_VERTICAL
510   );
511   lOperationMin = new wxStaticText(
512     dkctGUIContentsPanel,
513     wxID_ANY,
514     sTexts[24]
515   );
516   if(!(lOperationMin)) {
517     goto dkctGUILayoutFinished;
518   }
519   inputSizer->Add(
520     lOperationMin,
521     wxGBPosition(6, 0),
522     wxGBSpan(1, 1),
523     wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL
524   );
525   spOperationMin = new wxSpinCtrl(
526     dkctGUIContentsPanel,
527     wxID_ANY,
528     wxEmptyString,
529     wxDefaultPosition,
530     wxDefaultSize,
531     0,
532     1,
533     65535,
534     1
535   );
536   if(!(spOperationMin)) {
537     goto dkctGUILayoutFinished;
538   }
539   spOperationMin->SetToolTip(sTexts[26]);
540   inputSizer->Add(
541     spOperationMin,
542     wxGBPosition(6, 1),
543     wxGBSpan(1, 1),
544     wxALIGN_LEFT|wxALIGN_CENTER_VERTICAL
545   );
546   lOperationMax = new wxStaticText(
547     dkctGUIContentsPanel,
548     wxID_ANY,
549     sTexts[25]
550   );
551   if(!(lOperationMax)) {
552     goto dkctGUILayoutFinished;
553   }
554   inputSizer->Add(
555     lOperationMax,
556     wxGBPosition(7, 0),
557     wxGBSpan(1, 1),
558     wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL
559   );
560   spOperationMax = new wxSpinCtrl(
561     dkctGUIContentsPanel,
562     wxID_ANY,
563     wxEmptyString,
564     wxDefaultPosition,
565     wxDefaultSize,
566     0,
567     1,
568     65535,
569     1
570   );
571   if(!(spOperationMax)) {
572     goto dkctGUILayoutFinished;
573   }
574   spOperationMax->SetToolTip(sTexts[27]);
575   inputSizer->Add(
576     spOperationMax,
577     wxGBPosition(7, 1),
578     wxGBSpan(1, 1),
579     wxALIGN_LEFT|wxALIGN_CENTER_VERTICAL
580   );
581   contentsSizer->Add(
582     inputSizer
583   );
584   contentsSizer->Add(20, 20, 0);
585   runButtonSizer = new wxBoxSizer(
586     wxVERTICAL
587   );
588   if(!(runButtonSizer)) {
589     goto dkctGUILayoutFinished;
590   }
591   runButtonSizer->Add(10, 10, 1);
592   bRun = new wxBitmapButton(
593     dkctGUIContentsPanel,
594     ID_BUTTON_RUN,
595     xpm_run_conversion
596   );
597   if(!(bRun)) {
598     goto dkctGUILayoutFinished;
599   }
600   bRun->SetToolTip(sTexts[29]);
601   runButtonSizer->Add(
602     bRun
603   );
604   runButtonSizer->Add(10, 10, 1);
605   contentsSizer->Add(
606     runButtonSizer,
607     0,
608     wxGROW
609   );
610   contentsSizer->Add(20, 20, 0);
611   resultSizer = new wxBoxSizer(
612     wxVERTICAL
613   );
614   if(!(resultSizer)) {
615     goto dkctGUILayoutFinished;
616   }
617   lResults = new wxStaticText(
618     dkctGUIContentsPanel,
619     wxID_ANY,
620     sTexts[28]
621   );
622   if(!(lResults)) {
623     goto dkctGUILayoutFinished;
624   }
625   resultSizer->Add(
626     lResults,
627     0,
628     wxALIGN_LEFT
629   );
630   tResult = new wxGrid(
631     dkctGUIContentsPanel,
632     wxID_ANY
633   );
634   if(!(tResult)) {
635     goto dkctGUILayoutFinished;
636   }
637   tResult->CreateGrid(4, 4);
638   tResult->SetColLabelValue(0, sTexts[30]);
639   tResult->SetColLabelValue(1, sTexts[31]);
640   tResult->SetColLabelValue(2, sTexts[32]);
641   tResult->SetColLabelValue(3, sTexts[33]);
642   tResult->EnableEditing(false);
643   resultSizer->Add(
644     tResult,
645     1,
646     wxALIGN_LEFT|wxGROW
647   );
648   contentsSizer->Add(
649     resultSizer,
650     1,
651     wxGROW
652   );
653   verticalSizer->Add(
654     contentsSizer,
655     1,
656     wxGROW
657   );
658   verticalSizer->Add(10, 10, 0);
659   mainSizer->Add(
660     verticalSizer,
661     1,
662     wxGROW
663   );
664   mainSizer->Add(10, 10, 0);
665   dkctGUIContentsPanel->SetSizer(mainSizer);
666   SetIcon(wximgsz_icon);
667   dkctGUILayoutOK = true;
668   dkctGUILayoutFinished:
669 #if wxUSE_STATUSBAR
670   if(dkctGUILayoutOK) {
671     CreateStatusBar(1);
672     SetStatusText(sTexts[8]);
673   }
674 #endif
675   if(dkctGUILayoutOK) {
676     mainSizer->Fit(this);
677     mainSizer->SetSizeHints(this);
678   }
679 	if(dkctGUILayoutOK) {
680 		lInput->SetForegroundColour(cLabelRed);
681 		lChange->SetForegroundColour(cLabelRed);
682 		lResults->SetForegroundColour(cLabelRed);
683 #if	0
684 		spInputWidth->SetRange(1, INT_MAX);
685 		spInputHeight->SetRange(1, INT_MAX);
686 		spOperationMin->SetRange(1, INT_MAX);
687 		spOperationMax->SetRange(1, INT_MAX);
688 		inputSizer->Fit(spInputWidth);
689 		inputSizer->Fit(spInputHeight);
690 		inputSizer->Fit(spOperationMin);
691 		inputSizer->Fit(spOperationMax);
692 		mainSizer->Layout();
693 #endif
694 		cbOperation->SetSelection(0);
695 		spOperationMin->Enable(false);
696 		spOperationMax->Enable(false);
697 		SetTitle(nlWx[0]);
698 #if 0
699 		RestorePosition();
700 #endif
701 	}
702 
703 	/*	__CHANGE__ 012:	Release resources allocated by local variables.
704 	*/
705 
706 
707 }
708 
709 
710 
711 
~WximgszFrame()712 WximgszFrame::~WximgszFrame()
713 {
714 
715 
716 	/*	__CHANGE__ 011:	Release resources allocated by further class members.
717 	*/
718 
719 
720 }
721 
722 
723 
724 bool
CanClose(bool WXUNUSED (isLast))725 WximgszFrame::CanClose(bool WXUNUSED(isLast))
726 {
727 	bool		back	= true;
728 
729 
730 	/*	__CHANGE__ 013: Check for unsaved data.
731 						And probably change parameter to "bool WXUNUSED(isLast)"
732 	*/
733 
734 
735 	return back;
736 }
737 
738 
739 
740 void
OnFileOpen(wxCommandEvent & WXUNUSED (event))741 WximgszFrame::OnFileOpen(wxCommandEvent & WXUNUSED(event))
742 {
743 	dkChar			 buf[DK4_MAX_PATH];
744 	dk4_bif_t		*pbif;
745 	const wxChar	*ptrFilePath;
746 	bool			 success	=	false;
747 	int				 dke;
748 	int				 wxe;
749 	int				 res;
750 #if	wxCHECK_VERSION(2, 9, 0)
751 	wxFileDialog dlg(
752 		this, sTexts[42], sDirectory, wxEmptyString,
753 		image_files_to_open, (wxFD_OPEN | wxFD_FILE_MUST_EXIST)
754 	);
755 #else
756 	wxFileDialog dlg(
757 		this, sTexts[42], sDirectory, wxEmptyString,
758 		image_files_to_open, wxOPEN
759 	);
760 #endif
761 
762 	if(wxID_OK == dlg.ShowModal()) {
763 		wxString	pa	=	dlg.GetPath();
764 		wxFileName	wxfn(pa);
765 		if (wxfn.FileExists() && wxfn.IsFileReadable()) {
766 			sDirectory		=	dlg.GetDirectory();
767 			{
768 				wxCStrData	sFilePath	= pa.c_str();
769 				ptrFilePath = (wxChar const *)sFilePath;
770 				if (NULL != ptrFilePath) {
771 					dke = pAppHelp->GetDkEncoding();
772 					wxe = pAppHelp->GetWxEncoding();
773 					res = dk4recwx_wxchar_to_dkchar(
774 						buf, DK4_SIZEOF(buf,dkChar), dke, ptrFilePath, wxe, NULL
775 					);
776 					if (0 != res) {
777 						pbif = dk4bif_open(buf, 1, NULL, NULL);
778 						if (NULL != pbif) {
779 							dk4_bif_dim_t w = dk4bif_get_width(pbif);
780 							dk4_bif_dim_t h = dk4bif_get_height(pbif);
781 							if (
782 								((dk4_im_t)0L < (dk4_im_t)w)
783 								&& ((dk4_im_t)0L < (dk4_im_t)h)
784 								&& ((dk4_im_t)(MAXIMGDIM) >= (dk4_im_t)w)
785 								&& ((dk4_im_t)(MAXIMGDIM) >= (dk4_im_t)h)
786 							) {
787 								spInputWidth->SetValue((int)w);
788 								spInputHeight->SetValue((int)h);
789 								success = true;
790 							}
791 							dk4bif_close(pbif);
792 						}
793 					}
794 				}
795 			}
796 			if (!(success)) {
797 				wxBitmapType	t = bitmap_type_for_name(pa);
798 				if (wxBITMAP_TYPE_INVALID != t) {
799 					wxBitmap	bm(pa, t);
800 					if (bm.IsOk()) {
801 						int		w =	bm.GetWidth();
802 						int		h = bm.GetHeight();
803 						if ((0 < w) && (0 < h)) {
804 							spInputWidth->SetValue(w);
805 							spInputHeight->SetValue(h);
806 							success = true;
807 						}
808 						else {
809 							wxMessageBox(
810 								sTexts[44], sTexts[43],
811 								(wxOK | wxCENTRE | wxICON_ERROR)
812 							);
813 						}
814 					}
815 					else {
816 						wxMessageBox(
817 							sTexts[44], sTexts[43],
818 							(wxOK | wxCENTRE | wxICON_ERROR)
819 						);
820 					}
821 				}
822 				else {
823 					wxString	s(sTexts[49]);
824 					s.Append(pa);
825 					s.Append(sTexts[50]);
826 					wxMessageBox(
827 						s, wxString(sTexts[43]), (wxOK | wxCENTRE | wxICON_ERROR)
828 					);
829 				}
830 			}
831 			if(success) {
832 				Calculations();
833 			}
834 		}
835 		else {
836 			if (!(wxfn.FileExists())) {
837 				wxString	s(sTexts[45]);
838 				s.Append(pa);
839 				s.Append(sTexts[46]);
840 				wxMessageBox(
841 					s, wxString(sTexts[43]), (wxOK | wxCENTRE | wxICON_ERROR)
842 				);
843 			}
844 			else {
845 				if (!(wxfn.IsFileReadable())) {
846 					wxString	s(sTexts[47]);
847 					s.Append(pa);
848 					s.Append(sTexts[48]);
849 					wxMessageBox(
850 						s,wxString(sTexts[43]),(wxOK | wxCENTRE | wxICON_ERROR)
851 					);
852 				}
853 			}
854 		}
855 	}
856 
857 	Refresh();
858 	Update();
859 }
860 
861 
862 void
OnQuit(wxCommandEvent & WXUNUSED (event))863 WximgszFrame::OnQuit(wxCommandEvent & WXUNUSED(event))
864 {
865 
866 	bActive = false;
867 
868 	Close();
869 }
870 
871 
872 
873 void
OnAbout(wxCommandEvent & WXUNUSED (event))874 WximgszFrame::OnAbout(wxCommandEvent & WXUNUSED(event))
875 {
876 	wxString	text(wxT(""));
877 	wxString	title(wxT(""));
878 
879 	/* Construct message text. */
880 	text.Append(sNlWx[0]);
881 	text.Append(sNlWx[7]);
882 #if	0
883 	text.Append(sNlWx[1]);
884 #endif
885 	text.Append(DKT_VERSION_WX);
886 	text.Append(sNlWx[8]);
887 	text.Append(sTexts[9]);
888 	text.Append(sNlWx[2]);
889 	text.Append(sNlWx[8]);
890 	text.Append(sNlWx[8]);
891 	text.Append(sTexts[11]);
892 	text.Append(sNlWx[8]);
893 	text.Append(sNlWx[9]);
894 	text.Append(sNlWx[8]);
895 	text.Append(sNlWx[8]);
896 	text.Append(sTexts[12]);
897 	text.Append(sNlWx[8]);
898 	text.Append(sNlWx[10]);
899 	text.Append(sNlWx[8]);
900 	text.Append(sNlWx[11]);
901 	text.Append(sNlWx[8]);
902 	text.Append(sNlWx[12]);
903 	text.Append(sNlWx[8]);
904 	text.Append(sNlWx[13]);
905 	text.Append(sNlWx[8]);
906 	text.Append(sNlWx[14]);
907 	text.Append(sNlWx[8]);
908 	text.Append(sNlWx[15]);
909 	text.Append(sNlWx[8]);
910 
911 	/* Construct dialog box title. */
912 	title.Append(sTexts[10]);
913 	title.Append(sNlWx[0]);
914 
915 	/* Show dialog box. */
916 	wxMessageBox(text, title);
917 
918 	/*	__CHANGE__ 019:	Create better about box.
919 	*/
920 
921 }
922 
923 
924 
925 void
OnHelpContents(wxCommandEvent & WXUNUSED (event))926 WximgszFrame::OnHelpContents(wxCommandEvent & WXUNUSED(event))
927 {
928 
929 	DisplayContents();
930 
931 }
932 
933 
934 
935 static
936 int
bits_in_int(int x)937 bits_in_int(int x)
938 {
939 	int		back = 0;
940 	int		test = 1;
941 	int		done = 0;
942 
943 	while (0 == done) {
944 		if (0 != (x & test)) {
945 			if (1 < ++back) {
946 				done = 1;
947 			}
948 		}
949 		if ((INT_MAX / 2) >= test) {
950 			test = test * 2;
951 			if (test > x) {
952 				done = 1;
953 			}
954 		}
955 		else {
956 			done = 1;
957 		}
958 	}
959 	return back;
960 }
961 
962 
963 static
964 int
is_power_of_2(int x)965 is_power_of_2(int x)
966 {
967 	int			back = 0;
968 	if (1 == bits_in_int(x)) {
969 		back = 1;
970 	}
971 	return back;
972 }
973 
974 
975 
976 static
977 int
quality_for_fraction(int counter,int denom)978 quality_for_fraction(int counter, int denom)
979 {
980 	int		 back = 0;
981 	if (1 == denom) {
982 		back = 1;
983 		if (0 != is_power_of_2(counter)) {
984 			back = 2;
985 		}
986 	}
987 	else {
988 		if (1 == counter) {
989 			back = 1;
990 			if (0 != is_power_of_2(denom)) {
991 				back = 2;
992 			}
993 		}
994 	}
995 	return back;
996 }
997 
998 
999 
1000 static
1001 int
gcd(int a,int b)1002 gcd(int a, int b)
1003 {
1004 	int		h;
1005 
1006 	while (0 < b) {
1007 		h = a % b;
1008 		a = b;
1009 		b = h;
1010 	}
1011 	return a;
1012 }
1013 
1014 
1015 /*	__CHANGE__ 017:	Event handlers for further events.
1016 */
1017 
1018 void
Calculations(void)1019 WximgszFrame::Calculations(void)
1020 {
1021 	wxString	s1;			/* Width */
1022 	wxString	s2;			/* Height */
1023 	wxString	s3;			/* Factor */
1024 	wxString	m2(sTexts[36]);
1025 	wxString	m1(sTexts[35]);
1026 	wxString	m0(sTexts[34]);
1027 	int			w_ori;		/* Original width */
1028 	int			h_ori;		/* Original height */
1029 	int			w_min;		/* Minimum width */
1030 	int			h_min;		/* Minimum height */
1031 	int			gcd_ori;	/* Greatest common divisor original width height */
1032 	int			min;		/* Destination range minimum */
1033 	int			max;		/* Destination range maximum */
1034 	int			opsel;		/* Operation selection */
1035 	int			f_min;		/* Minimum factor */
1036 	int			f_max;		/* Maximum factor */
1037 	int			nrows;		/* Number of table rows */
1038 	int			passno;		/* Current pass number (table row index) */
1039 	int			f;			/* Current factor */
1040 	int			w;			/* Current width */
1041 	int			h;			/* Current height */
1042 	int			counter;	/* Fraction counter */
1043 	int			denom;		/* Fraction denominator */
1044 	int			gcd_fr;		/* Fraction greatest common divisor */
1045 	int			q;			/* Fraction quality */
1046 	int			i;			/* Walk through the columns */
1047 	bool		bDidSkip;	/* Flag: Restricted output to 2000 columns */
1048 
1049 	bDidSkip = false;
1050 	w_ori = spInputWidth->GetValue();
1051 	h_ori = spInputHeight->GetValue();
1052 	min   = spOperationMin->GetValue();
1053 	max   = spOperationMax->GetValue();
1054 	opsel = cbOperation->GetSelection();
1055 	if (0 >= w_ori) { w_ori = 1; }
1056 	if (0 >= h_ori) { h_ori = 1; }
1057 	if (0 >= min) { min = 1; }
1058 	if (0 >= max) { max = 1; }
1059 	gcd_ori = gcd(w_ori, h_ori);
1060 	w_min = w_ori / gcd_ori;
1061 	h_min = h_ori / gcd_ori;
1062 	f_min = 1;
1063 	f_max = gcd_ori;
1064 	switch (opsel) {
1065 		case 1: {
1066 			f_min = min / w_min;
1067 			f_max = max / w_min;
1068 			if (0 >= f_min) { f_min = 1; }
1069 			if (0 >= f_max) { f_max = 1; }
1070 		} break;
1071 		case 2: {
1072 			f_min = min / h_min;
1073 			f_max = max / h_min;
1074 			if (0 >= f_min) { f_min = 1; }
1075 			if (0 >= f_max) { f_max = 1; }
1076 		} break;
1077 	}
1078 	nrows = f_max - f_min + 1;
1079 	if (nrows > maxpass) { nrows = maxpass; bDidSkip = true; }
1080 	/*
1081 		Delete old table columns, allocate new columns
1082 	*/
1083 	passno = tResult->GetNumberRows();
1084 	tResult->DeleteRows(0, passno);
1085 	tResult->AppendRows(nrows);
1086 	/*
1087 		Fill table
1088 	*/
1089 	passno = 0;
1090 	f = f_min;
1091 	while (passno < nrows) {
1092 		w = f * w_min;
1093 		h = f * h_min;
1094 		gcd_fr = gcd(f, gcd_ori);
1095 		counter = f / gcd_fr;
1096 		denom   = gcd_ori / gcd_fr;
1097 		q       = quality_for_fraction(counter, denom);
1098 		s1.Printf(wxT("%d"), w);
1099 		s2.Printf(wxT("%d"), h);
1100 		if (1 == denom) {
1101 			s3.Printf(wxT("%d"), counter);
1102 		}
1103 		else {
1104 			s3.Printf(wxT("%d / %d"), counter, denom);
1105 		}
1106 		for (i = 0; i < 4; i++) {
1107 			tResult->SetCellTextColour(passno, i, cBlack);
1108 		}
1109 		tResult->SetCellValue(passno, 0, s1);
1110 		tResult->SetCellValue(passno, 1, s2);
1111 		tResult->SetCellValue(passno, 2, s3);
1112 		switch (q) {
1113 			case 2: {
1114 				tResult->SetCellValue(passno, 3, m2);
1115 				for (i = 0; i < 4; i++) {
1116 					tResult->SetCellBackgroundColour(
1117 						passno, i, cGreen
1118 					);
1119 				}
1120 			} break;
1121 			case 1: {
1122 				tResult->SetCellValue(passno, 3, m1);
1123 				for (i = 0; i < 4; i++) {
1124 					tResult->SetCellBackgroundColour(
1125 						passno, i, cYellow
1126 					);
1127 				}
1128 			} break;
1129 			case 0: {
1130 				tResult->SetCellValue(passno, 3, m0);
1131 				for (i = 0; i < 4; i++) {
1132 					tResult->SetCellBackgroundColour(
1133 						passno, i, cRed
1134 					);
1135 				}
1136 			} break;
1137 		}
1138 		tResult->SetCellAlignment(passno, 0, wxALIGN_CENTRE, wxALIGN_CENTRE);
1139 		tResult->SetCellAlignment(passno, 1, wxALIGN_CENTRE, wxALIGN_CENTRE);
1140 		tResult->SetCellAlignment(passno, 2, wxALIGN_CENTRE, wxALIGN_CENTRE);
1141 		tResult->SetCellAlignment(passno, 3, wxALIGN_CENTRE, wxALIGN_CENTRE);
1142 		passno++;
1143 		f++;
1144 	}
1145 	tResult->AutoSizeColumns();
1146 	tResult->EnableDragColSize(true);
1147 	if (bDidSkip) {
1148 		wxMessageBox( sTexts[39], sTexts[38], (wxOK | wxCENTRE | wxICON_ERROR));
1149 	}
1150 
1151 }
1152 
1153 
1154 
1155 void
OnButtonRun(wxCommandEvent & WXUNUSED (event))1156 WximgszFrame::OnButtonRun(wxCommandEvent & WXUNUSED(event))
1157 {
1158 
1159 	Calculations();
1160 
1161 	Refresh();
1162 	Update();
1163 }
1164 
1165 
1166 
1167 void
OnChoiceOperation(wxCommandEvent & WXUNUSED (event))1168 WximgszFrame::OnChoiceOperation(wxCommandEvent & WXUNUSED(event))
1169 {
1170 
1171 	switch (cbOperation->GetSelection()) {
1172 		case 2 : case 1 : {
1173 			spOperationMin->Enable();
1174 			spOperationMax->Enable();
1175 		} break;
1176 		default : {
1177 			spOperationMin->Enable(false);
1178 			spOperationMax->Enable(false);
1179 		} break;
1180 	}
1181 
1182 	Refresh();
1183 	Update();
1184 }
1185 
1186 
1187 /*	__CHANGE__ 014:	Implementation of further methods.
1188 */
1189 
1190 
1191 void
ActivateIdleProcessing(bool fl)1192 WximgszFrame::ActivateIdleProcessing(bool fl)
1193 {
1194 	bActive = fl;
1195 }
1196 
1197 
1198 void
ProcessSpecifiedFileName(void)1199 WximgszFrame::ProcessSpecifiedFileName(void)
1200 {
1201 	dkChar			 buf[DK4_MAX_PATH];
1202 	wxChar const	*ptrImageFileName;
1203 	dk4_bif_t		*pbif;
1204 	int				 dke;
1205 	int				 wxe;
1206 	int				 res;
1207 	bool			 success;
1208 
1209 	success = false;
1210 	wxFileName	wxfn(sImageFileName);
1211 	if (wxfn.FileExists() && wxfn.IsFileReadable()) {
1212 		wxCStrData	csImageFileName = sImageFileName.c_str();
1213 		ptrImageFileName = (wxChar const *)csImageFileName;
1214 		if (NULL != ptrImageFileName) {
1215 			dke = pAppHelp->GetDkEncoding();
1216 			wxe = pAppHelp->GetWxEncoding();
1217 			res = dk4recwx_wxchar_to_dkchar(
1218 				buf, DK4_SIZEOF(buf,dkChar), dke, ptrImageFileName, wxe, NULL
1219 			);
1220 			if (0 != res) {
1221 				pbif = dk4bif_open(buf, 1, NULL, NULL);
1222 				if (NULL != pbif) {
1223 					dk4_bif_dim_t w = dk4bif_get_width(pbif);
1224 					dk4_bif_dim_t h = dk4bif_get_height(pbif);
1225 					if (
1226 						((dk4_im_t)0L < (dk4_im_t)w)
1227 						&& ((dk4_im_t)0L < (dk4_im_t)h)
1228 						&& ((dk4_im_t)(MAXIMGDIM) >= (dk4_im_t)w)
1229 						&& ((dk4_im_t)(MAXIMGDIM) >= (dk4_im_t)h)
1230 					) {
1231 						spInputWidth->SetValue((int)w);
1232 						spInputHeight->SetValue((int)h);
1233 						success = true;
1234 					}
1235 #if	TRACE_DEBUG
1236 					else {
1237 					}
1238 #endif
1239 					dk4bif_close(pbif);
1240 				}
1241 #if	TRACE_DEBUG
1242 				else {
1243 				}
1244 #endif
1245 			}
1246 #if	TRACE_DEBUG
1247 			else {
1248 			}
1249 #endif
1250 		}
1251 #if	TRACE_DEBUG
1252 		else {
1253 		}
1254 #endif
1255 		if (!(success)) {
1256 			wxBitmapType	t = bitmap_type_for_name(sImageFileName);
1257 			if (wxBITMAP_TYPE_INVALID != t) {
1258 				wxBitmap		bm(sImageFileName, t);
1259 				if (bm.IsOk()) {
1260 					int	w = bm.GetWidth();
1261 					int	h = bm.GetHeight();
1262 					if ((0 < w) && (0 < h)) {
1263 						spInputWidth->SetValue(w);
1264 						spInputHeight->SetValue(h);
1265 						success = true;
1266 					}
1267 					else {
1268 #if	0
1269 						wxMessageBox(
1270 							sTexts[44], sTexts[43],
1271 							(wxOK | wxCENTRE | wxICON_ERROR)
1272 						);
1273 #endif
1274 					}
1275 				}
1276 				else {
1277 #if	0
1278 					wxMessageBox(
1279 						sTexts[44],sTexts[43],(wxOK | wxCENTRE | wxICON_ERROR)
1280 					);
1281 #endif
1282 				}
1283 			}
1284 			else {
1285 #if	0
1286 				wxString	s(sTexts[49]);
1287 				s.Append(sImageFileName);
1288 				s.Append(sTexts[50]);
1289 				wxMessageBox(
1290 					s, wxString(sTexts[43]), (wxOK | wxCENTRE | wxICON_ERROR)
1291 				);
1292 #endif
1293 			}
1294 		}
1295 		if (success) {
1296 			Calculations();
1297 		}
1298 	}
1299 	else {
1300 		if (!(wxfn.FileExists())) {
1301 #if	0
1302 			wxString	s(sTexts[45]);
1303 			s.Append(sImageFileName);
1304 			s.Append(sTexts[46]);
1305 			wxMessageBox(
1306 				s, wxString(sTexts[43]), (wxOK | wxCENTRE | wxICON_ERROR)
1307 			);
1308 #endif
1309 		}
1310 		else {
1311 			if (!(wxfn.IsFileReadable())) {
1312 #if	0
1313 				wxString	s(sTexts[47]);
1314 				s.Append(sImageFileName);
1315 				s.Append(sTexts[48]);
1316 				wxMessageBox(
1317 					s, wxString(sTexts[43]), (wxOK | wxCENTRE | wxICON_ERROR)
1318 				);
1319 #endif
1320 			}
1321 		}
1322 	}
1323 
1324 }
1325 
1326 /*	__CHANGE__ 008:	Remove OnIdle if no idle processing required.
1327 */
1328 
1329 /*	__CHANGE__ 008: Remove the request for more events if not needed.
1330 */
1331 
1332 /*	__CHANGE__ 008: Decide about Skip() call.
1333 	The function name is irritating: Skip() or Skip(true) will continue to
1334 	process the event, calling default handlers.
1335 	Skip(false) or handlers without Skip() will skip further processing of the
1336 	event.
1337 
1338 	From the wxWidgets documenation: Skip() should be called for all
1339 	non-command events to allow the default handling to take place.
1340 	The command events are, however, normally not skipped as usually a single
1341 	command such as a button click or menu item selection must only be
1342 	processed by one handler.
1343 
1344 	So my recommendation is to have a Skip() call in the idle event handler.
1345 */
1346 
1347 void
OnIdle(wxIdleEvent & event)1348 WximgszFrame::OnIdle(wxIdleEvent & event)
1349 {
1350 	bool	rqm	=	false;
1351 
1352 	/* __CHANGE__
1353 	*/
1354 	if (bActive) {
1355 		switch (cas.GetReaction()) {
1356 			case Dk4WxAutostartController::REACTION_START : {
1357 				cas.StartProcessing();
1358 				ProcessSpecifiedFileName();
1359 				cas.EndProcessing();
1360 				Refresh();
1361 				Update();
1362 			} break;
1363 		}
1364 		if (rqm) { event.RequestMore(); }
1365 	}
1366 
1367 	event.Skip();
1368 }
1369 
1370 
1371 /* vim: set ai sw=4 ts=4 : */
1372