ChaosCowboy

Fall.js

Sep 22nd, 2021
911
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. /*
  2. Falling
  3. A Roll20 script to indicate a falling token's number of feet below ground.
  4.  
  5. On Github:  https://github.com/blawson69
  6. Contact me: https://app.roll20.net/users/1781274/ben-l
  7.  
  8. Like this script? Become a patron:
  9.     https://www.patreon.com/benscripts
  10. */
  11.  
  12. var Falling = Falling || (function() {
  13.     'use strict';
  14.  
  15.     var version = '2.2.1',
  16.     debugMode = false,
  17.     MARKERS,
  18.     ALT_MARKERS = [{name:'red', tag: 'red', url:"#C91010"}, {name: 'blue', tag: 'blue', url: "#1076C9"}, {name: 'green', tag: 'green', url: "#2FC910"}, {name: 'brown', tag: 'brown', url: "#C97310"}, {name: 'purple', tag: 'purple', url: "#9510C9"}, {name: 'pink', tag: 'pink', url: "#EB75E1"}, {name: 'yellow', tag: 'yellow', url: "#E5EB75"}, {name: 'dead', tag: 'dead', url: "X"}],
  19.     styles = {
  20.         box:  'background-color: #fff; border: 1px solid #000; padding: 8px 10px; border-radius: 6px; margin-left: -40px; margin-right: 0px;',
  21.         title: 'padding: 0 0 10px 0; color: ##591209; font-size: 1.5em; font-weight: bold; font-variant: small-caps; font-family: "Times New Roman",Times,serif;',
  22.         button: 'background-color: #000; border-width: 0px; border-radius: 5px; padding: 5px 8px; margin: 8px 0; color: #fff; text-align: center;',
  23.         buttonWrapper: 'text-align: center; margin: 10px 0 4px; clear: both;',
  24.         textButton: 'background-color: transparent; border: none; padding: 0; color: #591209; text-decoration: underline;',
  25.         code: 'display: inline; font-family: "Courier New", Courier, monospace; background-color: #ddd; color: #000; padding: 1px 6px;',
  26.     },
  27.  
  28.     checkInstall = function () {
  29.         if (!_.has(state, 'Falling')) state['Falling'] = state['Falling'] || {};
  30.         if (typeof state['Falling'].fallMarker == 'undefined') state['Falling'].fallMarker = 'fluffy-wing';
  31.         var chatter = ['Ready for takeoff','Clear the runway','Fasten your seatbelts','Tray tables up','We may experience turbulance'];
  32.         MARKERS = JSON.parse(Campaign().get("token_markers"));
  33.         log('--> Falling v' + version + ' <-- ' + chatter[randomInteger(_.size(chatter)-1)] + '...');
  34.         if (debugMode) {
  35.             var d = new Date();
  36.             showDialog('Debug Mode', 'Falling v' + version + ' loaded at ' + d.toLocaleTimeString() + '<br><a style=\'' + styles.textButton + '\' href="!fall-config">Show config</a>', 'GM');
  37.         }
  38.     },
  39.  
  40.     handleInput = function(msg) {
  41.         if (msg.type !== "api") {
  42.             return;
  43.         }
  44.  
  45.         var parms = msg.content.split(/\s+/i);
  46.         switch (parms[0]) {
  47.             case '!fall-config':
  48.                 if (playerIsGM(msg.playerid)) showConfig();
  49.                 break;
  50.             case '!fall-markers':
  51.                 if (playerIsGM(msg.playerid)) showMarkers();
  52.                 break;
  53.             case '!fall-set':
  54.                 if (playerIsGM(msg.playerid)) {
  55.                     let marker = (parms[1]) ? parms[1] : '';
  56.                     setMarker(marker);
  57.                 }
  58.                 break;
  59.             case '!fall':
  60.                 if (!msg.selected) {
  61.                     showDialog('', 'No tokens were selected!', msg.who);
  62.                     break;
  63.                 }
  64.  
  65.                 var msgparts = msg.content.split(/\s+/), height = 0;
  66.                 if (msgparts[1]) msgparts[1] = msgparts[1].replace(/[^\d]+/,'');
  67.                 if (msgparts[1] && msgparts[1] !== 0) height = parseInt(msgparts[1]);
  68.  
  69.                 _.each(msg.selected, function(obj) {
  70.                     var token = getObj(obj._type, obj._id);
  71.                     if (token && token.get("type") === "graphic") {
  72.                         token.set('status_' + state['Falling'].fallMarker, false);
  73.                         if (height > 0) {
  74.                             var oldMarkers = token.get("statusmarkers"), newMarkers = [];
  75.                             var newHeight = height.toString().split('');
  76.  
  77.                             _.each(newHeight, function(num) {
  78.                                 newMarkers.push(state['Falling'].fallMarker + '@' + num);
  79.                             });
  80.  
  81.                             newMarkers = oldMarkers + ',' + newMarkers.join(',');
  82.                             token.set({statusmarkers: newMarkers});
  83.                         }
  84.                     }
  85.                 });
  86.         }
  87.     },
  88.  
  89.     showConfig = function () {
  90.         var marker_style = 'margin: 5px 10px 0 0; display: block; float: left;';
  91.         var message = '<span style=\'' + styles.code + '\'>!fall &lt;number&gt;</span> sets the Falling token marker on the selected token(s) with a marker for every digit. '
  92.         + 'Sending <span style=\'' + styles.code + '\'>!fall 45</span> will place one Falling marker with a "4" and another with a "5" on the token.<br><br>'
  93.         + 'No digits after <span style=\'' + styles.code + '\'>!fall</span> will "land" the token by removing all Falling markers.';
  94.  
  95.         var curr_marker = _.find(MARKERS, function (x) { return x.tag == state['Falling'].fallMarker; });
  96.         if (typeof curr_marker == 'undefined') curr_marker = _.find(ALT_MARKERS, function (x) { return x.tag == state['Falling'].fallMarker; });
  97.  
  98.         message += '<hr><h4>Falling Marker</h4>' + getMarker(curr_marker, marker_style);
  99.         if (typeof curr_marker == 'undefined') message += '<b style="color: #c00;">Warning:</b> The token marker "' + state['Falling'].fallMarker + '" is invalid!';
  100.         else message += 'This is the current Falling token marker. You may change it below.';
  101.  
  102.         message += '<div style="' + styles.buttonWrapper + '"><a style="' + styles.button + '" href="!fall-markers" title="This may result in a very long list...">Choose Marker</a></div>';
  103.         message += '<div style="text-align: center;"><a style="' + styles.textButton + '" href="!fall-set &#63;&#123;Token Marker&#124;&#125;">Set manually</a></div>';
  104.  
  105.         showDialog('Help Menu', message);
  106.     },
  107.  
  108.     showMarkers = function () {
  109.         var message = '<table style="border: 0; width: 100%;" cellpadding="0" cellspacing="2">';
  110.         _.each(ALT_MARKERS, function (marker) {
  111.             message += '<tr><td style="height: 24px;">' + getMarker(marker, 'margin-right: 10px;') + '</td><td style="white-space: nowrap; width: 100%;">' + marker.name + '</td>';
  112.             if (marker.tag == state['Falling'].fallMarker) {
  113.                 message += '<td style="text-align: center;">Current</td>';
  114.             } else {
  115.                 message += '<td style="text-align: center; white-space: nowrap; padding: 2px;"><a style="' + styles.button + '" href="!fall-set ' + marker.tag + '">Set Marker</a></td>';
  116.             }
  117.             message += '</tr>';
  118.         });
  119.  
  120.         _.each(MARKERS, function (icon) {
  121.             message += '<tr><td style="height: 24px;">' + getMarker(icon, 'margin-right: 10px;') + '</td><td style="white-space: nowrap; width: 100%;">' + icon.name + '</td>';
  122.             if (icon.tag == state['Falling'].fallMarker) {
  123.                 message += '<td style="text-align: center;">Current</td>';
  124.             } else {
  125.                 message += '<td style="text-align: center; white-space: nowrap; padding: 2px;"><a style="' + styles.button + '" href="!fall-set ' + icon.tag.replace('::','=') + '">Set Marker</a></td>';
  126.             }
  127.             message += '</tr>';
  128.         });
  129.  
  130.         message += '<tr><td colspan="3" style="text-align: center; padding: 7px;"><a style="' + styles.button + '" href="!fall-config">&#9668; Back</a></td></tr>';
  131.         message += '</table>';
  132.  
  133.         showDialog('Choose Falling Marker', message);
  134.     },
  135.  
  136.     setMarker = function (marker) {
  137.         marker = marker.replace('=', '::');
  138.         var status_markers = _.pluck(MARKERS, 'tag');
  139.         _.each(_.pluck(ALT_MARKERS, 'tag'), function (x) { status_markers.push(x); });
  140.         if (_.find(status_markers, function (tmp) {return tmp === marker; })) {
  141.             state['Falling'].fallMarker = marker;
  142.         } else {
  143.             showDialog('Error', 'The token marker "' + marker + '" is invalid. Please try again.');
  144.         }
  145.  
  146.         showConfig();
  147.     },
  148.  
  149.     getMarker = function (marker, style = '') {
  150.         var marker_style = 'width: 24px; height: 24px;' + style;
  151.         var return_marker = '<img src="" width="24" height="24" style="' + marker_style + ' border: 1px solid #ccc;" alt=" " />';
  152.         if (typeof marker != 'undefined' && typeof marker.tag != 'undefined') {
  153.             var status_markers = _.pluck(MARKERS, 'tag'),
  154.             alt_marker = _.find(ALT_MARKERS, function (x) { return x.tag == marker.tag; });
  155.  
  156.             if (_.find(status_markers, function (x) { return x == marker.tag; })) {
  157.                 var icon = _.find(MARKERS, function (x) { return x.tag == marker.tag; });
  158.                 return_marker = '<img src="' + icon.url + '" width="24" height="24" style="' + marker_style + '" />';
  159.             } else if (typeof alt_marker !== 'undefined') {
  160.                 if (alt_marker.url === 'X') {
  161.                     marker_style += 'color: #C91010; font-size: 30px; line-height: 24px; font-weight: bold; text-align: center; padding-top: 0px; overflow: hidden;';
  162.                     return_marker = '<div style="' + marker_style + '">X</div>';
  163.                 } else {
  164.                     marker_style += 'background-color: ' + alt_marker.url + '; border: 1px solid #fff; border-radius: 50%;';
  165.                     return_marker = '<div style="' + marker_style + '"></div>';
  166.                 }
  167.             }
  168.         }
  169.         return return_marker;
  170.     },
  171.  
  172.     showDialog = function (title, content, whom = 'GM') {
  173.         var whisperTo = '', gm = /\(GM\)/i;
  174.         whisperTo = (gm.test(whom)) ? 'GM' : '"' + whom + '" ';
  175.  
  176.         title = (title == '') ? '' : '<div style=\'' + styles.title + '\'>' + title + '</div>';
  177.         var body = '<div style=\'' + styles.box + '\'>' + title + '<div>' + content + '</div></div>';
  178.         sendChat('Falling','/w GM ' + whisperTo + body, null, {noarchive:true});
  179.     },
  180.  
  181.     registerEventHandlers = function() {
  182.         on('chat:message', handleInput);
  183.     };
  184.  
  185.     return {
  186.         CheckInstall: checkInstall,
  187.         RegisterEventHandlers: registerEventHandlers
  188.     };
  189.  
  190. }());
  191.  
  192. on("ready",function(){
  193.     'use strict';
  194.     Falling.CheckInstall();
  195.     Falling.RegisterEventHandlers();
  196. });
RAW Paste Data