svghmi/widget_jsontable.ysl2
branchsvghmi
changeset 3149 d32e6246cd59
parent 3081 9e55061c87fa
child 3150 5a1bb6ec48a0
equal deleted inserted replaced
3148:b8c0dfdf364b 3149:d32e6246cd59
     5     class JsonTableWidget extends Widget{
     5     class JsonTableWidget extends Widget{
     6         // arbitrary defaults to avoid missing entries in query
     6         // arbitrary defaults to avoid missing entries in query
     7         cache = [0,100,50];
     7         cache = [0,100,50];
     8         init() {
     8         init() {
     9             this.spread_json_data_bound = this.spread_json_data.bind(this);
     9             this.spread_json_data_bound = this.spread_json_data.bind(this);
       
    10             this.handle_http_response_bound = this.handle_http_response.bind(this);
       
    11             this.fetch_error_bound = this.fetch_error.bind(this);
       
    12             this.promised = false;
    10         }
    13         }
    11 
    14 
    12         handle_http_response(response) {
    15         handle_http_response(response) {
    13             if (!response.ok) {
    16             if (!response.ok) {
    14               console.log("HTTP error, status = " + response.status);
    17               console.log("HTTP error, status = " + response.status);
    15             }
    18             }
    16             return response.json();
    19             return response.json();
    17         }
    20         }
    18 
    21 
       
    22         fetch_error(e){
       
    23             console.log("HTTP fetch error, message = " + e.message + "Widget:" + this.element_id);
       
    24         }
       
    25 
    19         do_http_request(...opt) {
    26         do_http_request(...opt) {
       
    27             this.abort_controller = new AbortController();
    20             const query = {
    28             const query = {
    21                 args: this.args,
    29                 args: this.args,
    22                 range: this.cache[1],
    30                 range: this.cache[1],
    23                 position: this.cache[2],
    31                 position: this.cache[2],
    24                 visible: this.visible,
    32                 visible: this.visible,
    27             };
    35             };
    28 
    36 
    29             const options = {
    37             const options = {
    30                  method: 'POST',
    38                  method: 'POST',
    31                  body: JSON.stringify(query),
    39                  body: JSON.stringify(query),
    32                  headers: {'Content-Type': 'application/json'}
    40                  headers: {'Content-Type': 'application/json'},
       
    41                  signal: this.abort_controller.signal
    33             };
    42             };
    34 
    43 
    35             fetch(this.args[0], options)
    44             return fetch(this.args[0], options)
    36                 .then(this.handle_http_response)
    45                     .then(this.handle_http_response_bound)
    37                 .then(this.spread_json_data_bound);
    46                     .then(this.spread_json_data_bound)
    38 
    47                     .catch(this.fetch_error_bound);
    39         }
    48 
       
    49         }
       
    50         unsub(){
       
    51             this.abort_controller.abort();
       
    52             super.unsub();
       
    53         }
       
    54 
    40         dispatch(value, oldval, index) {
    55         dispatch(value, oldval, index) {
    41             this.cache[index] = value;
    56 
    42             this.do_http_request();
    57             if(this.cache[index] != value)
       
    58                 this.cache[index] = value;
       
    59             else
       
    60                 return;
       
    61 
       
    62             if(!this.promised){
       
    63                 this.promised = true;
       
    64                 Promise.resolve().then(() => {
       
    65                     return this.do_http_request().finally(() => {
       
    66                         this.promised = false;
       
    67                     });
       
    68                 })
       
    69             }
    43         }
    70         }
    44         make_on_click(...options){
    71         make_on_click(...options){
    45             let that = this;
    72             let that = this;
    46             return function(evt){
    73             return function(evt){
    47                 that.do_http_request(...options);
    74                 that.do_http_request(...options);
   194 
   221 
   195 template "svg:g", mode="json_table_render" {
   222 template "svg:g", mode="json_table_render" {
   196     param "expressions";
   223     param "expressions";
   197     param "widget_elts";
   224     param "widget_elts";
   198     param "label";
   225     param "label";
   199     const "gid", "@id";
       
   200 
   226 
   201     // use intermediate variables for optimization
   227     // use intermediate variables for optimization
   202     const "varprefix" > obj_«$gid»_
   228     const "varprefix" > obj_«@id»_
   203     |         try {
   229     |         try {
   204 
   230 
   205     foreach "$expressions/expression"{
   231     foreach "$expressions/expression"{
   206     |          let «$varprefix»«position()» = «@content»;
   232     |          let «$varprefix»«position()» = «@content»;
   207     |          if(«$varprefix»«position()» == undefined) {
   233     |          if(«$varprefix»«position()» == undefined) {
   208     |               console.log("«$varprefix»«position()» = «@content»");
       
   209     |               throw null;
   234     |               throw null;
   210     |          }
   235     |          }
   211     }
   236     }
   212 
   237 
   213     // because we put values in a variables, we can replace corresponding expression with variable name
   238     // because we put values in a variables, we can replace corresponding expression with variable name
   222     apply "*", mode="json_table_render_except_comments" {
   247     apply "*", mode="json_table_render_except_comments" {
   223         with "expressions", "func:json_expressions(exsl:node-set($new_expressions), $label)";
   248         with "expressions", "func:json_expressions(exsl:node-set($new_expressions), $label)";
   224         with "widget_elts", "$widget_elts";
   249         with "widget_elts", "$widget_elts";
   225     }
   250     }
   226     |         } catch(err) {
   251     |         } catch(err) {
   227     |           id("«$gid»").style = "display:none";
   252     |           id("«@id»").style = "display:none";
   228     |         }
   253     |         }
   229 }
   254 }
   230 
   255 
   231 template "widget[@type='JsonTable']", mode="widget_defs" {
   256 template "widget[@type='JsonTable']", mode="widget_defs" {
   232     param "hmi_element";
   257     param "hmi_element";
   234     optional_labels("forward backward cursor");
   259     optional_labels("forward backward cursor");
   235     const "data_elt", "$result_svg_ns//*[@id = $hmi_element/@id]/*[@inkscape:label = 'data']";
   260     const "data_elt", "$result_svg_ns//*[@id = $hmi_element/@id]/*[@inkscape:label = 'data']";
   236     |     visible: «count($data_elt/*[@inkscape:label])»,
   261     |     visible: «count($data_elt/*[@inkscape:label])»,
   237     |     spread_json_data: function(janswer) {
   262     |     spread_json_data: function(janswer) {
   238     |         let [range,position,jdata] = janswer;
   263     |         let [range,position,jdata] = janswer;
   239     |         this.apply_hmi_value(1, range);
   264     |         [[1, range], [2, position], [3, this.visible]].map(([i,v]) => {
   240     |         this.apply_hmi_value(2, position);
   265     |              this.apply_hmi_value(i,v);
   241     |         this.apply_hmi_value(3, this.visible);
   266     |              this.cache[i] = v;
       
   267     |         });
   242     apply "$data_elt", mode="json_table_render_except_comments" {
   268     apply "$data_elt", mode="json_table_render_except_comments" {
   243         with "expressions","$initexpr_ns";
   269         with "expressions","$initexpr_ns";
   244         with "widget_elts","$hmi_element/*[@inkscape:label = 'data']/descendant::svg:*";
   270         with "widget_elts","$hmi_element/*[@inkscape:label = 'data']/descendant::svg:*";
   245     }
   271     }
   246     |     }
   272     |     }