blob: 31064ba9735c966598a8693cb8b1b32801b0030c [file] [log] [blame]
Pierre Ossmand463b572011-05-16 12:04:43 +00001/* Copyright 2011 Pierre Ossman <ossman@cendio.se> for Cendio AB
2 *
3 * This is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation; either version 2 of the License, or
6 * (at your option) any later version.
7 *
8 * This software is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this software; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
16 * USA.
17 */
18
Pierre Ossman61fd4862011-05-16 12:46:51 +000019#include <stdlib.h>
20
Pierre Ossmand463b572011-05-16 12:04:43 +000021#include <list>
22
23#include <FL/Fl_Tabs.H>
24#include <FL/Fl_Button.H>
25#include <FL/Fl_Return_Button.H>
26
27#include <rdr/types.h>
28#include <rfb/encodings.h>
29
30#ifdef HAVE_GNUTLS
31#include <rfb/Security.h>
32#include <rfb/SecurityClient.h>
33#include <rfb/CSecurityTLS.h>
34#endif
35
36#include "OptionsDialog.h"
37#include "fltk_layout.h"
38#include "i18n.h"
39#include "parameters.h"
40
41using namespace std;
42using namespace rdr;
43using namespace rfb;
44
Pierre Ossman0c41e1d2011-05-17 09:36:04 +000045std::map<OptionsCallback*, void*> OptionsDialog::callbacks;
46
Pierre Ossmand463b572011-05-16 12:04:43 +000047OptionsDialog::OptionsDialog()
48 : Fl_Window(450, 450, _("VNC Viewer: Connection Options"))
49{
50 int x, y;
51 Fl_Button *button;
52
53 Fl_Tabs *tabs = new Fl_Tabs(OUTER_MARGIN, OUTER_MARGIN,
54 w() - OUTER_MARGIN*2,
55 h() - OUTER_MARGIN*2 - INNER_MARGIN - BUTTON_HEIGHT);
56
57 {
58 int tx, ty, tw, th;
59
60 tabs->client_area(tx, ty, tw, th, TABS_HEIGHT);
61
62 createCompressionPage(tx, ty, tw, th);
63 createSecurityPage(tx, ty, tw, th);
64 createInputPage(tx, ty, tw, th);
65 createMiscPage(tx, ty, tw, th);
66 }
67
68 tabs->end();
69
70 x = w() - BUTTON_WIDTH * 2 - INNER_MARGIN - OUTER_MARGIN;
71 y = h() - BUTTON_HEIGHT - OUTER_MARGIN;
72
73 button = new Fl_Button(x, y, BUTTON_WIDTH, BUTTON_HEIGHT, _("Cancel"));
74 button->callback(this->handleCancel, this);
75
76 x += BUTTON_WIDTH + INNER_MARGIN;
77
78 button = new Fl_Return_Button(x, y, BUTTON_WIDTH, BUTTON_HEIGHT, _("OK"));
79 button->callback(this->handleOK, this);
80
81 callback(this->handleCancel, this);
82
83 set_modal();
84}
85
86
87OptionsDialog::~OptionsDialog()
88{
89}
90
91
92void OptionsDialog::showDialog(void)
93{
94 static OptionsDialog *dialog = NULL;
95
96 if (!dialog)
97 dialog = new OptionsDialog();
98
99 if (dialog->shown())
100 return;
101
102 dialog->show();
103}
104
105
Pierre Ossman0c41e1d2011-05-17 09:36:04 +0000106void OptionsDialog::addCallback(OptionsCallback *cb, void *data)
107{
108 callbacks[cb] = data;
109}
110
111
112void OptionsDialog::removeCallback(OptionsCallback *cb)
113{
114 callbacks.erase(cb);
115}
116
117
Pierre Ossmand463b572011-05-16 12:04:43 +0000118void OptionsDialog::show(void)
119{
120 loadOptions();
121
122 Fl_Window::show();
123}
124
125
126void OptionsDialog::loadOptions(void)
127{
128 /* Compression */
129 autoselectCheckbox->value(autoSelect);
130
131 int encNum = encodingNum(preferredEncoding);
132
133 switch (encNum) {
134 case encodingTight:
135 tightButton->setonly();
136 break;
137 case encodingZRLE:
138 zrleButton->setonly();
139 break;
140 case encodingHextile:
141 hextileButton->setonly();
142 break;
143 case encodingRaw:
144 rawButton->setonly();
145 break;
146 }
147
148 if (fullColour)
149 fullcolorCheckbox->setonly();
150 else {
151 switch (lowColourLevel) {
152 case 0:
153 mediumcolorCheckbox->setonly();
154 break;
155 case 1:
156 lowcolorCheckbox->setonly();
157 break;
158 case 2:
159 verylowcolorCheckbox->setonly();
160 break;
161 }
162 }
163
164 char digit[2] = "0";
165
166 compressionCheckbox->value(customCompressLevel);
167 jpegCheckbox->value(!noJpeg);
168 digit[0] = '0' + compressLevel;
169 compressionInput->value(digit);
170 digit[0] = '0' + qualityLevel;
171 jpegInput->value(digit);
172
173 handleAutoselect(autoselectCheckbox, this);
174 handleCompression(compressionCheckbox, this);
175 handleJpeg(jpegCheckbox, this);
176
177#ifdef HAVE_GNUTLS
178 /* Security */
179 Security security(SecurityClient::secTypes);
180
181 list<U8> secTypes;
182 list<U8>::iterator iter;
183
184 list<U32> secTypesExt;
185 list<U32>::iterator iterExt;
186
187 vencryptCheckbox->value(false);
188
189 encNoneCheckbox->value(false);
190 encTLSCheckbox->value(false);
191 encX509Checkbox->value(false);
192
193 authNoneCheckbox->value(false);
194 authVncCheckbox->value(false);
195 authPlainCheckbox->value(false);
196
197 secTypes = security.GetEnabledSecTypes();
198 for (iter = secTypes.begin(); iter != secTypes.end(); ++iter) {
199 switch (*iter) {
200 case secTypeVeNCrypt:
201 vencryptCheckbox->value(true);
202 break;
203 case secTypeNone:
204 encNoneCheckbox->value(true);
205 authNoneCheckbox->value(true);
206 break;
207 case secTypeVncAuth:
208 encNoneCheckbox->value(true);
209 authVncCheckbox->value(true);
210 break;
211 }
212 }
213
214 secTypesExt = security.GetEnabledExtSecTypes();
215 for (iterExt = secTypesExt.begin(); iterExt != secTypesExt.end(); ++iterExt) {
216 switch (*iterExt) {
217 case secTypePlain:
218 encNoneCheckbox->value(true);
219 authPlainCheckbox->value(true);
220 break;
221 case secTypeTLSNone:
222 encTLSCheckbox->value(true);
223 authNoneCheckbox->value(true);
224 break;
225 case secTypeTLSVnc:
226 encTLSCheckbox->value(true);
227 authVncCheckbox->value(true);
228 break;
229 case secTypeTLSPlain:
230 encTLSCheckbox->value(true);
231 authPlainCheckbox->value(true);
232 break;
233 case secTypeX509None:
234 encX509Checkbox->value(true);
235 authNoneCheckbox->value(true);
236 break;
237 case secTypeX509Vnc:
238 encX509Checkbox->value(true);
239 authVncCheckbox->value(true);
240 break;
241 case secTypeX509Plain:
242 encX509Checkbox->value(true);
243 authPlainCheckbox->value(true);
244 break;
245 }
246 }
247
248 caInput->value(CSecurityTLS::x509ca);
249 crlInput->value(CSecurityTLS::x509crl);
250
251 handleVencrypt(vencryptCheckbox, this);
252 handleX509(encX509Checkbox, this);
253#endif
254
255 /* Input */
Pierre Ossman4e7271e2011-05-24 12:47:12 +0000256 const char *menuKeyBuf;
257
Pierre Ossmand463b572011-05-16 12:04:43 +0000258 viewOnlyCheckbox->value(viewOnly);
259 acceptClipboardCheckbox->value(acceptClipboard);
260 sendClipboardCheckbox->value(sendClipboard);
261 sendPrimaryCheckbox->value(sendPrimary);
Pierre Ossman407a5c32011-05-26 14:48:29 +0000262 systemKeysCheckbox->value(fullscreenSystemKeys);
Pierre Ossmand463b572011-05-16 12:04:43 +0000263
Pierre Ossman4e7271e2011-05-24 12:47:12 +0000264 menuKeyChoice->value(0);
265
266 menuKeyBuf = menuKey;
267 if (menuKeyBuf[0] == 'F') {
268 int num = atoi(menuKeyBuf+1);
269 if ((num >= 1) && (num <= 12))
270 menuKeyChoice->value(num);
271 }
272
Pierre Ossmand463b572011-05-16 12:04:43 +0000273 /* Misc. */
274 sharedCheckbox->value(shared);
275 fullScreenCheckbox->value(fullScreen);
276 localCursorCheckbox->value(useLocalCursor);
277 dotCursorCheckbox->value(dotWhenNoCursor);
278}
279
280
281void OptionsDialog::storeOptions(void)
282{
Pierre Ossman61fd4862011-05-16 12:46:51 +0000283 /* Compression */
284 autoSelect.setParam(autoselectCheckbox->value());
285
286 if (tightButton->value())
287 preferredEncoding.setParam(encodingName(encodingTight));
288 else if (zrleButton->value())
289 preferredEncoding.setParam(encodingName(encodingZRLE));
290 else if (hextileButton->value())
291 preferredEncoding.setParam(encodingName(encodingHextile));
292 else if (rawButton->value())
293 preferredEncoding.setParam(encodingName(encodingRaw));
294
295 fullColour.setParam(fullcolorCheckbox->value());
296 if (mediumcolorCheckbox->value())
297 lowColourLevel.setParam(0);
298 else if (lowcolorCheckbox->value())
299 lowColourLevel.setParam(1);
300 else if (verylowcolorCheckbox->value())
301 lowColourLevel.setParam(2);
302
303 customCompressLevel.setParam(compressionCheckbox->value());
304 noJpeg.setParam(!jpegCheckbox->value());
305 compressLevel.setParam(atoi(compressionInput->value()));
306 qualityLevel.setParam(atoi(jpegInput->value()));
307
308#ifdef HAVE_GNUTLS
309 /* Security */
310 Security security;
311
312 /* Process security types which don't use encryption */
313 if (encNoneCheckbox->value()) {
314 if (authNoneCheckbox->value())
315 security.EnableSecType(secTypeNone);
316 if (authVncCheckbox->value())
317 security.EnableSecType(secTypeVncAuth);
318
319 if (vencryptCheckbox->value()) {
320 if (authPlainCheckbox->value())
321 security.EnableSecType(secTypePlain);
322 }
323 }
324
325 if (vencryptCheckbox->value()) {
326 /* Process security types which use TLS encryption */
327 if (encTLSCheckbox->value()) {
328 if (authNoneCheckbox->value())
329 security.EnableSecType(secTypeTLSNone);
330 if (authVncCheckbox->value())
331 security.EnableSecType(secTypeTLSVnc);
332 if (authPlainCheckbox->value())
333 security.EnableSecType(secTypeTLSPlain);
334 }
335
336 /* Process security types which use X509 encryption */
337 if (encX509Checkbox->value()) {
338 if (authNoneCheckbox->value())
339 security.EnableSecType(secTypeX509None);
340 if (authVncCheckbox->value())
341 security.EnableSecType(secTypeX509Vnc);
342 if (authPlainCheckbox->value())
343 security.EnableSecType(secTypeX509Plain);
344 }
345 }
346
347 CSecurityTLS::x509ca.setParam(caInput->value());
348 CSecurityTLS::x509crl.setParam(crlInput->value());
349#endif
350
351 /* Input */
352 viewOnly.setParam(viewOnlyCheckbox->value());
353 acceptClipboard.setParam(acceptClipboardCheckbox->value());
354 sendClipboard.setParam(sendClipboardCheckbox->value());
355 sendPrimary.setParam(sendPrimaryCheckbox->value());
Pierre Ossman407a5c32011-05-26 14:48:29 +0000356 fullscreenSystemKeys.setParam(systemKeysCheckbox->value());
Pierre Ossman61fd4862011-05-16 12:46:51 +0000357
Pierre Ossman4e7271e2011-05-24 12:47:12 +0000358 if (menuKeyChoice->value() == 0)
359 menuKey.setParam("");
360 else {
361 char buf[16];
362 sprintf(buf, "F%d", menuKeyChoice->value());
363 menuKey.setParam(buf);
364 }
365
Pierre Ossman61fd4862011-05-16 12:46:51 +0000366 /* Misc. */
367 shared.setParam(sharedCheckbox->value());
368 fullScreen.setParam(fullScreenCheckbox->value());
369 useLocalCursor.setParam(localCursorCheckbox->value());
370 dotWhenNoCursor.setParam(dotCursorCheckbox->value());
Pierre Ossman0c41e1d2011-05-17 09:36:04 +0000371
372 std::map<OptionsCallback*, void*>::const_iterator iter;
373
374 for (iter = callbacks.begin();iter != callbacks.end();++iter)
375 iter->first(iter->second);
Pierre Ossmand463b572011-05-16 12:04:43 +0000376}
377
378
379void OptionsDialog::createCompressionPage(int tx, int ty, int tw, int th)
380{
381 Fl_Group *group = new Fl_Group(tx, ty, tw, th, _("Compression"));
382
383 int orig_tx, orig_ty;
384 int half_width, full_width;
385 int width, height;
386
387 tx += OUTER_MARGIN;
388 ty += OUTER_MARGIN;
389
390 full_width = tw - OUTER_MARGIN * 2;
391 half_width = (full_width - INNER_MARGIN) / 2;
392
393 /* AutoSelect checkbox */
394 autoselectCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
395 CHECK_MIN_WIDTH,
396 CHECK_HEIGHT,
397 _("Auto select")));
398 autoselectCheckbox->callback(handleAutoselect, this);
399 ty += CHECK_HEIGHT + INNER_MARGIN;
400
401 /* Two columns */
402 orig_tx = tx;
403 orig_ty = ty;
404
405 /* VNC encoding box */
406 ty += GROUP_LABEL_OFFSET;
407 height = GROUP_MARGIN * 2 + TIGHT_MARGIN * 3 + RADIO_HEIGHT * 4;
408 encodingGroup = new Fl_Group(tx, ty, half_width, height,
409 _("Preferred encoding"));
410 encodingGroup->box(FL_ENGRAVED_BOX);
411 encodingGroup->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
412
413 {
414 tx += GROUP_MARGIN;
415 ty += GROUP_MARGIN;
416
417 width = encodingGroup->w() - GROUP_MARGIN * 2;
418
419 tightButton = new Fl_Round_Button(LBLRIGHT(tx, ty,
420 RADIO_MIN_WIDTH,
421 RADIO_HEIGHT,
422 _("Tight")));
423 tightButton->type(FL_RADIO_BUTTON);
424 ty += RADIO_HEIGHT + TIGHT_MARGIN;
425
426 zrleButton = new Fl_Round_Button(LBLRIGHT(tx, ty,
427 RADIO_MIN_WIDTH,
428 RADIO_HEIGHT,
429 _("ZRLE")));
430 zrleButton->type(FL_RADIO_BUTTON);
431 ty += RADIO_HEIGHT + TIGHT_MARGIN;
432
433 hextileButton = new Fl_Round_Button(LBLRIGHT(tx, ty,
434 RADIO_MIN_WIDTH,
435 RADIO_HEIGHT,
436 _("Hextile")));
437 hextileButton->type(FL_RADIO_BUTTON);
438 ty += RADIO_HEIGHT + TIGHT_MARGIN;
439
440 rawButton = new Fl_Round_Button(LBLRIGHT(tx, ty,
441 RADIO_MIN_WIDTH,
442 RADIO_HEIGHT,
443 _("Raw")));
444 rawButton->type(FL_RADIO_BUTTON);
445 ty += RADIO_HEIGHT + TIGHT_MARGIN;
446 }
447
448 ty += GROUP_MARGIN - TIGHT_MARGIN;
449
450 encodingGroup->end();
451
452 /* Second column */
453 tx = orig_tx + half_width + INNER_MARGIN;
454 ty = orig_ty;
455
456 /* Color box */
457 ty += GROUP_LABEL_OFFSET;
458 height = GROUP_MARGIN * 2 + TIGHT_MARGIN * 3 + RADIO_HEIGHT * 4;
459 colorlevelGroup = new Fl_Group(tx, ty, half_width, height, _("Color level"));
460 colorlevelGroup->box(FL_ENGRAVED_BOX);
461 colorlevelGroup->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
462
463 {
464 tx += GROUP_MARGIN;
465 ty += GROUP_MARGIN;
466
467 width = colorlevelGroup->w() - GROUP_MARGIN * 2;
468
469 fullcolorCheckbox = new Fl_Round_Button(LBLRIGHT(tx, ty,
470 RADIO_MIN_WIDTH,
471 RADIO_HEIGHT,
472 _("Full (all available colors)")));
473 fullcolorCheckbox->type(FL_RADIO_BUTTON);
474 ty += RADIO_HEIGHT + TIGHT_MARGIN;
475
476 mediumcolorCheckbox = new Fl_Round_Button(LBLRIGHT(tx, ty,
477 RADIO_MIN_WIDTH,
478 RADIO_HEIGHT,
479 _("Medium (256 colors)")));
480 mediumcolorCheckbox->type(FL_RADIO_BUTTON);
481 ty += RADIO_HEIGHT + TIGHT_MARGIN;
482
483 lowcolorCheckbox = new Fl_Round_Button(LBLRIGHT(tx, ty,
484 RADIO_MIN_WIDTH,
485 RADIO_HEIGHT,
486 _("Low (64 colors)")));
487 lowcolorCheckbox->type(FL_RADIO_BUTTON);
488 ty += RADIO_HEIGHT + TIGHT_MARGIN;
489
490 verylowcolorCheckbox = new Fl_Round_Button(LBLRIGHT(tx, ty,
491 RADIO_MIN_WIDTH,
492 RADIO_HEIGHT,
493 _("Very low (8 colors)")));
494 verylowcolorCheckbox->type(FL_RADIO_BUTTON);
495 ty += RADIO_HEIGHT + TIGHT_MARGIN;
496 }
497
498 ty += GROUP_MARGIN - TIGHT_MARGIN;
499
500 colorlevelGroup->end();
501
502 /* Back to normal */
503 tx = orig_tx;
504 ty += INNER_MARGIN;
505
506 /* Checkboxes */
507 compressionCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
508 CHECK_MIN_WIDTH,
509 CHECK_HEIGHT,
510 _("Custom compression level:")));
511 compressionCheckbox->callback(handleCompression, this);
512 ty += CHECK_HEIGHT + TIGHT_MARGIN;
513
514 compressionInput = new Fl_Int_Input(tx + INDENT, ty,
515 INPUT_HEIGHT, INPUT_HEIGHT,
516 _("level (1=fast, 9=best)"));
517 compressionInput->align(FL_ALIGN_RIGHT);
518 ty += INPUT_HEIGHT + INNER_MARGIN;
519
520 jpegCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
521 CHECK_MIN_WIDTH,
522 CHECK_HEIGHT,
523 _("Allow JPEG compression:")));
524 jpegCheckbox->callback(handleJpeg, this);
525 ty += CHECK_HEIGHT + TIGHT_MARGIN;
526
527 jpegInput = new Fl_Int_Input(tx + INDENT, ty,
528 INPUT_HEIGHT, INPUT_HEIGHT,
529 _("quality (1=poor, 9=best)"));
530 jpegInput->align(FL_ALIGN_RIGHT);
531 ty += INPUT_HEIGHT + INNER_MARGIN;
532
533 group->end();
534}
535
536
537void OptionsDialog::createSecurityPage(int tx, int ty, int tw, int th)
538{
539#ifdef HAVE_GNUTLS
540 Fl_Group *group = new Fl_Group(tx, ty, tw, th, _("Security"));
541
542 int orig_tx;
543 int width, height;
544
545 tx += OUTER_MARGIN;
546 ty += OUTER_MARGIN;
547
548 width = tw - OUTER_MARGIN * 2;
549
550 orig_tx = tx;
551
552 /* Security */
553 vencryptCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
554 CHECK_MIN_WIDTH,
555 CHECK_HEIGHT,
556 _("Extended encryption and authentication methods (VeNCrypt)")));
557 vencryptCheckbox->callback(handleVencrypt, this);
558 ty += CHECK_HEIGHT + INNER_MARGIN;
559
560 /* Encryption */
561 ty += GROUP_LABEL_OFFSET;
562 height = GROUP_MARGIN * 2 + TIGHT_MARGIN * 4 + CHECK_HEIGHT * 3 + (INPUT_LABEL_OFFSET + INPUT_HEIGHT) * 2;
563 encryptionGroup = new Fl_Group(tx, ty, width, height, _("Encryption"));
564 encryptionGroup->box(FL_ENGRAVED_BOX);
565 encryptionGroup->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
566
567 {
568 tx += GROUP_MARGIN;
569 ty += GROUP_MARGIN;
570
571 encNoneCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
572 CHECK_MIN_WIDTH,
573 CHECK_HEIGHT,
574 _("None")));
575 ty += CHECK_HEIGHT + TIGHT_MARGIN;
576
577 encTLSCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
578 CHECK_MIN_WIDTH,
579 CHECK_HEIGHT,
580 _("TLS with anonymous certificates")));
581 ty += CHECK_HEIGHT + TIGHT_MARGIN;
582
583 encX509Checkbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
584 CHECK_MIN_WIDTH,
585 CHECK_HEIGHT,
586 _("TLS with X509 certificates")));
587 encX509Checkbox->callback(handleX509, this);
588 ty += CHECK_HEIGHT + TIGHT_MARGIN;
589
590 ty += INPUT_LABEL_OFFSET;
591 caInput = new Fl_Input(tx + INDENT, ty,
592 width - GROUP_MARGIN*2 - INDENT, INPUT_HEIGHT,
593 _("Path to X509 CA certificate"));
594 caInput->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
595 ty += INPUT_HEIGHT + TIGHT_MARGIN;
596
597 ty += INPUT_LABEL_OFFSET;
598 crlInput = new Fl_Input(tx + INDENT, ty,
599 width - GROUP_MARGIN*2 - INDENT, INPUT_HEIGHT,
600 _("Path to X509 CRL file"));
601 crlInput->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
602 ty += INPUT_HEIGHT + TIGHT_MARGIN;
603 }
604
605 ty += GROUP_MARGIN - TIGHT_MARGIN;
606
607 encryptionGroup->end();
608
609 /* Back to normal */
610 tx = orig_tx;
611 ty += INNER_MARGIN;
612
613 /* Authentication */
614 /* Encryption */
615 ty += GROUP_LABEL_OFFSET;
616 height = GROUP_MARGIN * 2 + TIGHT_MARGIN * 2 + CHECK_HEIGHT * 3;
617 authenticationGroup = new Fl_Group(tx, ty, width, height, _("Authentication"));
618 authenticationGroup->box(FL_ENGRAVED_BOX);
619 authenticationGroup->align(FL_ALIGN_LEFT | FL_ALIGN_TOP);
620
621 {
622 tx += GROUP_MARGIN;
623 ty += GROUP_MARGIN;
624
625 authNoneCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
626 CHECK_MIN_WIDTH,
627 CHECK_HEIGHT,
628 _("None")));
629 ty += CHECK_HEIGHT + TIGHT_MARGIN;
630
631 authVncCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
632 CHECK_MIN_WIDTH,
633 CHECK_HEIGHT,
634 _("Standard VNC (insecure without encryption)")));
635 ty += CHECK_HEIGHT + TIGHT_MARGIN;
636
637 authPlainCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
638 CHECK_MIN_WIDTH,
639 CHECK_HEIGHT,
640 _("Username and password (insecure without encryption)")));
641 ty += CHECK_HEIGHT + TIGHT_MARGIN;
642 }
643
644 ty += GROUP_MARGIN - TIGHT_MARGIN;
645
646 authenticationGroup->end();
647
648 /* Back to normal */
649 tx = orig_tx;
650 ty += INNER_MARGIN;
651
652 group->end();
653#endif
654}
655
656
657void OptionsDialog::createInputPage(int tx, int ty, int tw, int th)
658{
659 Fl_Group *group = new Fl_Group(tx, ty, tw, th, _("Input"));
660
661 tx += OUTER_MARGIN;
662 ty += OUTER_MARGIN;
663
664 viewOnlyCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
665 CHECK_MIN_WIDTH,
666 CHECK_HEIGHT,
667 _("View only (ignore mouse and keyboard)")));
668 ty += CHECK_HEIGHT + TIGHT_MARGIN;
669
670 acceptClipboardCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
671 CHECK_MIN_WIDTH,
672 CHECK_HEIGHT,
673 _("Accept clipboard from server")));
674 ty += CHECK_HEIGHT + TIGHT_MARGIN;
675
676 sendClipboardCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
677 CHECK_MIN_WIDTH,
678 CHECK_HEIGHT,
679 _("Send clipboard to server")));
680 ty += CHECK_HEIGHT + TIGHT_MARGIN;
681
682 sendPrimaryCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
683 CHECK_MIN_WIDTH,
684 CHECK_HEIGHT,
685 _("Send primary selection and cut buffer as clipboard")));
686 ty += CHECK_HEIGHT + TIGHT_MARGIN;
687
Pierre Ossman407a5c32011-05-26 14:48:29 +0000688 systemKeysCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
689 CHECK_MIN_WIDTH,
690 CHECK_HEIGHT,
691 _("Pass system keys directly to server (full screen)")));
692 ty += CHECK_HEIGHT + TIGHT_MARGIN;
693
Pierre Ossman4e7271e2011-05-24 12:47:12 +0000694 menuKeyChoice = new Fl_Choice(LBLLEFT(tx, ty, 150, CHOICE_HEIGHT, _("Menu key")));
695
696 menuKeyChoice->add(_("None"), 0, NULL, (void*)0, FL_MENU_DIVIDER);
697 for (int i = 1;i <= 12;i++) {
698 char buf[16];
699 sprintf(buf, "F%d", i);
700 menuKeyChoice->add(buf, 0, NULL, (void*)i, 0);
701 }
702
703 ty += CHOICE_HEIGHT + TIGHT_MARGIN;
704
Pierre Ossmand463b572011-05-16 12:04:43 +0000705 group->end();
706}
707
708
709void OptionsDialog::createMiscPage(int tx, int ty, int tw, int th)
710{
711 Fl_Group *group = new Fl_Group(tx, ty, tw, th, _("Misc."));
712
713 tx += OUTER_MARGIN;
714 ty += OUTER_MARGIN;
715
716 sharedCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
717 CHECK_MIN_WIDTH,
718 CHECK_HEIGHT,
719 _("Shared (don't disconnect other viewers)")));
720 ty += CHECK_HEIGHT + TIGHT_MARGIN;
721
722 fullScreenCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
723 CHECK_MIN_WIDTH,
724 CHECK_HEIGHT,
725 _("Full-screen mode")));
726 ty += CHECK_HEIGHT + TIGHT_MARGIN;
727
728 localCursorCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
729 CHECK_MIN_WIDTH,
730 CHECK_HEIGHT,
731 _("Render cursor locally")));
732 ty += CHECK_HEIGHT + TIGHT_MARGIN;
733
734 dotCursorCheckbox = new Fl_Check_Button(LBLRIGHT(tx, ty,
735 CHECK_MIN_WIDTH,
736 CHECK_HEIGHT,
737 _("Show dot when no cursor")));
738 ty += CHECK_HEIGHT + TIGHT_MARGIN;
739
740 group->end();
741}
742
743
744void OptionsDialog::handleAutoselect(Fl_Widget *widget, void *data)
745{
746 OptionsDialog *dialog = (OptionsDialog*)data;
747
748 if (dialog->autoselectCheckbox->value()) {
749 dialog->encodingGroup->deactivate();
750 dialog->colorlevelGroup->deactivate();
751 } else {
752 dialog->encodingGroup->activate();
753 dialog->colorlevelGroup->activate();
754 }
755
756 // JPEG setting is also affected by autoselection
757 dialog->handleJpeg(dialog->jpegCheckbox, dialog);
758}
759
760
761void OptionsDialog::handleCompression(Fl_Widget *widget, void *data)
762{
763 OptionsDialog *dialog = (OptionsDialog*)data;
764
765 if (dialog->compressionCheckbox->value())
766 dialog->compressionInput->activate();
767 else
768 dialog->compressionInput->deactivate();
769}
770
771
772void OptionsDialog::handleJpeg(Fl_Widget *widget, void *data)
773{
774 OptionsDialog *dialog = (OptionsDialog*)data;
775
776 if (dialog->jpegCheckbox->value() &&
777 !dialog->autoselectCheckbox->value())
778 dialog->jpegInput->activate();
779 else
780 dialog->jpegInput->deactivate();
781}
782
783
784void OptionsDialog::handleVencrypt(Fl_Widget *widget, void *data)
785{
786 OptionsDialog *dialog = (OptionsDialog*)data;
787
788 if (dialog->vencryptCheckbox->value()) {
789 dialog->encryptionGroup->activate();
790 dialog->authPlainCheckbox->activate();
791 } else {
792 dialog->encryptionGroup->deactivate();
793 dialog->authPlainCheckbox->deactivate();
794 }
795}
796
797
798void OptionsDialog::handleX509(Fl_Widget *widget, void *data)
799{
800 OptionsDialog *dialog = (OptionsDialog*)data;
801
802 if (dialog->encX509Checkbox->value()) {
803 dialog->caInput->activate();
804 dialog->crlInput->activate();
805 } else {
806 dialog->caInput->deactivate();
807 dialog->crlInput->deactivate();
808 }
809}
810
811
812void OptionsDialog::handleCancel(Fl_Widget *widget, void *data)
813{
814 OptionsDialog *dialog = (OptionsDialog*)data;
815
816 dialog->hide();
817}
818
819
820void OptionsDialog::handleOK(Fl_Widget *widget, void *data)
821{
822 OptionsDialog *dialog = (OptionsDialog*)data;
823
824 dialog->hide();
825
826 dialog->storeOptions();
827}