Include JSON File

Hi,

I think there was some kind of a json file binding for building up lists and tables with content. Is this still available in the web version? Is there an example file for that?

Best regards
Chris

Hi Chris,

we have one example in the “Data Binding Example”:

Currently you need to paste the json inside the header_include.html since we do not support external files. If you have further questions don’t hesitate to ask …

Cheers,

Felix

Hi Felix,

Thank you for your quick response. I was blind :slight_smile: I found it and it works now.

Best regards,
Chris

1 Like

I am trying to feed menus with different skins the values from the file. All working well until I add more objects. I want all these menu entries to receive values from the JSON data but only the first one in the list gets it:
image
Howdo I need to tweak this script?
loadJSON(targetCells[0], "Menu1")

this is an example we developed in a workshop (and did not really clean it up … ). The script is inside the header_include.html.

It replaces the contents of the container (here “TodayData” and “TomorrowData”) with similar rows, but the text-content is used from the data-Object in the header_include, mapping the values using NameInJavaScript -> $NameInJavaScript (in Antetype).

menu binding.zip (257.9 KB)

Here a simplified example, with a structure similar to yours.

Does this help?

I got that to work using the example you mentioned above. Quite straigt-forward. My question was how can I feed several “$Entry”-cells with the same value from the JSON file? Think of these as skins for Mac Aqua, mac dark mode and Windows. I just don’t want to fill up each menu individually. image

To be even more specific: if I just duplicate the “$Entry”-cell, only one will receive the values, not both.

in the current form the script replaces multiple $Entry values inside the Entry cell:

do you want to replace cells named $Entry outside of the repeated entries? :thinking:

Hmmm… in your example it seems to work, in mine it doesn’t. I’ll compare the two files and see what’s different. Thanks!

I got it to work now (but I don’t know why :yum:)
My menus look like this:


(Work in progress, don’t mind the colours).
So each time, one of the fields in the JSON part comes up blank, it prints the field name. I have tried to tweak this to just print nothing if the field name is empty:

function loadJSON(cell, dataName) {
let atRow = cell.orderedComponents[0]
  // if name contains "$" replace text with name
  atRow.deepOrderedComponents.forEach( c => {
      if (c.name.indexOf("$") == 0) {
          Antetype.cellSetProperty(c, "textString", c.name);
      }

  });

But I guess I am not far enough along in the JAVA course to be able to make much sense out of it so whatever I did, didn’t work. (To save me the embarrassment, I won’t post what I tried :grimacing:)

Any pointers?

the script is a little bit weird anyway (it started using those placeholder with an “$” inside the text, but later on it was changed to use it in the name of the cell … ).

if you have something like this (here the last entry is empty)

	
let data = {
Menu1: [
    {"Entry": "First Entry" },
    {"Entry": "Second Entry" },
    {"Entry": "" }     // <--- comes up blank 
]
}
;

and change remove the check if we have any data in fillDOMNode:

function loadJSON(cell, dataName) {
	let atRow = cell.orderedComponents[0]
    // if name contains "$" replace text with name
    atRow.deepOrderedComponents.forEach( c => {
        if (c.name.indexOf("$") == 0) {
            Antetype.cellSetProperty(c, "textString", c.name);
        }

    });

    function fillDOMNode(domNode, rowData) {
        // find spans with "$" in textContent
        let it = document.createNodeIterator(domNode, NodeFilter.SHOW_ELEMENT, (e) => {
            return e.nodeName.toLowerCase() == "span" && e.textContent.indexOf("$") == 0;
        });

        let nextSpan = null;
        while (nextSpan = it.nextNode()) {
            let placeHolder = nextSpan.textContent;
            placeHolder = placeHolder.replace("$", "");
// remove the check if the json data is empty:
//            if (rowData[placeHolder]) {
                nextSpan.textContent = rowData[placeHolder];
//            }
        }
    }
    
    let rowTemplate = atRow.DOMElement;
    rowTemplate.parentElement.removeChild(rowTemplate);
    let tableData = data[dataName];
    tableData.forEach( rowData => {
        let newDOMNode = rowTemplate.cloneNode(true)
        cell.DOMElement.appendChild(newDOMNode)
        fillDOMNode(newDOMNode, rowData);
    })


}

it will insert the empty string. Does this help? One day we have to cleanup this mess :smiley:

menu binding.zip (258.3 KB)

Yeah, that’s what I was after. it doesn’t seem to work in my file but I guess I can refactor it to do what I need. Thanks!

It is working perfectly now. Could I also tweak a cell’s width by checking if the string is empty and then settings the cell’s width to 0?
So the cell has a fixed with of 20px unless it contains an empty entry in which case it will be set to zero.

For my automatic conversion to work, I need to have the string
⌥⇧⌘ replaced with Ctrl+Shift+Alt to allow switching from Mac to Windows prototype.
image
image
-> You can see here why I need that last cell (The one containing the “A”, “C” and “I”) to collapse to zero if it is empty. If no shortcuts are present, the first cell (containing the modifiers) will already collapse because it is set to “shrink”. But this last cell needs to have a fixed width to keep the ⌘ in the same place.

My idea to do the size magic was to put a script in the last cell on Load Sreen. I have read through the API pages abut I am not sure how to target the cell width correctly. I would do something like

let cell = targetCells[0]
let states = cell.widget.states


states.forEach( s => at.cellSetPropertyInState(cell, "width", 20, s) )
if ("textString" == '') {
		"width" = 0;}

Sorry, I’m only on chapter two of the JAVA tutorial (which is great, BTW!)

For the string replacement and reshuffling, I am pretty much lost still and for the left click targeting, I am totally out of my depth :slight_smile:

I think I am getting there though. Reading from the JSON file and creating the menu entries on the fly will be difficult because I need to target each widget to be able to use each menu item to do something. So I was thinking why not create a dummy widget whose name is converted to a cell text string.

The widget could look like this:

image

And the script takes each string that is separated by the | and places it in each theme’s cell’s text property. I could then target the widget and use the “Visible in Viewport” state to turn the same properties on and off for hidden menus (of other themes).