#include chat.js #include cookies.js #include copyright.js #include emotes.js #include messages.js #include notify.js #include reconnect.js #include servers.js #include settings.js #include sockchat.js #include sound.js #include styles.js #include title.js #include txtrigs.js #include utility.js var AmiContext = function(title, auth, loading) { var pub = {}; var settings = new AmiSettings; pub.settings = settings; settings.define('style', 'string', ''); settings.define('soundMute', 'boolean'); settings.define('soundVolume', 'number', 0.8); settings.define('soundPack', 'string'); settings.define('enableNotifs', 'boolean'); settings.define('msgAutoScroll', 'boolean', true, true, true); settings.define('runJokeTriggers', 'boolean', true); settings.define('dumpPackets', 'boolean'); settings.define('parseEmoticons', 'boolean', true); settings.define('parseLinks', 'boolean', true); settings.define('bbAutoEmbedV1', 'boolean', false); settings.define('bbParse', 'boolean', true); settings.define('bbParseColour', 'boolean', true); settings.define('bbParseImage', 'boolean', true); settings.define('bbParseVideo', 'boolean', true); settings.define('bbParseAudio', 'boolean', true); settings.define('bbPersistBold', 'boolean'); settings.define('bbPersistItalics', 'boolean'); settings.define('bbPersistUnderline', 'boolean'); settings.define('bbPersistStrike', 'boolean'); settings.define('bbPersistSjis', 'boolean'); settings.define('bbPersistColour', 'string'); settings.define('migrated', 'boolean', false); if(!settings.get('migrated')) { settings.set('migrated', true); var scBBEnable = JSON.parse(AmiCookies.getCookie('sockchat_bbenable') || null), scOpts = JSON.parse(AmiCookies.getCookie('sockchat_opts') || null), scPersist = JSON.parse(AmiCookies.getCookie('sockchat_persist') || null), scStyle = AmiCookies.getCookie('sockchat_style'); if(typeof scStyle === 'string') settings.set('style', scStyle); if(scOpts) { if(typeof scOpts.bbcode === 'boolean') settings.set('bbParse', scOpts.bbcode); if(typeof scOpts.emotes === 'boolean') settings.set('parseEmoticons', scOpts.emotes); if(typeof scOpts.links === 'boolean') settings.set('parseLinks', scOpts.links); if(typeof scOpts.sound === 'boolean') settings.set('soundMute', !scOpts.sound); if(typeof scOpts.spack === 'string') settings.set('soundPack', scOpts.spack); if(typeof scOpts.volume === 'string') settings.set('soundVolume', parseFloat(scOpts.volume)); else if(typeof scOpts.volume === 'number') settings.set('soundVolume', scOpts.volume); } if(scBBEnable) { if(typeof scBBEnable.color === 'boolean') settings.set('bbParseColour', scBBEnable.color); if(typeof scBBEnable.img === 'boolean') settings.set('bbParseImage', scBBEnable.img); if(typeof scBBEnable.video === 'boolean') settings.set('bbParseVideo', scBBEnable.video); if(typeof scBBEnable.audio === 'boolean') settings.set('bbParseAudio', scBBEnable.audio); } if(scPersist) { if(typeof scPersist.b === 'object') settings.set('bbPersistBold', !!scPersist.b.enable); if(typeof scPersist.i === 'object') settings.set('bbPersistItalics', !!scPersist.i.enable); if(typeof scPersist.u === 'object') settings.set('bbPersistUnderline', !!scPersist.u.enable); if(typeof scPersist.s === 'object') settings.set('bbPersistStrike', !!scPersist.s.enable); if(typeof scPersist.color === 'object') settings.set('bbPersistColour', scPersist.color.enable ? (scPersist.color.value || '').toString() : null); } AmiCookies.removeCookie('sockchat_bbenable'); AmiCookies.removeCookie('sockchat_opts'); AmiCookies.removeCookie('sockchat_persist'); AmiCookies.removeCookie('sockchat_style'); } var sound = new AmiSound; pub.sound = sound; settings.watch('soundVolume', function(value) { sound.setVolume(value); }); settings.watch('soundPack', function(value) { sound.setPackName(value); }); var textTriggers = new AmiTextTriggers; pub.textTriggers = textTriggers; settings.watch('runJokeTriggers', function(value) { if(!textTriggers.hasTriggers()) futami.getJson('texttriggers', function(trigInfos) { textTriggers.addTriggers(trigInfos); }); }); var styles = new AmiStyles; pub.styles = styles; styles.register('beige', 'Beige'); styles.register('black', 'Black', true); styles.register('blue', 'Blue'); styles.register('cobalt', 'Cobalt'); styles.register('halext', 'Halext'); styles.register('legacy', 'Legacy'); styles.register('lithium', 'Lithium'); styles.register('mio', 'Mio'); styles.register('misuzu', 'Misuzu'); styles.register('nico', 'Nico'); styles.register('oxygen', 'Oxygen'); styles.register('sulfur', 'Sulfur'); styles.register('techno', 'Techno'); styles.register('white', 'White'); styles.register('yuuno', 'Yuuno'); settings.watch('style', function(value) { try { styles.apply(value); } catch(ex) { styles.setDefault(); } }); var notifications = new AmiNotify; pub.notifications = notifications; settings.watch('enableNotifs', function(value) { if(!value) { notifications.disable(); return; } notifications.enable(function(state) { if(!state) settings.set('enableNotifs', false); }); }); var emoticons = new AmiEmoticons; pub.emoticons = emoticons; pub.servers = new AmiServers; pub.windowTitle = new AmiWindowTitle(title); var sockChat = new AmiSockChat(auth); pub.sockChat = sockChat; var chat = new AmiChat(pub, title, document.body); pub.chat = chat; settings.watch('parseEmoticons', function(value) { if(!value) { chat.emoticonList.hide(); emoticons.clear(); return; } futami.getJson('emotes', function(emotes) { if(Array.isArray(emotes)) emoticons.loadLegacy(emotes); chat.emoticonList.render(emoticons); }); }); var reconnecter = new AmiReconnecter(chat); pub.reconnecter = reconnecter; pub.pageIsHidden = function() { if('visibilityState' in document) return document.visibilityState !== 'visible'; if('hidden' in document) return document.hidden; return false; }; sockChat.watch('conn:init', function(info) { console.log('conn:init', info); if(!info.wasConnected) loading.setTextRaw(AmiStrings.getMenuString('conn')); }); sockChat.watch('conn:ready', function(info) { console.log('conn:ready', info); if(!info.wasConnected) loading.setTextRaw(AmiStrings.getMenuString('auth')); chat.statusIndicator.setGreen('Ready!'); if(reconnecter.isActive()) reconnecter.session(function(man) { man.success(); }); }); sockChat.watch('conn:lost', function(info) { console.log('conn:lost', info); if(info.wasConnected) { chat.statusIndicator.setRed('Connection with server has been lost.'); if(!reconnecter.isActive()) reconnecter.start(function() { sockChat.open(); }); UI.AddMessage('rc', null, UI.ChatBot, info.msg, false, false); } else { var msg = { '_1000': 'The connection has been ended.', '_1001': 'Something went wrong on the server side.', '_1002': 'Your client sent broken data to the server.', '_1003': 'Your client sent data to the server that it doesn\'t understand.', '_1005': 'No additional information was provided.', '_1006': 'You lost connection unexpectedly!', '_1007': 'Your client sent broken data to the server.', '_1008': 'Your client did something the server did not agree with.', '_1009': 'Your client sent too much data to the server at once.', '_1011': 'Something went wrong on the server side.', '_1012': 'The server is restarting, reconnecting soon...', '_1013': 'You cannot connect to the server right now, try again later.', '_1015': 'Your client and the server could not establish a secure connection.', }['_' + info.code.toString()] || ('Something caused an unexpected connection loss, the error code was: ' + info.code.toString() + '.'); loading.hideIndicator(); loading.setTextRaw(AmiStrings.getMenuString('term') + '

