$DisplayedAttributes

I’ve just tried to create a template which makes an HTML table of the displayed attributes and their values of a note using it.

I’ve used a loop using $DisplayedAttributes.each(x){…} (largely to make it generic for any note and therefore not have to hard code the template with a note’s particular $Attribues

I’ve tried to access the values with variations of ^value(“$”+x) and eval() versions to no effect.

aTBRef says …

Note that this is a list of attribute names and not references so do not use a $-prefix if editing the list by hand or via action code.

Does this explain why I’m failing? I think it does but wondered if I’ve missed something

tia

Mark

vTable+="<td>"+eval("$"+x)+"</td>";

Seems to have done the trick :roll_eyes:

1 Like

Yep — that’s the way to do it!

One way to may this cleaner might be a function.

function tableCellFor(attributeName:string) {
    var:string val=eval("$"+attributeName);
    return "<td>"+val+"</td>";
   }

This makes your loop

$DisplayedAttributes.each(attribute) {
     vTable=tableCellFor(attribute);
1 Like

@Markoconnor you might want to read this, Constructing $Attribute references in loops, as it addresses exactly this issue.

I was surprised, given the above, to see the article says not to use eval() but rather to use action() which might seem to run counter to the above—though that advice came after past discussion with @eastgate. IIRC the issue is that sometimes the run of the code causes an eval() statement of ‘over-evaluate’. Thus, instead of eval("$"+"MyString") giving you "MyString", you get true (the resolved boolean value of a string attribute with a non-empty value).

So I guess a more nuanced version of the article above is use eval() if it works or else use action(). For simplicity, as most readers want a single solution that works, I advise using action() as it works when eval() doesn’t. So, in context, this:

vTable+="<td>"+eval("$"+x)+"</td>";

can be re-written as:

vTable+=action("<td>"+"$"+x+"</td>");
// or more succinctly
vTable+=action("<td>$"+x+"</td>");

and in the function:

var:string val=eval("$"+attributeName);
//becomes
var:string val=action("$"+attributeName);

The underlying issue, for the app, is whether the users intent it to:

  • (a) generate a string holding reference to an attribute of the name in the source string, i.e. literally "$MyString"
  • or (b) generate a string that is the actual value of that reference, i.e. `“Hello world”

In some cases it doesn’t matter, in others is does. IOW, at the end of the process you get true, i.e. the boolean test of whether the attribute called ‘MyString’ has a value, rather than Hello world which is the value of ‘$MyString’.

It’s also another example of how there is more than one way to do things in action code

1 Like

Too funny. @TomDiaz and I just did this last weekend. Funny how innovation comes in clusters.

Here is our completed template.

TBX L - Dynamic Columns and Rows Table.tbx (251.7 KB)

Click on My Report and hit preview. It will dynamically add columns as attributes are displayed in My Report. Pickup values form new notes. If you want to change the label of the column from the attribute name to something different, use the $DictAttribute in TBX conflict. Also, if the attribute is a URL it will make the URL active.

We purposely left our other table drafts to show the incremental formalization. tTable4 is our final result.

1 Like

Thanks Michael

I shall look at this in more detail later - Just one quick question about the 1... - is this a range operator limiting the extent of the .each loop?

Correct - see here.

It’s a newish operator and less often seen. Important note, the operator is written as 3 dots (AmE: period, BrE: full stop). An ellipsis character (3 dots in one character) will not work. I mention the latter is helpful auto-correct in some writing tools ‘corrects’ one form to the other.

1 Like

Yes you can hard code it 1...8.each{}, i.e., have a look run 8 times, or var1...var2.each, i.e., feed the range a number form attributes or variables. It is wickedly cool!

Thanks Michael,

There is an html tag called <caption> that I think would be a useful addtion for your excellent table templates;

vTable+='<caption>'+eval($Name)+'</caption>';

Will place a nice caption of the parent note’s name at the top of the table. Needs to be the next line after the table is created with the <table> tag

I have been playing with trying to make tables responsive on a web page ( ie look good at all screen sizes) and considering using div tags and CSS to do that and not bothering with table tags at all - However, this css-you-tuber ( who I have followed for a couple of years when he first started out and now has circa 750k followers) , Kevin Powell has an interesting video on precisely this which you and others might find interesting - How to create a responsive HTML table - YouTube

Best Wishes

Mark

1 Like

I may be missing something, but I don’t believe you want to eval the $Name in the caption.

Agreed - but it works, whereas I couldn’t get ^value($Name)^ to behave itself ( added +/ characters appeared and likewise action() as per thread above didn’t work - I just wanted to highlight the utility of the caption tag but grateful for any update on the correct syntax