dialog_iemgui.html 20.4 KB
Newer Older
1
2
3
<!DOCTYPE html>
<html>
  <head>
Jonathan Wilkes's avatar
Jonathan Wilkes committed
4
5
    <link id="page_style" rel="stylesheet"
          type="text/css" href="css/default.css">
6
  </head>
7
  <body class="dialog_body">
8
9
10
11
12
13
14
15
16
17
18
19
20
    <div class="container">
    <form> 
      <fieldset> 
        <legend data-i18n="iem.prop.heading.size"></legend> 

        <table class="pairs">
          <tr class="size prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.size_tt">
                <span data-i18n="iem.prop.size"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.size_tt">
21
22
              <input type="text" name="size"
                     onchange="update_attr(this);">
23
24
25
26
27
28
29
30
31
            </td>
          </tr>
          <tr class="selection-size prop hidden">
            <td>
              <label data-i18n="[title]iem.select_size_tt">
                <span data-i18n="iem.prop.select_size"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.select_size_tt">
32
33
              <input type="text" name="selection-size"
                     onchange="update_attr(this);">
34
35
36
37
38
39
40
41
42
            </td>
          </tr>
          <tr class="number prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.number_tt">
                <span data-i18n="iem.prop.number"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.number_tt">
43
44
              <input type="number" name="number"
                     onchange="update_attr(this);">
45
46
47
48
49
50
51
52
53
            </td>
          </tr>
          <tr class="nonzero-value prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.nonzero_value_tt">
                <span data-i18n="iem.prop.nonzero_value"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.nonzero_value_tt">
54
55
              <input type="text" name="nonzero-value"
                     onchange="update_attr(this);">
56
57
58
59
60
61
62
63
64
            </td>
          </tr>
          <tr class="width prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.width_tt"> 
                <span data-i18n="iem.prop.width"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.width_tt">
65
66
              <input type="text" name="width"
                     onchange="update_attr(this);">
67
68
69
70
71
72
73
            </td>
            <td>
              <label data-i18n="[title]iem.prop.height_tt">
                <span data-i18n="iem.prop.height"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.height_tt">
74
75
              <input type="text" name="height"
                     onchange="update_attr(this);">
76
77
78
79
80
81
82
83
84
            </td>
          </tr>
          <tr class="visible-width prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.visible_width_tt">
                <span data-i18n="iem.prop.visible_width"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.visible_width_tt">
85
86
              <input type="text" name="visible-width"
                     onchange="update_attr(this);">
87
88
89
90
91
92
93
            </td>
            <td>
              <label data-i18n="iem.prop.visible_height">
                <span data-i18n="iem.prop.visible_height"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.visible_height_tt">
94
95
              <input type="text" name="visible-height"
                     onchange="update_attr(this);">
96
97
98
99
100
101
102
103
104
            </td>
          </tr>
          <tr class="minimum-range prop pair hidden">
            <td>
              <label data-i18n="[title]iem.prop.minimum_tt">
                <span data-i18n="iem.prop.minimum"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.minimum_tt">
105
106
              <input type="text" name="minimum-range"
                     onchange="update_attr(this);">
107
108
109
110
111
112
113
            </td>
            <td>
              <label data-i18n="[title]iem.prop.maximum_tt">
                <span data-i18n="iem.prop.maximum"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.maximum_tt">
114
115
              <input type="text" name="maximum-range"
                     onchange="update_attr(this);">
116
117
118
119
120
121
122
123
124
            </td>
          </tr>
          <tr class="flash-interrupt prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.flash_interrupt_tt">
                <span data-i18n="iem.prop.flash_interrupt"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.flash_interrupt_tt">
125
126
              <input type="text" name="flash-interrupt"
                     onchange="update_attr(this);">
127
128
129
130
131
132
133
            </td>
            <td>
              <label data-i18n="[title]iem.prop.flash_hold_tt">
                <span data-i18n="iem.prop.flash_hold"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.flash_hold_tt">
134
135
              <input type="text" name="flash-hold"
                     onchange="update_attr(this);">
136
137
138
139
140
141
142
143
144
145
            </td>
          </tr>
          <tr class="log-height prop hidden">
            <td></td><td></td>
            <td>
              <label data-i18n="[title]iem.prop.log_height_tt">
                <span data-i18n="iem.prop.log_height"></span>
              </label>
            </td>
            <td>
