# HG changeset patch # User Edouard Tisserant # Date 1632145337 -7200 # Node ID 9fe5b4a04acca57a452810e096e7dd328050151f # Parent aee9e98c856adcf376551ef99e42517414d19c4a SVGHMI: Add TextList widget, add support for TextList in DropDown widget, move List, TextStyleList and TextList widget code in dedicated file with documentation. diff -r aee9e98c856a -r 9fe5b4a04acc svghmi/detachable_pages.ysl2 --- a/svghmi/detachable_pages.ysl2 Mon Sep 13 22:23:14 2021 +0200 +++ b/svghmi/detachable_pages.ysl2 Mon Sep 20 15:42:17 2021 +0200 @@ -88,10 +88,7 @@ const "required_page_elements", "func:required_elements($hmi_pages | $keypads)/ancestor-or-self::svg:*"; -const "hmi_lists_descs", "$parsed_widgets/widget[@type = 'List']"; -const "hmi_lists", "$hmi_elements[@id = $hmi_lists_descs/@id]"; - -const "required_list_elements", "func:refered_elements($hmi_lists[@id = $required_page_elements/@id])"; +const "required_list_elements", "func:refered_elements(($hmi_lists | $hmi_textlists)[@id = $required_page_elements/@id])"; const "required_elements", "$defs | $required_list_elements | $required_page_elements"; diff -r aee9e98c856a -r 9fe5b4a04acc svghmi/gen_index_xhtml.ysl2 --- a/svghmi/gen_index_xhtml.ysl2 Mon Sep 13 22:23:14 2021 +0200 +++ b/svghmi/gen_index_xhtml.ysl2 Mon Sep 20 15:42:17 2021 +0200 @@ -49,6 +49,8 @@ include geometry.ysl2 + include lists.ysl2 + include detachable_pages.ysl2 include inline_svg.ysl2 diff -r aee9e98c856a -r 9fe5b4a04acc svghmi/widget_dropdown.ysl2 --- a/svghmi/widget_dropdown.ysl2 Mon Sep 13 22:23:14 2021 +0200 +++ b/svghmi/widget_dropdown.ysl2 Mon Sep 20 15:42:17 2021 +0200 @@ -7,16 +7,21 @@ DropDown widget let user select an entry in a list of texts, given as arguments. Single variable path is index of selection. - It needs "text" (svg:text), "box" (svg:rect), "button" (svg:*), - and "highlight" (svg:rect) labeled elements. + It needs "text" (svg:text or svg:use referring to svg:text), + "box" (svg:rect), "button" (svg:*), and "highlight" (svg:rect) + labeled elements. When user clicks on "button", "text" is duplicated to display enties in the limit of available space in page, and "box" is extended to contain all texts. "highlight" is moved over pre-selected entry. - When only one argument is given, and argment contains "#langs" then list of - texts is automatically set to the list of human-readable languages supported - by this HMI. + When only one argument is given and argment contains "#langs" then list of + texts is automatically set to the human-readable list of supported + languages by this HMI. + + If "text" labeled element is of type svg:use and refers to a svg:text + element part of a TextList widget, no argument is expected. In that case + list of texts is set to TextList content. || shortdesc > Let user select text entry in a drop-down menu @@ -34,6 +39,7 @@ if(!this.opened) this.set_selection(value); } init() { + this.init_specific(); this.button_elt.onclick = this.on_button_click.bind(this); // Save original size of rectangle this.box_bbox = this.box_elt.getBBox() @@ -79,7 +85,7 @@ let display_str; if(value >= 0 && value < this.content.length){ // if valid selection resolve content - display_str = this.content[value]; + display_str = gettext(this.content[value]); this.last_selection = value; } else { // otherwise show problem @@ -185,7 +191,7 @@ let c = 0; for(let item of this.content){ let span=spans[c]; - span.textContent = item; + span.textContent = gettext(item); let sel = c; this.make_clickable(span, (evt) => this.bound_on_selection_click(sel)); c++; @@ -251,7 +257,7 @@ span.setAttribute("dx", (m.width - o.width)/2); // otherwise normal content }else{ - span.textContent = this.content[i]; + span.textContent = gettext(this.content[i]); let sel = i; onclickfunc = (evt) => this.bound_on_selection_click(sel); span.removeAttribute("dx"); @@ -360,19 +366,43 @@ } widget_defs("DropDown") { - labels("text box button highlight"); + labels("box button highlight"); // It is assumed that list content conforms to Array interface. - > content: + const "text_elt","$hmi_element//*[@inkscape:label='text'][1]"; + | init_specific: function() { choose{ // special case when used for language selection when "count(arg) = 1 and arg[1]/@value = '#langs'" { - > langs + | this.text_elt = id("«$text_elt/@id»"); + | this.content = langs; + } + when "count(arg) = 0"{ + if "not($text_elt[self::svg:use])" + error > No argrument for HMI:DropDown widget id="«$hmi_element/@id»" and "text" labeled element is not a svg:use element + const "real_text_elt","$result_widgets[@id = $hmi_element/@id]//*[@original=$text_elt/@id]/svg:text"; + | this.text_elt = id("«$real_text_elt/@id»"); + const "from_list_id", "substring-after($text_elt/@xlink:href,'#')"; + const "from_list", "$hmi_textlists[(@id | */@id) = $from_list_id]"; + if "count($from_list) = 0" + error > HMI:DropDown widget id="«$hmi_element/@id»" "text" labeled element does not point to a svg:text owned by a HMI:List widget + | this.content = hmi_widgets["«$from_list/@id»"].texts; } otherwise { - > [\n + | this.text_elt = id("«$text_elt/@id»"); + | this.content = [ foreach "arg" | "«@value»", - > ] + | ]; } } - > ,\n + | } } + +emit "declarations:DropDown" +|| +function gettext(o) { + if(typeof(o) == "string"){ + return o; + } + return svg_text_to_multiline(o); +}; +|| diff -r aee9e98c856a -r 9fe5b4a04acc svghmi/widget_jsontable.ysl2 --- a/svghmi/widget_jsontable.ysl2 Mon Sep 13 22:23:14 2021 +0200 +++ b/svghmi/widget_jsontable.ysl2 Mon Sep 20 15:42:17 2021 +0200 @@ -108,17 +108,6 @@ } -const "hmi_textstylelists_descs", "$parsed_widgets/widget[@type = 'TextStyleList']"; -const "hmi_textstylelists", "$hmi_elements[@id = $hmi_textstylelists_descs/@id]"; - -const "textstylelist_related" foreach "$hmi_textstylelists" list { - attrib "listid" value "@id"; - foreach "func:refered_elements(.)" elt { - attrib "eltid" value "@id"; - } -} -const "textstylelist_related_ns", "exsl:node-set($textstylelist_related)"; - def "func:json_expressions" { param "expressions"; param "label"; diff -r aee9e98c856a -r 9fe5b4a04acc svghmi/widget_list.ysl2 --- a/svghmi/widget_list.ysl2 Mon Sep 13 22:23:14 2021 +0200 +++ b/svghmi/widget_list.ysl2 Mon Sep 20 15:42:17 2021 +0200 @@ -1,6 +1,22 @@ // widget_list.ysl2 + widget_desc("List") { - // TODO + longdesc + || + List widget is a svg:group, list items are labeled elements + in that group. + + To use a List, clone (svg:use) one of the items inside the widget that + expects a List. + + Positions of items are relative to each other, and they must all be in the + same place. In order to make editing easier it is therefore recommanded to + make stacked clones of svg elements spread nearby the list. + || + + shortdesc > A named list of named graphical elements + + arg name="listname" } widget_defs("List") { @@ -11,15 +27,3 @@ | }, } -widget_defs("TextStyleList") { - // TODO -} - -widget_defs("TextStyleList") { - | styles: { - foreach "$hmi_element/*[@inkscape:label]" { - const "style", "func:refered_elements(.)[self::svg:text]/@style"; - | «@inkscape:label»: "«$style»", - } - | }, -}