// ==UserScript== // @name TW Friends // @name:el TW Friends // @name:es TW Friends // @name:fr TW Friends // @version 0.18 // @description Friend Management for The West Events // @description:el Διαχείριση Φίλων για τις Εκδηλώσεις του The West // @description:es Gestión de Amigos para Eventos de The West // @description:fr Gestion des Amis pour les Evénements de The West // @author hiroaki // @include http://*.the-west.*/game.php* // @include https://*.the-west.*/game.php* // @grant none // @namespace https://greasyfork.org/users/3197 // @downloadURL none // ==/UserScript== function hiroFriendsScript(fn) { var script = document.createElement('script'); script.setAttribute("type", "application/javascript"); script.textContent = '(' + fn + ')();'; document.body.appendChild(script); document.body.removeChild(script); } hiroFriendsScript (function() { var VERSION = 0.18; var installURL = "https://greasyfork.org/scripts/2992-tw-friends"; var scriptName = "TW Friends"; var scriptAuthor = "hiroaki"; var refreshMs = 2 * 60 * 1000; // 2 minutes HiroFriends = { api: TheWestApi.register('HiroFriends', scriptName, '2.0', Game.version.toString(), scriptAuthor, installURL), version: VERSION, storageItem: "HiroFriends.version", cdnBase: '', eventName : '', eventInfo : {}, eventEndStamp : 0, friends : [], interval: false, locale: 'en_US', messages: { el_GR: { description: '

Διαχείριση Φίλων για τις Εκδηλώσεις του The West

Μην κλικάρετε πολύ γρήγορα, για να αποφύγετε ένα σερί κακής τύχης :)

Υποστηριζόμενες Εκδηλώσεις:

Συζήτηση στο Φόρουμ | Feedback: Αναφορά Bugs, Ιδέες, Μεταφράσεις.

', refresh: 'Ανανέωση', availFriends: 'Αριθμός Φιλων στους οποίους μπορείς να στείλεις τώρα', totalFriends: 'Αριθμός Φίλων', noFriends: 'Δεν έχεις φίλους', name: 'Όνομα', received: 'Έλαβες', removeFriend: 'Αφαίρεση φίλου', removeConfirm: 'Θέλεις πραγματικά να διαγράψεις αυτόν τον παίχτη από τη λίστα;', removeSuccess: 'Ο φίλος αφαιρέθηκε από τη λίστα.', removeFailed: 'Ο φίλος δεν μπόρεσε να αφαιρεθεί', collected: 'Έχεις συλλέξει', friends: 'Φίλοι', jobs: 'Εργασίες', fortBattles: 'Μάχες Οχυρών', adventures: 'Adventures', duels: 'Μονομαχίες', npcDuels: 'Μονομαχίες με NPC', construction: 'Χτίσιμο', itemUse: 'Χρήση Αντικειμένων', other: 'Άλλα', used: 'Έχεις χρησιμοποιήσει', timerReset: 'Μηδενισμός χρονομέτρου', bribe: 'Δωροδοκίες', theEnd: 'Τετέλεσται', }, en_US: { description: '

Friend Management for The West Events

Don't click too fast, to avoid a streak of bad luck upon you :)

Supported Events:

Feedback: Bug Reports, Ideas, Translations (in English).

', refresh: 'Refresh', availFriends: 'Number of Friends you can send now', totalFriends: 'Number of Friends', noFriends: 'No Friends', name: 'Name', received: 'Received', removeFriend: 'Remove friend', removeConfirm: 'Do you really want to delete this player from the list?', removeSuccess: 'Friend removed from your list.', removeFailed: 'Friend could not be removed', collected: 'Collected', friends: 'Friends', jobs: 'Jobs', fortBattles: 'Fort Battles', adventures: 'Adventures', duels: 'Duels', npcDuels: 'NPC Duels', construction: 'Construction', itemUse: 'Item Use', other: 'Other', used: 'Used', timerReset: 'Reset Timers', bribe: 'Bribe', theEnd: 'The End', }, es_ES: { description: '