' + msg); } }); sockChat.watch('conn:error', function() { console.log('conn:error'); if(reconnecter.isActive()) reconnecter.session(function(man) { man.fail(); }); }); sockChat.watch('ping:send', function() { console.log('ping:send'); chat.statusIndicator.setYellow('Pinging...'); }); sockChat.watch('ping:long', function() { console.log('ping:long'); chat.statusIndicator.setRed('Server is taking longer than 2 seconds to respond.'); }); sockChat.watch('ping:recv', function(info) { console.log('ping:recv', info); chat.statusIndicator.setGreen('Server took ' + info.diff.toLocaleString() + 'ms to respond.'); }); sockChat.watch('session:start', function(info) { console.log('session:start', info); if(!info.wasConnected) { loading.hideIndicator(); loading.setTextRaw('Welcome!'); loading.close(); loading = undefined; } UserContext.self = new User(info.user.id, info.user.name, info.user.colour, info.user.permsRaw); UserContext.self.channel = info.channel.name; UI.AddUser(UserContext.self, false); UI.RedrawUserList(); }); sockChat.watch('session:fail', function(info) { console.log('session:fail', info); var overlay = AmiStrings.getMenuString(info.session.reason); if(info.baka) { if(info.baka.perma) overlay += '
' + AmiStrings.getMenuString('eot'); else overlay += '
' + info.baka.until.toLocaleString(); } overlay += '