146
147
              <input type="text" name="log-height"
                     onchange="update_attr(this);">
148
149
150
151
152
153
            </td>
          </tr>
        </table>

        <div class="init prop hidden">
          <label data-i18n="[title]iem.prop.init_tt">
154
155
            <input type="checkbox" name="init" value="on"
                   onchange="update_attr(this);">
156
157
158
159
160
161
162
163
            <span data-i18n="iem.prop.init"></span>
          </label>
          <br>
        </div>

        <div class="vu-scale prop hidden">
          <label data-i18n="[title]iem.prop.vu_scale_tt">
            <span data-i18n="iem.prop.vu_scale"></span>
164
165
            <input type="checkbox" name="vu-scale" value="on"
                   onchange="update_attr(this);">
166
167
168
169
170
171
          </label>
          <br>
        </div>

        <div class="log-scaling prop hidden">
          <label data-i18n="[title]iem.prop.log_scale_tt">
172
173
            <input type="checkbox" name="log-scaling" value="on"
                   onchange="update_attr(this);">
174
175
176
177
178
179
180
            <span data-i18n="iem.prop.log_scale"></span>
          </label>
          <br>
        </div>

        <div class="steady-on-click prop hidden">
          <label data-i18n="[title]iem.prop.steady_tt">
181
182
            <input type="checkbox" name="steady-on-click" value="on"
                   onchange="update_attr(this);">
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
            <span data-i18n="iem.prop.steady"></span>
          </label>
          <br>
        </div>
      </fieldset> 

      <fieldset> 
        <legend data-i18n="iem.prop.heading.messages"></legend> 

        <table>
          <tr class="send-symbol prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.send_tt">
                <span data-i18n="iem.prop.send"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.send_tt">
200
201
              <input type="text" name="send-symbol"
                     onchange="update_attr(this);">
202
203
204
205
206
207
208
209
210
            </td>
            <td>
          <tr class="receive-symbol prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.receive_tt">
                <span data-i18n="iem.prop.receive"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.receive_tt">
211
212
              <input type="text" name="receive-symbol"
                     onchange="update_attr(this);">
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
            </td>
            <td>
          </tr>
        </table>
      </fieldset> 

      <fieldset> 
        <legend data-i18n="iem.prop.heading.label">wrong stuff</legend> 

        <table class="pairs">
          <tr class="label prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.label_tt">
                <span data-i18n="iem.prop.label"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.label_tt">
230
231
              <input type="text" name="label"
                     onchange="update_attr(this);">
232
233
234
235
236
237
238
            </td>
            <td>
              <label data-i18n="[title]iem.prop.xoffset_tt">
                <span data-i18n="iem.prop.xoffset"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.xoffset_tt">
239
240
              <input type="text" name="x-offset"
                     onchange="update_attr(this);">
241
242
243
244
245
246
247
            </td>
            <td>
              <label data-i18n="[title]iem.prop.yoffset_tt">
                <span data-i18n="iem.prop.yoffset"></span>
              </label>
            </td>
            <td data-i18n="[title]iem.prop.yoffset_tt">
248
249
              <input type="text" name="y-offset"
                     onchange="update_attr(this);">
250
251
252
253
254
255
256
257
            </td>
          </tr>
          <tr class="font-style prop hidden">
            <td>
              <label data-i18n="[title]iem.prop.font_tt">
                <span data-i18n="iem.prop.font"></span>
            </td>
            <td data-i18n="[title]iem.prop.font_tt">
258
259
              <select name="font-style"
                      onchange="update_attr(this);">
260
261
262
                <option>DejaVu Sans Mono</option>
                <option>Helvetica</option>
                <option>Times</option>
263
264
265
266
267
              </select>
            </td>
            <td colspan="4">
              <label data-i18n="[title]iem.prop.fontsize_tt">
                <span data-i18n="iem.prop.fontsize"></span>
268
269
                <input type="text" name="font-size"
                       onchange="update_attr(this);">
270
271
272
273
274
275
276
277
278
279
280
              <label>
            </td>
          </tr>
        </table>
      </fieldset> 

      <fieldset> 
      <legend data-i18n="iem.prop.heading.colors"></legend> 

      <div class="background-color prop hidden">
        <label data-i18n="[title]iem.prop.bgcolor_tt">