Gestión de Amigos para Eventos de The West

No haga clic demasiado rápido, para evitar una racha de mala suerte :)

Eventos soportados:

Comentarios: Bug Reports, Ideas, Translations (in English).

', refresh: 'Actualizar', availFriends: 'Número de Amigos que se puede enviar ahora', totalFriends: 'Número de Amigos', noFriends: 'Sin Amigos', name: 'Nombre', received: 'Has recibido', removeFriend: 'Remover amigo', removeConfirm: '¿Esta seguro de que quiere eliminar a este jugador de su lista?', removeSuccess: 'Amigo removido de tu lista', removeFailed: 'El amigo no ha podido ser eliminado', collected: 'Conseguidos', friends: 'Amicos', jobs: 'Trabajos', fortBattles: 'Batallas de fuertes', adventures: 'Aventuras', duels: 'Duelos', npcDuels: 'Duelos NPC', construction: 'Ampliación', itemUse: 'Objetos usados', other: 'Otros', used: 'Usados', timerReset: 'Reiniciar temporizadores', bribe: 'Soborno', theEnd: 'El Fin', }, fr_FR: { description: '

Gestion des Amis pour les Evénements de The West

Ne cliquez pas trop vite, pour éviter une série de malchance sur vous :)

Evénements:

Commentaires: Bug Reports, Ideas, Translations (in English).

