Add description ranges/outcomes
This commit is contained in:
		
							
								
								
									
										6
									
								
								src/constants.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								src/constants.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,6 @@ | |||||||
|  | const constants = { | ||||||
|  | rollRegex: /^(\d+)?([dhl])(\d+)(\s*([+\-*x\/])\s*(\d+))?/, | ||||||
|  | descriptionRegex: /\s*(\d+(-\d+)?)?([^;\n]+)/g | ||||||
|  | } | ||||||
|  |  | ||||||
|  | export default constants | ||||||
							
								
								
									
										72
									
								
								src/index.js
									
									
									
									
									
								
							
							
						
						
									
										72
									
								
								src/index.js
									
									
									
									
									
								
							| @@ -1,43 +1,81 @@ | |||||||
| import { Client, GatewayIntentBits } from 'discord.js'; | import { Client, GatewayIntentBits } from 'discord.js'; | ||||||
| import * as dotenv from 'dotenv' | import * as dotenv from 'dotenv' | ||||||
|  | import constants from './constants.js'; | ||||||
| dotenv.config() | dotenv.config() | ||||||
|  |  | ||||||
| const regex = /^(\d+)?([dhl])(\d+)(\s*([+\-*x\/])\s*(\d+))?(.*?)$/ |  | ||||||
|  |  | ||||||
| const replies = new Map() | const replies = new Map() | ||||||
|  |  | ||||||
| const parseMatch = match => { | const parseRoll = content => { | ||||||
|  |   let match = constants.rollRegex.exec(content.trim()) | ||||||
|  |  | ||||||
|  |   if(match == null) | ||||||
|  |     return | ||||||
|  |  | ||||||
|   let [ |   let [ | ||||||
|     count, |     count, | ||||||
|     mode, |     mode, | ||||||
|     size, |     size, | ||||||
|     modifierString, |     modifierString, | ||||||
|     operation, |     operation, | ||||||
|     modifier, |     modifier | ||||||
|     description |  | ||||||
|   ] = match.slice(1) |   ] = match.slice(1) | ||||||
|  |  | ||||||
|  |   let description = content.slice(match[0].length) | ||||||
|  |  | ||||||
|   return { |   return { | ||||||
|     count: count ? parseInt(count) : 1, |     count: count ? parseInt(count) : 1, | ||||||
|     mode, |     mode, | ||||||
|     size: parseInt(size), |     size: parseInt(size), | ||||||
|     operation, |     operation, | ||||||
|     modifier: modifier ? parseInt(modifier) : undefined, |     modifier: modifier ? parseInt(modifier) : undefined, | ||||||
|     description: description.trim() |     descriptionConditions: description && parseDescription(description) | ||||||
|   } |   } | ||||||
| } | } | ||||||
|  |  | ||||||
|  | const parseDescription = description => { | ||||||
|  |   let conditions = [], | ||||||
|  |       match | ||||||
|  |  | ||||||
|  |   while((match = constants.descriptionRegex.exec(description)) !== null) { | ||||||
|  |     // Prevent infinite loops if there's somehow a zero-length match | ||||||
|  |     if(match.index == constants.descriptionRegex.lastIndex) | ||||||
|  |       regex.lastIndex++ | ||||||
|  |  | ||||||
|  |     let [ | ||||||
|  |       range, | ||||||
|  |       upperRange, | ||||||
|  |       content | ||||||
|  |     ] = match.slice(1) | ||||||
|  |  | ||||||
|  |     conditions.push({ | ||||||
|  |       range: range && { | ||||||
|  |         lower: range[0], | ||||||
|  |         upper: upperRange ? upperRange[1] : range[0] | ||||||
|  |       }, | ||||||
|  |       content: content.trim() | ||||||
|  |     }) | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   return conditions | ||||||
|  | } | ||||||
|  |  | ||||||
| const handleMessage = (message, respond) => { | const handleMessage = (message, respond) => { | ||||||
|   let match = regex.exec(message.content.trim()) |   let dice = parseRoll(message.content) | ||||||
|  |  | ||||||
|   if(match == null) |   if(dice == undefined) | ||||||
|     return |     return // No dice | ||||||
|  |  | ||||||
|   let dice = parseMatch(match) |   if(dice.size > 255) { | ||||||
|  |  | ||||||
|   if(dice.size > 256) { |  | ||||||
|     respond('That die is way too big... .-.') |     respond('That die is way too big... .-.') | ||||||
|     return |     return | ||||||
|  |   } else if(dice.size < 2) { | ||||||
|  |     respond('I cannot even fathom a die with that geometry ;-;') | ||||||
|  |     return | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   if(dice.count > 100) { | ||||||
|  |     respond('I don\'t have that many dice O_O') | ||||||
|  |     return | ||||||
|   } |   } | ||||||
|  |  | ||||||
|   let rolls = [ ...crypto.getRandomValues(new Uint8Array(dice.count) ) ] |   let rolls = [ ...crypto.getRandomValues(new Uint8Array(dice.count) ) ] | ||||||
| @@ -80,8 +118,12 @@ const handleMessage = (message, respond) => { | |||||||
|       break |       break | ||||||
|   } |   } | ||||||
|  |  | ||||||
|   if(dice.description) |   if(dice.descriptionConditions) { | ||||||
|     response += `'${dice.description}', ` |     for(let { range, content } of dice.descriptionConditions) { | ||||||
|  |       if(!range || result >= range.lower && result <= range.upper) | ||||||
|  |         response += `'${content}', ` | ||||||
|  |     } | ||||||
|  |   } | ||||||
|    |    | ||||||
|   response += `\` ${result} \` \u27F5 [${rolls.join(', ')}] ${dice.count + dice.mode + dice.size}` |   response += `\` ${result} \` \u27F5 [${rolls.join(', ')}] ${dice.count + dice.mode + dice.size}` | ||||||
|  |  | ||||||
| @@ -142,7 +184,7 @@ client.on('messageUpdate', async (oldMessage, newMessage) => { | |||||||
|  |  | ||||||
|     newMessage.channel.messages.fetch(id) |     newMessage.channel.messages.fetch(id) | ||||||
|       .then(reply => rehandleMessage(newMessage, reply) ) |       .then(reply => rehandleMessage(newMessage, reply) ) | ||||||
|       .catch(err => messageCycle(newMessage, ) ) |       .catch(err => messageCycle(newMessage) ) | ||||||
|   } else { |   } else { | ||||||
|     messageCycle(newMessage) |     messageCycle(newMessage) | ||||||
|   } |   } | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user