Roll20 uses cookies to improve your experience on our site. Cookies enable you to enjoy certain features, social sharing functionality, and tailor message and display ads to your interests on our site and others. They also help us understand how our site is being used. By continuing to use our site, you consent to our use of cookies. Update your cookie preferences .
×
Create a free account

Simple UI Question

I've started playing around with UI output from my script and I've run into a little quirk, which I was hoping someone knew a nice work around? Basically I have something like this: `<div style="border:1px black dotted"><br/>${c._usage}<br/><p>${c._desc}</p><p>${c._help}</p><p><code>${escapeHtmlForR20(c._example)}</code></p></div>` In a `sendChat()` call.  But when it is emitted, I end up with two `div`s, presumably due to length.  Anyway to suppress this "feature"?  (The border makes the div separation more obvious ;).
1542584493
Scott C.
Forum Champion
Sheet Author
API Scripter
Compendium Curator
Hmm, never run into that before and I've made some very large chat ouputs. Where in that output does the break occur?
In that case in the middle of the example, but that's my help command, so it breaks "randomly" depending on which it is, and where it is in the history.  I.e. it seems to use an algorithm where if Person X says something and then says something else, they are concatenated together into the same div, unless that div is longer than Y, then it will create a new div.  Whether the text came from the same sendChat or several separated in time does not seem to matter.
1542636344
Scott C.
Forum Champion
Sheet Author
API Scripter
Compendium Curator
Ah, ok, you've got an unclosed div somewhere. Could be another element of some sort, but most likely a div. Are passing html formatting in any of those variables?
I assume you have validated the final html you sent to to sendChat to rule out something goofy like unclosed elements?  If you have, then my only relevant data I have is that ALL my dialogs are a single <div> containing a single <ul> with <li> containing all the vertical elements.  It is entirely possible that <UL> is triggering some code in Roll20 that prevents it from splitting.  I did it this way because Robin did it this way and I didn't want to screw with something like what you are seeing now :) so I religiously followed.
1542675468

Edited 1542675693
The Aaron
Pro
API Scripter
You might enjoy looking at the _h object in TokenMod, and how I use it in showHelp().  Makes it easier to not worry so much about HTML.  Here's an extraction of it that should work to drop in somewhere: const ch = function (c) { var entities = { '<' : 'lt', '>' : 'gt', "'" : '#39', '@' : '#64', '{' : '#123', '|' : '#124', '}' : '#125', '[' : '#91', ']' : '#93', '"' : 'quot', '*' : 'ast', '/' : 'sol', ' ' : 'nbsp' }; if(_.has(entities,c) ){ return ('&'+entities[c]+';'); } return ''; }; const _h = { outer: (...o) => `<div style="border: 1px solid black; background-color: white; padding: 3px 3px;">${o.join(' ')}</div>`, title: (t,v) => `<div style="font-weight: bold; border-bottom: 1px solid black;font-size: 130%;">${t} v${v}</div>`, subhead: (...o) => `<b>${o.join(' ')}</b>`, minorhead: (...o) => `<u>${o.join(' ')}</u>`, optional: (...o) => `${ch('[')}${o.join(` ${ch('|')} `)}${ch(']')}`, required: (...o) => `${ch('<')}${o.join(` ${ch('|')} `)}${ch('>')}`, header: (...o) => `<div style="padding-left:10px;margin-bottom:3px;">${o.join(' ')}</div>`, section: (s,...o) => `${_h.subhead(s)}${_h.inset(...o)}`, paragraph: (...o) => `<p>${o.join(' ')}</p>`, items: (o) => `<li>${o.join('</li><li>')}</li>`, ol: (...o) => `<ol>${_h.items(o)}</ol>`, ul: (...o) => `<ul>${_h.items(o)}</ul>`, grid: (...o) => `<div style="padding: 12px 0;">${o.join('')}<div style="clear:both;"></div></div>`, cell: (o) => `<div style="width: 130px; padding: 0 3px; float: left;">${o}</div>`, inset: (...o) => `<div style="padding-left: 10px;padding-right:20px">${o.join(' ')}</div>`, pre: (...o) =>`<div style="border:1px solid #e1e1e8;border-radius:4px;padding:8.5px;margin-bottom:9px;font-size:12px;white-space:normal;word-break:normal;word-wrap:normal;background-color:#f7f7f9;font-family:monospace;overflow:auto;">${o.join(' ')}</div>`, preformatted: (...o) =>_h.pre(o.join('<br>').replace(/\s/g,ch(' '))), code: (...o) => `<code>${o.join(' ')}</code>`, attr: { bare: (o)=>`${ch('@')}${ch('{')}${o}${ch('}')}`, selected: (o)=>`${ch('@')}${ch('{')}selected${ch('|')}${o}${ch('}')}`, target: (o)=>`${ch('@')}${ch('{')}target${ch('|')}${o}${ch('}')}`, char: (o,c)=>`${ch('@')}${ch('{')}${c||'CHARACTER NAME'}${ch('|')}${o}${ch('}')}` }, bold: (...o) => `<b>${o.join(' ')}</b>`, italic: (...o) => `<i>${o.join(' ')}</i>`, font: { command: (...o)=>`<b><span style="font-family:serif;">${o.join(' ')}</span></b>` } }; The basic idea is to build up output as the return of a bunch of function calls (Partial example): sendChat('', '/w "'+who+'" '+ _h.outer( _h.title('TokenMod',version), _h.header( _h.paragraph( 'TokenMod provides an interface to setting almost all settable properties of a token.') ), _h.subhead('Commands'), _h.inset( _h.font.command( `!token-mod `, _h.required( `--help`, `--ignore-selected`, `--current-page`, `--active-pages`, `--config`, `--on`, `--off`, `--flip`, `--set` ), _h.required(`parameter`), _h.optional(`${_h.required(`parameter`)} ...`), `...`, _h.optional( `--ids`, _h.required(`token_id`), _h.optional(`${_h.required(`token_id`)} ...`) ) ),                 /* ... etc ... */
well, so much for my theory that it might be the unordered list tag :)  since you don't use one.  I do know that if you don't remove all actual carriage returns from your HTML, you will get problems like it breaking into multiple chats.  maybe that's all it is and you have a \n in there somewhere.  I also have enormous dialogs being emitted, and they never break across messages.
Yeah, I'll have to check, it might be a CR embedded in a template string...
1542732823
The Aaron
Pro
API Scripter
Yeah, a rogue carriage return will definitely break it. 
Yes, it was white space in my template literals...  Which shouldn't have mattered, but :(.  Instead I have to have massive run-on lines or composite them in multiple literals.  Ah well.  Thanks for the help again! 8)
happy to help... just really looking forward to seeing your work.  You know so much more about JS and web things that I am excited to see what your stuff looks like.
1542889215
The Aaron
Pro
API Scripter
One thing you can do is strip out all the carriage returns before sending to chat. Something like: sendChat('',msg.replace(/[\n\r]/g,' '));
1542893111

Edited 1542893254
Sure, that just makes the code intent more obfuscated, though, The Aaron, imo :).  But you of course right 8) Ammo  said: happy to help... just really looking forward to seeing your work.  You know so much more about JS and web things that I am excited to see what your stuff looks like. Well, I don't know about all that :/.  Right now I'm making a fully automated version of the Black Crusade combat system for our GM, so he doesn't lose his mind.  I don't think I can "release" it, though, because it contains basically a full implementation of their rules system, which I think is a copyright violation if I release it.