281
282
          <input type="color" name="background-color"
                 onchange="update_attr(this);">
283
284
285
286
287
288
289
          <span data-i18n="iem.prop.bgcolor"></span>
        </label>
        <br>
      </div>

      <div class="foreground-color prop hidden">
        <label data-i18n="[title]iem.prop.fgcolor_tt">
290
291
          <input type="color" name="foreground-color"
                 onchange="update_attr(this);">
292
293
294
295
296
297
298
          <span data-i18n="iem.prop.fgcolor"></span>
        </label>
        <br>
      </div>

      <div class="label-color prop hidden">
        <label data-i18n="[title]iem.prop.label_color_tt">
299
300
          <input type="color" name="label-color"
                 onchange="update_attr(this);">
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
          <span data-i18n="iem.prop.label_color"></span>
        </label>
        <br>
      </div>
    </fieldset> 

    <div class="prop hidden">
      <input type="hidden" name="minimum-size">
      <input type="hidden" name="range-schedule">
      <input type="hidden" name="hide-frame">
    </div>

    <div class="submit_buttons">
      <button type="button" onClick="ok()" data-i18n="[title]iem.prop.ok_tt">
        <span data-i18n="iem.prop.ok"></span>
      </button>
      <button type="button" onClick="apply()" data-i18n="[title]iem.prop.apply_tt">
        <span data-i18n="iem.prop.apply"></span>
      </button>
320
      <button type="button" onClick="cancel(true)" data-i18n="[title]iem.prop.cancel_tt">
321
322
323
324
325
326
327
328
        <span data-i18n="iem.prop.cancel"></span>
      </button>
    </div>

  </form> 
  </div>      

  <script>
329
"use strict";
330
var gui = require("nw.gui");
331
var pdgui = require("./pdgui.js");
332

333
334
// For translations
var l = pdgui.get_local_string;
335

Jonathan Wilkes's avatar
Jonathan Wilkes committed
336
// gui preset
337
pdgui.skin.apply(window);
Jonathan Wilkes's avatar
Jonathan Wilkes committed
338

339
340
341
var pd_object_callback,
    old_attrs = {}, // original state. Used if we cancel the dialog
    new_attrs = {}; // changed state. Used if we apply or click "Ok"
342

343
344
function substitute_space(arg) {
    var fake_space = String.fromCharCode(11);
345
    return arg.split(" ").join(fake_space);
346
}
347

348
function strip_problem_chars(arg) {
349
350
351
352
    var problem_chars = [";", ",", "{", "}", "\\"],
        ret = arg,
        i;
    for(i = 0; i < problem_chars.length; i++) {
353
        ret = ret.split(";").join("");
354
    }
355
356
    return ret;
}
357

358
359
360
361
362
363
364
365
function update_attr(elem) {
    pdgui.post("updating attr " + elem.name);
    if (!new_attrs.hasOwnProperty(elem.name)) {
        pdgui.post("warning: new_attrs[" + elem.name + "] doesn't exist");
    }
    if (elem.type === "checkbox") {
        new_attrs[elem.name] = elem.checked ? 1 : 0;
    } else if (elem.type === "select-one") {
366
367
368
        new_attrs[elem.name] = elem.selectedIndex;
    } else if (elem.type === "color") {
        new_attrs[elem.name] = parseInt(elem.value.slice(1), 16)
369
    } else {
370
        new_attrs[elem.name] = elem.value;
371
372
373
    }
}

374
375
//Clean up strings to send as symbol arguments to Pd
function pd_symbol_carwash(s) {
376
    s = !s ? "empty" : s;
377
378
379
380
381
    if (s.charAt(0) === "$") {
        s = "#" + s.slice(1);
    }
    s = substitute_space(s);
    s = strip_problem_chars(s);
382
    return s;
383
384
385
}

