dialog_iemgui.html 20.3 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 id="iemgui_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
337
338
// gui preset
pdgui.skin.apply(this);

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
    var problem_chars = [";", ",", "{", "}", "\\"];
350
351
    var ret = arg;
    for(var i = 0; i < problem_chars.length; i++) {
352
        ret = ret.split(";").join("");
353
    }
354
355
    return ret;
}
356

357
358
359
360
361
362
363
364
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") {
365
366
367
        new_attrs[elem.name] = elem.selectedIndex;
    } else if (elem.type === "color") {
        new_attrs[elem.name] = parseInt(elem.value.slice(1), 16)
368
    } else {
369
        new_attrs[elem.name] = elem.value;
370
371
372
    }
}

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

function send_params(attrs, create_undo_point) {
384
    pdgui.post("we're applying iemgui changes!");
385
386
387
388
389
390
391
392
    /* 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
    */
393

394
395
396
397
398
399
400
pdgui.post("label is " + attrs["label"]);
    var send_symbol = attrs["send-symbol"],
        receive_symbol = attrs["receive-symbol"],
        label =  attrs["label"];
    pd_symbol_carwash(send_symbol);
    pd_symbol_carwash(receive_symbol);
    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
415
416
    var size = attrs["size"];
    if (!size) {
        size = attrs["selection-size"];
417
    }
418

419
    if (size) {
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

430
431
432
    if (!slot3) {
        slot3 = attrs["flash-interrupt"];
        slot4 = attrs["flash-hold"];
433
    }
434

435
436
437
    if (!slot3) {
        slot3 = attrs["visible-width"];
        slot4 = attrs["visible-height"];
438
    }
439

440
441
    if (!slot3) { // toggle
        slot3 = attrs["nonzero-value"];
442
        if (slot3 === "") {
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
        pdgui.post("slot five is " + slot5);
457
    }
458
    pdgui.post("slot five is " + slot5);
459

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

463
464
465
    var slot7 = attrs["log-height"];
    if (!slot7) {
        slot7 = attrs["number"];
466
    }
467
    if (!slot7) {
468
        slot7 = 0;
469
470
    }

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

474
475
    var font_size = attrs["font-size"];
    if (!font_size) { font_size = 0; }
476

477
478
479
    var foreground_color = attrs["foreground-color"];
    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
        0);
504
}
505

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

523
524
525
526
527
528
529
530
531
532
533
534
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();
    send_params(new_attrs, true);
    cancel(false);
}

535
536
537
// 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
538
function register_window_id(gfxstub, attr_object) {
539
    var attr;
540
    pd_object_callback = gfxstub;
541
542
543
544
545
546
    old_attrs = attr_object;
    for (attr in old_attrs) {
        if (old_attrs.hasOwnProperty(attr)) {
            new_attrs[attr] = old_attrs[attr];
        }
    }
547
    console.log("attr object is " + attr_object.toString());
548
549
    add_events(gfxstub);
    translate_form();
550
    populate_form(attr_object);
551
552
553
554
    // 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.
555
556
    document.getElementsByClassName("container")[0]
        .style.setProperty("display", "inline");
557
    pdgui.resize_window(pd_object_callback);
558
}
559
560

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

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

579
580
581
function populate_form(attr_object) {
    var attr;
    for(attr in attr_object) {
582
        // Unhide the span with the class with the same name as the id
583
        var prop_group = document.getElementsByClassName(attr)[0];
584
        if (prop_group !== undefined) {
585
            console.log("the thing here is " + attr);
586
            prop_group.classList.remove("hidden");
587
        } else {
588
            pdgui.post("Error: couldn't find iemgui prop group for " +
589
                attr);
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);
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>