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

Hidden Custom Turn Order Items

Is there a way of creating turn order (specifically, round-calculation based)  items such that the players cant see them? IE: I have timed events that may occur 10, 12, 15 rounds in, and want to keep track of them, without my players seeing a countdown coming or round counter ticking upward...
A character token on the GM layer has no visibility to players in the turn order.  Set them in the correct position with a -1 calculation and when they reach 0... boom... action
Ok...then the question becomes how do you set a Calculation to a Token's order?
1532191735

Edited 1697909972
The Aaron
Pro
API Scripter
Try this: !aict +1 0 --Counts up by one !aict -1 10 --Counts down from 10 !aict -1 [[2d4+3]] --Rounds till Reinforcements Mostly place nice, though if you're using a script that changes the turn order (TurnMarker1, for example), the value won't be changed if that script changes the turn order to one of these turns.&nbsp; In practice, if you see one not changing, make sure the thing above it wasn't TurnMarker or some such.&nbsp; I'll try to fix that in the future... Here's the script: // Add Invisible CustomTurn // By: The Aaron, Arcane Scriptomancer // Contact: <a href="https://app.roll20.net/users/104025/the-aaron" rel="nofollow">https://app.roll20.net/users/104025/the-aaron</a> var API_Meta = API_Meta||{}; //eslint-disable-line no-var API_Meta.AddInvisibleCustomTurn={offset:Number.MAX_SAFE_INTEGER,lineCount:-1}; {try{throw new Error('');}catch(e){API_Meta.AddInvisibleCustomTurn.offset=(parseInt(e.stack.split(/\n/)[1].replace(/^.*:(\d+):.*$/,'$1'),10)-6);}} on('ready',() =&gt; { const version = '0.1.2'; API_Meta.AddInvisibleCustomTurn.version = version; const aictImgSrc = "<a href="https://s3.amazonaws.com/files.d20.io/images/58732795/pfn3AoNw630KlzHP0dGMWw/thumb.png?1532188342" rel="nofollow">https://s3.amazonaws.com/files.d20.io/images/58732795/pfn3AoNw630KlzHP0dGMWw/thumb.png?1532188342</a>"; const activeAICTs = findObjs({type:'graphic',layer:'gmlayer'}) .filter((t)=&gt;/images\/58732795\/pfn3AoNw630KlzHP0dGMWw\//.test(t.get('imgsrc'))) .filter((()=&gt;{ const toIds = JSON.parse(Campaign().get('turnorder')||'[]').map(to=&gt;to.id); return t =&gt; { if( ! toIds.includes(t.id)){ t.remove(); return false; } return true; }; })()) .map((t)=&gt;t.id) ; const getPageForPlayer = (playerid) =&gt; { let player = getObj('player',playerid); if(playerIsGM(playerid)){ return player.get('lastpage'); } let psp = Campaign().get('playerspecificpages'); if(psp[playerid]){ return psp[playerid]; } return Campaign().get('playerpageid'); }; let lastTurnCache = ''; const checkFormulaOnTurn = _.debounce(() =&gt; { let to=JSON.parse(Campaign().get('turnorder')||'[]'); if(to.length){ if(to[0].id!==lastTurnCache &amp;&amp; activeAICTs.includes(to[0].id)) { sendChat('',`[[${to[0].pr}+(${to[0].formula||0})]]`,(r)=&gt;{ to[0].pr=r[0].inlinerolls[0].results.total; Campaign().set('turnorder',JSON.stringify(to)); }); } lastTurnCache = to[0].id; } },10); const processInlinerolls = (msg) =&gt; { if(msg.hasOwnProperty('inlinerolls')){ return msg.inlinerolls .reduce((m,v,k) =&gt; { let ti=v.results.rolls.reduce((m2,v2) =&gt; { if(v2.hasOwnProperty('table')){ m2.push(v2.results.reduce((m3,v3) =&gt; [...m3,(v3.tableItem||{}).name],[]).join(", ")); } return m2; },[]).join(', '); return [...m,{k:`$[[${k}]]`, v:(ti.length &amp;&amp; ti) || v.results.total || 0}]; },[]) .reduce((m,o) =&gt; m.replace(o.k,o.v), msg.content); } else { return msg.content; } }; on('chat:message',function(msg){ if('api' === msg.type) { if(msg.content.match(/^!aict\b/) ){ let who=(getObj('player',msg.playerid)||{get:()=&gt;'API'}).get('_displayname'); let content = processInlinerolls(msg); let args = content .replace(/&lt;br\/&gt;\n/g, ' ') .replace(/(\{\{(.*?)\}\})/g," $2 ") .split(/\s+--/); let cmds = args.shift().split(/\s+/); let change = parseFloat(cmds[1]); change = ( isNaN(change) ? '+1': change ); change = `${/^[+-]\d/.test(change)?'':'+'}${change}`; let initial = parseFloat(cmds[2])||0; let entry = args.join(' '); if(entry.length){ let to=JSON.parse(Campaign().get('turnorder')||'[]'); let pageid = getPageForPlayer(msg.playerid); let token = createObj('graphic', { subtype: 'token', imgsrc: aictImgSrc, pageid: pageid, layer: 'gmlayer', top: -100, left: -100, width: 70, height: 70, name: entry, showname: true }); activeAICTs.push(token.id); to.unshift({ id: token.id, pr: initial, _pageid: pageid, formula: change }); Campaign().set('turnorder',JSON.stringify(to)); if(!playerIsGM(msg.playerid)){ sendChat('AICT',`/w gm &lt;div style="padding:1px 3px;border: 1px solid #8B4513;background: #eeffee; color: #8B4513; font-size: 80%;"&gt;&lt;div style="background-color: #ffeeee;"&gt;&lt;b&gt;${who}&lt;/b&gt; added entry for &lt;b&gt;${entry}&lt;/b&gt; starting at &lt;b&gt;${initial}&lt;/b&gt; and changing by &lt;b&gt;${change}&lt;/b&gt;.&lt;/div&gt;&lt;/div&gt;`); } } else { sendChat('AICT',`/w "${who}" &lt;div style="padding:1px 3px;border: 1px solid #8B4513;background: #eeffee; color: #8B4513; font-size: 80%;"&gt;&lt;div style="background-color: #ffeeee;"&gt;Use &lt;b&gt;&lt;pre&gt;!aict [formula] [starting value] --[description]&lt;/pre&gt;&lt;/b&gt;&lt;/div&gt;&lt;/div&gt;`); } } else if(msg.content.match(/^!eot/i)){ _.defer(checkFormulaOnTurn); } } }); on('change:campaign:turnorder',()=&gt;{ _.defer(checkFormulaOnTurn); }); }); {try{throw new Error('');}catch(e){API_Meta.AddInvisibleCustomTurn.lineCount=(parseInt(e.stack.split(/\n/)[1].replace(/^.*:(\d+):.*$/,'$1'),10)-API_Meta.AddInvisibleCustomTurn.offset);}} Edit 2023-10-21: Updated to work with the changes to TurnOrder
1532191922
The Aaron
Pro
API Scripter
Many thanks for that, Aaron. I take your response to mean "It's not possible with roll20's toolset, but here's a script way around it." I will also assume for my own head canon that !aict&nbsp;stands for "Aaron's Invisible Countdown Timer" ;) Thanks again.
1532272067
The Aaron
Pro
API Scripter
HAHAHAHAAH, A dd I nvisible C ustom T urn. =D&nbsp; I have another script which adds a custom turn with the same syntax named A dd C ustom T urn.&nbsp; Let me know if there are any issues with that.