' + AmiStrings.getMenuString('back') + ''; loading.hideIndicator(); loading.setTextRaw(overlay); }); sockChat.watch('session:term', function(info) { console.log('session:term', info); var overlay = AmiStrings.getMenuString(info.baka.type); if(info.baka.until) overlay += '
' + info.baka.until.toLocaleString(); overlay += '

' + AmiStrings.getMenuString('back') + ''; if(loading === undefined) loading = new AmiLoadingOverlay(document.body); loading.setTextRaw(overlay); }); sockChat.watch('user:add', function(info) { console.log('user:add', info); if(UserContext.self.id !== info.user.id) UI.AddUser(new User(info.user.id, info.user.name, info.user.colour, info.user.permsRaw, info.user.hidden)); if(info.msg) { UI.AddMessage(info.msg.id, info.msg.time, UI.ChatBot, info.msg.text, true, false); sound.playEventSound('join'); } }); sockChat.watch('user:remove', function(info) { console.log('user:remove', info); if(info.msg) { var sounds = { 'flood': ['flood', 'kick', 'leave'], 'kick': ['kick', 'leave'], 'timeout': ['timeout', 'leave'], }; UI.AddMessage(info.msg.id, info.msg.time, UI.ChatBot, info.msg.text, true, false); ami.sound.playEventSound(info.leave.type in sounds ? sounds[info.leave.type] : 'leave'); } UI.RemoveUser(info.user.id); }); sockChat.watch('user:update', function(info) { console.log('user:update', info); if(UserContext.self.id === info.user.id) { UserContext.self.username = info.user.name; UserContext.self.color = info.user.colour; UserContext.self.permstr = info.user.permsRaw; UserContext.self.EvaluatePermString(); UI.ModifyUser(UserContext.self); } else { UserContext.users[info.user.id].username = info.user.name; UserContext.users[info.user.id].color = info.user.colour; UserContext.users[info.user.id].permstr = info.user.permsRaw; UserContext.users[info.user.id].EvaluatePermString(); UI.ModifyUser(UserContext.users[info.user.id]); } }); sockChat.watch('user:clear', function() { console.log('user:clear'); UserContext.users = {}; UI.RedrawUserList(); }); sockChat.watch('chan:add', function(info) { console.log('chan:add', info); UI.AddChannel(info.channel.name, info.channel.hasPassword, info.channel.isTemporary, false); }); sockChat.watch('chan:remove', function(info) { console.log('chan:remove', info); UI.RemoveChannel(info.channel.name); }); sockChat.watch('chan:update', function(info) { console.log('chan:update', info); UI.ModifyChannel(info.channel.previousName, info.channel.name, info.channel.hasPassword, info.channel.isTemporary); }); sockChat.watch('chan:clear', function() { console.log('chan:clear'); UI.RedrawChannelList(); }); sockChat.watch('chan:focus', function(info) { console.log('chan:focus', info); UI.SwitchChannel(info.channel.name); }); sockChat.watch('chan:join', function(info) { console.log('chan:join', info); if(UserContext.self.id !== info.user.id) { UI.AddUser(new User(info.user.id, info.user.name, info.user.colour, info.user.permsRaw)); UI.AddMessage(info.msg.id, null, UI.ChatBot, info.msg.text, true, false); ami.sound.playEventSound('join'); } }); sockChat.watch('chan:leave', function(info) { console.log('chan:leave', info); if(UserContext.self.id !== info.user.id) { UI.AddMessage(info.msg.id, null, UI.ChatBot, info.msg.text, true, false); UI.RemoveUser(info.user.id); ami.sound.playEventSound('leave'); } }); sockChat.watch('msg:add', function(info) { console.log('msg:add', info); if(info.msg.silent !== undefined) UI.AddMessage(info.msg.id, info.msg.time, info.msg.isBot ? UI.ChatBot : new User(info.msg.sender.id, info.msg.sender.name, info.msg.sender.colour, info.msg.sender.permsRaw), info.msg.text, !info.msg.silent, !info.msg.silent, info.msg.flagsRaw); else if(info.msg.isBot) UI.AddMessage(info.msg.id, info.msg.time, UI.ChatBot, info.msg.text, true, true, info.msg.flagsRaw); else if(UserContext.self.id === info.msg.sender.id) UI.AddMessage(info.msg.id, info.msg.time, UserContext.self, info.msg.text, true, true, info.msg.flagsRaw); else UI.AddMessage(info.msg.id, info.msg.time, UserContext.users[info.msg.sender.id], info.msg.text, true, true, info.msg.flagsRaw); }); sockChat.watch('msg:remove', function(info) { console.log('msg:remove', info); }); sockChat.watch('msg:clear', function() { console.log('msg:clear'); }); return pub; };