function send_params(attrs, create_undo_point) {
386
387
388
389
390
391
392
393
    /* Not sure what these are...
        iemgui_clip_dim $id
        iemgui_clip_num $id
        iemgui_sched_rng $id
        iemgui_verify_rng $id
        iemgui_sched_rng $id
        iemgui_clip_fontsize $id
    */
394

395
396
397
    var send_symbol = attrs["send-symbol"],
        receive_symbol = attrs["receive-symbol"],
        label =  attrs["label"];
398
399
400
    send_symbol = pd_symbol_carwash(send_symbol);
    receive_symbol = pd_symbol_carwash(receive_symbol);
    label = pd_symbol_carwash(label);
401

402
403
    var label_x_offset =  attrs["x-offset"];
    var label_y_offset =  attrs["y-offset"];
404

405
    // make sure the offset boxes have a value
406
407
408
409
410
411
    if (!label_x_offset) {
        label_x_offset = 0;
    }
    if (!label_y_offset) {
        label_y_offset = 0;
    }
412

413
    var height, width;
414
    var size = attrs["size"];
Jonathan Wilkes's avatar
Jonathan Wilkes committed
415
    if (size === undefined) {
416
        size = attrs["selection-size"];
417
    }
418

Jonathan Wilkes's avatar
Jonathan Wilkes committed
419
    if (size !== undefined) {
420
421
422
        width = size;
        height = size;
    } else {
423
424
        width = attrs["width"];
        height = attrs["height"];
425
    }
426

427
428
    var slot3 = attrs["minimum-range"];
    var slot4 = attrs["maximum-range"];
429

Jonathan Wilkes's avatar
Jonathan Wilkes committed
430
    if (slot3 === undefined) {
431
432
        slot3 = attrs["flash-interrupt"];
        slot4 = attrs["flash-hold"];
433
    }
434

Jonathan Wilkes's avatar
Jonathan Wilkes committed
435
    if (slot3 === undefined) {
436
437
        slot3 = attrs["visible-width"];
        slot4 = attrs["visible-height"];
438
    }
439

Jonathan Wilkes's avatar
Jonathan Wilkes committed
440
    if (slot3 === undefined) { // toggle
441
        slot3 = attrs["nonzero-value"];
Jonathan Wilkes's avatar
Jonathan Wilkes committed
442
        if (slot3 === undefined) {
443
            slot3 = 0;
444
        }
445
446
        slot4 = 0;
    }
447

448
    var slot5 = attrs["log-scaling"] ? +attrs["log-scaling"] : 0;
449
450
    // Hack to accomodate the vu-scale property, which exists in the same
    // slot as this one
451
452
    var log_scaling_div = document.querySelector(".log-scaling");
    var no_log_display = log_scaling_div.classList.contains("hidden");
453

454
    if (no_log_display) {
455
        slot5 = attrs["vu-scale"] ? +attrs["vu-scale"] : 0;
456
    }
457

458
459
    var init = +attrs["init"];
    if (!init) { init = 0; }
460

461
    var slot7 = attrs["log-height"];
Jonathan Wilkes's avatar
Jonathan Wilkes committed
462
    if (slot7 === undefined) {
463
        slot7 = attrs["number"];
464
    }
Jonathan Wilkes's avatar
Jonathan Wilkes committed
465
    if (slot7 === undefined) {
466
        slot7 = 0;
467
468
    }

469
470
    var font_style = attrs["font-style"];
    //if (font_style !== null) { font_style = 0; }
471

472
    var font_size = attrs["font-size"];
Jonathan Wilkes's avatar
Jonathan Wilkes committed
473
    if (font_size === undefined) { font_size = 0; }
474

475
476
477
    // [vu] doesn't have a foreground color
    var foreground_color = attrs["foreground-color"] ?
        attrs["foreground-color"] : 0;
478
479
    var background_color = attrs["background-color"];
    var label_color = attrs["label-color"];
480

481
    var slot18 = attrs["steady-on-click"] ? +attrs["steady-on-click"] : 0;
482

483
    pdgui.pdsend(pd_object_callback, "dialog",
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
        width, height,
        slot3, // bng: flash-interrupt
               // slider: min-range
               // toggle: nonzero-value
               // my_canvas: visible_width
        slot4, // bng: flash-hold
               // slider: max-range
               // my_canvas: visible_height
        slot5, // slider: lin/log thingy
               // nbx: lin/log
               // vu: vu-scale
        init,
        slot7, // log-height or vradio/hradio number
        send_symbol, receive_symbol, label,
        label_x_offset, label_y_offset,
        font_style, font_size,
        background_color, foreground_color,
        label_color,
        slot18, // steady on click
503
504
505
        0, // not sure what this is doing here
        create_undo_point ? 1 : 0 // whether we set an undo point
    );
506
}
507