', refresh: 'Rafraîchir', availFriends: 'Nombre des amis que tu peux envoyer maintenant', totalFriends: 'Nombre des Amis', noFriends: 'Pas d' Amis', name: 'Nom', received: 'Tu as reçu', removeFriend: 'Supprimer l'ami(e)", ', removeConfirm: 'Veux-tu vraiment supprimer ce joueur de la liste?', removeSuccess: 'Ami supprimé de la liste', removeFailed: 'L#039;ami n#039;a pas pu être supprimé', collected: 'Collectés', friends: 'Amis', jobs: 'Travaux', fortBattles: 'Batailles', adventures: 'Aventures', duels: 'Duels', npcDuels: 'Duels PNJ', construction: 'Agrandissement', itemUse: 'Objets utilisés', other: 'Autres', used: 'Utilisés', timerReset: 'Se battre en duel', bribe: 'Soudoyer', theEnd: 'La Fin', }, }, timeLeft : 0, total : 0, avail: 0, log: { lastLog: 0, friendLog: {}, count_friends: 0, count_job: 0, count_duel: 0, count_npc: 0, count_fort: 0, count_mpi: 0, count_build: 0, count_item: 0, count_other: 0, count_reset: 0, count_bribe: 0, times_reset: 0, times_bribe: 0, received: 0, used: 0 }, spanCounter: $("", { id: "hiro_friends_counter", style: "position: absolute; right: 5px; color: #f8c57c; font-size: 13pt; height: 25px; line-height: 25px; bottom: 0px" }), spanTimeLeft: $("", { id: "hiro_event_timeleft", style: "position: absolute; left: 5px; color: #d3d3d3; font-size: 11px; height: 25px; line-height: 25px" }) }; HiroFriends.init = function(eventName) { if (undefined === Game.sesData[eventName] || undefined === Game.sesData[eventName].friendsbar) return false; HiroFriends.eventName = eventName; HiroFriends.eventInfo = Game.sesData[eventName].friendsbar; if (undefined === Game.sesData[HiroFriends.eventName].meta.end) return false; HiroFriends.eventEndStamp = (buildTimestamp(Game.sesData[HiroFriends.eventName].meta.end) - Game.serverTimeDifference) / 1000; HiroFriends.timeLeft = HiroFriends.eventEndStamp - Game.getServerTime(); if (HiroFriends.timeLeft < 0) return false; HiroFriends.cdnBase = (undefined === Game.cdnURL) ? "https://westzzs.innogamescdn.com" : Game.cdnURL; HiroFriends.getLog(); var eventImage = HiroFriends.cdnBase + "/images/interface/friendsbar/events/" + HiroFriends.eventName + ".png"; // event based var divContainer = $("
", { id: "hiro_friends_container", style: "position: absolute; top: 32px; right: 50%; margin-right: 120px; z-index: 16; width: 180px; height: 36px; text-align: left; text-shadow: 1px 1px 1px #000; background: url('"+HiroFriends.cdnBase+"/images/interface/custom_unit_counter_sprite.png?2') no-repeat scroll 50% 0px transparent;" }) var divCounter = $("
", { id: "hiro_friends", style: "background: url('"+HiroFriends.cdnBase+"/images/interface/custom_unit_counter_sprite.png?2') no-repeat scroll 0 -36px rgba(0, 0, 0, 0); height: 25px; left: 32px; line-height: 25px; padding: 0 5px; position: absolute; top: 3px; width: 105px; z-index: 1; text-shadow: 1px 1px 1px #000;" }); var divRefresh = $("
", { style: "width: 24px; height: 24px; position: absolute; left: 8px; top: 3px; z-index: 3; padding: 4px 0px 0px 4px;" }); var spanRefresh = $('', { title: HiroFriends.localeMsg('refresh'), style: "display: inline-block; width: 20px; height: 20px; cursor: pointer; background: url('"+HiroFriends.cdnBase+"/images/tw2gui/window/window2_buttons.png?5') repeat scroll 0px -20px transparent;" }); var spanSend = $("", { style: "width: 26px; height: 26px; left: auto; position: absolute; right: 7px; top: 2px; z-index: 3;" }); var imageSend = $("", { src: eventImage, title: HiroFriends.eventInfo.label, style: "width: 26px; height: 26px; cursor: pointer" }); divContainer.append(divRefresh.append(spanRefresh), spanSend.append(imageSend), divCounter.append(HiroFriends.spanTimeLeft, HiroFriends.spanCounter)).appendTo("#user-interface");; spanRefresh.hover(function() { $(this).css("background-position", ""); }, function() { $(this).css("background-position", "0px -20px"); }); spanRefresh.click(function() { HiroFriends.spanCounter.slideUp(500, function() { HiroFriends.fetch(); }).slideDown(1500); }); imageSend.click(function() { HiroFriends.open(); }); HiroFriends.updateTimer(); if(typeof(Storage) !== "undefined") { var previousVersion = (localStorage.getItem(HiroFriends.storageItem) === null) ? 0 : parseFloat(localStorage.getItem(HiroFriends.storageItem)); localStorage.setItem(HiroFriends.storageItem, HiroFriends.version); // if (previousVersion && HiroFriends.version > previousVersion) var msg=new west.gui.Dialog("TW Friends", "Script upgraded to version "+HiroFriends.version, west.gui.Dialog.SYS_WARNING).addButton("OK").show(); } $("").appendTo("head"); return true; }; HiroFriends.localeMsg = function(msg) { if (HiroFriends.messages[HiroFriends.locale][msg]) return HiroFriends.messages[HiroFriends.locale][msg]; if (HiroFriends.messages.en_US.msg) return HiroFriends.messages.en_US.msg; return ''; } HiroFriends.fetch = function() { if (HiroFriends.interval !== false) clearInterval (HiroFriends.interval); var event_times = {}; var friends = [], total = 0, avail = 0, recv = 0; var server_time = Game.getServerTime(), activation_time, friend_time; if (HiroFriends.timeLeft < 0) { $("#hiro_friends_container").slideUp(5000); throw "Event is over"; } return $.post( "/game.php?window=friendsbar&mode=search", { search_type: "friends" } , function (data) { $.each(data.eventActivations, function (key, val) { if (val.event_name == HiroFriends.eventName) event_times[val.friend_id] = val.activation_time; }); $.each(data.players, function (key, val) { if (val.name !== Character.name) { activation_time = (event_times[val.player_id] !== undefined) ? event_times[val.player_id]: 0; friend_time = activation_time + HiroFriends.eventInfo.cooldown - server_time; recv = (undefined === HiroFriends.log.friendLog[val.player_id]) ? 0 : HiroFriends.log.friendLog[val.player_id]; friends.push ({ id: val.player_id, name: val.name, time: friend_time, recv: recv }); ++ total; if (friend_time <= 0) ++ avail; } }); HiroFriends.friends = friends; HiroFriends.avail = avail; HiroFriends.total = total; HiroFriends.interval = setInterval(function() { HiroFriends.fetch(); }, refreshMs); HiroFriends.update(); }); } HiroFriends.getLog = function() { var hasNext = true; var limit = 100; var page = 1; var count = 0; var details; var maxDate = HiroFriends.log.lastLog; while (hasNext) { $.ajax({ type: "POST", url: "/game.php?window=ses&mode=log", data: { ses_id: HiroFriends.eventName, page: page, limit: limit }, async: false, success: function(data) { hasNext = data.hasNext; limit = data.limit; page = data.page + 1; $.each(data.entries, function (key, val) { count = parseInt(val.value); if (val.date <= HiroFriends.log.lastLog) { hasNext = false; return false; } if (val.date > maxDate) maxDate = val.date; switch (val.type) { case "friendDrop": details = JSON.parse(val.details); if (undefined !== HiroFriends.friends[details.player_id]) HiroFriends.friends[details.player_id].recv += count; if (undefined === HiroFriends.log.friendLog[details.player_id]) HiroFriends.log.friendLog[details.player_id] = count; else HiroFriends.log.friendLog[details.player_id] += count; HiroFriends.log.count_friends += count; HiroFriends.log.received += count; break; case "jobDrop": HiroFriends.log.count_job += count; HiroFriends.log.received += count; break; case "buildDrop": HiroFriends.log.count_build += count; HiroFriends.log.received += count; break; case "duelDrop": HiroFriends.log.count_duel += count; HiroFriends.log.received += count; break; case "duelNPCDrop": HiroFriends.log.count_npc += count; HiroFriends.log.received += count; break; case "battleDrop": HiroFriends.log.count_fort += count; HiroFriends.log.received += count; break; case "adventureDrop": HiroFriends.log.count_mpi += count; HiroFriends.log.received += count; break; case "itemUse": HiroFriends.log.count_item += count; HiroFriends.log.received += count; break; case "wofPay": HiroFriends.log.used += count; if (val.details == "timerreset") { HiroFriends.log.count_reset += count; ++ HiroFriends.log.times_reset; } else if (val.details == "sneakyshot") { HiroFriends.log.count_bribe += count; ++ HiroFriends.log.times_bribe; } break; default: HiroFriends.log.count_other += count; HiroFriends.log.received += count; } }); }}); } HiroFriends.log.lastLog = maxDate; } HiroFriends.display = function(sort) { var maindiv = $('
'); if (!HiroFriends.friends.length) $('

