{ "version": 3, "sources": ["../../../../server/chat-commands/info.ts"], "sourcesContent": ["/**\r\n * Informational Commands\r\n * Pokemon Showdown - https://pokemonshowdown.com/\r\n *\r\n * These are informational commands. For instance, you can define the command\r\n * 'whois' here, then use it by typing /whois into Pokemon Showdown.\r\n * For the API, see chat-plugins/COMMANDS.md\r\n *\r\n * @license MIT\r\n */\r\nimport * as net from 'net';\r\nimport {YouTube, Twitch} from '../chat-plugins/youtube';\r\nimport {Net, Utils} from '../../lib';\r\nimport {RoomSections} from './room-settings';\r\n\r\nconst ONLINE_SYMBOL = ` \\u25C9 `;\r\nconst OFFLINE_SYMBOL = ` \\u25CC `;\r\n\r\nexport function getCommonBattles(\r\n\tuserID1: ID, user1: User | null, userID2: ID, user2: User | null, connection: Connection\r\n) {\r\n\tconst battles = [];\r\n\tfor (const curRoom of Rooms.rooms.values()) {\r\n\t\tif (!curRoom.battle) continue;\r\n\t\tif (\r\n\t\t\t(user1?.inRooms.has(curRoom.roomid) || curRoom.auth.get(userID1) === Users.PLAYER_SYMBOL) &&\r\n\t\t\t(user2?.inRooms.has(curRoom.roomid) || curRoom.auth.get(userID2) === Users.PLAYER_SYMBOL)\r\n\t\t) {\r\n\t\t\tif (connection) {\r\n\t\t\t\tvoid curRoom.uploadReplay(connection.user, connection, \"forpunishment\");\r\n\t\t\t}\r\n\t\t\tbattles.push(curRoom.roomid);\r\n\t\t}\r\n\t}\r\n\treturn battles;\r\n}\r\n\r\nexport function findFormats(targetId: string, isOMSearch = false) {\r\n\tconst exactFormat = Dex.formats.get(targetId);\r\n\r\n\tconst formatList = exactFormat.exists ? [exactFormat] : Dex.formats.all();\r\n\r\n\t// Filter formats and group by section\r\n\tconst sections: {[k: string]: {name: string, formats: ID[]}} = {};\r\n\tlet totalMatches = 0;\r\n\tfor (const format of formatList) {\r\n\t\tconst sectionId = toID(format.section);\r\n\t\t// Skip generation prefix if it wasn't provided\r\n\t\tconst formatId = /^gen\\d+/.test(targetId) ? format.id : format.id.slice(4);\r\n\t\tif (\r\n\t\t\t!targetId || format[targetId + 'Show' as 'searchShow'] || sectionId === targetId ||\r\n\t\t\tformatId.startsWith(targetId) || exactFormat.exists\r\n\t\t) {\r\n\t\t\tif (isOMSearch) {\r\n\t\t\t\tconst officialFormats = [\r\n\t\t\t\t\t'ou', 'uu', 'ru', 'nu', 'pu', 'ubers', 'lc', 'monotype', 'customgame', 'doublescustomgame', 'gbusingles', 'gbudoubles',\r\n\t\t\t\t];\r\n\t\t\t\tif (format.id.startsWith('gen') && officialFormats.includes(format.id.slice(4))) {\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\ttotalMatches++;\r\n\t\t\tif (!sections[sectionId]) sections[sectionId] = {name: format.section!, formats: []};\r\n\t\t\tsections[sectionId].formats.push(format.id);\r\n\t\t}\r\n\t}\r\n\treturn {totalMatches, sections};\r\n}\r\n\r\nexport const commands: Chat.ChatCommands = {\r\n\tip: 'whois',\r\n\trooms: 'whois',\r\n\talt: 'whois',\r\n\talts: 'whois',\r\n\twhoare: 'whois',\r\n\taltsnorecurse: 'whois',\r\n\tprofile: 'whois',\r\n\twhois(target, room, user, connection, cmd) {\r\n\t\tif (room?.roomid === 'staff' && !this.runBroadcast()) return;\r\n\t\tconst targetUser = this.getUserOrSelf(target, {exactName: user.tempGroup === ' '});\r\n\t\tconst showAll = (cmd === 'ip' || cmd === 'whoare' || cmd === 'alt' || cmd === 'alts' || cmd === 'altsnorecurse');\r\n\t\tconst showRecursiveAlts = showAll && (cmd !== 'altsnorecurse');\r\n\t\tif (!targetUser) {\r\n\t\t\tif (showAll) return this.parse('/offlinewhois ' + target);\r\n\t\t\treturn this.errorReply(`User ${target} not found.`);\r\n\t\t}\r\n\t\tif (showAll && !user.trusted && targetUser !== user) {\r\n\t\t\treturn this.errorReply(`/${cmd} - Access denied.`);\r\n\t\t}\r\n\r\n\t\tlet buf = Utils.html`${targetUser.tempGroup}${targetUser.name} `;\r\n\t\tconst ac = targetUser.autoconfirmed;\r\n\t\tif (ac && showAll) {\r\n\t\t\tbuf += ` (ac${targetUser.id === ac ? `` : `: ${ac}`})`;\r\n\t\t}\r\n\t\tconst trusted = targetUser.trusted;\r\n\t\tif (trusted && showAll) {\r\n\t\t\tbuf += ` (trusted${targetUser.id === trusted ? `` : `: ${trusted}`})`;\r\n\t\t}\r\n\t\tif (!targetUser.connected) buf += ` (offline)`;\r\n\t\tconst roomauth = room?.auth.getDirect(targetUser.id);\r\n\t\tif (roomauth && Config.groups[roomauth]?.name) {\r\n\t\t\tbuf += Utils.html`
${Config.groups[roomauth].name} (${roomauth})`;\r\n\t\t}\r\n\t\tif (Config.groups[targetUser.tempGroup]?.name) {\r\n\t\t\tbuf += Utils.html`
Global ${Config.groups[targetUser.tempGroup].name} (${targetUser.tempGroup})`;\r\n\t\t}\r\n\t\tif (Users.globalAuth.sectionLeaders.has(targetUser.id)) {\r\n\t\t\tbuf += Utils.html`
Section Leader (${RoomSections.sectionNames[Users.globalAuth.sectionLeaders.get(targetUser.id)!]})`;\r\n\t\t}\r\n\t\tif (targetUser.isSysop) {\r\n\t\t\tbuf += `
(Pokémon Showdown System Operator)`;\r\n\t\t}\r\n\t\tif (!targetUser.registered) {\r\n\t\t\tbuf += `
(Unregistered)`;\r\n\t\t}\r\n\t\tlet publicrooms = ``;\r\n\t\tlet hiddenrooms = ``;\r\n\t\tlet privaterooms = ``;\r\n\t\tfor (const roomid of targetUser.inRooms) {\r\n\t\t\tconst targetRoom = Rooms.get(roomid)!;\r\n\r\n\t\t\tconst authSymbol = targetRoom.auth.getDirect(targetUser.id).trim();\r\n\t\t\tconst battleTitle = (targetRoom.battle ? ` title=\"${targetRoom.title}\"` : '');\r\n\t\t\tconst output = `${authSymbol}${roomid}`;\r\n\t\t\tif (targetRoom.settings.isPrivate === true) {\r\n\t\t\t\tif (targetRoom.settings.modjoin === '~') continue;\r\n\t\t\t\tif (privaterooms) privaterooms += ` | `;\r\n\t\t\t\tprivaterooms += output;\r\n\t\t\t} else if (targetRoom.settings.isPrivate) {\r\n\t\t\t\tif (hiddenrooms) hiddenrooms += ` | `;\r\n\t\t\t\thiddenrooms += output;\r\n\t\t\t} else {\r\n\t\t\t\tif (publicrooms) publicrooms += ` | `;\r\n\t\t\t\tpublicrooms += output;\r\n\t\t\t}\r\n\t\t}\r\n\t\tbuf += `
Rooms: ${publicrooms || `(no public rooms)`}`;\r\n\r\n\t\tif (!showAll) {\r\n\t\t\treturn this.sendReplyBox(buf);\r\n\t\t}\r\n\t\tconst canViewAlts = (user === targetUser ? user.can('altsself') : user.can('alts', targetUser));\r\n\t\tconst canViewPunishments = canViewAlts ||\r\n\t\t\t(room && room.settings.isPrivate !== true && user.can('mute', targetUser, room) && targetUser.id in room.users);\r\n\t\tconst canViewSecretRooms = user === targetUser || (canViewAlts && targetUser.locked) || user.can('makeroom');\r\n\t\tbuf += `
`;\r\n\r\n\t\tif (canViewAlts) {\r\n\t\t\tlet prevNames = targetUser.previousIDs.map(userid => {\r\n\t\t\t\tconst punishments = Punishments.userids.get(userid);\r\n\t\t\t\tif (!punishments || !user.can('alts')) return userid;\r\n\t\t\t\treturn punishments.map(\r\n\t\t\t\t\tpunishment => (\r\n\t\t\t\t\t\t`${userid}${punishment ? ` (${Punishments.punishmentTypes.get(punishment.type)?.desc || `punished`}` +\r\n\t\t\t\t\t\t`${punishment.id !== targetUser.id ? ` as ${punishment.id}` : ``})` : ``}`\r\n\t\t\t\t\t)\r\n\t\t\t\t).join(' | ');\r\n\t\t\t}).join(\", \");\r\n\t\t\tif (prevNames) buf += Utils.html`
Previous names: ${prevNames}`;\r\n\r\n\t\t\tfor (const targetAlt of targetUser.getAltUsers(true)) {\r\n\t\t\t\tif (!targetAlt.named && !targetAlt.connected) continue;\r\n\t\t\t\tif (targetAlt.tempGroup === '~' && user.tempGroup !== '~') continue;\r\n\r\n\t\t\t\tconst punishments = Punishments.userids.get(targetAlt.id) || [];\r\n\t\t\t\tconst punishMsg = !user.can('alts') ? '' : punishments.map(punishment => (\r\n\t\t\t\t\t` (${Punishments.punishmentTypes.get(punishment.type)?.desc || 'punished'}` +\r\n\t\t\t\t\t`${punishment.id !== targetAlt.id ? ` as ${punishment.id}` : ''})`\r\n\t\t\t\t)).join(' | ');\r\n\t\t\t\tbuf += Utils.html`
Alt: ${targetAlt.name}${punishMsg}`;\r\n\t\t\t\tif (!targetAlt.connected) buf += ` (offline)`;\r\n\t\t\t\tprevNames = targetAlt.previousIDs.map(userid => {\r\n\t\t\t\t\tconst p = Punishments.userids.get(userid);\r\n\t\t\t\t\tif (!p || !user.can('alts')) return userid;\r\n\t\t\t\t\treturn p.map(\r\n\t\t\t\t\t\tcur => `${userid} (${Punishments.punishmentTypes.get(cur.type)?.desc || 'punished'}` + `${cur.id !== targetAlt.id ? ` as ${cur.id}` : ``})`\r\n\t\t\t\t\t).join(' | ');\r\n\t\t\t\t}).join(\", \");\r\n\t\t\t\tif (prevNames) buf += `
Previous names: ${prevNames}`;\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (canViewPunishments) {\r\n\t\t\tif (targetUser.namelocked) {\r\n\t\t\t\tbuf += `
NAMELOCKED: ${targetUser.namelocked}`;\r\n\t\t\t\tconst punishment = Punishments.userids.getByType(targetUser.locked!, 'NAMELOCK');\r\n\t\t\t\tif (punishment) {\r\n\t\t\t\t\tconst expiresIn = Punishments.checkLockExpiration(targetUser.locked);\r\n\t\t\t\t\tif (expiresIn) buf += expiresIn;\r\n\t\t\t\t\tif (punishment.reason) buf += Utils.html` (reason: ${punishment.reason})`;\r\n\t\t\t\t}\r\n\t\t\t} else if (targetUser.locked) {\r\n\t\t\t\tbuf += `
LOCKED: ${targetUser.locked}`;\r\n\t\t\t\tswitch (targetUser.locked) {\r\n\t\t\t\tcase '#rangelock':\r\n\t\t\t\t\tbuf += ` - IP or host is in a temporary range-lock`;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase '#hostfilter':\r\n\t\t\t\t\tbuf += ` - host is permanently locked for being a proxy`;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t\tconst punishment = Punishments.userids.getByType(targetUser.locked, 'LOCK');\r\n\t\t\t\tif (punishment) {\r\n\t\t\t\t\tconst expiresIn = Punishments.checkLockExpiration(targetUser.locked);\r\n\t\t\t\t\tif (expiresIn) buf += expiresIn;\r\n\t\t\t\t\tif (punishment.reason) buf += Utils.html` (reason: ${punishment.reason})`;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (user.can('lock')) {\r\n\t\t\t\tconst battlebanned = Punishments.isBattleBanned(targetUser);\r\n\t\t\t\tif (battlebanned) {\r\n\t\t\t\t\tbuf += `
BATTLEBANNED: ${battlebanned.id}`;\r\n\t\t\t\t\tbuf += ` ${Punishments.checkPunishmentExpiration(battlebanned)}`;\r\n\t\t\t\t\tif (battlebanned.reason) buf += Utils.html` (reason: ${battlebanned.reason})`;\r\n\t\t\t\t}\r\n\r\n\t\t\t\tconst groupchatbanned = Punishments.isGroupchatBanned(targetUser);\r\n\t\t\t\tif (groupchatbanned) {\r\n\t\t\t\t\tbuf += `
Banned from using groupchats${groupchatbanned.id !== targetUser.id ? `: ${groupchatbanned.id}` : ``}`;\r\n\t\t\t\t\tbuf += ` ${Punishments.checkPunishmentExpiration(groupchatbanned)}`;\r\n\t\t\t\t\tif (groupchatbanned.reason) buf += Utils.html` (reason: ${groupchatbanned.reason})`;\r\n\t\t\t\t}\r\n\r\n\t\t\t\tconst ticketbanned = Punishments.isTicketBanned(targetUser.id);\r\n\t\t\t\tif (ticketbanned) {\r\n\t\t\t\t\tbuf += `
Banned from creating help tickets${ticketbanned.id !== targetUser.id ? `: ${ticketbanned.id}` : ``}`;\r\n\t\t\t\t\tbuf += ` ${Punishments.checkPunishmentExpiration(ticketbanned)}`;\r\n\t\t\t\t\tif (ticketbanned.reason) buf += Utils.html` (reason: ${ticketbanned.reason})`;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (targetUser.semilocked) {\r\n\t\t\t\tbuf += `
Semilocked: ${user.can('lock') ? targetUser.semilocked : \"(reason hidden)\"}`;\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (user === targetUser ? user.can('ipself') : user.can('ip', targetUser)) {\r\n\t\t\tconst ips = targetUser.ips.map(ip => {\r\n\t\t\t\tconst status = [];\r\n\t\t\t\tconst punishments = Punishments.ips.get(ip);\r\n\t\t\t\tif (user.can('alts') && punishments) {\r\n\t\t\t\t\tfor (const punishment of punishments) {\r\n\t\t\t\t\t\tconst {type, id} = punishment;\r\n\t\t\t\t\t\tlet punishMsg = Punishments.punishmentTypes.get(type)?.desc || type;\r\n\t\t\t\t\t\tif (id !== targetUser.id) punishMsg += ` as ${id}`;\r\n\t\t\t\t\t\tstatus.push(punishMsg);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tif (Punishments.isSharedIp(ip)) {\r\n\t\t\t\t\tlet sharedStr = 'shared';\r\n\t\t\t\t\tif (Punishments.sharedIps.get(ip)) {\r\n\t\t\t\t\t\tsharedStr += `: ${Punishments.sharedIps.get(ip)}`;\r\n\t\t\t\t\t}\r\n\t\t\t\t\tstatus.push(sharedStr);\r\n\t\t\t\t}\r\n\t\t\t\treturn `${ip}` + (status.length ? ` (${status.join('; ')})` : '');\r\n\t\t\t});\r\n\t\t\tbuf += `
IP${Chat.plural(ips)}: ${ips.join(\", \")}`;\r\n\t\t\tif (user.tempGroup !== ' ' && targetUser.latestHost) {\r\n\t\t\t\tbuf += Utils.html`
Host: ${targetUser.latestHost} [${targetUser.latestHostType}]`;\r\n\t\t\t}\r\n\t\t} else if (user === targetUser) {\r\n\t\t\tbuf += `
IP: ${connection.ip}`;\r\n\t\t}\r\n\t\tif ((user === targetUser || canViewAlts) && hiddenrooms) {\r\n\t\t\tbuf += `
Hidden rooms: ${hiddenrooms}`;\r\n\t\t}\r\n\t\tif (canViewSecretRooms && privaterooms) {\r\n\t\t\tbuf += `
Secret rooms: ${privaterooms}`;\r\n\t\t}\r\n\r\n\t\tconst gameRooms = [];\r\n\t\tfor (const curRoom of Rooms.rooms.values()) {\r\n\t\t\tif (!curRoom.game) continue;\r\n\t\t\tconst inPlayerTable = targetUser.id in curRoom.game.playerTable && !targetUser.inRooms.has(curRoom.roomid);\r\n\t\t\tconst hasPlayerSymbol = curRoom.auth.getDirect(targetUser.id) === Users.PLAYER_SYMBOL;\r\n\t\t\tconst canSeeRoom = canViewAlts || user === targetUser || !curRoom.settings.isPrivate;\r\n\r\n\t\t\tif ((inPlayerTable || hasPlayerSymbol) && canSeeRoom) {\r\n\t\t\t\tgameRooms.push(curRoom.roomid);\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (gameRooms.length) {\r\n\t\t\tbuf += `
Recent games: ${gameRooms.map(id => {\r\n\t\t\t\tconst shortId = id.startsWith('battle-') ? id.slice(7) : id;\r\n\t\t\t\treturn Utils.html`${shortId}`;\r\n\t\t\t}).join(' | ')}`;\r\n\t\t}\r\n\r\n\t\tif (canViewPunishments) {\r\n\t\t\tconst punishments = Punishments.getRoomPunishments(targetUser, {checkIps: true});\r\n\r\n\t\t\tif (punishments.length) {\r\n\t\t\t\tbuf += `
Room punishments: `;\r\n\r\n\t\t\t\tbuf += punishments.map(([curRoom, curPunishment]) => {\r\n\t\t\t\t\tconst {type: punishType, id: punishUserid, expireTime, reason} = curPunishment;\r\n\t\t\t\t\tlet punishDesc = Punishments.roomPunishmentTypes.get(punishType)?.desc || punishType;\r\n\t\t\t\t\tif (punishUserid !== targetUser.id) punishDesc += ` as ${punishUserid}`;\r\n\t\t\t\t\tconst expiresIn = new Date(expireTime).getTime() - Date.now();\r\n\t\t\t\t\tconst expireString = Chat.toDurationString(expiresIn, {precision: 1});\r\n\t\t\t\t\tpunishDesc += ` for ${expireString}`;\r\n\r\n\t\t\t\t\tif (reason) punishDesc += `: ${reason}`;\r\n\t\t\t\t\treturn `${curRoom} (${punishDesc})`;\r\n\t\t\t\t}).join(', ');\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.sendReplyBox(buf);\r\n\r\n\t\tif (showRecursiveAlts && canViewAlts) {\r\n\t\t\tconst targetId = toID(target);\r\n\t\t\tfor (const alt of Users.users.values()) {\r\n\t\t\t\tif (alt !== targetUser && alt.previousIDs.includes(targetId)) {\r\n\t\t\t\t\tvoid this.parse(`/altsnorecurse ${alt.name}`);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t},\r\n\twhoishelp: [\r\n\t\t`/whois - Get details on yourself: alts, group, IP address, and rooms.`,\r\n\t\t`/whois [username] - Get details on a username: alts (Requires: % @ &), group, IP address (Requires: @ &), and rooms.`,\r\n\t],\r\n\r\n\t'chp': 'offlinewhois',\r\n\tcheckpunishment: 'offlinewhois',\r\n\tofflinewhois(target, room, user) {\r\n\t\tif (!user.trusted) {\r\n\t\t\treturn this.errorReply(\"/offlinewhois - Access denied.\");\r\n\t\t}\r\n\t\tconst userid = toID(target);\r\n\t\tif (!userid) return this.errorReply(\"Please enter a valid username.\");\r\n\t\tconst targetUser = Users.get(userid);\r\n\t\tlet buf = Utils.html`${target}`;\r\n\t\tif (!targetUser?.connected) buf += ` (offline)`;\r\n\r\n\t\tconst roomauth = room?.auth.getDirect(userid);\r\n\t\tif (roomauth && Config.groups[roomauth]?.name) {\r\n\t\t\tbuf += `
${Config.groups[roomauth].name} (${roomauth})`;\r\n\t\t}\r\n\t\tconst group = Users.globalAuth.get(userid);\r\n\t\tif (Config.groups[group]?.name) {\r\n\t\t\tbuf += `
Global ${Config.groups[group].name} (${group})`;\r\n\t\t}\r\n\t\tif (Users.globalAuth.sectionLeaders.has(userid)) {\r\n\t\t\tbuf += `
Section Leader (${RoomSections.sectionNames[Users.globalAuth.sectionLeaders.get(userid)!]})`;\r\n\t\t}\r\n\r\n\t\tbuf += `

`;\r\n\t\tlet atLeastOne = false;\r\n\r\n\t\tconst idPunishments = Punishments.userids.get(userid);\r\n\t\tif (idPunishments) {\r\n\t\t\tfor (const p of idPunishments) {\r\n\t\t\t\tconst {type: punishType, id: punishUserid, reason} = p;\r\n\t\t\t\tif (!user.can('alts') && !['LOCK', 'BAN'].includes(punishType)) continue;\r\n\t\t\t\tconst punishDesc = (Punishments.punishmentTypes.get(punishType)?.desc || punishType);\r\n\t\t\t\tbuf += `${punishDesc}: ${punishUserid}`;\r\n\t\t\t\tconst expiresIn = Punishments.checkLockExpiration(userid);\r\n\t\t\t\tif (expiresIn) buf += expiresIn;\r\n\t\t\t\tif (reason) buf += Utils.html` (reason: ${reason})`;\r\n\t\t\t\tbuf += '
';\r\n\t\t\t\tatLeastOne = true;\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (!user.can('alts') && !atLeastOne) {\r\n\t\t\tconst hasJurisdiction = room && user.can('mute', null, room) && Punishments.roomUserids.nestedHas(room.roomid, userid);\r\n\t\t\tif (!hasJurisdiction) {\r\n\t\t\t\treturn this.errorReply(\"/checkpunishment - User not found.\");\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tconst punishments = Punishments.getRoomPunishments(targetUser || {id: userid} as User);\r\n\r\n\t\tif (punishments?.length) {\r\n\t\t\tbuf += `
Room punishments: `;\r\n\r\n\t\t\tbuf += punishments.map(([curRoom, curPunishment]) => {\r\n\t\t\t\tconst {type: punishType, id: punishUserid, expireTime, reason} = curPunishment;\r\n\t\t\t\tlet punishDesc = Punishments.roomPunishmentTypes.get(punishType)?.desc || punishType;\r\n\t\t\t\tif (punishUserid !== userid) punishDesc += ` as ${punishUserid}`;\r\n\t\t\t\tconst expiresIn = new Date(expireTime).getTime() - Date.now();\r\n\t\t\t\tconst expireString = Chat.toDurationString(expiresIn, {precision: 1});\r\n\t\t\t\tpunishDesc += ` for ${expireString}`;\r\n\r\n\t\t\t\tif (reason) punishDesc += `: ${reason}`;\r\n\t\t\t\treturn `${curRoom} (${punishDesc})`;\r\n\t\t\t}).join(', ');\r\n\t\t\tatLeastOne = true;\r\n\t\t}\r\n\t\tif (!atLeastOne) {\r\n\t\t\tbuf += `This username has no punishments associated with it.`;\r\n\t\t}\r\n\t\tthis.sendReplyBox(buf);\r\n\t},\r\n\tofflinewhoishelp: [\r\n\t\t`/offlinewhois [username] - Get details on a username without requiring them to be online.`,\r\n\t\t`Requires: trusted user. `,\r\n\t],\r\n\r\n\tsbtl: 'sharedbattles',\r\n\tsharedbattles(target, room) {\r\n\t\tthis.checkCan('lock');\r\n\r\n\t\tconst [targetUsername1, targetUsername2] = target.split(',');\r\n\t\tif (!targetUsername1 || !targetUsername2) return this.parse(`/help sharedbattles`);\r\n\t\tconst user1 = Users.get(targetUsername1);\r\n\t\tconst user2 = Users.get(targetUsername2);\r\n\t\tconst userID1 = toID(targetUsername1);\r\n\t\tconst userID2 = toID(targetUsername2);\r\n\r\n\t\tconst battles = getCommonBattles(userID1, user1, userID2, user2, this.connection);\r\n\r\n\t\tif (!battles.length) return this.sendReply(`${targetUsername1} and ${targetUsername2} have no common battles.`);\r\n\r\n\t\tthis.sendReplyBox(Utils.html`Common battles between ${targetUsername1} and ${targetUsername2}:
` + battles.map(id => {\r\n\t\t\tconst shortId = id.startsWith('battle-') ? id.slice(7) : id;\r\n\t\t\treturn Utils.html`${shortId}`;\r\n\t\t}).join(' | '));\r\n\t},\r\n\tsharedbattleshelp: [`/sharedbattles [user1], [user2] - Finds recent battles common to [user1] and [user2]. Requires % @ &`],\r\n\r\n\tsp: 'showpunishments',\r\n\tshowpunishments(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tif (!room.persist) {\r\n\t\t\treturn this.errorReply(\"This command is unavailable in temporary rooms.\");\r\n\t\t}\r\n\t\treturn this.parse(`/join view-punishments-${room}`);\r\n\t},\r\n\tshowpunishmentshelp: [`/showpunishments - Shows the current punishments in the room. Requires: % @ # &`],\r\n\r\n\tsgp: 'showglobalpunishments',\r\n\tshowglobalpunishments(target, room, user) {\r\n\t\tthis.checkCan('lock');\r\n\t\treturn this.parse(`/join view-globalpunishments`);\r\n\t},\r\n\tshowglobalpunishmentshelp: [`/showpunishments - Shows the current global punishments. Requires: % @ # &`],\r\n\r\n\tasync host(target, room, user, connection, cmd) {\r\n\t\tif (!target) return this.parse('/help host');\r\n\t\tthis.checkCan('alts');\r\n\t\ttarget = target.trim();\r\n\t\tif (!net.isIPv4(target)) return this.errorReply('You must pass a valid IPv4 IP to /host.');\r\n\t\tconst {dnsbl, host, hostType} = await IPTools.lookup(target);\r\n\t\tconst dnsblMessage = dnsbl ? ` [${dnsbl}]` : ``;\r\n\t\tthis.sendReply(`IP ${target}: ${host || \"ERROR\"} [${hostType}]${dnsblMessage}`);\r\n\t},\r\n\thosthelp: [`/host [ip] - Gets the host for a given IP. Requires: % @ &`],\r\n\r\n\tsearchip: 'ipsearch',\r\n\tipsearchall: 'ipsearch',\r\n\thostsearch: 'ipsearch',\r\n\tipsearch(target, room, user, connection, cmd) {\r\n\t\tif (!target.trim()) return this.parse(`/help ipsearch`);\r\n\t\tthis.checkCan('rangeban');\r\n\r\n\t\tconst [ipOrHost, roomid] = this.splitOne(target);\r\n\t\tconst targetRoom = roomid ? Rooms.get(roomid) : null;\r\n\t\tif (typeof targetRoom === 'undefined') {\r\n\t\t\treturn this.errorReply(`The room \"${roomid}\" does not exist.`);\r\n\t\t}\r\n\t\tconst results: string[] = [];\r\n\t\tconst isAll = (cmd === 'ipsearchall');\r\n\r\n\t\tif (/[a-z]/.test(ipOrHost)) {\r\n\t\t\t// host\r\n\t\t\tthis.sendReply(`Users with host ${ipOrHost}${targetRoom ? ` in the room ${targetRoom.title}` : ``}:`);\r\n\t\t\tfor (const curUser of Users.users.values()) {\r\n\t\t\t\tif (results.length > 100 && !isAll) break;\r\n\t\t\t\tif (!curUser.latestHost?.endsWith(ipOrHost)) continue;\r\n\t\t\t\tif (targetRoom && !curUser.inRooms.has(targetRoom.roomid)) continue;\r\n\t\t\t\tresults.push(`${curUser.connected ? ONLINE_SYMBOL : OFFLINE_SYMBOL} ${curUser.name}`);\r\n\t\t\t}\r\n\t\t} else if (IPTools.ipRegex.test(ipOrHost)) {\r\n\t\t\t// ip\r\n\t\t\tthis.sendReply(`Users with IP ${ipOrHost}${targetRoom ? ` in the room ${targetRoom.title}` : ``}:`);\r\n\t\t\tfor (const curUser of Users.users.values()) {\r\n\t\t\t\tif (!curUser.ips.some(ip => ip === ipOrHost)) continue;\r\n\t\t\t\tif (targetRoom && !curUser.inRooms.has(targetRoom.roomid)) continue;\r\n\t\t\t\tresults.push(`${curUser.connected ? ONLINE_SYMBOL : OFFLINE_SYMBOL} ${curUser.name}`);\r\n\t\t\t}\r\n\t\t} else if (IPTools.isValidRange(ipOrHost)) {\r\n\t\t\t// range\r\n\t\t\tthis.sendReply(`Users in IP range ${ipOrHost}${targetRoom ? ` in the room ${targetRoom.title}` : ``}:`);\r\n\t\t\tconst checker = IPTools.checker(ipOrHost);\r\n\t\t\tfor (const curUser of Users.users.values()) {\r\n\t\t\t\tif (results.length > 100 && !isAll) continue;\r\n\t\t\t\tif (!curUser.ips.some(ip => checker(ip))) continue;\r\n\t\t\t\tif (targetRoom && !curUser.inRooms.has(targetRoom.roomid)) continue;\r\n\t\t\t\tresults.push(`${curUser.connected ? ONLINE_SYMBOL : OFFLINE_SYMBOL} ${curUser.name}`);\r\n\t\t\t}\r\n\t\t} else {\r\n\t\t\treturn this.errorReply(`${ipOrHost} is not a valid IP, IP range, or host.`);\r\n\t\t}\r\n\r\n\t\tif (!results.length) {\r\n\t\t\treturn this.sendReply(`No users found.`);\r\n\t\t}\r\n\t\tthis.sendReply(results.slice(0, 100).join('; '));\r\n\t\tif (results.length > 100 && !isAll) {\r\n\t\t\tthis.sendReply(`More than 100 users found. Use /ipsearchall for the full list.`);\r\n\t\t}\r\n\t},\r\n\tipsearchhelp: [`/ipsearch [ip|range|host], (room) - Find all users with specified IP, IP range, or host. If a room is provided only users in the room will be shown. Requires: &`],\r\n\r\n\tcheckchallenges(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tif (!user.can('addhtml', null, room)) this.checkCan('ban', null, room);\r\n\t\tif (!this.runBroadcast(true)) return;\r\n\t\tif (!this.broadcasting) {\r\n\t\t\tthis.errorReply(`This command must be broadcast:`);\r\n\t\t\treturn this.parse(`/help checkchallenges`);\r\n\t\t}\r\n\t\tif (!target || !target.includes(',')) return this.parse(`/help checkchallenges`);\r\n\t\tconst {targetUser: user1, rest} = this.requireUser(target);\r\n\t\tconst {targetUser: user2, rest: rest2} = this.requireUser(rest);\r\n\t\tif (user1 === user2 || rest2) return this.parse(`/help checkchallenges`);\r\n\t\tif (!(user1.id in room.users) || !(user2.id in room.users)) {\r\n\t\t\treturn this.errorReply(`Both users must be in this room.`);\r\n\t\t}\r\n\t\tconst chall = Ladders.challenges.search(user1.id, user2.id);\r\n\r\n\t\tif (!chall) {\r\n\t\t\treturn this.sendReplyBox(Utils.html`${user1.name} and ${user2.name} are not challenging each other.`);\r\n\t\t}\r\n\t\tconst [from, to] = user1.id === chall.from ? [user1, user2] : [user2, user1];\r\n\t\tthis.sendReplyBox(Utils.html`${from.name} is challenging ${to.name} in ${Dex.formats.get(chall.format).name}.`);\r\n\t},\r\n\tcheckchallengeshelp: [`!checkchallenges [user1], [user2] - Check if the specified users are challenging each other. Requires: * @ # &`],\r\n\r\n\t/*********************************************************\r\n\t * Client fallback\r\n\t *********************************************************/\r\n\r\n\tunignore: 'ignore',\r\n\tignore(target, room, user) {\r\n\t\tif (!room) {\r\n\t\t\tthis.errorReply(`In PMs, this command can only be used by itself to ignore the person you're talking to: \"/${this.cmd}\", not \"/${this.cmd} ${target}\"`);\r\n\t\t}\r\n\t\tthis.errorReply(`You're using a custom client that doesn't support the ignore command.`);\r\n\t},\r\n\tignorehelp: [`/ignore [user] - Ignore the given [user].`],\r\n\r\n\t/*********************************************************\r\n\t * Data Search Dex\r\n\t *********************************************************/\r\n\r\n\tpstats: 'data',\r\n\tstats: 'data',\r\n\tdex: 'data',\r\n\tpokedex: 'data',\r\n\tdata(target, room, user, connection, cmd) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tconst gen = parseInt(cmd.substr(-1));\r\n\t\tif (gen) target += `, gen${gen}`;\r\n\r\n\t\tconst {dex, format, targets} = this.splitFormat(target, true);\r\n\r\n\t\tlet buffer = '';\r\n\t\ttarget = targets.join(',');\r\n\t\tconst targetId = toID(target);\r\n\t\tif (!targetId) return this.parse('/help data');\r\n\t\tconst targetNum = parseInt(target);\r\n\t\tif (!isNaN(targetNum) && `${targetNum}` === target) {\r\n\t\t\tfor (const pokemon of Dex.species.all()) {\r\n\t\t\t\tif (pokemon.num === targetNum) {\r\n\t\t\t\t\ttarget = pokemon.baseSpecies;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\tconst newTargets = dex.dataSearch(target);\r\n\t\tconst showDetails = (cmd.startsWith('dt') || cmd === 'details');\r\n\t\tif (!newTargets || !newTargets.length) {\r\n\t\t\treturn this.errorReply(`No Pok\\u00e9mon, item, move, ability or nature named '${target}' was found${Dex.gen > dex.gen ? ` in Gen ${dex.gen}` : \"\"}. (Check your spelling?)`);\r\n\t\t}\r\n\r\n\t\tfor (const [i, newTarget] of newTargets.entries()) {\r\n\t\t\tif (newTarget.isInexact && !i) {\r\n\t\t\t\tbuffer = `No Pok\\u00e9mon, item, move, ability or nature named '${target}' was found${Dex.gen > dex.gen ? ` in Gen ${dex.gen}` : \"\"}. Showing the data of '${newTargets[0].name}' instead.\\n`;\r\n\t\t\t}\r\n\t\t\tlet details: {[k: string]: string} = {};\r\n\t\t\tswitch (newTarget.searchType) {\r\n\t\t\tcase 'nature':\r\n\t\t\t\tconst nature = Dex.natures.get(newTarget.name);\r\n\t\t\t\tbuffer += `${nature.name} nature: `;\r\n\t\t\t\tif (nature.plus) {\r\n\t\t\t\t\tbuffer += `+10% ${Dex.stats.names[nature.plus]}, -10% ${Dex.stats.names[nature.minus!]}.`;\r\n\t\t\t\t} else {\r\n\t\t\t\t\tbuffer += `No effect.`;\r\n\t\t\t\t}\r\n\t\t\t\treturn this.sendReply(buffer);\r\n\t\t\tcase 'pokemon':\r\n\t\t\t\tlet pokemon = dex.species.get(newTarget.name);\r\n\t\t\t\tif (format?.onModifySpecies) {\r\n\t\t\t\t\tpokemon = format.onModifySpecies.call({dex, clampIntRange: Utils.clampIntRange, toID} as Battle, pokemon) || pokemon;\r\n\t\t\t\t}\r\n\t\t\t\tlet tierDisplay = room?.settings.dataCommandTierDisplay;\r\n\t\t\t\tif (!tierDisplay && room?.battle) {\r\n\t\t\t\t\tif (room.battle.format.includes('doubles') || room.battle.format.includes('vgc')) {\r\n\t\t\t\t\t\ttierDisplay = 'doubles tiers';\r\n\t\t\t\t\t} else if (room.battle.format.includes('nationaldex')) {\r\n\t\t\t\t\t\ttierDisplay = 'National Dex tiers';\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tif (!tierDisplay) tierDisplay = 'tiers';\r\n\t\t\t\tconst displayedTier = tierDisplay === 'tiers' ? pokemon.tier :\r\n\t\t\t\t\ttierDisplay === 'doubles tiers' ? pokemon.doublesTier :\r\n\t\t\t\t\ttierDisplay === 'National Dex tiers' ? pokemon.natDexTier :\r\n\t\t\t\t\tpokemon.num >= 0 ? String(pokemon.num) : pokemon.tier;\r\n\t\t\t\tbuffer += `|raw|${Chat.getDataPokemonHTML(pokemon, dex.gen, displayedTier)}\\n`;\r\n\t\t\t\tif (showDetails) {\r\n\t\t\t\t\tlet weighthit = 20;\r\n\t\t\t\t\tif (pokemon.weighthg >= 2000) {\r\n\t\t\t\t\t\tweighthit = 120;\r\n\t\t\t\t\t} else if (pokemon.weighthg >= 1000) {\r\n\t\t\t\t\t\tweighthit = 100;\r\n\t\t\t\t\t} else if (pokemon.weighthg >= 500) {\r\n\t\t\t\t\t\tweighthit = 80;\r\n\t\t\t\t\t} else if (pokemon.weighthg >= 250) {\r\n\t\t\t\t\t\tweighthit = 60;\r\n\t\t\t\t\t} else if (pokemon.weighthg >= 100) {\r\n\t\t\t\t\t\tweighthit = 40;\r\n\t\t\t\t\t}\r\n\t\t\t\t\tdetails = {\r\n\t\t\t\t\t\t\"Dex#\": String(pokemon.num),\r\n\t\t\t\t\t\tGen: String(pokemon.gen) || 'CAP',\r\n\t\t\t\t\t\tHeight: `${pokemon.heightm} m`,\r\n\t\t\t\t\t};\r\n\t\t\t\t\tdetails[\"Weight\"] = `${pokemon.weighthg / 10} kg (${weighthit} BP)`;\r\n\t\t\t\t\tconst gmaxMove = pokemon.canGigantamax || dex.species.get(pokemon.changesFrom).canGigantamax;\r\n\t\t\t\t\tif (gmaxMove && dex.gen >= 8) details[\"G-Max Move\"] = gmaxMove;\r\n\t\t\t\t\tif (pokemon.color && dex.gen >= 5) details[\"Dex Colour\"] = pokemon.color;\r\n\t\t\t\t\tif (pokemon.eggGroups && dex.gen >= 2) details[\"Egg Group(s)\"] = pokemon.eggGroups.join(\", \");\r\n\t\t\t\t\tconst evos: string[] = [];\r\n\t\t\t\t\tfor (const evoName of pokemon.evos) {\r\n\t\t\t\t\t\tconst evo = dex.species.get(evoName);\r\n\t\t\t\t\t\tif (evo.gen <= dex.gen) {\r\n\t\t\t\t\t\t\tconst condition = evo.evoCondition ? ` ${evo.evoCondition}` : ``;\r\n\t\t\t\t\t\t\tswitch (evo.evoType) {\r\n\t\t\t\t\t\t\tcase 'levelExtra':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (level-up${condition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'levelFriendship':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (level-up with high Friendship${condition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'levelHold':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (level-up holding ${evo.evoItem}${condition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'useItem':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (${evo.evoItem})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'levelMove':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (level-up with ${evo.evoMove}${condition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'other':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (${evo.evoCondition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tcase 'trade':\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (trade${evo.evoItem ? ` holding ${evo.evoItem}` : condition})`);\r\n\t\t\t\t\t\t\t\tbreak;\r\n\t\t\t\t\t\t\tdefault:\r\n\t\t\t\t\t\t\t\tevos.push(`${evo.name} (${evo.evoLevel}${condition})`);\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (!evos.length) {\r\n\t\t\t\t\t\tdetails[`Does Not Evolve`] = \"\";\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\tdetails[\"Evolution\"] = evos.join(\", \");\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tbreak;\r\n\t\t\tcase 'item':\r\n\t\t\t\tconst item = dex.items.get(newTarget.name);\r\n\t\t\t\tbuffer += `|raw|${Chat.getDataItemHTML(item)}\\n`;\r\n\t\t\t\tif (showDetails) {\r\n\t\t\t\t\tdetails = {\r\n\t\t\t\t\t\tGen: String(item.gen),\r\n\t\t\t\t\t};\r\n\r\n\t\t\t\t\tif (dex.gen >= 4) {\r\n\t\t\t\t\t\tif (item.fling) {\r\n\t\t\t\t\t\t\tdetails[\"Fling Base Power\"] = String(item.fling.basePower);\r\n\t\t\t\t\t\t\tif (item.fling.status) details[\"Fling Effect\"] = item.fling.status;\r\n\t\t\t\t\t\t\tif (item.fling.volatileStatus) details[\"Fling Effect\"] = item.fling.volatileStatus;\r\n\t\t\t\t\t\t\tif (item.isBerry) details[\"Fling Effect\"] = \"Activates the Berry's effect on the target.\";\r\n\t\t\t\t\t\t\tif (item.id === 'whiteherb') details[\"Fling Effect\"] = \"Restores the target's negative stat stages to 0.\";\r\n\t\t\t\t\t\t\tif (item.id === 'mentalherb') {\r\n\t\t\t\t\t\t\t\tconst flingEffect = \"Removes the effects of Attract, Disable, Encore, Heal Block, Taunt, and Torment from the target.\";\r\n\t\t\t\t\t\t\t\tdetails[\"Fling Effect\"] = flingEffect;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} else {\r\n\t\t\t\t\t\t\tdetails[\"Fling\"] = \"This item cannot be used with Fling.\";\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (item.naturalGift && dex.gen >= 3) {\r\n\t\t\t\t\t\tdetails[\"Natural Gift Type\"] = item.naturalGift.type;\r\n\t\t\t\t\t\tdetails[\"Natural Gift Base Power\"] = String(item.naturalGift.basePower);\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (item.isNonstandard) {\r\n\t\t\t\t\t\tdetails[`Unobtainable in Gen ${dex.gen}`] = \"\";\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tbreak;\r\n\t\t\tcase 'move':\r\n\t\t\t\tconst move = dex.moves.get(newTarget.name);\r\n\t\t\t\tbuffer += `|raw|${Chat.getDataMoveHTML(move)}\\n`;\r\n\t\t\t\tif (showDetails) {\r\n\t\t\t\t\tdetails = {\r\n\t\t\t\t\t\tPriority: String(move.priority),\r\n\t\t\t\t\t\tGen: String(move.gen) || 'CAP',\r\n\t\t\t\t\t};\r\n\r\n\t\t\t\t\tif (move.isNonstandard === \"Past\" && dex.gen >= 8) details[\"✗ Past Gens Only\"] = \"\";\r\n\t\t\t\t\tif (move.secondary || move.secondaries || move.hasSheerForce) details[\"✓ Boosted by Sheer Force\"] = \"\";\r\n\t\t\t\t\tif (move.flags['contact'] && dex.gen >= 3) details[\"✓ Contact\"] = \"\";\r\n\t\t\t\t\tif (move.flags['sound'] && dex.gen >= 3) details[\"✓ Sound\"] = \"\";\r\n\t\t\t\t\tif (move.flags['bullet'] && dex.gen >= 6) details[\"✓ Bullet\"] = \"\";\r\n\t\t\t\t\tif (move.flags['pulse'] && dex.gen >= 6) details[\"✓ Pulse\"] = \"\";\r\n\t\t\t\t\tif (!move.flags['protect'] && move.target !== 'self') details[\"✓ Bypasses Protect\"] = \"\";\r\n\t\t\t\t\tif (move.flags['bypasssub']) details[\"✓ Bypasses Substitutes\"] = \"\";\r\n\t\t\t\t\tif (move.flags['defrost']) details[\"✓ Thaws user\"] = \"\";\r\n\t\t\t\t\tif (move.flags['bite'] && dex.gen >= 6) details[\"✓ Bite\"] = \"\";\r\n\t\t\t\t\tif (move.flags['punch'] && dex.gen >= 4) details[\"✓ Punch\"] = \"\";\r\n\t\t\t\t\tif (move.flags['powder'] && dex.gen >= 6) details[\"✓ Powder\"] = \"\";\r\n\t\t\t\t\tif (move.flags['reflectable'] && dex.gen >= 3) details[\"✓ Bounceable\"] = \"\";\r\n\t\t\t\t\tif (move.flags['charge']) details[\"✓ Two-turn move\"] = \"\";\r\n\t\t\t\t\tif (move.flags['recharge']) details[\"✓ Has recharge turn\"] = \"\";\r\n\t\t\t\t\tif (move.flags['gravity'] && dex.gen >= 4) details[\"✗ Suppressed by Gravity\"] = \"\";\r\n\t\t\t\t\tif (move.flags['dance'] && dex.gen >= 7) details[\"✓ Dance move\"] = \"\";\r\n\t\t\t\t\tif (move.flags['slicing'] && dex.gen >= 9) details[\"✓ Slicing move\"] = \"\";\r\n\t\t\t\t\tif (move.flags['wind'] && dex.gen >= 9) details[\"✓ Wind move\"] = \"\";\r\n\r\n\t\t\t\t\tif (dex.gen >= 7) {\r\n\t\t\t\t\t\tif (move.gen >= 8 && move.isMax) {\r\n\t\t\t\t\t\t\t// Don't display Z-Power for Max/G-Max moves\r\n\t\t\t\t\t\t} else if (move.zMove?.basePower) {\r\n\t\t\t\t\t\t\tdetails[\"Z-Power\"] = String(move.zMove.basePower);\r\n\t\t\t\t\t\t} else if (move.zMove?.effect) {\r\n\t\t\t\t\t\t\tconst zEffects: {[k: string]: string} = {\r\n\t\t\t\t\t\t\t\tclearnegativeboost: \"Restores negative stat stages to 0\",\r\n\t\t\t\t\t\t\t\tcrit2: \"Crit ratio +2\",\r\n\t\t\t\t\t\t\t\theal: \"Restores HP 100%\",\r\n\t\t\t\t\t\t\t\tcurse: \"Restores HP 100% if user is Ghost type, otherwise Attack +1\",\r\n\t\t\t\t\t\t\t\tredirect: \"Redirects opposing attacks to user\",\r\n\t\t\t\t\t\t\t\thealreplacement: \"Restores replacement's HP 100%\",\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tdetails[\"Z-Effect\"] = zEffects[move.zMove.effect];\r\n\t\t\t\t\t\t} else if (move.zMove?.boost) {\r\n\t\t\t\t\t\t\tdetails[\"Z-Effect\"] = \"\";\r\n\t\t\t\t\t\t\tconst boost = move.zMove.boost;\r\n\t\t\t\t\t\t\tconst stats: {[k in BoostID]: string} = {\r\n\t\t\t\t\t\t\t\tatk: 'Attack', def: 'Defense', spa: 'Sp. Atk', spd: 'Sp. Def', spe: 'Speed', accuracy: 'Accuracy', evasion: 'Evasiveness',\r\n\t\t\t\t\t\t\t};\r\n\t\t\t\t\t\t\tlet h: BoostID;\r\n\t\t\t\t\t\t\tfor (h in boost) {\r\n\t\t\t\t\t\t\t\tdetails[\"Z-Effect\"] += ` ${stats[h]} +${boost[h]}`;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} else if (move.isZ && typeof move.isZ === 'string') {\r\n\t\t\t\t\t\t\tdetails[\"✓ Z-Move\"] = \"\";\r\n\t\t\t\t\t\t\tconst zCrystal = dex.items.get(move.isZ);\r\n\t\t\t\t\t\t\tdetails[\"Z-Crystal\"] = zCrystal.name;\r\n\t\t\t\t\t\t\tif (zCrystal.itemUser) {\r\n\t\t\t\t\t\t\t\tdetails[\"User\"] = zCrystal.itemUser.join(\", \");\r\n\t\t\t\t\t\t\t\tdetails[\"Required Move\"] = dex.items.get(move.isZ).zMoveFrom!;\r\n\t\t\t\t\t\t\t}\r\n\t\t\t\t\t\t} else {\r\n\t\t\t\t\t\t\tdetails[\"Z-Effect\"] = \"None\";\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tif (dex.gen >= 8) {\r\n\t\t\t\t\t\tif (move.isMax) {\r\n\t\t\t\t\t\t\tdetails[\"✓ Max Move\"] = \"\";\r\n\t\t\t\t\t\t\tif (typeof move.isMax === \"string\") details[\"User\"] = `${move.isMax}`;\r\n\t\t\t\t\t\t} else if (move.maxMove?.basePower) {\r\n\t\t\t\t\t\t\tdetails[\"Dynamax Power\"] = String(move.maxMove.basePower);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tconst targetTypes: {[k: string]: string} = {\r\n\t\t\t\t\t\tnormal: \"One Adjacent Pok\\u00e9mon\",\r\n\t\t\t\t\t\tself: \"User\",\r\n\t\t\t\t\t\tadjacentAlly: \"One Ally\",\r\n\t\t\t\t\t\tadjacentAllyOrSelf: \"User or Ally\",\r\n\t\t\t\t\t\tadjacentFoe: \"One Adjacent Opposing Pok\\u00e9mon\",\r\n\t\t\t\t\t\tallAdjacentFoes: \"All Adjacent Opponents\",\r\n\t\t\t\t\t\tfoeSide: \"Opposing Side\",\r\n\t\t\t\t\t\tallySide: \"User's Side\",\r\n\t\t\t\t\t\tallyTeam: \"User's Side\",\r\n\t\t\t\t\t\tallAdjacent: \"All Adjacent Pok\\u00e9mon\",\r\n\t\t\t\t\t\tany: \"Any Pok\\u00e9mon\",\r\n\t\t\t\t\t\tall: \"All Pok\\u00e9mon\",\r\n\t\t\t\t\t\tscripted: \"Chosen Automatically\",\r\n\t\t\t\t\t\trandomNormal: \"Random Adjacent Opposing Pok\\u00e9mon\",\r\n\t\t\t\t\t\tallies: \"User and Allies\",\r\n\t\t\t\t\t};\r\n\t\t\t\t\tdetails[\"Target\"] = targetTypes[move.target] || \"Unknown\";\r\n\r\n\t\t\t\t\tif (move.id === 'snatch' && dex.gen >= 3) {\r\n\t\t\t\t\t\tdetails[`Non-Snatchable Moves`] = '';\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (move.id === 'mirrormove') {\r\n\t\t\t\t\t\tdetails[`Non-Mirrorable Moves`] = '';\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (move.isNonstandard === 'Unobtainable') {\r\n\t\t\t\t\t\tdetails[`Unobtainable in Gen ${dex.gen}`] = \"\";\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t\tbreak;\r\n\t\t\tcase 'ability':\r\n\t\t\t\tconst ability = dex.abilities.get(newTarget.name);\r\n\t\t\t\tbuffer += `|raw|${Chat.getDataAbilityHTML(ability)}\\n`;\r\n\t\t\t\tif (showDetails) {\r\n\t\t\t\t\tdetails = {\r\n\t\t\t\t\t\tGen: String(ability.gen) || 'CAP',\r\n\t\t\t\t\t};\r\n\t\t\t\t\tif (ability.isPermanent) details[\"✓ Not affected by Gastro Acid\"] = \"\";\r\n\t\t\t\t\tif (ability.isBreakable) details[\"✓ Ignored by Mold Breaker\"] = \"\";\r\n\t\t\t\t}\r\n\t\t\t\tbreak;\r\n\t\t\tdefault:\r\n\t\t\t\tthrow new Error(`Unrecognized searchType`);\r\n\t\t\t}\r\n\r\n\t\t\tif (showDetails) {\r\n\t\t\t\tbuffer += `|raw|${Object.entries(details).map(([detail, value]) => (\r\n\t\t\t\t\tvalue === '' ? detail : `${detail}: ${value}`\r\n\t\t\t\t)).join(\" |  \")}\\n`;\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.sendReply(buffer);\r\n\t},\r\n\tdatahelp: [\r\n\t\t`/data [pokemon/item/move/ability/nature] - Get details on this pokemon/item/move/ability/nature.`,\r\n\t\t`/data [pokemon/item/move/ability/nature], Gen [generation number/format name] - Get details on this pokemon/item/move/ability/nature for that generation/format.`,\r\n\t\t`!data [pokemon/item/move/ability/nature] - Show everyone these details. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tdt: 'details',\r\n\tdt1: 'details',\r\n\tdt2: 'details',\r\n\tdt3: 'details',\r\n\tdt4: 'details',\r\n\tdt5: 'details',\r\n\tdt6: 'details',\r\n\tdt7: 'details',\r\n\tdt8: 'details',\r\n\tdt9: 'details',\r\n\tdetails(target) {\r\n\t\tif (!target) return this.parse('/help details');\r\n\t\tthis.run('data');\r\n\t},\r\n\tdetailshelp() {\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`/details [Pok\\u00e9mon/item/move/ability/nature]: get additional details on this Pok\\u00e9mon/item/move/ability/nature.
` +\r\n\t\t\t`/details [Pok\\u00e9mon/item/move/ability/nature], Gen [generation number]: get details on this Pok\\u00e9mon/item/move/ability/nature in that generation.
` +\r\n\t\t\t`You can also append the generation number to /dt; for example, /dt1 Mewtwo gets details on Mewtwo in Gen 1.
` +\r\n\t\t\t`/details [Pok\\u00e9mon/item/move/ability/nature], [format]: get details on this Pok\\u00e9mon/item/move/ability/nature in that format.
` +\r\n\t\t\t`!details [Pok\\u00e9mon/item/move/ability/nature]: show everyone these details. Requires: + % @ # &`\r\n\t\t);\r\n\t},\r\n\r\n\tweaknesses: 'weakness',\r\n\tweak: 'weakness',\r\n\tresist: 'weakness',\r\n\tweakness(target, room, user) {\r\n\t\tif (!target) return this.parse('/help weakness');\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tconst {format, dex, targets} = this.splitFormat(target.split(/[,/]/).map(toID));\r\n\r\n\t\tlet isInverse = false;\r\n\t\tif (format && Dex.formats.getRuleTable(format).has('inversemod')) {\r\n\t\t\tisInverse = true;\r\n\t\t} else if (targets[targets.length - 1] === 'inverse') {\r\n\t\t\tisInverse = true;\r\n\t\t\ttargets.pop();\r\n\t\t}\r\n\r\n\t\tlet species: {types: string[], [k: string]: any} = dex.species.get(targets[0]);\r\n\t\tconst type1 = dex.types.get(targets[0]);\r\n\t\tconst type2 = dex.types.get(targets[1]);\r\n\t\tconst type3 = dex.types.get(targets[2]);\r\n\r\n\t\tif (species.exists) {\r\n\t\t\ttarget = species.name;\r\n\t\t} else {\r\n\t\t\tconst types = [];\r\n\t\t\tif (type1.exists) {\r\n\t\t\t\ttypes.push(type1.name);\r\n\t\t\t\tif (type2.exists && type2 !== type1) {\r\n\t\t\t\t\ttypes.push(type2.name);\r\n\t\t\t\t}\r\n\t\t\t\tif (type3.exists && type3 !== type1 && type3 !== type2) {\r\n\t\t\t\t\ttypes.push(type3.name);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (types.length === 0) {\r\n\t\t\t\treturn this.sendReplyBox(Utils.html`${target} isn't a recognized type or Pokemon${Dex.gen > dex.gen ? ` in Gen ${dex.gen}` : \"\"}.`);\r\n\t\t\t}\r\n\t\t\tspecies = {types: types};\r\n\t\t\ttarget = types.join(\"/\");\r\n\t\t}\r\n\r\n\t\tconst weaknesses = [];\r\n\t\tconst resistances = [];\r\n\t\tconst immunities = [];\r\n\t\tfor (const type of dex.types.names()) {\r\n\t\t\tconst notImmune = dex.getImmunity(type, species);\r\n\t\t\tif (notImmune || isInverse) {\r\n\t\t\t\tlet typeMod = !notImmune && isInverse ? 1 : 0;\r\n\t\t\t\ttypeMod += (isInverse ? -1 : 1) * dex.getEffectiveness(type, species);\r\n\t\t\t\tswitch (typeMod) {\r\n\t\t\t\tcase 1:\r\n\t\t\t\t\tweaknesses.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase 2:\r\n\t\t\t\t\tweaknesses.push(`${type}`);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase 3:\r\n\t\t\t\t\tweaknesses.push(`${type}`);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase -1:\r\n\t\t\t\t\tresistances.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase -2:\r\n\t\t\t\t\tresistances.push(`${type}`);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase -3:\r\n\t\t\t\t\tresistances.push(`${type}`);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\timmunities.push(type);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tconst statuses: {[k: string]: string} = {\r\n\t\t\tbrn: \"Burn\",\r\n\t\t\tfrz: \"Frozen\",\r\n\t\t\thail: \"Hail damage\",\r\n\t\t\tpar: \"Paralysis\",\r\n\t\t\tpowder: \"Powder moves\",\r\n\t\t\tprankster: \"Prankster\",\r\n\t\t\tsandstorm: \"Sandstorm damage\",\r\n\t\t\ttox: \"Toxic\",\r\n\t\t\ttrapped: \"Trapping\",\r\n\t\t};\r\n\t\tfor (const status in statuses) {\r\n\t\t\tif (!dex.getImmunity(status, species)) {\r\n\t\t\t\timmunities.push(statuses[status]);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tconst buffer = [];\r\n\t\tbuffer.push(`${species.exists ? `${species.name} (ignoring abilities):` : `${target}:`}`);\r\n\t\tbuffer.push(`Weaknesses: ${weaknesses.join(', ') || 'None'}`);\r\n\t\tbuffer.push(`Resistances: ${resistances.join(', ') || 'None'}`);\r\n\t\tbuffer.push(`Immunities: ${immunities.join(', ') || 'None'}`);\r\n\t\tthis.sendReplyBox(buffer.join('
'));\r\n\t},\r\n\tweaknesshelp: [\r\n\t\t`/weakness [pokemon] - Provides a Pok\\u00e9mon's resistances, weaknesses, and immunities, ignoring abilities.`,\r\n\t\t`/weakness [type 1]/[type 2] - Provides a type or type combination's resistances, weaknesses, and immunities, ignoring abilities.`,\r\n\t\t`!weakness [pokemon] - Shows everyone a Pok\\u00e9mon's resistances, weaknesses, and immunities, ignoring abilities. Requires: + % @ # &`,\r\n\t\t`!weakness [type 1]/[type 2] - Shows everyone a type or type combination's resistances, weaknesses, and immunities, ignoring abilities. Requires: + % @ # &`,\r\n\t],\r\n\r\n\teff: 'effectiveness',\r\n\ttype: 'effectiveness',\r\n\tmatchup: 'effectiveness',\r\n\teffectiveness(target, room, user) {\r\n\t\tconst {dex, targets} = this.splitFormat(target.split(/[,/]/));\r\n\t\tif (targets.length !== 2) return this.errorReply(\"Attacker and defender must be separated with a comma.\");\r\n\r\n\t\tlet searchMethods = ['types', 'moves', 'species'];\r\n\t\tconst sourceMethods = ['types', 'moves'];\r\n\t\tconst targetMethods = ['types', 'species'];\r\n\t\tlet source;\r\n\t\tlet defender;\r\n\t\tlet foundData;\r\n\t\tlet atkName;\r\n\t\tlet defName;\r\n\r\n\t\tfor (let i = 0; i < 2; ++i) {\r\n\t\t\tlet method!: string;\r\n\t\t\tfor (const m of searchMethods) {\r\n\t\t\t\tfoundData = (dex as any)[m].get(targets[i]);\r\n\t\t\t\tif (foundData.exists) {\r\n\t\t\t\t\tmethod = m;\r\n\t\t\t\t\tbreak;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (!foundData.exists) return this.parse('/help effectiveness');\r\n\t\t\tif (!source && sourceMethods.includes(method)) {\r\n\t\t\t\tif (foundData.type) {\r\n\t\t\t\t\tsource = foundData;\r\n\t\t\t\t\tatkName = foundData.name;\r\n\t\t\t\t} else {\r\n\t\t\t\t\tsource = foundData.name;\r\n\t\t\t\t\tatkName = foundData.name;\r\n\t\t\t\t}\r\n\t\t\t\tsearchMethods = targetMethods;\r\n\t\t\t} else if (!defender && targetMethods.includes(method)) {\r\n\t\t\t\tif (foundData.types) {\r\n\t\t\t\t\tdefender = foundData;\r\n\t\t\t\t\tdefName = `${foundData.name} (not counting abilities)`;\r\n\t\t\t\t} else {\r\n\t\t\t\t\tdefender = {types: [foundData.name]};\r\n\t\t\t\t\tdefName = foundData.name;\r\n\t\t\t\t}\r\n\t\t\t\tsearchMethods = sourceMethods;\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (!this.runBroadcast()) return;\r\n\r\n\t\tlet factor = 0;\r\n\t\tif (dex.getImmunity(source, defender) ||\r\n\t\t\tsource.ignoreImmunity && (source.ignoreImmunity === true || source.ignoreImmunity[source.type])) {\r\n\t\t\tlet totalTypeMod = 0;\r\n\t\t\tif (source.effectType !== 'Move' || source.category !== 'Status' && (source.basePower || source.basePowerCallback)) {\r\n\t\t\t\tfor (const type of defender.types) {\r\n\t\t\t\t\tconst baseMod = dex.getEffectiveness(source, type);\r\n\t\t\t\t\tconst moveMod = source.onEffectiveness?.call({dex: Dex} as Battle, baseMod, null, type, source);\r\n\t\t\t\t\ttotalTypeMod += typeof moveMod === 'number' ? moveMod : baseMod;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tfactor = Math.pow(2, totalTypeMod);\r\n\t\t}\r\n\r\n\t\tconst hasThousandArrows = source.id === 'thousandarrows' && defender.types.includes('Flying');\r\n\t\tconst additionalInfo = hasThousandArrows ? \"
However, Thousand Arrows will be 1x effective on the first hit.\" : \"\";\r\n\r\n\t\tthis.sendReplyBox(`${atkName} is ${factor}x effective against ${defName}.${additionalInfo}`);\r\n\t},\r\n\teffectivenesshelp: [\r\n\t\t`/effectiveness [attack], [defender] - Provides the effectiveness of a move or type on another type or a Pok\\u00e9mon.`,\r\n\t\t`!effectiveness [attack], [defender] - Shows everyone the effectiveness of a move or type on another type or a Pok\\u00e9mon.`,\r\n\t],\r\n\r\n\tcover: 'coverage',\r\n\tcoverage(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tif (!target) return this.parse(\"/help coverage\");\r\n\r\n\t\tconst {dex, targets} = this.splitFormat(target.split(/[,+/]/));\r\n\t\tconst sources: (string | Move)[] = [];\r\n\t\tlet dispTable = false;\r\n\t\tconst bestCoverage: {[k: string]: number} = {};\r\n\t\tlet hasThousandArrows = false;\r\n\r\n\t\tfor (const type of dex.types.names()) {\r\n\t\t\t// This command uses -5 to designate immunity\r\n\t\t\tbestCoverage[type] = -5;\r\n\t\t}\r\n\r\n\t\tfor (let arg of targets) {\r\n\t\t\targ = toID(arg);\r\n\r\n\t\t\t// arg is the gen?\r\n\t\t\tif (arg === dex.currentMod) continue;\r\n\r\n\t\t\t// arg is 'table' or 'all'?\r\n\t\t\tif (arg === 'table' || arg === 'all') {\r\n\t\t\t\tif (this.broadcasting) return this.sendReplyBox(\"The full table cannot be broadcast.\");\r\n\t\t\t\tdispTable = true;\r\n\t\t\t\tcontinue;\r\n\t\t\t}\r\n\r\n\t\t\t// arg is a type?\r\n\t\t\tconst argType = arg.charAt(0).toUpperCase() + arg.slice(1);\r\n\t\t\tlet eff;\r\n\t\t\tif (dex.types.isName(argType)) {\r\n\t\t\t\tsources.push(argType);\r\n\t\t\t\tfor (const type in bestCoverage) {\r\n\t\t\t\t\tif (!dex.getImmunity(argType, type)) continue;\r\n\t\t\t\t\teff = dex.getEffectiveness(argType, type);\r\n\t\t\t\t\tif (eff > bestCoverage[type]) bestCoverage[type] = eff;\r\n\t\t\t\t}\r\n\t\t\t\tcontinue;\r\n\t\t\t}\r\n\r\n\t\t\t// arg is a move?\r\n\t\t\tconst move = dex.moves.get(arg);\r\n\t\t\tif (!move.exists) {\r\n\t\t\t\treturn this.errorReply(`Type or move '${arg}' not found.`);\r\n\t\t\t} else if (move.gen > dex.gen) {\r\n\t\t\t\treturn this.errorReply(`Move '${arg}' is not available in Gen ${dex.gen}.`);\r\n\t\t\t}\r\n\r\n\t\t\tif (!move.basePower && !move.basePowerCallback) continue;\r\n\t\t\tif (move.id === 'thousandarrows') hasThousandArrows = true;\r\n\t\t\tsources.push(move);\r\n\t\t\tfor (const type in bestCoverage) {\r\n\t\t\t\tif (move.id === \"struggle\") {\r\n\t\t\t\t\teff = 0;\r\n\t\t\t\t} else {\r\n\t\t\t\t\tif (!dex.getImmunity(move.type, type) && !move.ignoreImmunity) continue;\r\n\t\t\t\t\tconst baseMod = dex.getEffectiveness(move, type);\r\n\t\t\t\t\tconst moveMod = move.onEffectiveness?.call({dex} as Battle, baseMod, null, type, move as ActiveMove);\r\n\t\t\t\t\teff = typeof moveMod === 'number' ? moveMod : baseMod;\r\n\t\t\t\t}\r\n\t\t\t\tif (eff > bestCoverage[type]) bestCoverage[type] = eff;\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (sources.length === 0) return this.errorReply(\"No moves using a type table for determining damage were specified.\");\r\n\t\tif (sources.length > 4) return this.errorReply(\"Specify a maximum of 4 moves or types.\");\r\n\r\n\t\t// converts to fractional effectiveness, 0 for immune\r\n\t\tfor (const type in bestCoverage) {\r\n\t\t\tif (bestCoverage[type] === -5) {\r\n\t\t\t\tbestCoverage[type] = 0;\r\n\t\t\t\tcontinue;\r\n\t\t\t}\r\n\t\t\tbestCoverage[type] = Math.pow(2, bestCoverage[type]);\r\n\t\t}\r\n\r\n\t\tif (!dispTable) {\r\n\t\t\tconst buffer: string[] = [];\r\n\t\t\tconst superEff: string[] = [];\r\n\t\t\tconst neutral: string[] = [];\r\n\t\t\tconst resists: string[] = [];\r\n\t\t\tconst immune: string[] = [];\r\n\r\n\t\t\tfor (const type in bestCoverage) {\r\n\t\t\t\tswitch (bestCoverage[type]) {\r\n\t\t\t\tcase 0:\r\n\t\t\t\t\timmune.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase 0.25:\r\n\t\t\t\tcase 0.5:\r\n\t\t\t\t\tresists.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase 1:\r\n\t\t\t\t\tneutral.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tcase 2:\r\n\t\t\t\tcase 4:\r\n\t\t\t\t\tsuperEff.push(type);\r\n\t\t\t\t\tbreak;\r\n\t\t\t\tdefault:\r\n\t\t\t\t\tthrow new Error(`/coverage effectiveness of ${bestCoverage[type]} from parameters: ${target}`);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tbuffer.push(`Coverage for ${sources.join(' + ')}:`);\r\n\t\t\tbuffer.push(`Super Effective: ${superEff.join(', ') || 'None'}`);\r\n\t\t\tbuffer.push(`Neutral: ${neutral.join(', ') || 'None'}`);\r\n\t\t\tbuffer.push(`Resists: ${resists.join(', ') || 'None'}`);\r\n\t\t\tbuffer.push(`Immunities: ${immune.join(', ') || 'None'}`);\r\n\t\t\treturn this.sendReplyBox(buffer.join('
'));\r\n\t\t} else {\r\n\t\t\tlet buffer = '
';\r\n\t\t\tconst icon: {[k: string]: string} = {};\r\n\t\t\tfor (const type of dex.types.names()) {\r\n\t\t\t\ticon[type] = ``;\r\n\t\t\t\t// row of icons at top\r\n\t\t\t\tbuffer += ``;\r\n\t\t\t}\r\n\t\t\tbuffer += '';\r\n\t\t\tfor (const type1 of dex.types.names()) {\r\n\t\t\t\t// assembles the rest of the rows\r\n\t\t\t\tbuffer += ``;\r\n\t\t\t\tfor (const type2 of dex.types.names()) {\r\n\t\t\t\t\tlet typing: string;\r\n\t\t\t\t\tlet cell = '';\r\n\t\t\t\t\tbuffer += cell;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tbuffer += '
${icon[type]}
${icon[type1]} bestEff) bestEff = curEff;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t\tif (bestEff === -5) {\r\n\t\t\t\t\t\t\tbestEff = 0;\r\n\t\t\t\t\t\t} else {\r\n\t\t\t\t\t\t\tbestEff = Math.pow(2, bestEff);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\t\t\t\t\tswitch (bestEff) {\r\n\t\t\t\t\tcase 0:\r\n\t\t\t\t\t\tcell += `bgcolor=#666666 title=\"${typing}\">${bestEff}`;\r\n\t\t\t\t\t\tbreak;\r\n\t\t\t\t\tcase 0.25:\r\n\t\t\t\t\tcase 0.5:\r\n\t\t\t\t\t\tcell += `bgcolor=#AA5544 title=\"${typing}\">${bestEff}`;\r\n\t\t\t\t\t\tbreak;\r\n\t\t\t\t\tcase 1:\r\n\t\t\t\t\t\tcell += `bgcolor=#6688AA title=\"${typing}\">${bestEff}`;\r\n\t\t\t\t\t\tbreak;\r\n\t\t\t\t\tcase 2:\r\n\t\t\t\t\tcase 4:\r\n\t\t\t\t\t\tcell += `bgcolor=#559955 title=\"${typing}\">${bestEff}`;\r\n\t\t\t\t\t\tbreak;\r\n\t\t\t\t\tdefault:\r\n\t\t\t\t\t\tthrow new Error(`/coverage effectiveness of ${bestEff} from parameters: ${target}`);\r\n\t\t\t\t\t}\r\n\t\t\t\t\tcell += '
';\r\n\r\n\t\t\tif (hasThousandArrows) {\r\n\t\t\t\tbuffer += \"
Thousand Arrows has neutral type effectiveness on Flying-type Pok\\u00e9mon if not already smacked down.\";\r\n\t\t\t}\r\n\r\n\t\t\tthis.sendReplyBox(`Coverage for ${sources.join(' + ')}:
${buffer}`);\r\n\t\t}\r\n\t},\r\n\tcoveragehelp: [\r\n\t\t`/coverage [move 1], [move 2] ... - Provides the best effectiveness match-up against all defending types for given moves or attacking types`,\r\n\t\t`!coverage [move 1], [move 2] ... - Shows this information to everyone.`,\r\n\t\t`Adding the parameter 'all' or 'table' will display the information with a table of all type combinations.`,\r\n\t],\r\n\r\n\tstatcalc(target, room, user) {\r\n\t\tif (!target) return this.parse(\"/help statcalc\");\r\n\t\tif (!this.runBroadcast()) return;\r\n\r\n\t\tconst targets = target.split(' ');\r\n\r\n\t\tlet lvlSet = false;\r\n\t\tlet natureSet = false;\r\n\t\tlet ivSet = false;\r\n\t\tlet evSet = false;\r\n\t\tlet baseSet = false;\r\n\t\tlet modSet = false;\r\n\t\tlet realSet = false;\r\n\r\n\t\tlet pokemon: StatsTable | undefined;\r\n\t\tlet useStat: StatID | '' = '';\r\n\r\n\t\tlet level = 100;\r\n\t\tlet calcHP = false;\r\n\t\tlet nature = 1.0;\r\n\t\tlet iv = 31;\r\n\t\tlet ev = 252;\r\n\t\tlet baseStat = -1;\r\n\t\tlet modifier = 0;\r\n\t\tlet positiveMod = true;\r\n\t\tlet realStat = 0;\r\n\r\n\t\tfor (const arg of targets) {\r\n\t\t\tconst lowercase = arg.toLowerCase();\r\n\r\n\t\t\tif (!lvlSet) {\r\n\t\t\t\tif (lowercase === 'lc') {\r\n\t\t\t\t\tlevel = 5;\r\n\t\t\t\t\tlvlSet = true;\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t} else if (lowercase === 'vgc') {\r\n\t\t\t\t\tlevel = 50;\r\n\t\t\t\t\tlvlSet = true;\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t} else if (lowercase.startsWith('lv') || lowercase.startsWith('level')) {\r\n\t\t\t\t\tlevel = parseInt(arg.replace(/\\D/g, ''));\r\n\t\t\t\t\tlvlSet = true;\r\n\t\t\t\t\tif (level < 1 || level > 9999) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('Invalid value for level: ' + level);\r\n\t\t\t\t\t}\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!useStat) {\r\n\t\t\t\tswitch (lowercase) {\r\n\t\t\t\tcase 'hp':\r\n\t\t\t\tcase 'hitpoints':\r\n\t\t\t\t\tcalcHP = true;\r\n\t\t\t\t\tuseStat = 'hp';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\tcase 'atk':\r\n\t\t\t\tcase 'attack':\r\n\t\t\t\t\tuseStat = 'atk';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\tcase 'def':\r\n\t\t\t\tcase 'defense':\r\n\t\t\t\t\tuseStat = 'def';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\tcase 'spa':\r\n\t\t\t\t\tuseStat = 'spa';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\tcase 'spd':\r\n\t\t\t\tcase 'sdef':\r\n\t\t\t\t\tuseStat = 'spd';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\tcase 'spe':\r\n\t\t\t\tcase 'speed':\r\n\t\t\t\t\tuseStat = 'spe';\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!natureSet) {\r\n\t\t\t\tif (lowercase === 'boosting' || lowercase === 'positive') {\r\n\t\t\t\t\tnature = 1.1;\r\n\t\t\t\t\tnatureSet = true;\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t} else if (lowercase === 'negative' || lowercase === 'inhibiting') {\r\n\t\t\t\t\tnature = 0.9;\r\n\t\t\t\t\tnatureSet = true;\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t} else if (lowercase === 'neutral') {\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!pokemon) {\r\n\t\t\t\tconst testPoke = Dex.species.get(arg);\r\n\t\t\t\tif (testPoke.exists) {\r\n\t\t\t\t\tpokemon = testPoke.baseStats;\r\n\t\t\t\t\tbaseSet = true;\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!ivSet) {\r\n\t\t\t\tif (lowercase.endsWith('iv') || lowercase.endsWith('ivs')) {\r\n\t\t\t\t\tiv = parseInt(arg);\r\n\t\t\t\t\tivSet = true;\r\n\r\n\t\t\t\t\tif (isNaN(iv)) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('Invalid value for IVs: ' + Utils.escapeHTML(arg));\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!evSet) {\r\n\t\t\t\tif (lowercase === 'invested' || lowercase === 'max') {\r\n\t\t\t\t\tevSet = true;\r\n\t\t\t\t\tif (lowercase === 'max' && !natureSet) {\r\n\t\t\t\t\t\tnature = 1.1;\r\n\t\t\t\t\t\tnatureSet = true;\r\n\t\t\t\t\t}\r\n\t\t\t\t} else if (lowercase === 'uninvested') {\r\n\t\t\t\t\tev = 0;\r\n\t\t\t\t\tevSet = true;\r\n\t\t\t\t} else if (lowercase.endsWith('ev') || lowercase.endsWith('evs') ||\r\n\t\t\t\t\tlowercase.endsWith('+') || lowercase.endsWith('-')) {\r\n\t\t\t\t\tev = parseInt(arg);\r\n\t\t\t\t\tevSet = true;\r\n\r\n\t\t\t\t\tif (isNaN(ev)) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('Invalid value for EVs: ' + Utils.escapeHTML(arg));\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (ev > 255 || ev < 0) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('The amount of EVs should be between 0 and 255.');\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tif (!natureSet) {\r\n\t\t\t\t\t\tif (arg.includes('+')) {\r\n\t\t\t\t\t\t\tnature = 1.1;\r\n\t\t\t\t\t\t\tnatureSet = true;\r\n\t\t\t\t\t\t} else if (arg.includes('-')) {\r\n\t\t\t\t\t\t\tnature = 0.9;\r\n\t\t\t\t\t\t\tnatureSet = true;\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!modSet) {\r\n\t\t\t\tif (['band', 'scarf', 'specs'].includes(arg)) {\r\n\t\t\t\t\tmodifier = 1;\r\n\t\t\t\t\tmodSet = true;\r\n\t\t\t\t} else if (arg.startsWith('+')) {\r\n\t\t\t\t\tmodifier = parseInt(arg.charAt(1));\r\n\t\t\t\t\tmodSet = true;\r\n\t\t\t\t} else if (arg.startsWith('-')) {\r\n\t\t\t\t\tpositiveMod = false;\r\n\t\t\t\t\tmodifier = parseInt(arg.charAt(1));\r\n\t\t\t\t\tmodSet = true;\r\n\t\t\t\t}\r\n\t\t\t\tif (isNaN(modifier)) {\r\n\t\t\t\t\treturn this.sendReplyBox('Invalid value for modifier: ' + Utils.escapeHTML(String(modifier)));\r\n\t\t\t\t}\r\n\t\t\t\tif (modifier > 6) {\r\n\t\t\t\t\treturn this.sendReplyBox('Modifier should be a number between -6 and +6');\r\n\t\t\t\t}\r\n\t\t\t\tif (modSet) continue;\r\n\t\t\t}\r\n\r\n\t\t\tconst tempStat = parseInt(arg);\r\n\r\n\t\t\tif (!realSet) {\r\n\t\t\t\tif (lowercase.endsWith('real')) {\r\n\t\t\t\t\trealStat = tempStat;\r\n\t\t\t\t\trealSet = true;\r\n\r\n\t\t\t\t\tif (isNaN(realStat)) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('Invalid value for target real stat: ' + Utils.escapeHTML(arg));\r\n\t\t\t\t\t}\r\n\t\t\t\t\tif (realStat < 0) {\r\n\t\t\t\t\t\treturn this.sendReplyBox('The target real stat must be greater than 0.');\r\n\t\t\t\t\t}\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\r\n\t\t\tif (!isNaN(tempStat) && !baseSet && tempStat > 0 && tempStat < 256) {\r\n\t\t\t\tbaseStat = tempStat;\r\n\t\t\t\tbaseSet = true;\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (pokemon) {\r\n\t\t\tif (useStat) {\r\n\t\t\t\tbaseStat = pokemon[useStat];\r\n\t\t\t} else {\r\n\t\t\t\treturn this.sendReplyBox('No stat found.');\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (realSet) {\r\n\t\t\tif (!baseSet) {\r\n\t\t\t\tif (calcHP) {\r\n\t\t\t\t\tbaseStat = Math.ceil((100 * realStat - 10 - level * (Math.floor(ev / 4) + iv + 100)) / (2 * level));\r\n\t\t\t\t} else {\r\n\t\t\t\t\tif (!positiveMod) {\r\n\t\t\t\t\t\trealStat *= (2 + modifier) / 2;\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\trealStat *= 2 / (2 + modifier);\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tbaseStat = Math.ceil(\r\n\t\t\t\t\t\t(100 * Math.ceil(realStat) - nature * (level * (Math.floor(ev / 4) + iv) + 500)) /\r\n\t\t\t\t\t\t(2 * level * nature)\r\n\t\t\t\t\t);\r\n\t\t\t\t}\r\n\t\t\t\tif (baseStat < 0) {\r\n\t\t\t\t\treturn this.sendReplyBox('No valid value for base stat possible with given parameters.');\r\n\t\t\t\t}\r\n\t\t\t} else if (!evSet) {\r\n\t\t\t\tif (calcHP) {\r\n\t\t\t\t\tev = Math.ceil(100 * (realStat - 10) / level - 2 * (baseStat + 50));\r\n\t\t\t\t} else {\r\n\t\t\t\t\tif (!positiveMod) {\r\n\t\t\t\t\t\trealStat *= (2 + modifier) / 2;\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\trealStat *= 2 / (2 + modifier);\r\n\t\t\t\t\t}\r\n\r\n\t\t\t\t\tev = Math.ceil(-1 * (2 * (nature * (baseStat * level + 250) - 50 * Math.ceil(realStat))) / (level * nature));\r\n\t\t\t\t}\r\n\t\t\t\tev -= 31;\r\n\t\t\t\tif (ev < 0) iv += ev;\r\n\t\t\t\tev *= 4;\r\n\t\t\t\tif (iv < 0 || ev > 255) {\r\n\t\t\t\t\treturn this.sendReplyBox('No valid EV/IV combination possible with given parameters. Maybe try a different nature?' + ev);\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\treturn this.sendReplyBox('Too many parameters given; nothing to calculate.');\r\n\t\t\t}\r\n\t\t} else if (baseStat < 0) {\r\n\t\t\treturn this.sendReplyBox('No valid value for base stat found.');\r\n\t\t}\r\n\r\n\t\tlet output: number;\r\n\r\n\t\tif (calcHP) {\r\n\t\t\toutput = (((iv + (2 * baseStat) + Math.floor(ev / 4) + 100) * level) / 100) + 10;\r\n\t\t} else {\r\n\t\t\toutput = Math.floor(nature * Math.floor((((iv + (2 * baseStat) + Math.floor(ev / 4)) * level) / 100) + 5));\r\n\t\t\tif (positiveMod) {\r\n\t\t\t\toutput *= (2 + modifier) / 2;\r\n\t\t\t} else {\r\n\t\t\t\toutput *= 2 / (2 + modifier);\r\n\t\t\t}\r\n\t\t}\r\n\t\treturn this.sendReplyBox(`Base ${baseStat} ${calcHP ? ' HP ' : ' '}at level ${level} with ${iv} IVs, ${ev}${nature === 1.1 ? '+' : nature === 0.9 ? '-' : ''} EVs${modifier > 0 && !calcHP ? ` at ${positiveMod ? '+' : '-'}${modifier}` : ''}: ${Math.floor(output)}.`);\r\n\t},\r\n\tstatcalchelp: [\r\n\t\t`/statcalc [level] [base stat] [IVs] [nature] [EVs] [modifier] (only base stat is required) - Calculates what the actual stat of a Pok\u00E9mon is with the given parameters. For example, '/statcalc lv50 100 30iv positive 252ev scarf' calculates the speed of a base 100 scarfer with HP Ice in Battle Spot, and '/statcalc uninvested 90 neutral' calculates the attack of an uninvested Crobat.`,\r\n\t\t`!statcalc [level] [base stat] [IVs] [nature] [EVs] [modifier] (only base stat is required) - Shows this information to everyone.`,\r\n\t\t`Inputing 'hp' as an argument makes it use the formula for HP. Instead of giving nature, '+' and '-' can be appended to the EV amount (e.g. 252+ev) to signify a boosting or inhibiting nature.`,\r\n\t\t`An actual stat can be given in place of a base stat or EVs. In this case, the minumum base stat or EVs necessary to have that real stat with the given parameters will be determined. For example, '/statcalc 502real 252+ +1' calculates the minimum base speed necessary for a positive natured fully invested scarfer to outspeed`,\r\n\t],\r\n\r\n\t/*********************************************************\r\n\t * Informational commands\r\n\t *********************************************************/\r\n\r\n\tuptime(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tconst uptime = process.uptime();\r\n\t\tlet uptimeText;\r\n\t\tif (uptime > 24 * 60 * 60) {\r\n\t\t\tconst uptimeDays = Math.floor(uptime / (24 * 60 * 60));\r\n\t\t\tuptimeText = uptimeDays + \" \" + (uptimeDays === 1 ? \"day\" : \"days\");\r\n\t\t\tconst uptimeHours = Math.floor(uptime / (60 * 60)) - uptimeDays * 24;\r\n\t\t\tif (uptimeHours) uptimeText += \", \" + uptimeHours + \" \" + (uptimeHours === 1 ? \"hour\" : \"hours\");\r\n\t\t} else {\r\n\t\t\tuptimeText = Chat.toDurationString(uptime * 1000);\r\n\t\t}\r\n\t\tthis.sendReplyBox(\"Uptime: \" + uptimeText + \"\");\r\n\t},\r\n\tuptimehelp: [`/uptime - Shows how long the server has been online for.`],\r\n\r\n\tst: 'servertime',\r\n\tservertime(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tconst servertime = new Date();\r\n\t\tthis.sendReplyBox(`Server time: ${servertime.toLocaleString()}`);\r\n\t},\r\n\tservertimehelp: [`/servertime - Shows the current time where the server is.`],\r\n\r\n\tgroups(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\ttarget = toID(target);\r\n\t\tconst showRoom = (target !== 'global');\r\n\t\tconst showGlobal = (target !== 'room' && target !== 'rooms');\r\n\r\n\t\tconst roomRanks = [\r\n\t\t\t`Room ranks`,\r\n\t\t\t`^ Prize Winner - They don't have any powers beyond a symbol.`,\r\n\t\t\t`+ Voice - They can use ! commands like !groups`,\r\n\t\t\t`% Driver - The above, and they can mute and warn`,\r\n\t\t\t`@ Moderator - The above, and they can room ban users`,\r\n\t\t\t`* Bot - An automated account that can mute, warn, and use HTML`,\r\n\t\t\t`# Room Owner - They are leaders of the room and can almost totally control it`,\r\n\t\t];\r\n\r\n\t\tconst globalRanks = [\r\n\t\t\t`Global ranks`,\r\n\t\t\t`+ Global Voice - They can use ! commands like !groups`,\r\n\t\t\t`\u00A7 Section Leader - They oversee rooms in a particular section`,\r\n\t\t\t`% Global Driver - Like Voice, and they can lock users and check for alts`,\r\n\t\t\t`@ Global Moderator - The above, and they can globally ban users`,\r\n\t\t\t`* Global Bot - An automated account that can use HTML anywhere`,\r\n\t\t\t`& Global Administrator - They can do anything, like change what this message says and promote users globally`,\r\n\t\t];\r\n\r\n\t\tthis.sendReplyBox(\r\n\t\t\t(showRoom ? roomRanks.map(str => this.tr(str)).join('
') : ``) +\r\n\t\t\t(showRoom && showGlobal ? `

` : ``) +\r\n\t\t\t(showGlobal ? globalRanks.map(str => this.tr(str)).join('
') : ``)\r\n\t\t);\r\n\t},\r\n\tgroupshelp: [\r\n\t\t`/groups - Explains what the symbols (like % and @) before people's names mean.`,\r\n\t\t`/groups [global|room] - Explains only global or room symbols.`,\r\n\t\t`!groups - Shows everyone that information. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tpunishments(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\ttarget = toID(target);\r\n\t\tconst showRoom = (target !== 'global');\r\n\t\tconst showGlobal = (target !== 'room' && target !== 'rooms');\r\n\r\n\t\tconst roomPunishments = [\r\n\t\t\t`Room punishments:`,\r\n\t\t\t`warn - Displays a popup with the rules.`,\r\n\t\t\t`mute - Mutes a user (makes them unable to talk) for 7 minutes.`,\r\n\t\t\t`hourmute - Mutes a user for 60 minutes.`,\r\n\t\t\t`ban - Bans a user (makes them unable to join the room) for 2 days.`,\r\n\t\t\t`weekban - Bans a user from the room for a week.`,\r\n\t\t\t`blacklist - Bans a user for a year.`,\r\n\t\t];\r\n\r\n\t\tconst globalPunishments = [\r\n\t\t\t`Global punishments:`,\r\n\t\t\t`lock - Locks a user (makes them unable to talk in any rooms or PM non-staff) for 2 days.`,\r\n\t\t\t`weeklock - Locks a user for a week.`,\r\n\t\t\t`namelock - Locks a user and prevents them from having a username for 2 days.`,\r\n\t\t\t`globalban - Globally bans (makes them unable to connect and play games) for a week.`,\r\n\t\t];\r\n\r\n\t\tconst indefinitePunishments = [\r\n\t\t\tthis.tr`Indefinite global punishments:`,\r\n\t\t\tthis.tr`permalock - Issued for repeated instances of bad behavior and is rarely the result of a single action. ` +\r\n\t\t\t\tthis.tr`These can be appealed in the Discipline Appeal` +\r\n\t\t\t\tthis.tr` forum after at least 3 months without incident.`,\r\n\t\t\tthis.tr`permaban - Unappealable global ban typically issued for the most severe cases of offensive/inappropriate behavior.`,\r\n\t\t];\r\n\r\n\t\tthis.sendReplyBox(\r\n\t\t\t(showRoom ? roomPunishments.map(str => this.tr(str)).join('
') : ``) +\r\n\t\t\t(showRoom && showGlobal ? `

` : ``) +\r\n\t\t\t(showGlobal ? globalPunishments.map(str => this.tr(str)).join('
') : ``) +\r\n\t\t\t(showGlobal ? `

${indefinitePunishments.join('
')}` : ``)\r\n\t\t);\r\n\t},\r\n\tpunishmentshelp: [\r\n\t\t`/punishments - Explains punishments.`,\r\n\t\t`!punishments - Show everyone that information. Requires: + % @ # &`,\r\n\t],\r\n\r\n\trepo: 'opensource',\r\n\trepository: 'opensource',\r\n\tgit: 'opensource',\r\n\topensource(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`Pokémon Showdown is open source:
` +\r\n\t\t\t`- Language: mostly TypeScript, a little PHP
` +\r\n\t\t\t`- What's new?
` +\r\n\t\t\t`- Server source code
` +\r\n\t\t\t`- Client source code
` +\r\n\t\t\t`- Dex source code` +\r\n\t\t\t`- Login server source code`\r\n\t\t);\r\n\t},\r\n\topensourcehelp: [\r\n\t\t`/opensource - Links to PS's source code repository.`,\r\n\t\t`!opensource - Show everyone that information. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tstaff(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(`Pokémon Showdown Staff List`);\r\n\t},\r\n\tstaffhelp: [`/staff - View the staff list.`],\r\n\r\n\tforums(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(`Pokémon Showdown Forums`);\r\n\t},\r\n\tforumshelp: [`/forums - Links to the PS forums.`],\r\n\r\n\tprivacypolicy(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox([\r\n\t\t\tthis.tr`- We log PMs so you can report them - staff can't look at them without permission unless there's a law enforcement reason.`,\r\n\t\t\tthis.tr`- We log IPs to enforce bans and mutes.`,\r\n\t\t\tthis.tr`- We use cookies to save your login info and teams, and for Google Analytics and AdSense.`,\r\n\t\t\tthis.tr`- For more information, you can read our full privacy policy.`,\r\n\t\t].join(`
`));\r\n\t},\r\n\tprivacypolicyhelp: [`/privacypolicy - Displays PS's privacy policy.`],\r\n\r\n\tsuggest: 'suggestions',\r\n\tsuggestion: 'suggestions',\r\n\tsuggestions(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(`Make a suggestion for Pokémon Showdown`);\r\n\t},\r\n\tsuggestionshelp: [`/suggestions - Links to the place to make suggestions for Pokemon Showdown.`],\r\n\r\n\tbugreport: 'bugs',\r\n\tbugreports: 'bugs',\r\n\tbugs(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tif (room?.battle) {\r\n\t\t\tthis.sendReplyBox(`
QuestionsBug Reports
`);\r\n\t\t} else {\r\n\t\t\tthis.sendReplyBox(\r\n\t\t\t\t`Have a replay showcasing a bug on Pokémon Showdown?
` +\r\n\t\t\t\t`- Questions
` +\r\n\t\t\t\t`- Bug Reports (ask in Help before posting in the thread if you're unsure)`\r\n\t\t\t);\r\n\t\t}\r\n\t},\r\n\tbugshelp: [`/bugs - Links to the various bug reporting services.`],\r\n\r\n\toptionbutton: 'optionsbutton',\r\n\toptionsbutton(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(` (The Sound and Options buttons are at the top right, next to your username)`);\r\n\t},\r\n\toptionsbuttonhelp: [`/optionsbutton - Provides a button to the Options menu.`],\r\n\r\n\tsoundsbutton: 'soundbutton',\r\n\tvolumebutton: 'soundbutton',\r\n\tsoundbutton(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(` (The Sound and Options buttons are at the top right, next to your username)`);\r\n\t},\r\n\tsoundbuttonhelp: [`/soundbutton - Provides a button to the Sounds menu.`],\r\n\r\n\tintroduction: 'intro',\r\n\tintro(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`New to competitive Pokémon?
` +\r\n\t\t\t`- Beginner's Guide to Pokémon Showdown
` +\r\n\t\t\t`- An introduction to competitive Pokémon
` +\r\n\t\t\t`- What do 'OU', 'UU', etc mean?
` +\r\n\t\t\t`- What are the rules for each format?
` +\r\n\t\t\t`- What is 'Sleep Clause' and other clauses?
` +\r\n\t\t\t`- Next Steps for Competitive Battling`\r\n\t\t);\r\n\t},\r\n\tintrohelp: [\r\n\t\t`/intro - Provides an introduction to competitive Pok\\u00e9mon.`,\r\n\t\t`!intro - Show everyone that information. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tmentoring: 'smogintro',\r\n\tsmogonintro: 'smogintro',\r\n\tsmogintro(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`Welcome to Smogon's official simulator! The Information & Resources forum can help you get integrated into the community.
` +\r\n\t\t\t`- Useful Smogon Info
` +\r\n\t\t\t`- Tiering FAQ
`\r\n\t\t);\r\n\t},\r\n\tsmogintrohelp: [`/smogintro - Provides an introduction to Smogon.`],\r\n\r\n\tbsscalc: 'calc',\r\n\tcalculator: 'calc',\r\n\tcantsaycalc: 'calc',\r\n\tdamagecalculator: 'calc',\r\n\tdamagecalc: 'calc',\r\n\thonkalculator: 'calc',\r\n\thonkocalc: 'calc',\r\n\trandomscalc: 'calc',\r\n\trandbatscalc: 'calc',\r\n\trcalc: 'calc',\r\n\tcalc(target, room, user, connection, cmd) {\r\n\t\tif (cmd === 'calc' && target) return this.run('calculate');\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tconst DEFAULT_CALC_COMMANDS = ['honkalculator', 'honkocalc'];\r\n\t\tconst RANDOMS_CALC_COMMANDS = ['randomscalc', 'randbatscalc', 'rcalc'];\r\n\t\tconst BATTLESPOT_CALC_COMMANDS = ['bsscalc', 'cantsaycalc'];\r\n\t\tconst SUPPORTED_RANDOM_FORMATS = [\r\n\t\t\t'gen8randombattle', 'gen8unratedrandombattle', 'gen7randombattle', 'gen6randombattle', 'gen5randombattle', 'gen4randombattle', 'gen3randombattle', 'gen2randombattle', 'gen1randombattle',\r\n\t\t];\r\n\t\tconst SUPPORTED_BATTLESPOT_FORMATS = [\r\n\t\t\t'gen5gbusingles', 'gen5gbudoubles', 'gen6battlespotsingles', 'gen6battlespotdoubles', 'gen6battlespottriples', 'gen7battlespotsingles', 'gen7battlespotdoubles', 'gen7bssfactory',\r\n\t\t];\r\n\t\tconst isRandomBattle = (room?.battle && SUPPORTED_RANDOM_FORMATS.includes(room.battle.format));\r\n\t\tconst isBattleSpotBattle = (room?.battle && (SUPPORTED_BATTLESPOT_FORMATS.includes(room.battle.format) ||\r\n\t\t\troom.battle.format.includes(\"battlespotspecial\")));\r\n\t\tif (RANDOMS_CALC_COMMANDS.includes(cmd) ||\r\n\t\t\t(isRandomBattle && !DEFAULT_CALC_COMMANDS.includes(cmd) && !BATTLESPOT_CALC_COMMANDS.includes(cmd))) {\r\n\t\t\treturn this.sendReplyBox(\r\n\t\t\t\t`Random Battles damage calculator. (Courtesy of Austin)
` +\r\n\t\t\t\t`- Random Battles Damage Calculator`\r\n\t\t\t);\r\n\t\t}\r\n\t\tif (BATTLESPOT_CALC_COMMANDS.includes(cmd) || (isBattleSpotBattle && !DEFAULT_CALC_COMMANDS.includes(cmd))) {\r\n\t\t\treturn this.sendReplyBox(\r\n\t\t\t\t`Battle Spot damage calculator. (Courtesy of cant say & LegoFigure11)
` +\r\n\t\t\t\t`- Battle Spot Damage Calculator`\r\n\t\t\t);\r\n\t\t}\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`Pokémon Showdown! damage calculator. (Courtesy of Honko, Austin, & Kris)
` +\r\n\t\t\t`- Damage Calculator`\r\n\t\t);\r\n\t},\r\n\tcalchelp: [\r\n\t\t`/calc - Provides a link to a damage calculator`,\r\n\t\t`/rcalc - Provides a link to the random battles damage calculator`,\r\n\t\t`/bsscalc - Provides a link to the Battle Spot damage calculator`,\r\n\t\t`!calc - Shows everyone a link to a damage calculator. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tcapintro: 'cap',\r\n\tcap(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`An introduction to the Create-A-Pokémon project:
` +\r\n\t\t\t`- CAP project website and description
` +\r\n\t\t\t`- CAP project discussion forum
` +\r\n\t\t\t`- What Pokémon have been made?
` +\r\n\t\t\t`- Talk about the metagame here
` +\r\n\t\t\t`- Sample SS CAP teams`\r\n\t\t);\r\n\t},\r\n\tcaphelp: [\r\n\t\t`/cap - Provides an introduction to the Create-A-Pok\\u00e9mon project.`,\r\n\t\t`!cap - Show everyone that information. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tgennext(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t\"NEXT (also called Gen-NEXT) is a mod that makes changes to the game:
\" +\r\n\t\t\t`- README: overview of NEXT
` +\r\n\t\t\t\"Example replays:
\" +\r\n\t\t\t`- Zergo vs Mr Weegle Snarf
` +\r\n\t\t\t`- NickMP vs Khalogie`\r\n\t\t);\r\n\t},\r\n\tgennexthelp: [`/gennext - Provides information on the Gen-NEXT mod.`],\r\n\r\n\tbattlerules(target, room, user) {\r\n\t\treturn this.parse(`/join view-battlerules`);\r\n\t},\r\n\tbattleruleshelp: [\r\n\t\t`/battlerules - Provides information on the rules that can be added to tournament and challenge battles.`,\r\n\t],\r\n\r\n\tbanlists: 'formathelp',\r\n\ttier: 'formathelp',\r\n\ttiers: 'formathelp',\r\n\tformats: 'formathelp',\r\n\ttiershelp: 'formathelp',\r\n\tformatshelp: 'formathelp',\r\n\tviewbanlist: 'formathelp',\r\n\tformathelp(target, room, user, connection, cmd) {\r\n\t\tif (!target && this.runBroadcast()) {\r\n\t\t\treturn this.sendReplyBox(\r\n\t\t\t\t`- Smogon Tiers
` +\r\n\t\t\t\t`- Tiering FAQ
` +\r\n\t\t\t\t`- The banlists for each tier
` +\r\n\t\t\t\t\"
Type /formatshelp [format|section] to get details about an available format or group of formats.\"\r\n\t\t\t);\r\n\t\t}\r\n\r\n\t\tconst isOMSearch = (cmd === 'om' || cmd === 'othermetas');\r\n\r\n\t\tlet targetId = toID(target);\r\n\t\tif (targetId === 'ladder') targetId = 'search' as ID;\r\n\t\tif (targetId === 'all') targetId = '';\r\n\t\tconst {totalMatches, sections} = findFormats(targetId, isOMSearch);\r\n\r\n\t\tif (!totalMatches) return this.errorReply(\"No matched formats found.\");\r\n\r\n\t\tconst format = totalMatches === 1 ? Dex.formats.get(Object.values(sections)[0].formats[0]) : null;\r\n\r\n\t\tif (!this.runBroadcast(`!formathelp ${format ? format.id : target}`)) return;\r\n\r\n\t\tif (format) {\r\n\t\t\tconst rules: string[] = [];\r\n\t\t\tlet rulesetHtml = '';\r\n\t\t\tif (['Format', 'Rule', 'ValidatorRule'].includes(format.effectType)) {\r\n\t\t\t\tif (format.ruleset?.length) {\r\n\t\t\t\t\trules.push(`Ruleset - ${Utils.escapeHTML(format.ruleset.join(\", \"))}`);\r\n\t\t\t\t}\r\n\t\t\t\tif (format.banlist?.length) {\r\n\t\t\t\t\trules.push(`Bans - ${Utils.escapeHTML(format.banlist.join(\", \"))}`);\r\n\t\t\t\t}\r\n\t\t\t\tif (format.unbanlist?.length) {\r\n\t\t\t\t\trules.push(`Unbans - ${Utils.escapeHTML(format.unbanlist.join(\", \"))}`);\r\n\t\t\t\t}\r\n\t\t\t\tif (format.restricted?.length) {\r\n\t\t\t\t\trules.push(`Restricted - ${Utils.escapeHTML(format.restricted.join(\", \"))}`);\r\n\t\t\t\t}\r\n\t\t\t\tif (rules.length > 0) {\r\n\t\t\t\t\trulesetHtml = `
Banlist/Ruleset${rules.join(\"
\")}
`;\r\n\t\t\t\t} else {\r\n\t\t\t\t\trulesetHtml = `No ruleset found for ${format.name}`;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tlet formatType: string = (format.gameType || \"singles\");\r\n\t\t\tformatType = formatType.charAt(0).toUpperCase() + formatType.slice(1).toLowerCase();\r\n\t\t\tif (!format.desc && !format.threads) {\r\n\t\t\t\tif (format.effectType === 'Format') {\r\n\t\t\t\t\treturn this.sendReplyBox(`No description found for this ${formatType} ${format.section} format.
${rulesetHtml}`);\r\n\t\t\t\t} else {\r\n\t\t\t\t\treturn this.sendReplyBox(`No description found for this rule.
${rulesetHtml}`);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tconst descHtml = [...(format.desc ? [format.desc] : []), ...(format.threads || [])];\r\n\t\t\treturn this.sendReplyBox(`${descHtml.join(\"
\")}
${rulesetHtml}`);\r\n\t\t}\r\n\r\n\t\tlet tableStyle = `border:1px solid gray; border-collapse:collapse`;\r\n\r\n\t\tif (this.broadcasting) {\r\n\t\t\ttableStyle += `; display:inline-block; max-height:240px;\" class=\"scrollable`;\r\n\t\t}\r\n\r\n\t\t// Build tables\r\n\t\tconst buf = [``];\r\n\t\tfor (const sectionId in sections) {\r\n\t\t\tbuf.push(Utils.html``);\r\n\t\t\tfor (const section of sections[sectionId].formats) {\r\n\t\t\t\tconst subformat = Dex.formats.get(section);\r\n\t\t\t\tconst nameHTML = Utils.escapeHTML(subformat.name);\r\n\t\t\t\tconst desc = [...(subformat.desc ? [subformat.desc] : []), ...(subformat.threads || [])];\r\n\t\t\t\tconst descHTML = desc.length ? desc.join(\"
\") : \"—\";\r\n\t\t\t\tbuf.push(``);\r\n\t\t\t}\r\n\t\t}\r\n\t\tbuf.push(`
${sections[sectionId].name}
${nameHTML}${descHTML}
`);\r\n\t\treturn this.sendReply(`|raw|${buf.join(\"\")}`);\r\n\t},\r\n\tformathelphelp: [\r\n\t\t`/formathelp [format] - Provides information on the given [format].`,\r\n\t\t`If no format is given, provides information on how tiers work.`,\r\n\t],\r\n\r\n\troomhelp(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tthis.checkBroadcast(false, '!htmlbox');\r\n\t\tif (this.broadcastMessage) this.checkCan('declare', null, room);\r\n\r\n\t\tif (!this.runBroadcast(false, '!htmlbox')) return;\r\n\r\n\t\tconst strings = [\r\n\t\t\t[\r\n\t\t\t\t`Room drivers (%) can use:`,\r\n\t\t\t\t`- /warn OR /k username: warn a user and show the Pokémon Showdown rules`,\r\n\t\t\t\t`- /mute OR /m username: 7 minute mute`,\r\n\t\t\t\t`- /hourmute OR /hm username: 60 minute mute`,\r\n\t\t\t\t`- /unmute username: unmute`,\r\n\t\t\t\t`- /hidetext username: hide a user's messages from the room`,\r\n\t\t\t\t`- /announce OR /wall message: make an announcement`,\r\n\t\t\t\t`- /modlog username: search the moderator log of the room`,\r\n\t\t\t\t`- /modnote note: add a moderator note that can be read through modlog`,\r\n\t\t\t\t`- !show [image or youtube link]: display given media in chat.`,\r\n\t\t\t],\r\n\t\t\t[\r\n\t\t\t\t`Room moderators (@) can also use:`,\r\n\t\t\t\t`- /roomban OR /rb username: ban user from the room`,\r\n\t\t\t\t`- /roomunban username: unban user from the room`,\r\n\t\t\t\t`- /roomvoice username: appoint a room voice`,\r\n\t\t\t\t`- /roomdevoice username: remove a room voice`,\r\n\t\t\t\t`- /staffintro intro: set the staff introduction that will be displayed for all staff joining the room`,\r\n\t\t\t\t`- /roomsettings: change a variety of room settings, namely modchat`,\r\n\t\t\t],\r\n\t\t\t[\r\n\t\t\t\t`Room owners (#) can also use:`,\r\n\t\t\t\t`- /roomintro intro: set the room introduction that will be displayed for all users joining the room`,\r\n\t\t\t\t`- /rules rules link: set the room rules link seen when using /rules`,\r\n\t\t\t\t`- /roommod, /roomdriver username: appoint a room moderator/driver`,\r\n\t\t\t\t`- /roomdemod, /roomdedriver username: remove a room moderator/driver`,\r\n\t\t\t\t`- /roomdeauth username: remove all room auth from a user`,\r\n\t\t\t\t`- /declare message: make a large blue declaration to the room`,\r\n\t\t\t\t`- !htmlbox HTML code: broadcast a box of HTML code to the room`,\r\n\t\t\t\t`- /roomsettings: change a variety of room settings, including modchat, capsfilter, etc`,\r\n\t\t\t],\r\n\t\t\t[\r\n\t\t\t\t`More detailed help can be found in the roomauth guide`,\r\n\t\t\t],\r\n\t\t\t[\r\n\t\t\t\t`Tournament Help:`,\r\n\t\t\t\t`- /tour create format, elimination: create a new single elimination tournament in the current room.`,\r\n\t\t\t\t`- /tour create format, roundrobin: create a new round robin tournament in the current room.`,\r\n\t\t\t\t`- /tour end: forcibly end the tournament in the current room`,\r\n\t\t\t\t`- /tour start: start the tournament in the current room`,\r\n\t\t\t\t`- /tour banlist [pokemon], [talent], [...]: ban moves, abilities, Pok\u00E9mon or items from being used in a tournament (it must be created first)`,\r\n\t\t\t],\r\n\t\t\t[\r\n\t\t\t\t`More detailed help can be found in the tournaments guide`,\r\n\t\t\t],\r\n\t\t];\r\n\r\n\t\tthis.sendReplyBox(\r\n\t\t\tstrings.map(par => par.map(string => this.tr(string)).join('
')).join('

')\r\n\t\t);\r\n\t},\r\n\r\n\trestarthelp(target, room, user) {\r\n\t\tif (!Rooms.global.lockdown) this.checkCan('lockdown');\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(\r\n\t\t\t`The server is restarting. Things to know:
` +\r\n\t\t\t`- We wait a few minutes before restarting so people can finish up their battles
` +\r\n\t\t\t`- The restart itself will take around 0.6 seconds
` +\r\n\t\t\t`- Your ladder ranking and teams will not change
` +\r\n\t\t\t`- We are restarting to update Pokémon Showdown to a newer version`\r\n\t\t);\r\n\t},\r\n\r\n\trule: 'rules',\r\n\troomrules: \"rules\",\r\n\trules(target, room, user, connection, cmd) {\r\n\t\tif (!target) {\r\n\t\t\tif (!this.runBroadcast()) return;\r\n\t\t\tthis.sendReplyBox(\r\n\t\t\t\t`${room ? this.tr`Please follow the rules:` + '
' : ``}` +\r\n\t\t\t\t`${room?.settings.rulesLink ? Utils.html`- ${this.tr`${room.title} room rules`}
` : ``}` +\r\n\t\t\t\t`- ${this.tr`Global Rules`}`\r\n\t\t\t);\r\n\t\t\treturn;\r\n\t\t}\r\n\t\tif (!room) {\r\n\t\t\treturn this.errorReply(`This is not a room you can set the rules of.`);\r\n\t\t}\r\n\t\tconst possibleRoom = Rooms.search(toID(target));\r\n\t\tconst {totalMatches: formatMatches} = findFormats(toID(target));\r\n\t\tif (formatMatches && possibleRoom && cmd !== 'roomrules') {\r\n\t\t\tthis.errorReply(`'${target}' is both a room and a tier. `);\r\n\t\t\tthis.errorReply(`If you were looking for rules of that room, use /roomrules [room].`);\r\n\t\t\tthis.errorReply(`Otherwise, use /tier [tiername].`);\r\n\t\t\treturn;\r\n\t\t}\r\n\r\n\t\tif (possibleRoom) {\r\n\t\t\tconst rulesLink = possibleRoom.settings.rulesLink;\r\n\t\t\treturn this.sendReplyBox(\r\n\t\t\t\t`${possibleRoom.title}'s rules:
` +\r\n\t\t\t\t`${rulesLink ? Utils.html`- ${this.tr`${possibleRoom.title} room rules`}
` : `None set.`}`\r\n\t\t\t);\r\n\t\t}\r\n\r\n\t\tif (formatMatches > 0 && cmd !== 'roomrules') {\r\n\t\t\treturn this.parse(`/tier ${target}`);\r\n\t\t}\r\n\t\tthis.checkCan('editroom', null, room);\r\n\t\tif (target.length > 150) {\r\n\t\t\treturn this.errorReply(`Error: Room rules link is too long (must be under 150 characters). You can use a URL shortener to shorten the link.`);\r\n\t\t}\r\n\r\n\t\ttarget = target.trim();\r\n\r\n\t\tif (target === 'delete' || target === 'remove') {\r\n\t\t\tif (!room.settings.rulesLink) return this.errorReply(`This room does not have rules set to remove.`);\r\n\t\t\tdelete room.settings.rulesLink;\r\n\t\t\tthis.privateModAction(`${user.name} has removed the room rules link.`);\r\n\t\t\tthis.modlog('RULES', null, `removed room rules link`);\r\n\t\t} else {\r\n\t\t\troom.settings.rulesLink = target;\r\n\t\t\tthis.privateModAction(`${user.name} changed the room rules link to: ${target}`);\r\n\t\t\tthis.modlog('RULES', null, `changed link to: ${target}`);\r\n\t\t}\r\n\r\n\t\troom.saveSettings();\r\n\t},\r\n\truleshelp: [\r\n\t\t`/rules - Show links to room rules and global rules.`,\r\n\t\t`!rules - Show everyone links to room rules and global rules. Requires: + % @ # &`,\r\n\t\t`/rules [url] - Change the room rules URL. Requires: # &`,\r\n\t\t`/rules remove - Removes a room rules URL. Requires: # &`,\r\n\t],\r\n\r\n\tfaq(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\ttarget = toID(target);\r\n\t\tconst showAll = target === 'all';\r\n\t\tif (showAll && this.broadcasting) {\r\n\t\t\treturn this.sendReplyBox(this.tr`You cannot broadcast all FAQs at once.`);\r\n\t\t}\r\n\r\n\t\tconst buffer = [];\r\n\t\tif (showAll || target === 'staff') {\r\n\t\t\tbuffer.push(`${this.tr`Staff FAQ`}`);\r\n\t\t}\r\n\t\tif (showAll || target === 'autoconfirmed' || target === 'ac') {\r\n\t\t\tbuffer.push(this.tr`A user is autoconfirmed when they have won at least one rated battle and have been registered for one week or longer. In order to prevent spamming and trolling, most chatrooms only allow autoconfirmed users to chat. If you are not autoconfirmed, you can politely PM a staff member (staff have %, @, or # in front of their username) in the room you would like to chat and ask them to disable modchat. However, staff are not obligated to disable modchat.`);\r\n\t\t\tif (!this.broadcasting) void this.parse(`/regtime`);\r\n\t\t}\r\n\t\tif (showAll || target === 'ladder' || target === 'ladderhelp' || target === 'decay') {\r\n\t\t\tbuffer.push(`${this.tr`How the ladder works`}`);\r\n\t\t}\r\n\t\tif (showAll || target === 'tiering' || target === 'tiers' || target === 'tier') {\r\n\t\t\tbuffer.push(`${this.tr`Tiering FAQ`}`);\r\n\t\t}\r\n\t\tif (showAll || target === 'badge' || target === 'badges') {\r\n\t\t\tbuffer.push(`${this.tr`Badge FAQ`}`);\r\n\t\t}\r\n\t\tif (showAll || target === 'rng') {\r\n\t\t\tbuffer.push(`${this.tr`Common misconceptions about our RNG`}`);\r\n\t\t}\r\n\t\tif (showAll || ['tournaments', 'tournament', 'tours', 'tour'].includes(target)) {\r\n\t\t\tbuffer.push(this.tr`To join a room tournament, click the Join! button or type the command /tour join in the room's chat. You can check if your team is legal for the tournament by clicking the Validate button once you've joined and selected a team. To battle your opponent in the tournament, click the Ready! button when it appears. There are two different types of room tournaments: elimination (if a user loses more than a certain number of times, they are eliminated) and round robin (all users play against each other, and the user with the most wins is the winner).`);\r\n\t\t}\r\n\t\tif (showAll || ['vpn', 'proxy'].includes(target)) {\r\n\t\t\tbuffer.push(`${this.tr`Proxy lock help`}`);\r\n\t\t}\r\n\t\tif (showAll || ['ca', 'customavatar', 'customavatars'].includes(target)) {\r\n\t\t\tbuffer.push(this.tr`Custom avatars are given to Global Staff members, contributors (coders and spriters) to Pokemon Showdown, and Smogon badgeholders at the discretion of Zarel. They are also sometimes given out as prizes for major room events or Smogon tournaments.`);\r\n\t\t}\r\n\t\tif (showAll || ['privacy', 'private'].includes(target)) {\r\n\t\t\tbuffer.push(`${this.tr`Pok\u00E9mon Showdown privacy policy`}`);\r\n\t\t}\r\n\t\tif (showAll || ['lostpassword', 'password', 'lostpass'].includes(target)) {\r\n\t\t\tbuffer.push(`If you need your Pok\u00E9mon Showdown password reset, you can fill out a ${this.tr`Password Reset Form`}. You will need to make a Smogon account to be able to fill out the form, as password resets are processed through the Smogon forums.`);\r\n\t\t}\r\n\t\tif (!buffer.length && target) {\r\n\t\t\tthis.errorReply(`'${target}' is an invalid FAQ.`);\r\n\t\t\treturn this.parse(`/help faq`);\r\n\t\t}\r\n\t\tif (!target || showAll) {\r\n\t\t\tbuffer.unshift(`${this.tr`Frequently Asked Questions`}`);\r\n\t\t}\r\n\t\tthis.sendReplyBox(buffer.join(`
`));\r\n\t},\r\n\tfaqhelp: [\r\n\t\t`/faq [theme] - Provides a link to the FAQ. Add autoconfirmed, badges, proxy, ladder, staff, or tiers for a link to these questions. Add all for all of them.`,\r\n\t\t`!faq [theme] - Shows everyone a link to the FAQ. Add autoconfirmed, badges, proxy, ladder, staff, or tiers for a link to these questions. Add all for all of them. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tanalysis: 'smogdex',\r\n\tstrategy: 'smogdex',\r\n\tsmogdex(target, room, user) {\r\n\t\tif (!target) return this.parse('/help smogdex');\r\n\t\tif (!this.runBroadcast()) return;\r\n\r\n\t\tconst targets = target.split(',');\r\n\t\tlet pokemon = Dex.species.get(targets[0]);\r\n\t\tconst item = Dex.items.get(targets[0]);\r\n\t\tconst move = Dex.moves.get(targets[0]);\r\n\t\tconst ability = Dex.abilities.get(targets[0]);\r\n\t\tconst format = Dex.formats.get(targets[0]);\r\n\t\tlet atLeastOne = false;\r\n\t\tlet generation = (targets[1] || 'sv').trim().toLowerCase();\r\n\t\tlet genNumber = 9;\r\n\t\tconst extraFormat = Dex.formats.get(targets[2]);\r\n\r\n\t\tif (['9', 'gen9', 'nine', 'sv'].includes(generation)) {\r\n\t\t\tgeneration = 'sv';\r\n\t\t} else if (['8', 'gen8', 'eight', 'ss', 'swsh'].includes(generation)) {\r\n\t\t\tgeneration = 'ss';\r\n\t\t\tgenNumber = 8;\r\n\t\t} else if (['7', 'gen7', 'seven', 'sm', 'sumo', 'usm', 'usum'].includes(generation)) {\r\n\t\t\tgeneration = 'sm';\r\n\t\t\tgenNumber = 7;\r\n\t\t} else if (['6', 'gen6', 'oras', 'six', 'xy'].includes(generation)) {\r\n\t\t\tgeneration = 'xy';\r\n\t\t\tgenNumber = 6;\r\n\t\t} else if (['5', 'b2w2', 'bw', 'bw2', 'five', 'gen5'].includes(generation)) {\r\n\t\t\tgeneration = 'bw';\r\n\t\t\tgenNumber = 5;\r\n\t\t} else if (['4', 'dp', 'dpp', 'four', 'gen4', 'hgss'].includes(generation)) {\r\n\t\t\tgeneration = 'dp';\r\n\t\t\tgenNumber = 4;\r\n\t\t} else if (['3', 'adv', 'frlg', 'gen3', 'rs', 'rse', 'three'].includes(generation)) {\r\n\t\t\tgeneration = 'rs';\r\n\t\t\tgenNumber = 3;\r\n\t\t} else if (['2', 'gen2', 'gs', 'gsc', 'two'].includes(generation)) {\r\n\t\t\tgeneration = 'gs';\r\n\t\t\tgenNumber = 2;\r\n\t\t} else if (['1', 'gen1', 'one', 'rb', 'rby', 'rgy'].includes(generation)) {\r\n\t\t\tgeneration = 'rb';\r\n\t\t\tgenNumber = 1;\r\n\t\t} else {\r\n\t\t\tgeneration = 'ss';\r\n\t\t}\r\n\r\n\t\t// Pokemon\r\n\t\tif (pokemon.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tif (genNumber < pokemon.gen) {\r\n\t\t\t\treturn this.sendReplyBox(`${pokemon.name} did not exist in ${generation.toUpperCase()}!`);\r\n\t\t\t}\r\n\r\n\t\t\tif ((pokemon.battleOnly && pokemon.baseSpecies !== 'Greninja') ||\r\n\t\t\t\t['Keldeo', 'Genesect'].includes(pokemon.baseSpecies)) {\r\n\t\t\t\tpokemon = Dex.species.get(pokemon.changesFrom || pokemon.baseSpecies);\r\n\t\t\t}\r\n\r\n\t\t\tlet formatName = extraFormat.name;\r\n\t\t\tlet formatId: string = extraFormat.id;\r\n\t\t\tif (formatName.startsWith('[Gen ') && formatName.slice(6, 8) === '] ') {\r\n\t\t\t\tformatName = formatName.slice(8);\r\n\t\t\t\tformatId = toID(formatName);\r\n\t\t\t}\r\n\t\t\tif (formatId === 'anythinggoes') {\r\n\t\t\t\tformatId = 'ag';\r\n\t\t\t} else if (formatId === 'battlespotdoubles') {\r\n\t\t\t\tformatId = 'battle_spot_doubles';\r\n\t\t\t} else if (formatId === 'battlespottriples') {\r\n\t\t\t\tformatId = 'battle_spot_triples';\r\n\t\t\t\tif (genNumber > 6) {\r\n\t\t\t\t\treturn this.sendReplyBox(`Triples formats are not an available format in Pokémon generation ${generation.toUpperCase()}.`);\r\n\t\t\t\t}\r\n\t\t\t} else if (formatId === 'doublesou') {\r\n\t\t\t\tformatId = 'doubles';\r\n\t\t\t} else if (formatId === 'balancedhackmons') {\r\n\t\t\t\tformatId = 'bh';\r\n\t\t\t} else if (formatId === 'battlespotsingles') {\r\n\t\t\t\tformatId = 'battle_spot_singles';\r\n\t\t\t} else if (formatId === 'ubers') {\r\n\t\t\t\tformatId = 'uber';\r\n\t\t\t} else if (formatId.includes('vgc')) {\r\n\t\t\t\tformatId = 'vgc' + formatId.slice(-2);\r\n\t\t\t\tformatName = 'VGC 20' + formatId.slice(-2);\r\n\t\t\t} else if (extraFormat.effectType !== 'Format') {\r\n\t\t\t\tformatName = formatId = '';\r\n\t\t\t}\r\n\t\t\tconst supportedLanguages: {[k: string]: string} = {\r\n\t\t\t\tspanish: 'es',\r\n\t\t\t\tfrench: 'fr',\r\n\t\t\t\titalian: 'it',\r\n\t\t\t\tgerman: 'de',\r\n\t\t\t\tportuguese: 'pt',\r\n\t\t\t};\r\n\t\t\tlet id = pokemon.name.toLowerCase();\r\n\t\t\tif (id === 'meowstic') id = 'meowstic-m';\r\n\t\t\tif (id === 'zygarde-10%') id = 'zygarde-10';\r\n\t\t\tif (['ou', 'uu'].includes(formatId) && generation === 'sm' &&\r\n\t\t\t\troom?.settings.language && room.settings.language in supportedLanguages) {\r\n\t\t\t\t// Limited support for translated analysis\r\n\t\t\t\t// Translated analysis do not support automatic redirects from a id to the proper page\r\n\t\t\t\tthis.sendReplyBox(\r\n\t\t\t\t\tUtils.html`${generation.toUpperCase()} ${formatName} ${pokemon.name} analysis, brought to you by Smogon University`\r\n\t\t\t\t);\r\n\t\t\t} else if (['ou', 'uu'].includes(formatId) && generation === 'sm') {\r\n\t\t\t\tthis.sendReplyBox(\r\n\t\t\t\t\tUtils.html`${generation.toUpperCase()} ${formatName} ${pokemon.name} analysis, brought to you by Smogon University
` +\r\n\t\t\t\t\t`Other languages: Espa\u00F1ol, Fran\u00E7ais, Italiano, ` +\r\n\t\t\t\t\t`Deutsch, Portugu\u00EAs`\r\n\t\t\t\t);\r\n\t\t\t} else {\r\n\t\t\t\tthis.sendReplyBox(Utils.html`${generation.toUpperCase()} ${formatName} ${pokemon.name} analysis, brought to you by Smogon University`);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\t// Item\r\n\t\tif (item.exists && genNumber > 1 && item.gen <= genNumber) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tthis.sendReplyBox(`${generation.toUpperCase()} ${item.name} item analysis, brought to you by Smogon University`);\r\n\t\t}\r\n\r\n\t\t// Ability\r\n\t\tif (ability.exists && genNumber > 2 && ability.gen <= genNumber) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tthis.sendReplyBox(`${generation.toUpperCase()} ${ability.name} ability analysis, brought to you by Smogon University`);\r\n\t\t}\r\n\r\n\t\t// Move\r\n\t\tif (move.exists && move.gen <= genNumber) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tthis.sendReplyBox(`${generation.toUpperCase()} ${move.name} move analysis, brought to you by Smogon University`);\r\n\t\t}\r\n\r\n\t\t// Format\r\n\t\tif (format.id) {\r\n\t\t\tlet formatName = format.name;\r\n\t\t\tlet formatId: string = format.id;\r\n\t\t\tif (formatName.startsWith('[Gen ') && formatName.slice(6, 8) === '] ') {\r\n\t\t\t\tformatName = formatName.slice(8);\r\n\t\t\t\tformatId = toID(formatName);\r\n\t\t\t}\r\n\t\t\tif (formatId === 'anythinggoes') {\r\n\t\t\t\tformatId = 'ag';\r\n\t\t\t} else if (formatId === 'battlespotdoubles') {\r\n\t\t\t\tformatId = 'battle_spot_doubles';\r\n\t\t\t} else if (formatId === 'battlespottriples') {\r\n\t\t\t\tformatId = 'battle_spot_triples';\r\n\t\t\t\tif (genNumber > 6) {\r\n\t\t\t\t\treturn this.sendReplyBox(`Triples formats are not an available format in Pokémon generation ${generation.toUpperCase()}.`);\r\n\t\t\t\t}\r\n\t\t\t} else if (formatId === 'doublesou') {\r\n\t\t\t\tformatId = 'doubles';\r\n\t\t\t} else if (formatId === 'balancedhackmons') {\r\n\t\t\t\tformatId = 'bh';\r\n\t\t\t} else if (formatId === 'battlespotsingles') {\r\n\t\t\t\tformatId = 'battle_spot_singles';\r\n\t\t\t} else if (formatId === 'ubers') {\r\n\t\t\t\tformatId = 'uber';\r\n\t\t\t} else if (formatId.includes('vgc')) {\r\n\t\t\t\tformatId = `vgc${formatId.slice(-2)}`;\r\n\t\t\t\tformatName = `VGC 20${formatId.slice(-2)}`;\r\n\t\t\t} else if (format.effectType !== 'Format') {\r\n\t\t\t\tformatName = formatId = '';\r\n\t\t\t}\r\n\t\t\tif (formatName) {\r\n\t\t\t\tatLeastOne = true;\r\n\t\t\t\tthis.sendReplyBox(Utils.html`${generation.toUpperCase()} ${formatName} format analysis, brought to you by Smogon University`);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (!atLeastOne) {\r\n\t\t\treturn this.sendReplyBox(`Pokémon, item, move, ability, or format not found for generation ${generation.toUpperCase()}.`);\r\n\t\t}\r\n\t},\r\n\tsmogdexhelp: [\r\n\t\t`/analysis [pokemon], [generation], [format] - Links to the Smogon University analysis for this Pok\\u00e9mon in the given generation.`,\r\n\t\t`!analysis [pokemon], [generation], [format] - Shows everyone this link. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tveekun(target, broadcast, user) {\r\n\t\tif (!target) return this.parse('/help veekun');\r\n\t\tif (!this.runBroadcast()) return;\r\n\r\n\t\tconst baseLink = 'http://veekun.com/dex/';\r\n\r\n\t\tconst pokemon = Dex.species.get(target);\r\n\t\tconst item = Dex.items.get(target);\r\n\t\tconst move = Dex.moves.get(target);\r\n\t\tconst ability = Dex.abilities.get(target);\r\n\t\tconst nature = Dex.natures.get(target);\r\n\t\tlet atLeastOne = false;\r\n\r\n\t\t// Pokemon\r\n\t\tif (pokemon.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tif (pokemon.isNonstandard && pokemon.isNonstandard !== 'Past') {\r\n\t\t\t\treturn this.errorReply(`${pokemon.name} is not a real Pok\\u00e9mon.`);\r\n\t\t\t}\r\n\r\n\t\t\tconst baseSpecies = pokemon.baseSpecies || pokemon.name;\r\n\t\t\tlet forme = pokemon.forme;\r\n\r\n\t\t\t// Showdown and Veekun have different names for various formes\r\n\t\t\tif (baseSpecies === 'Meowstic' && forme === 'F') forme = 'Female';\r\n\t\t\tif (baseSpecies === 'Zygarde' && forme === '10%') forme = '10';\r\n\t\t\tif (baseSpecies === 'Necrozma' && !Dex.species.get(baseSpecies + forme).battleOnly) forme = forme.substr(0, 4);\r\n\t\t\tif (baseSpecies === 'Pikachu' && Dex.species.get(baseSpecies + forme).gen === 7) forme += '-Cap';\r\n\t\t\tif (forme.endsWith('Totem')) {\r\n\t\t\t\tif (baseSpecies === 'Raticate') forme = 'Totem-Alola';\r\n\t\t\t\tif (baseSpecies === 'Marowak') forme = 'Totem';\r\n\t\t\t\tif (baseSpecies === 'Mimikyu') forme += forme === 'Busted-Totem' ? '-Busted' : '-Disguised';\r\n\t\t\t}\r\n\r\n\t\t\tlet link = `${baseLink}pokemon/${baseSpecies.toLowerCase()}`;\r\n\t\t\tif (forme) {\r\n\t\t\t\tif (baseSpecies === 'Arceus' || baseSpecies === 'Silvally') link += '/flavor';\r\n\t\t\t\tlink += `?form=${forme.toLowerCase()}`;\r\n\t\t\t}\r\n\r\n\t\t\tthis.sendReplyBox(`${pokemon.name} description by Veekun`);\r\n\t\t}\r\n\r\n\t\t// Item\r\n\t\tif (item.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tif (item.isNonstandard && item.isNonstandard !== 'Past') {\r\n\t\t\t\treturn this.errorReply(`${item.name} is not a real item.`);\r\n\t\t\t}\r\n\t\t\tconst link = `${baseLink}items/${item.name.toLowerCase()}`;\r\n\t\t\tthis.sendReplyBox(`${item.name} item description by Veekun`);\r\n\t\t}\r\n\r\n\t\t// Ability\r\n\t\tif (ability.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tif (ability.isNonstandard && ability.isNonstandard !== 'Past') {\r\n\t\t\t\treturn this.errorReply(`${ability.name} is not a real ability.`);\r\n\t\t\t}\r\n\t\t\tconst link = `${baseLink}abilities/${ability.name.toLowerCase()}`;\r\n\t\t\tthis.sendReplyBox(`${ability.name} ability description by Veekun`);\r\n\t\t}\r\n\r\n\t\t// Move\r\n\t\tif (move.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tif (move.isNonstandard && move.isNonstandard !== 'Past') {\r\n\t\t\t\treturn this.errorReply(`${move.name} is not a real move.`);\r\n\t\t\t}\r\n\t\t\tconst link = `${baseLink}moves/${move.name.toLowerCase()}`;\r\n\t\t\tthis.sendReplyBox(`${move.name} move description by Veekun`);\r\n\t\t}\r\n\r\n\t\t// Nature\r\n\t\tif (nature.exists) {\r\n\t\t\tatLeastOne = true;\r\n\t\t\tconst link = `${baseLink}natures/${nature.name.toLowerCase()}`;\r\n\t\t\tthis.sendReplyBox(`${nature.name} nature description by Veekun`);\r\n\t\t}\r\n\r\n\t\tif (!atLeastOne) {\r\n\t\t\treturn this.sendReplyBox(`Pokémon, item, move, ability, or nature not found.`);\r\n\t\t}\r\n\t},\r\n\tveekunhelp: [\r\n\t\t`/veekun [pokemon] - Links to Veekun website for this pokemon/item/move/ability/nature.`,\r\n\t\t`!veekun [pokemon] - Shows everyone this link. Requires: + % @ # &`,\r\n\t],\r\n\r\n\tregister() {\r\n\t\tif (!this.runBroadcast()) return;\r\n\t\tthis.sendReplyBox(`You will be prompted to register upon winning a rated battle. Alternatively, there is a register button in the menu in the upper right.`);\r\n\t},\r\n\tregisterhelp: [`/register - Provides information on how to register.`],\r\n\r\n\t/*********************************************************\r\n\t * Miscellaneous commands\r\n\t *********************************************************/\r\n\r\n\troll: 'dice',\r\n\tdice(target, room, user) {\r\n\t\tif (!target || /[^\\d\\sdHL+-]/i.test(target)) return this.parse('/help dice');\r\n\t\tif (!this.runBroadcast(true)) return;\r\n\r\n\t\t// ~30 is widely regarded as the sample size required for sum to be a Gaussian distribution.\r\n\t\t// This also sets a computation time constraint for safety.\r\n\t\tconst maxDice = 40;\r\n\r\n\t\tlet diceQuantity = 1;\r\n\t\tconst diceDataStart = target.indexOf('d');\r\n\t\tif (diceDataStart >= 0) {\r\n\t\t\tif (diceDataStart) diceQuantity = Number(target.slice(0, diceDataStart));\r\n\t\t\ttarget = target.slice(diceDataStart + 1);\r\n\t\t\tif (!Number.isInteger(diceQuantity) || diceQuantity <= 0 || diceQuantity > maxDice) {\r\n\t\t\t\treturn this.sendReply(`The amount of dice rolled should be a natural number up to ${maxDice}.`);\r\n\t\t\t}\r\n\t\t}\r\n\t\tlet offset = 0;\r\n\t\tlet removeOutlier = 0;\r\n\r\n\t\tconst modifierData = /[+-]/.exec(target);\r\n\t\tif (modifierData) {\r\n\t\t\tswitch (target.slice(modifierData.index).trim().toLowerCase()) {\r\n\t\t\tcase '-l':\r\n\t\t\t\tremoveOutlier = -1;\r\n\t\t\t\tbreak;\r\n\t\t\tcase '-h':\r\n\t\t\t\tremoveOutlier = +1;\r\n\t\t\t\tbreak;\r\n\t\t\tdefault:\r\n\t\t\t\toffset = Number(target.slice(modifierData.index));\r\n\t\t\t\tif (isNaN(offset)) return this.parse('/help dice');\r\n\t\t\t\tif (!Number.isSafeInteger(offset)) {\r\n\t\t\t\t\treturn this.errorReply(`The specified offset must be an integer up to ${Number.MAX_SAFE_INTEGER}.`);\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tif (removeOutlier && diceQuantity <= 1) {\r\n\t\t\t\treturn this.errorReply(`More than one dice should be rolled before removing outliers.`);\r\n\t\t\t}\r\n\t\t\ttarget = target.slice(0, modifierData.index);\r\n\t\t}\r\n\r\n\t\tlet diceFaces = 6;\r\n\t\tif (target.length) {\r\n\t\t\tdiceFaces = Number(target);\r\n\t\t\tif (!Number.isSafeInteger(diceFaces) || diceFaces <= 0) {\r\n\t\t\t\treturn this.errorReply(`Rolled dice must have a natural amount of faces up to ${Number.MAX_SAFE_INTEGER}.`);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tif (diceQuantity > 1) {\r\n\t\t\t// Make sure that we can deal with high rolls\r\n\t\t\tif (!Number.isSafeInteger(offset < 0 ? diceQuantity * diceFaces : diceQuantity * diceFaces + offset)) {\r\n\t\t\t\treturn this.errorReply(`The maximum sum of rolled dice must be lower or equal than ${Number.MAX_SAFE_INTEGER}.`);\r\n\t\t\t}\r\n\t\t}\r\n\r\n\t\tlet maxRoll = 0;\r\n\t\tlet minRoll = Number.MAX_SAFE_INTEGER;\r\n\r\n\t\tconst trackRolls = diceQuantity * (('' + diceFaces).length + 1) <= 60;\r\n\t\tconst rolls = [];\r\n\t\tlet rollSum = 0;\r\n\r\n\t\tfor (let i = 0; i < diceQuantity; ++i) {\r\n\t\t\tconst curRoll = Math.floor(Math.random() * diceFaces) + 1;\r\n\t\t\trollSum += curRoll;\r\n\t\t\tif (curRoll > maxRoll) maxRoll = curRoll;\r\n\t\t\tif (curRoll < minRoll) minRoll = curRoll;\r\n\t\t\tif (trackRolls) rolls.push(curRoll);\r\n\t\t}\r\n\r\n\t\t// Apply modifiers\r\n\r\n\t\tif (removeOutlier > 0) {\r\n\t\t\trollSum -= maxRoll;\r\n\t\t} else if (removeOutlier < 0) {\r\n\t\t\trollSum -= minRoll;\r\n\t\t}\r\n\t\tif (offset) rollSum += offset;\r\n\r\n\t\t// Reply with relevant information\r\n\r\n\t\tlet offsetFragment = \"\";\r\n\t\tif (offset) offsetFragment += `${offset > 0 ? ` + ${offset}` : offset}`;\r\n\r\n\t\tif (diceQuantity === 1) return this.sendReplyBox(`Rolling (1 to ${diceFaces})${offsetFragment}: ${rollSum}`);\r\n\r\n\t\tconst outlierFragment = removeOutlier ? ` except ${removeOutlier > 0 ? \"highest\" : \"lowest\"}` : ``;\r\n\t\tconst rollsFragment = trackRolls ? \": \" + rolls.join(\", \") : \"\";\r\n\t\treturn this.sendReplyBox(\r\n\t\t\t`${diceQuantity} rolls (1 to ${diceFaces})${rollsFragment}
` +\r\n\t\t\t`Sum${offsetFragment}${outlierFragment}: ${rollSum}`\r\n\t\t);\r\n\t},\r\n\tdicehelp: [\r\n\t\t`/dice [max number] - Randomly picks a number between 1 and the number you choose.`,\r\n\t\t`/dice [number of dice]d[number of sides] - Simulates rolling a number of dice, e.g., /dice 2d4 simulates rolling two 4-sided dice.`,\r\n\t\t`/dice [number of dice]d[number of sides][+/-][offset] - Simulates rolling a number of dice and adding an offset to the sum, e.g., /dice 2d6+10: two standard dice are rolled; the result lies between 12 and 22.`,\r\n\t\t`/dice [number of dice]d[number of sides]-[H/L] - Simulates rolling a number of dice with removal of extreme values, e.g., /dice 3d8-L: rolls three 8-sided dice; the result ignores the lowest value.`,\r\n\t],\r\n\r\n\tpr: 'pickrandom',\r\n\tpick: 'pickrandom',\r\n\tpickrandom(target, room, user) {\r\n\t\tif (!target) return false;\r\n\t\tif (!target.includes(',')) return this.parse('/help pick');\r\n\t\tif (!this.runBroadcast(true)) return false;\r\n\t\tif (this.broadcasting) {\r\n\t\t\t[, target] = Utils.splitFirst(this.message, ' ');\r\n\t\t}\r\n\t\tconst options = target.split(',');\r\n\t\tconst pickedOption = options[Math.floor(Math.random() * options.length)].trim();\r\n\t\treturn this.sendReplyBox(Utils.html`We randomly picked: ${pickedOption}`);\r\n\t},\r\n\tpickrandomhelp: [`/pick [option], [option], ... - Randomly selects an item from a list containing 2 or more elements.`],\r\n\r\n\tshuffle(target, room, user) {\r\n\t\tif (!target?.includes(',')) return this.parse('/help shuffle');\r\n\t\tconst args = target.split(',');\r\n\t\tif (!this.runBroadcast(true)) return false;\r\n\t\tconst results = Utils.shuffle(args.map(arg => arg.trim()));\r\n\t\treturn this.sendReplyBox(Utils.html`Shuffled:
${results.join(', ')}`);\r\n\t},\r\n\tshufflehelp: [\r\n\t\t`/shuffle [option], [option], [option], ... - Randomly shuffles a list of 2 or more elements.`,\r\n\t],\r\n\r\n\tshowimage(target, room, user) {\r\n\t\treturn this.errorReply(`/showimage has been deprecated - use /show instead.`);\r\n\t},\r\n\r\n\tasync requestshow(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tthis.checkChat();\r\n\t\tif (!room.settings.requestShowEnabled) {\r\n\t\t\treturn this.errorReply(`Media approvals are disabled in this room.`);\r\n\t\t}\r\n\t\tif (user.can('showmedia', null, room, '/show')) return this.errorReply(`Use !show instead.`);\r\n\t\tif (room.pendingApprovals?.has(user.id)) return this.errorReply('You have a request pending already.');\r\n\t\tif (!toID(target)) return this.parse(`/help requestshow`);\r\n\r\n\t\tlet [link, comment] = target.split(',');\r\n\t\tif (!/^https?:\\/\\//.test(link)) link = `https://${link}`;\r\n\t\tlink = encodeURI(link);\r\n\t\tlet dimensions;\r\n\t\tif (!/^(https?:\\/\\/)?(www\\.)?(youtube\\.com|youtu\\.be)(\\/|$)/i.test(link)) {\r\n\t\t\tif (link.includes('data:image/png;base64')) {\r\n\t\t\t\tthrow new Chat.ErrorMessage('Please provide an actual link (you probably copied the URL wrong?).');\r\n\t\t\t}\r\n\t\t\ttry {\r\n\t\t\t\tdimensions = await Chat.fitImage(link);\r\n\t\t\t} catch {\r\n\t\t\t\tthrow new Chat.ErrorMessage('Invalid link.');\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (comment && this.checkChat(comment) !== comment) {\r\n\t\t\treturn this.errorReply(`You cannot use filtered words in comments.`);\r\n\t\t}\r\n\t\tif (!room.pendingApprovals) room.pendingApprovals = new Map();\r\n\t\troom.pendingApprovals.set(user.id, {\r\n\t\t\tname: user.name,\r\n\t\t\tlink: link,\r\n\t\t\tcomment: comment,\r\n\t\t\tdimensions: dimensions,\r\n\t\t});\r\n\t\tthis.sendReply(`You have requested to show the link: ${link}${comment ? ` (with the comment ${comment})` : ''}.`);\r\n\t\tconst message = `|tempnotify|pendingapprovals|Pending media request!` +\r\n\t\t\t`|${user.name} has requested to show media in ${room.title}.|new media request`;\r\n\t\troom.sendRankedUsers(message, '%');\r\n\t\troom.sendMods(\r\n\t\t\tUtils.html`|uhtml|request-${user.id}|
${user.name} wants to show ${link}
` +\r\n\t\t\t(comment ? Utils.html`Comment: ${comment}
` : '') +\r\n\t\t\t`
` +\r\n\t\t\t`
`\r\n\t\t);\r\n\t},\r\n\trequestshowhelp: [`/requestshow [link], [comment] - Requests permission to show media in the room.`],\r\n\r\n\tasync approveshow(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tthis.checkCan('mute', null, room);\r\n\t\tif (!room.settings.requestShowEnabled) {\r\n\t\t\treturn this.errorReply(`Media approvals are disabled in this room.`);\r\n\t\t}\r\n\t\tconst userid = toID(target);\r\n\t\tif (!userid) return this.parse(`/help approveshow`);\r\n\t\tconst request = room.pendingApprovals?.get(userid);\r\n\t\tif (!request) return this.errorReply(`${userid} has no pending request.`);\r\n\t\tif (userid === user.id) {\r\n\t\t\treturn this.errorReply(`You can't approve your own /show request.`);\r\n\t\t}\r\n\t\troom.pendingApprovals!.delete(userid);\r\n\t\troom.sendMods(`|uhtmlchange|request-${target}|`);\r\n\t\troom.sendRankedUsers(`|tempnotifyoff|pendingapprovals`, '%');\r\n\r\n\t\tlet buf;\r\n\t\tif (request.dimensions) { // image\r\n\t\t\tconst [width, height, resized] = request.dimensions;\r\n\t\t\tbuf = Utils.html``;\r\n\t\t\tif (resized) buf += Utils.html`
full-size image`;\r\n\t\t} else {\r\n\t\t\tbuf = await YouTube.generateVideoDisplay(request.link);\r\n\t\t\tif (!buf) return this.errorReply('Could not get YouTube video');\r\n\t\t}\r\n\t\tbuf += Utils.html`
(Requested by ${request.name})`;\r\n\t\tif (request.comment) {\r\n\t\t\tbuf += Utils.html`
${request.comment}
`;\r\n\t\t} else {\r\n\t\t\tbuf += ``;\r\n\t\t}\r\n\t\troom.add(`|c| ${request.name}|/raw ${buf}`);\r\n\t\tthis.privateModAction(`${user.name} approved showing media from ${request.name}.`);\r\n\t},\r\n\tapproveshowhelp: [`/approveshow [user] - Approves the media display request of [user]. Requires: % @ # &`],\r\n\r\n\tdenyshow(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\tthis.checkCan('mute', null, room);\r\n\t\tif (!room.settings.requestShowEnabled) {\r\n\t\t\treturn this.errorReply(`Media approvals are disabled in this room.`);\r\n\t\t}\r\n\t\ttarget = toID(target);\r\n\t\tif (!target) return this.parse(`/help denyshow`);\r\n\r\n\t\tconst entry = room.pendingApprovals?.get(target);\r\n\t\tif (!entry) return this.errorReply(`${target} has no pending request.`);\r\n\r\n\t\troom.pendingApprovals!.delete(target);\r\n\t\troom.sendMods(`|uhtmlchange|request-${target}|`);\r\n\t\troom.sendRankedUsers(`|tempnotifyoff|pendingapprovals`, '%');\r\n\t\tthis.privateModAction(`${user.name} denied ${target}'s request to display ${entry.link}.`);\r\n\r\n\t\tconst targetUser = Users.get(target);\r\n\t\tif (!targetUser) return;\r\n\t\troom.sendUser(targetUser, `|raw|
Your media request was denied.
`);\r\n\t\troom.sendUser(targetUser, `|notify|Media request denied`);\r\n\t},\r\n\tdenyshowhelp: [`/denyshow [user] - Denies the media display request of [user]. Requires: % @ # &`],\r\n\r\n\tapprovallog(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\treturn this.parse(`/sl approved showing media from, ${room.roomid}`);\r\n\t},\r\n\tapprovalloghelp: [`/approvallog - View a log of past media approvals in the current room. Requires: % @ # &`],\r\n\r\n\tviewapprovals(target, room, user) {\r\n\t\troom = this.requireRoom();\r\n\t\treturn this.parse(`/join view-approvals-${room.roomid}`);\r\n\t},\r\n\tviewapprovalshelp: [\r\n\t\t`/viewapprovals - View a list of users who have requested to show media in the current room.`,\r\n\t\t`Requires: % @ # &`,\r\n\t],\r\n\r\n\tasync show(target, room, user, connection) {\r\n\t\tif (!room?.persist && !this.pmTarget && !room?.roomid.startsWith('help-')) {\r\n\t\t\treturn this.errorReply(`/show cannot be used in temporary rooms.`);\r\n\t\t}\r\n\t\tif (!toID(target).trim()) return this.parse(`/help show`);\r\n\t\tif (Monitor.countNetRequests(connection.ip)) {\r\n\t\t\treturn this.errorReply(`You are using this command too quickly. Wait a bit and try again.`);\r\n\t\t}\r\n\r\n\t\tconst [link, comment] = Utils.splitFirst(target, ',').map(f => f.trim());\r\n\r\n\t\tlet buf;\r\n\t\tif (YouTube.linkRegex.test(link)) {\r\n\t\t\tbuf = await YouTube.generateVideoDisplay(link);\r\n\t\t\tthis.message = this.message.replace(/&ab_channel=(.*)(&|)/ig, '').replace(/https:\\/\\/www\\./ig, '');\r\n\t\t} else if (Twitch.linkRegex.test(link)) {\r\n\t\t\tconst channelId = Twitch.linkRegex.exec(link)?.[2]?.trim();\r\n\t\t\tif (!channelId) return this.errorReply(`Specify a Twitch channel.`);\r\n\t\t\tconst info = await Twitch.getChannel(channelId);\r\n\t\t\tif (!info) return this.errorReply(`Channel ${channelId} not found.`);\r\n\t\t\tbuf = `Watching ${info.display_name}...
`;\r\n\t\t\tbuf += ``;\r\n\t\t} else {\r\n\t\t\tif (link.includes('data:image/png;base64')) {\r\n\t\t\t\tthrow new Chat.ErrorMessage('Please provide an actual link (you probably copied it wrong?).');\r\n\t\t\t}\r\n\t\t\ttry {\r\n\t\t\t\tconst [width, height, resized] = await Chat.fitImage(link);\r\n\t\t\t\tbuf = Utils.html``;\r\n\t\t\t\tif (resized) buf += Utils.html`
full-size image`;\r\n\t\t\t} catch {\r\n\t\t\t\treturn this.errorReply('Invalid image');\r\n\t\t\t}\r\n\t\t}\r\n\t\tif (comment) {\r\n\t\t\tif (this.checkChat(comment) !== comment) {\r\n\t\t\t\treturn this.errorReply(`You cannot use filtered words in comments.`);\r\n\t\t\t}\r\n\t\t\tbuf += Utils.html`
(${comment})`;\r\n\t\t}\r\n\r\n\t\tthis.checkBroadcast();\r\n\t\tif (this.broadcastMessage) {\r\n\t\t\tif (room) {\r\n\t\t\t\tthis.checkCan('show', null, room);\r\n\t\t\t} else {\r\n\t\t\t\tthis.checkCan('altsself');\r\n\t\t\t}\r\n\t\t}\r\n\t\tthis.runBroadcast();\r\n\t\tthis.sendReplyBox(buf);\r\n\t},\r\n\tshowhelp: [\r\n\t\t`/show [url] - Shows you an image or YouTube video.`,\r\n\t\t`!show [url] - Shows an image or YouTube to everyone in a chatroom. Requires: whitelist % @ # &`,\r\n\t],\r\n\r\n\trebroadcast(target, room, user, connection) {\r\n\t\tif (!target || !target.startsWith('!') || !this.shouldBroadcast()) {\r\n\t\t\treturn this.parse('/help rebroadcast');\r\n\t\t}\r\n\t\troom = this.requireRoom();\r\n\t\troom.lastBroadcast = '';\r\n\t\tthis.parse(target, {broadcastPrefix: \"!rebroadcast \"});\r\n\t},\r\n\trebroadcasthelp: [\r\n\t\t`!rebroadcast ![command] - Bypasses the broadcast cooldown to broadcast a command.`,\r\n\t],\r\n\r\n\tregdate: 'registertime',\r\n\tregtime: 'registertime',\r\n\tasync registertime(target, room, user, connection) {\r\n\t\tthis.runBroadcast();\r\n\t\tif (Monitor.countNetRequests(connection.ip)) {\r\n\t\t\treturn this.errorReply(`You are using this command too quickly. Wait a bit and try again.`);\r\n\t\t}\r\n\t\tif (!user.autoconfirmed) return this.errorReply(`Only autoconfirmed users can use this command.`);\r\n\t\ttarget = toID(target);\r\n\t\tif (!target) target = user.id;\r\n\t\tlet rawResult;\r\n\t\ttry {\r\n\t\t\trawResult = await Net(`https://${Config.routes.root}/users/${target}.json`).get();\r\n\t\t} catch (e: any) {\r\n\t\t\tif (e.message.includes('Not found')) throw new Chat.ErrorMessage(`User '${target}' is unregistered.`);\r\n\t\t\tthrow new Chat.ErrorMessage(e.message);\r\n\t\t}\r\n\t\t// not in a try-catch block because if this doesn't work, this is a problem that should be known\r\n\t\tconst result = JSON.parse(rawResult);\r\n\t\tconst date = new Date(result.registertime * 1000);\r\n\t\tconst duration = Date.now() - date.getTime();\r\n\t\t// hardcode, since the loginserver doesn't store exact times, and\r\n\t\t// so this can look quite inaccurate if it was within the last day\r\n\t\tconst regTimeAgo = duration > 24 * 60 * 60 * 1000 ?\r\n\t\t\tChat.toDurationString(duration, {precision: 1}) :\r\n\t\t\t'less than a day';\r\n\t\tthis.sendReplyBox(Utils.html`The user '${target}' registered ${regTimeAgo} ago, on the date ${date.toDateString()}.`);\r\n\t},\r\n\tregistertimehelp: [`/registertime OR /regtime [user] - Find out when [user] registered.`],\r\n\r\n\tpi(target, room, user) {\r\n\t\tif (!this.runBroadcast()) return false;\r\n\t\treturn this.sendReplyBox(\r\n\t\t\t'Did you mean: 1. 3.1415926535897932384626... (Decimal)
' +\r\n\t\t\t'2. 3.184809493B91866... (Duodecimal)
' +\r\n\t\t\t'3. 3.243F6A8885A308D... (Hexadecimal)

' +\r\n\t\t\t'How many digits of pi do YOU know? Test it out here!'\r\n\t\t);\r\n\t},\r\n\tpihelp: [`/pi - Displays the first several digits of pi in several notation types.`],\r\n\r\n\tcode(target, room, user, connection) {\r\n\t\t// target is trimmed by Chat#splitMessage, but leading spaces can be\r\n\t\t// important to code block indentation.\r\n\t\ttarget = this.message.substr(this.cmdToken.length + this.cmd.length + +this.message.includes(' ')).trimRight();\r\n\t\tif (!target) return this.parse('/help code');\r\n\t\tif (target.length >= 8192) return this.errorReply(\"Your code must be under 8192 characters long!\");\r\n\t\tif (target.length < 80 && !target.includes('\\n') && !target.includes('```') && this.shouldBroadcast()) {\r\n\t\t\treturn this.checkChat(`\\`\\`\\`${target}\\`\\`\\``);\r\n\t\t}\r\n\r\n\t\tif (this.room?.settings.isPersonal !== false && this.shouldBroadcast()) {\r\n\t\t\ttarget = this.filter(target)!;\r\n\t\t\tif (!target) return this.errorReply(`Invalid code.`);\r\n\t\t}\r\n\r\n\t\tthis.checkBroadcast(true, '!code');\r\n\t\tthis.runBroadcast(true);\r\n\r\n\t\tif (this.broadcasting) {\r\n\t\t\treturn `/raw
${Chat.getReadmoreCodeBlock(target)}
`;\r\n\t\t} else {\r\n\t\t\tthis.sendReplyBox(Chat.getReadmoreCodeBlock(target));\r\n\t\t}\r\n\t},\r\n\tcodehelp: [\r\n\t\t`!code [code] - Broadcasts code to a room. Accepts multi-line arguments. Requires: + % @ & #`,\r\n\t\t`/code [code] - Shows you code. Accepts multi-line arguments.`,\r\n\t],\r\n\r\n\tbuildformat(target, room, user) {\r\n\t\ttarget = toID(target);\r\n\t\tif (target && this.connection.openPages?.has('buildformat')) {\r\n\t\t\tthis.closePage('buildformat');\r\n\t\t}\r\n\t\treturn this.parse(`/j view-buildformat${target ? `-${target}` : \"\"}`);\r\n\t},\r\n\r\n\tmakecustomchallenge(target, room, user) {\r\n\t\ttarget = target.trim();\r\n\t\tif (!target.length) {\r\n\t\t\treturn this.popupReply(`No parameters given.`);\r\n\t\t}\r\n\t\tconst args = Chat.parseArguments(target, ' | ', {\r\n\t\t\tallowEmpty: true, useIDs: false,\r\n\t\t});\r\n\t\tconst format = Dex.formats.get(toID(args.format[0]));\r\n\t\tif (!format.exists) {\r\n\t\t\treturn this.popupReply(`The format '${format}' does not exist.`);\r\n\t\t}\r\n\t\tdelete args.format;\r\n\t\tconst targetUserID = toID(args.user[0]);\r\n\t\tif (targetUserID) {\r\n\t\t\tthis.checkChat();\r\n\t\t\tif (!Users.get(targetUserID)) {\r\n\t\t\t\treturn this.popupReply(`User '${targetUserID}' not found.`);\r\n\t\t\t}\r\n\t\t}\r\n\t\tdelete args.user;\r\n\t\tconst challengeBuf = [];\r\n\t\tif (args.bans?.[0]) {\r\n\t\t\tconst bans = args.bans[0].split(',').map(f => f.trim());\r\n\t\t\tchallengeBuf.push(...bans);\r\n\t\t}\r\n\t\tdelete args.bans;\r\n\r\n\t\tfor (const k in args) {\r\n\t\t\tif (k.endsWith('-enabled')) continue;\r\n\t\t\tlet name = k;\r\n\t\t\tif (name.endsWith('-val')) {\r\n\t\t\t\tname = name.slice(0, -4);\r\n\t\t\t}\r\n\t\t\tconst rule = Dex.data.Rulesets[name];\r\n\t\t\tif (!rule || rule.effectType === 'Format') {\r\n\t\t\t\treturn this.popupReply(`Invalid rule or modifier: ${name}`);\r\n\t\t\t}\r\n\t\t\tconst id = rule.id || toID(rule.name);\r\n\t\t\tlet val = args[k][0];\r\n\t\t\t// BUG: when there are numbers in the form elem/param name,\r\n\t\t\t// the `{name}` specifier doesn't get removed from the string\r\n\t\t\tif (val.startsWith('{')) {\r\n\t\t\t\tval = '';\r\n\t\t\t}\r\n\r\n\t\t\tconst ruleTable = Dex.formats.getRuleTable(format);\r\n\t\t\tif (rule.hasValue) {\r\n\t\t\t\tconst enabled = args[`${id}-enabled`][0] || \"\";\r\n\t\t\t\tval = args[`${id}-val`][0] || \"\";\r\n\t\t\t\tif (enabled) {\r\n\t\t\t\t\tconst current = ruleTable.valueRules.get(id);\r\n\t\t\t\t\tif (typeof current !== 'undefined') {\r\n\t\t\t\t\t\tif (current !== val) {\r\n\t\t\t\t\t\t\tchallengeBuf.push(`!! ${rule.name} = ${val}`);\r\n\t\t\t\t\t\t}\r\n\t\t\t\t\t} else {\r\n\t\t\t\t\t\tchallengeBuf.push(`${rule.name} = ${val}`);\r\n\t\t\t\t\t}\r\n\t\t\t\t} else {\r\n\t\t\t\t\tif (ruleTable.valueRules.has(id)) {\r\n\t\t\t\t\t\tchallengeBuf.push(`!${rule.name}`);\r\n\t\t\t\t\t}\r\n\t\t\t\t}\r\n\t\t\t} else {\r\n\t\t\t\t// adding one that's already there\r\n\t\t\t\tif (val && ruleTable.has(id)) {\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t\tif (!val && !ruleTable.has(id)) {\r\n\t\t\t\t\t// removing a rule that isn't there\r\n\t\t\t\t\tcontinue;\r\n\t\t\t\t}\r\n\t\t\t\tchallengeBuf.push(`${!val ? '!' : \"\"}${rule.name}`);\r\n\t\t\t}\r\n\t\t}\r\n\t\tconst fullFormat = `${format.id}@@@${challengeBuf.join(',')}`;\r\n\t\ttry {\r\n\t\t\tDex.formats.validate(fullFormat);\r\n\t\t} catch (e: any) {\r\n\t\t\tthis.refreshPage(`buildformat-${format.id}`);\r\n\t\t\treturn this.popupReply(e.message);\r\n\t\t}\r\n\t\tif (targetUserID) {\r\n\t\t\tthis.closePage(`buildformat`);\r\n\t\t\treturn this.parse(`/challenge ${targetUserID},${fullFormat}`);\r\n\t\t} else {\r\n\t\t\tthis.connection.send(\r\n\t\t\t\t`>view-buildformat-${format.id}\\n|selectorhtml|#output|` +\r\n\t\t\t\t`Here's the string for your desired rules!
${fullFormat}
` +\r\n\t\t\t\t`Use /challenge [user],${fullFormat} to challenge someone with it!`\r\n\t\t\t);\r\n\t\t}\r\n\t},\r\n\r\n\tadminhelp(target, room, user) {\r\n\t\tthis.checkCan('rangeban');\r\n\t\tlet cmds = Chat.allCommands();\r\n\t\tconst canExecute = (perm: string) => !(\r\n\t\t\t// gotta make sure no lower group has it\r\n\t\t\tObject.values(Config.groups).slice(1).some(f => (f as any)[perm])\r\n\t\t);\r\n\t\tcmds = cmds.filter(\r\n\t\t\tf => f.requiredPermission && canExecute(f.requiredPermission) && f.fullCmd !== this.handler?.fullCmd\r\n\t\t);\r\n\t\tcmds = Utils.sortBy(cmds, f => f.fullCmd);\r\n\t\tlet namespaces = new Map();\r\n\t\tfor (const cmd of cmds) {\r\n\t\t\tconst namespace = cmd.fullCmd.split(' ')[0];\r\n\t\t\tconst list = namespaces.get(namespace) || [];\r\n\t\t\tlist.push(cmd.fullCmd.trim());\r\n\t\t\tnamespaces.set(namespace, list);\r\n\t\t}\r\n\t\tlet buf = `Admin commands:
`;\r\n\t\tnamespaces = new Map(Utils.sortBy([...namespaces], ([, cmdList]) => cmdList.length === 1));\r\n\t\tfor (const [namespace, cmdList] of namespaces) {\r\n\t\t\tif (cmdList.length > 1 || cmdList[0].includes(' ')) {\r\n\t\t\t\tbuf += `
${namespace}`;\r\n\t\t\t\tbuf += cmdList.map(f => `• /${f}`).join('
');\r\n\t\t\t\tbuf += `
`;\r\n\t\t\t} else {\r\n\t\t\t\tbuf += `• ${cmdList[0]}`;\r\n\t\t\t\tconst help = Chat.commands[namespace + 'help'];\r\n\t\t\t\tif (help) {\r\n\t\t\t\t\tconst text = Array.isArray(help) ?\r\n\t\t\t\t\t\thelp.join(' | ') : typeof help === 'function' ?\r\n\t\t\t\t\t\t\t`` : '';\r\n\t\t\t\t\tbuf += text ? ` (${text})` : `(no help found)`;\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\tbuf += `
`;\r\n\t\t}\r\n\t\tthis.sendReplyBox(buf);\r\n\t},\r\n\tadminhelphelp: [`/adminhelp - Programmatically generates a list of all administrator commands. Requires: &`],\r\n\r\n\taltlog: 'altslog',\r\n\taltslog(target, room, user) {\r\n\t\tthis.checkCan('lock');\r\n\t\ttarget = toID(target);\r\n\t\tif (!target) {\r\n\t\t\treturn this.parse(`/help altslog`);\r\n\t\t}\r\n\t\treturn this.parse(`/join view-altslog-${target}`);\r\n\t},\r\n\taltsloghelp: [\r\n\t\t`/altslog [userid] - View the alternate account history for the given [userid]. Requires: % @ &`,\r\n\t],\r\n};\r\n\r\nexport const handlers: Chat.Handlers = {\r\n\tonRename(user, oldID, newID) {\r\n\t\tif (oldID === newID || !Config.usesqlite || [oldID, newID].some(f => f.startsWith('guest'))) return;\r\n\t\tvoid Chat.database.run(\r\n\t\t\t`REPLACE INTO alts_log (to_id, from_id, ip) VALUES (?, ?, ?)`,\r\n\t\t\t[newID, oldID, user.latestIp]\r\n\t\t);\r\n\t},\r\n};\r\n\r\nexport const pages: Chat.PageTable = {\r\n\tasync altslog(query, user) {\r\n\t\tthis.checkCan('lock');\r\n\t\tthis.title = '[Alts Log]';\r\n\t\tconst target = toID(query.shift());\r\n\t\tif (!target) {\r\n\t\t\treturn this.errorReply(`Please specify a user to find alternate accounts for.`);\r\n\t\t}\r\n\t\tthis.title += ` ${target}`;\r\n\t\tif (!Config.usesqlite) {\r\n\t\t\treturn this.errorReply(`The alternate account log is currently disabled.`);\r\n\t\t}\r\n\t\tconst rawLimit = query.shift() || \"100\";\r\n\t\tconst num = parseInt(rawLimit);\r\n\t\tif (num > 3000) {\r\n\t\t\treturn this.errorReply(`3000 is the maximum number of results from the alternate account log.`);\r\n\t\t}\r\n\t\tif (isNaN(num) || num < 1) {\r\n\t\t\treturn this.errorReply(`The max results must be a real number that is at least one (received \"${rawLimit}\")`);\r\n\t\t}\r\n\t\tconst showIPs = user.can('globalban');\r\n\t\tconst results = await Chat.database.all(\r\n\t\t\t'SELECT to_id, from_id, ip FROM alts_log WHERE (to_id = ? OR from_id = ?) LIMIT ?',\r\n\t\t\t[target, target, num]\r\n\t\t);\r\n\t\tlet buf = `

Alternate accounts for ${target}

`;\r\n\t\tbuf += `${results.length} found.
`;\r\n\r\n\t\tconst ipTable = {} as Record;\r\n\t\tconst userids = new Set();\r\n\t\tconst useridToIp = new Map();\r\n\t\tfor (const result of results) {\r\n\t\t\tconst id = result.from_id === target ? result.to_id : result.from_id;\r\n\t\t\tuserids.add(id);\r\n\t\t\tlet prevIps = useridToIp.get(id);\r\n\t\t\tif (!prevIps) {\r\n\t\t\t\tprevIps = [];\r\n\t\t\t}\r\n\t\t\tif (!prevIps.includes(result.ip)) {\r\n\t\t\t\tprevIps.push(result.ip);\r\n\t\t\t}\r\n\t\t\tuseridToIp.set(id, prevIps);\r\n\t\t\tif (!ipTable[result.ip]) ipTable[result.ip] = 0;\r\n\t\t\tipTable[result.ip]++;\r\n\t\t}\r\n\t\tbuf += `
${showIPs ? `` : \"\"}`;\r\n\t\tfor (const id of userids) {\r\n\t\t\tconst ips = useridToIp.get(id) || [];\r\n\t\t\tbuf += ``;\r\n\t\t\tconst ipStr = ips.map(f => `${f}`).join(', ');\r\n\t\t\tbuf += `${showIPs ? `` : \"\"}`;\r\n\t\t}\r\n\t\tbuf += `
UseridLatest IP
`;\r\n\t\t\tbuf += `${id}${ipStr}
`;\r\n\t\tif (showIPs) {\r\n\t\t\tbuf += `
`;\r\n\t\t\tfor (const ip in ipTable) {\r\n\t\t\t\tbuf += ``;\r\n\t\t\t}\r\n\t\t\tbuf += `
IPTimes Used
${ip}${ipTable[ip]}
`;\r\n\t\t}\r\n\t\treturn buf;\r\n\t},\r\n\tbattlerules(query, user) {\r\n\t\tconst rules = Object.values(Dex.data.Rulesets).filter(rule => rule.effectType !== \"Format\");\r\n\t\tconst tourHelp = `https://www.smogon.com/forums/threads/pok%C3%A9mon-showdown-forum-rules-resources-read-here-first.3570628/#post-6777489`;\r\n\t\tthis.title = \"Custom Rules\";\r\n\t\tlet rulesHTML = `

Custom Rules in challenges and tournaments

`;\r\n\t\tconst basics = [\r\n\t\t\t`

Pokémon Showdown! supports custom rules in three ways:

`,\r\n\t\t\t`
  • Challenging another user, using the command /challenge USERNAME, FORMAT @@@ RULES
  • `,\r\n\t\t\t`
  • Tournaments, using the command /tour rules RULES (see the Tournament command help)
  • `,\r\n\t\t\t`
  • Custom rules on your own server
`,\r\n\t\t\t`

Bans

`,\r\n\t\t\t`

Bans are just a - followed by the thing you want to ban.

`,\r\n\t\t\t`

Individual bans

`,\r\n\t\t\t`
  • - Arceus: Ban a Pokémon (including all formes)
  • `,\r\n\t\t\t`
  • - Arceus-Flying or - Giratina-Altered: Ban a Pokémon forme
  • `,\r\n\t\t\t`
  • - Baton Pass: Ban a move/item/ability/etc
`,\r\n\t\t\t`

Group bans

`,\r\n\t\t\t`
  • - OU or - DUU: Ban a tier
  • `,\r\n\t\t\t`
  • - Mega or - CAP: Ban a Pokémon category
`,\r\n\t\t\t`

Complex bans

`,\r\n\t\t\t`
  • - Blaziken + Speed Boost: Ban a combination of things in a single Pokemon (you can have a Blaziken, and you can have Speed Boost on the same team, but the Blaziken can't have Speed Boost)
  • `,\r\n\t\t\t`
  • - Drizzle ++ Swift Swim: Ban a combination of things in a team (if any Pok\u00E9mon on your team have Drizzle, no Pok\u00E9mon can have Swift Swim)
`,\r\n\t\t\t`

Unbans

`,\r\n\t\t\t`

Using a + instead of a - unbans that category.

`,\r\n\t\t\t`
  • + Blaziken: Unban/unrestrict a Pokémon.
`,\r\n\t\t\t`

More details

`,\r\n\t\t];\r\n\t\tconst rulesets = [\r\n\t\t\t`

Rules, mods, and clauses

`,\r\n\t\t\t`

The following rules can be added to challenges/tournaments to modify the style of play. Alternatively, already present rules can be removed from formats by preceding the rule name with !

`,\r\n\t\t\t`

However, some rules, like Obtainable, are made of subrules, that can be individually turned on and off.

`,\r\n\t\t\t`
`,\r\n\t\t];\r\n\t\tfor (const rule of rules) {\r\n\t\t\tif (rule.hasValue) continue;\r\n\t\t\tconst desc = rule.desc ? rule.desc : \"No description.\";\r\n\t\t\trulesets.push(``);\r\n\t\t}\r\n\t\trulesets.push(\r\n\t\t\t`
Rule NameDescription
${rule.name}${desc}
`,\r\n\t\t\t`

Value rules

`,\r\n\t\t\t`
  • Value rules are formatted like [Name] = [value], e.g. \"Force Monotype = Water\" or \"Min Team Size = 4\"
  • `,\r\n\t\t\t`
  • To remove a value rule, use ![rule name].
  • `,\r\n\t\t\t`
  • To override another value rule, use !! [Name] = [new value]. For example, overriding the Min Source Gen on [Gen 8] VGC 2021 from 8 to 3 would look like !! Min Source Gen = 3.
`,\r\n\t\t\t`
`\r\n\t\t);\r\n\t\tfor (const rule of rules) {\r\n\t\t\tif (!rule.hasValue) continue;\r\n\t\t\tconst desc = rule.desc ? rule.desc : \"No description.\";\r\n\t\t\trulesets.push(``);\r\n\t\t}\r\n\t\trulesets.push(`
Rule NameDescription
${rule.name}${desc}
`);\r\n\t\trulesHTML += `${basics.concat(rulesets).join('')}
`;\r\n\t\treturn rulesHTML;\r\n\t},\r\n\tbuildformat(query, user) {\r\n\t\tthis.title = '[Format Customizer]';\r\n\t\tconst rules = Object.values(Dex.data.Rulesets).filter(rule => rule.effectType !== \"Format\");\r\n\t\tlet buf = `

Format customizer

`;\r\n\t\tbuf += ``;\r\n\t\tbuf += `
`;\r\n\t\tconst formatId = toID(query[0]);\r\n\t\tconst format = Dex.formats.get(formatId);\r\n\t\tif (!formatId || !format.exists) {\r\n\t\t\tif (formatId && !format.exists) {\r\n\t\t\t\tbuf += `
The format '${formatId}' does not exist.

`;\r\n\t\t\t}\r\n\t\t\tbuf += `
`;\r\n\t\t\tbuf += `Choose your format:
`;\r\n\t\t\tbuf += ``;\r\n\t\t\tbuf += `
`;\r\n\t\t\treturn buf;\r\n\t\t}\r\n\r\n\t\tbuf += `
`;\r\n\t\tconst ruleTable = Dex.formats.getRuleTable(format);\r\n\t\tconst cmd = [`format=${formatId}`, 'user={user}'];\r\n\t\tbuf += `Format: ${format.name}
`;\r\n\t\tbuf += `User to challenge: (optional)`;\r\n\t\tbuf += `

`;\r\n\t\tbuf += `Bans/Unbans
`;\r\n\t\tbuf += `
`;\r\n\t\tbuf += `Bans are a - followed by the thing you want to ban. `;\r\n\t\tbuf += `Using a + instead unbans Pokemon.`;\r\n\t\tbuf += `

Individual bans

`;\r\n\t\tbuf += `
  • - Arceus: Ban a Pokémon (including all formes)
  • `;\r\n\t\tbuf += `
  • - Arceus-Flying or - Giratina-Altered: Ban a Pokémon forme
  • `;\r\n\t\tbuf += `
  • - Baton Pass: Ban a move/item/ability/etc
`;\r\n\t\tbuf += `

Group bans

`;\r\n\t\tbuf += `
  • - OU or - DUU: Ban a tier
  • `;\r\n\t\tbuf += `
  • - Mega or - CAP: Ban a Pokémon category
`;\r\n\t\tbuf += `

Complex bans

`;\r\n\t\tbuf += `
  • - Blaziken + Speed Boost: Ban a combination of things in a single Pokemon (you can have a Blaziken, and you can have Speed Boost on the same team, but the Blaziken can't have Speed Boost)
  • `;\r\n\t\tbuf += `
  • - Drizzle ++ Swift Swim: Ban a combination of things in a team (if any Pok\u00E9mon on your team have Drizzle, no Pok\u00E9mon can have Swift Swim)
`;\r\n\t\tbuf += `

Unbans

`;\r\n\t\tbuf += `

Using a + instead of a - unbans that category.

`;\r\n\t\tbuf += `
  • + Blaziken: Unban/unrestrict a Pokémon.

`;\r\n\t\tcmd.push(`bans={bans}`);\r\n\t\tbuf += `Bans/Unbans: (separated by commas)

`;\r\n\t\tbuf += `
Clauses`;\r\n\t\tbuf += `

The following rules can be added to challenges/tournaments to modify the style of play. `;\r\n\t\tbuf += `Alternatively, already present rules can be removed from formats by preceding the rule name with !.

`;\r\n\t\tbuf += `

However, some rules, like Obtainable, are made of subrules, that can be individually turned on and off.

`;\r\n\t\tbuf += `

Note that if you do not explicitly check a mod to include it, it will not be included in the final output.

`;\r\n\t\tbuf += `
`;\r\n\t\tfor (const rule of rules) {\r\n\t\t\tif (rule.hasValue) continue;\r\n\t\t\tconst desc = rule.desc || \"No description.\";\r\n\t\t\tconst id = toID(rule.name);\r\n\t\t\tbuf += ``;\r\n\t\t\tbuf += ``;\r\n\t\t\tbuf += ``;\r\n\t\t\tbuf += ``;\r\n\t\t\tcmd.push(`${id}={${id}}`);\r\n\t\t}\r\n\t\tbuf += `
Rule NameDescriptionToggle
${rule.name}${desc}

`;\r\n\t\tbuf += `
Value Rules`;\r\n\t\tbuf += `Click the \"enabled\" checkbox and fill in a value to enable a rule - uncheck the box to remove the rule.`;\r\n\t\tbuf += `
`;\r\n\t\tfor (const rule of rules) {\r\n\t\t\tif (!rule.hasValue) continue;\r\n\t\t\tconst desc = rule.desc || \"No description.\";\r\n\t\t\tbuf += ``;\r\n\t\t\tconst id = toID(rule.name);\r\n\t\t\tconst existing = ruleTable.valueRules.get(id);\r\n\t\t\tbuf += ``;\r\n\t\t\tbuf += ``;\r\n\t\t}\r\n\t\tbuf += ``;\r\n\t\tbuf = buf.replace(`{{cmd}}`, `/makecustomchallenge ${cmd.join(' | ')}`);\r\n\t\tbuf += `

`;\r\n\t\tbuf += ``;\r\n\t\tbuf += ``;\r\n\t\treturn buf;\r\n\t},\r\n\tpunishments(query, user) {\r\n\t\tthis.title = 'Punishments';\r\n\t\tconst room = this.requireRoom();\r\n\r\n\t\tlet buf = \"\";\r\n\t\tif (!user.named) return Rooms.RETRY_AFTER_LOGIN;\r\n\t\tif (!room.persist) return;\r\n\t\tthis.checkCan('mute', null, room);\r\n\t\t// Ascending order\r\n\t\tconst sortedPunishments = Utils.sortBy([...Punishments.getPunishments(room.roomid)], ([id, entry]) => (\r\n\t\t\tentry.expireTime\r\n\t\t));\r\n\t\tconst sP = new Map();\r\n\t\tfor (const [id, entry] of sortedPunishments) {\r\n\t\t\tsP.set(id, entry);\r\n\t\t}\r\n\t\tbuf += Punishments.visualizePunishments(sP, user);\r\n\t\treturn buf;\r\n\t},\r\n\tglobalpunishments(query, user) {\r\n\t\tthis.title = 'Global Punishments';\r\n\t\tlet buf = \"\";\r\n\t\tif (!user.named) return Rooms.RETRY_AFTER_LOGIN;\r\n\t\tthis.checkCan('lock');\r\n\t\t// Ascending order\r\n\t\tconst sortedPunishments = Utils.sortBy([...Punishments.getPunishments()], ([id, entry]) => (\r\n\t\t\tentry.expireTime\r\n\t\t));\r\n\t\tconst sP = new Map();\r\n\t\tfor (const punishment of sortedPunishments) {\r\n\t\t\tsP.set(punishment[0], punishment[1]);\r\n\t\t}\r\n\t\tbuf += Punishments.visualizePunishments(sP, user);\r\n\t\treturn buf;\r\n\t},\r\n\tapprovals(args) {\r\n\t\tconst room = Rooms.get(args[0]) as ChatRoom | GameRoom;\r\n\t\tthis.checkCan('mute', null, room);\r\n\t\tif (!room.pendingApprovals) room.pendingApprovals = new Map();\r\n\t\tif (room.pendingApprovals.size < 1) return `

No pending approvals on ${room.title}

`;\r\n\t\tlet buf = `
Pending media requests on ${room.title}
`;\r\n\t\tfor (const [userid, entry] of room.pendingApprovals) {\r\n\t\t\tbuf += `${entry.name}
`;\r\n\t\t\tbuf += `Requester ID: ${userid}
`;\r\n\t\t\tbuf += `Link: ${entry.link}
`;\r\n\t\t\tbuf += `Comment: ${entry.comment}`;\r\n\t\t\tbuf += `

`;\r\n\t\t}\r\n\t\treturn buf;\r\n\t},\r\n};\r\n\r\nprocess.nextTick(() => {\r\n\tDex.includeData();\r\n\tChat.multiLinePattern.register(\r\n\t\t'/htmlbox', '/quote', '/addquote', '!htmlbox', '/addhtmlbox', '/addrankhtmlbox', '/adduhtml',\r\n\t\t'/changeuhtml', '/addrankuhtmlbox', '/changerankuhtmlbox', '/addrankuhtml', '/addhtmlfaq',\r\n\t\t'/sendhtmlpage',\r\n\t);\r\n});\r\n"], "mappings": "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", "names": [] }
Rule NameDescriptionToggle
${rule.name}${desc}Enabled:
`;\r\n\t\t\tbuf += `Value: `;\r\n\t\t\tcmd.push(`${id}-enabled={${id}enabled}`);\r\n\t\t\tcmd.push(`${id}-val={${id}val}`);\r\n\t\t\tbuf += `