508
509
function cancel(revert_changes) {
    var dirty = false, attr;
510
    //window.close(true);
511
512
513
514
515
516
517
518
519
520
    if (revert_changes) {
        for (attr in old_attrs) {
            if (old_attrs[attr] !== new_attrs[attr]) {
                dirty = true;
            }
        }
        if (dirty) {
            send_params(old_attrs, false);
        }
    }
521
    pdgui.pdsend(pd_object_callback, "cancel");
522
523
}

524
525
526
527
528
529
530
531
function apply() {
    send_params(new_attrs, false);
}

function ok() {
    // Steal focus from any active input to make sure it triggers an
    // onchange event
    document.querySelector("button").focus();
532
533
    // send the old attrs first so we can set an undo point on them
    send_params(old_attrs, false);
534
535
536
537
    send_params(new_attrs, true);
    cancel(false);
}

538
539
540
// This gets called from the nw_create_window function in index.html
// It provides us with our window id from the C side.  Once we have it
// we can create the menu and register event callbacks
541
function register_window_id(gfxstub, attr_object) {
542
    var attr;
543
    pd_object_callback = gfxstub;
544
545
546
547
548
549
    old_attrs = attr_object;
    for (attr in old_attrs) {
        if (old_attrs.hasOwnProperty(attr)) {
            new_attrs[attr] = old_attrs[attr];
        }
    }
550
    console.log("attr object is " + attr_object.toString());
551
552
    add_events(gfxstub);
    translate_form();
553
    populate_form(attr_object);
554
555
556
557
    // We don't turn on rendering of the "container" div until
    // We've finished displaying all the spans and populating the
    // labels and form elements.  That makes it more efficient and
    // snappier, at least on older machines.
558
559
    document.getElementsByClassName("container")[0]
        .style.setProperty("display", "inline");
560
    pdgui.resize_window(pd_object_callback);
561
}
562
563

function tr_text(id) {
564
565
    var elem = document.getElementById("iem.prop." + id);
    elem.textContent = l("iem.prop." + id);
566
567
568
569
570
}

// Stop-gap translator
function translate_form() {
    var i
571
    var elements = document.querySelectorAll("[data-i18n]");
572
573
    for (i = 0; i < elements.length; i++) {
        var data = elements[i].dataset.i18n;
574
        if (data.slice(0,7) === "[title]") {
575
576
577
578
579
580
581
            elements[i].title = l(data.slice(7));
        } else {
            elements[i].textContent = l(data);
        }
    }
}

582
583
584
function populate_form(attr_object) {
    var attr;
    for(attr in attr_object) {
585
        // Unhide the span with the class with the same name as the id
586
        var prop_group = document.getElementsByClassName(attr)[0];
587
        if (prop_group !== undefined) {
588
            console.log("the thing here is " + attr);
589
            prop_group.classList.remove("hidden");
590
591
592
593
        }
        // iemguis use the string 'empty' for null because of
        // the limitations of Pd's state-saving API.  So we have
        // to filter that one out
594
        if (attr_object[attr] !== "empty") {
595
            var elem = document.getElementsByName(attr);
596
            if (elem.length > 0) {
597
                if(attr.slice(-5) === "color") {
598
                    var hex_string = Number(attr_object[attr]).toString(16);
599
                    var color_string = "#" +
600
                        (hex_string === "0" ? "000000" : hex_string);
Jonathan Wilkes's avatar
Jonathan Wilkes committed
601
                    //pdgui.post("color is " + color_string);
602
                    elem[0].value = color_string;
603
                } else if (elem[0].type === "checkbox") {
604
605
                    // The attr here is a string, so we need to
                    // force it to number, hence the "+" below
606
                    elem[0].checked = +attr_object[attr];
607
                } else if (elem[0].type === "select-one") {
608
                    elem[0].selectedIndex = +attr_object[attr];
609
                } else {
610
                    elem[0].value = attr_object[attr];
611
612
613
614
615
616
617
618
                }
            }
        }
    }
}

function add_events(name) {
    // closing the Window
619
    gui.Window.get().on("close", function() {
620
        // this needs to do whatever the "cancel" button does
621
        //pdgui.pdsend(name, "menuclose 0");
622
        //cancel();
623
        pdgui.remove_dialogwin(pd_object_callback);
624
        gui.Window.get().close(true);
625
    });
626
    pdgui.dialog_bindings(name);
627
628
629
630
631
}

  </script>
  </body>
</html>