'+HiroFriends.localeMsg('noFriends')+'

').appendTo(maindiv); else { switch (sort) { case "name" : HiroFriends.friends.sort(HiroFriends.nameCompare); break; case "name_desc": HiroFriends.friends.sort(HiroFriends.nameCompare).reverse(); break; case "recv" : HiroFriends.friends.sort(HiroFriends.recvCompare); break; case "recv_asc" : HiroFriends.friends.sort(HiroFriends.recvCompare).reverse(); break; case "time_asc" : HiroFriends.friends.sort(HiroFriends.timeCompare).reverse(); break; case "time" : default : sort = "time"; HiroFriends.friends.sort(HiroFriends.timeCompare); } var thName = $(' '+HiroFriends.localeMsg('name')+'').click(function (){ HiroFriends.display(sort == 'name' ? 'name_desc' : 'name'); }); var thAction = $(' '+HiroFriends.eventInfo.label+'').click(function (){ HiroFriends.display(sort == 'time' ? 'time_asc' : 'time'); }); var thRecv = $(' '+HiroFriends.localeMsg('received')+'').click(function (){ HiroFriends.display(sort == 'recv' ? 'recv_asc' : 'recv'); }); var hiroTable = new west.gui.Table().appendTo(maindiv).addColumn("hf_idx").addColumn("hf_player").addColumn("hf_action").addColumn("hf_log").addColumn("hf_delete").appendToCell("head", "hf_idx", ' ').appendToCell("head", "hf_player", thName).appendToCell("head", "hf_action", thAction).appendToCell("head","hf_log",thRecv).appendToCell("head", "hf_delete", ' '); var idx = 1; $.each(HiroFriends.friends, function (key, val) { var actionCell; if (val.time > HiroFriends.timeLeft) actionCell = '(Next Year)'; else if (val.time > 0) actionCell = '('+val.time.formatDurationBuffWay()+')'; else { actionCell = $(''+HiroFriends.eventInfo.label+'').click({ id: val.id, ev: HiroFriends.eventName }, function (e) { $(this).parent().parent().remove(); Ajax.remoteCall("friendsbar", "event", { player_id: val.id, event: HiroFriends.eventName }, function (response) { if (response.error) return MessageError(response.msg).show(); MessageSuccess(response.msg).show(); val.time += 86400; if (HiroFriends.avail) -- HiroFriends.avail; HiroFriends.update(); if (WestUi.FriendsBar.friendsBarUi !== null) WestUi.FriendsBar.friendsBarUi.friendsBar.eventActivations[val.id][HiroFriends.eventName] = response.activationTime; }); }); } hiroTable.appendRow(null, 'hiroFriendRow_'+val.id) .appendToCell(-1, "hf_idx", idx) .appendToCell(-1, "hf_player", '' + val.name + '') .appendToCell(-1, "hf_action", actionCell) .appendToCell(-1, "hf_log", val.recv) .appendToCell(-1, "hf_delete", 'delete'); ++ idx; }); hiroTable.appendToCell('foot', 'hf_action', 'TW Friends version ' + HiroFriends.version.toFixed(2) + ''); if ('http://gr1.the-west.gr' == Game.gameURL || 'http://gr4.the-west.gr' == Game.gameURL || 'http://gr5.the-west.gr' == Game.gameURL) hiroTable.appendToCell('foot', 'hf_log', 'by '+scriptAuthor+''); else if ('https://zz1.beta.the-west.net' == Game.gameURL) hiroTable.appendToCell('foot', 'hf_log', 'by '+scriptAuthor+''); } $('
').appendTo(maindiv); $(''+(HiroFriends.log.used?'' : '') + '
'+HiroFriends.localeMsg('collected')+':'+HiroFriends.log.received+' '+HiroFriends.localeMsg('friends')+': '+HiroFriends.log.count_friends+', '+HiroFriends.localeMsg('jobs')+': '+HiroFriends.log.count_job+', '+HiroFriends.localeMsg('fortBattles')+': '+HiroFriends.log.count_fort+', '+HiroFriends.localeMsg('adventures')+': '+HiroFriends.log.count_mpi+', '+HiroFriends.localeMsg('duels')+': '+HiroFriends.log.count_duel+', '+HiroFriends.localeMsg('npcDuels')+': '+HiroFriends.log.count_npc+', '+HiroFriends.localeMsg('construction')+': '+HiroFriends.log.count_build+', '+HiroFriends.localeMsg('itemUse')+': '+HiroFriends.log.count_item+', '+HiroFriends.localeMsg('other')+': '+HiroFriends.log.count_other+'
'+HiroFriends.localeMsg('used')+':'+HiroFriends.log.used+''+HiroFriends.localeMsg('timerReset')+' '+HiroFriends.log.count_reset+' (#'+HiroFriends.log.times_reset+'), '+HiroFriends.localeMsg('bribe')+': '+HiroFriends.log.count_bribe+' (#'+HiroFriends.log.times_bribe+')
').appendTo(maindiv); var hiroWindow = wman.open("HiroFriends_"+HiroFriends.eventName, null, "noreload").setMiniTitle(HiroFriends.eventInfo.label).setTitle(HiroFriends.eventInfo.label); hiroWindow.appendToContentPane(maindiv); } HiroFriends.open = function() { if (!WestUi.FriendsBar.hidden) WestUi.FriendsBar.toggle(); HiroFriends.getLog(); return HiroFriends.fetch().done(function() { HiroFriends.display('time'); }); } HiroFriends.nameCompare = function(a, b) { return a.name.toLowerCase().localeCompare(b.name.toLowerCase()); } HiroFriends.recvCompare = function(a, b) { if (a.recv > b.recv) return -1; if (a.recv < b.recv) return 1; return 0; } HiroFriends.timeCompare = function(a, b) { if (a.time < b.time) return -1; if (a.time > b.time) return 1; return 0; } HiroFriends.updateTimer = function() { HiroFriends.timeLeft = HiroFriends.eventEndStamp - Game.getServerTime(); if (HiroFriends.timeLeft <= 0) { HiroFriends.spanTimeLeft.html(HiroFriends.localeMsg('theEnd')); HiroFriends.fetch(); return; } HiroFriends.spanTimeLeft.html(HiroFriends.timeLeft.formatDurationBuffWay()); var seconds = 0; if (HiroFriends.timeLeft < 70) seconds = 1; else if (HiroFriends.timeLeft < 3660) seconds = 10; else if (HiroFriends.timeLeft < 86520) seconds = 60; else seconds = 120; setTimeout (function() { HiroFriends.updateTimer(); }, seconds * 1000); } HiroFriends.update = function() { HiroFriends.spanCounter.html(''+HiroFriends.avail+' / '+HiroFriends.total+''); } HiroFriends.removeFriend = function(charId) { new west.gui.Dialog(HiroFriends.localeMsg('removeFriend'), HiroFriends.localeMsg('removeConfirm')).setIcon(west.gui.Dialog.SYS_QUESTION).addButton("yes", function() { Ajax.remoteCall('character', 'cancel_friendship', { friend_id: charId }, function(json) { if (json["result"]) { new UserMessage(HiroFriends.localeMsg('removeSuccess'), UserMessage.TYPE_SUCCESS).show(); $("div.hiroFriendRow_" + charId).remove(); $("div.friendData_" + charId, FriendslistWindow.DOM).remove(); if (HiroFriends.avail) -- HiroFriends.avail; if (HiroFriends.total) -- HiroFriends.total; HiroFriends.update(); Chat.Friendslist.removeFriend(charId); } else new UserMessage(HiroFriends.localeMsg('removeFailed'), UserMessage.TYPE_ERROR).show(); }); }).addButton("no").show(); } HiroFriends.scriptInit = function(tries, maxTries) { var ev, eventName; if (tries >= maxTries) return false; if (Game && Game.loaded) { HiroFriends.locale = (undefined === Game.locale || undefined == HiroFriends.messages[Game.locale]) ? "en_US" : Game.locale; HiroFriends.api.setGui(HiroFriends.localeMsg('description')); for (eventName in Game.sesData) { if (!Game.sesData.hasOwnProperty(eventName)) continue; var ev = Game.sesData[eventName]; if (!ev.friendsbar) continue; if ('Hearts' == eventName || 'Easter' == eventName || 'Independence' == eventName || 'DayOfDead' == eventName) { if (HiroFriends.init(eventName)) HiroFriends.fetch(); return false; } } return true; } ++ tries; setTimeout(function() { HiroFriends.scriptInit(tries, maxTries); }, tries * 1000); } HiroFriends.scriptInit(0, 100); });