Diff
checker
テキスト
テキスト
画像
ドキュメント
Excel
フォルダ
Legal
Enterprise
デスクトップ
料金
ログイン
Diffchecker デスクトップのダウンロード
テキスト比較
2 つのテキスト ファイルの違いを見つける
ツール
履歴
ライブエディター
未変更行を折りたたむ
折り返しなし
レイアウト
分割
統合
比較精度
スマート
単語
文字
シンタックスハイライト
構文を選択
無視
テキスト変換
最初の差分へ移動
入力を編集
Diffchecker Desktop
Diffcheckerを実行する最も安全な方法。Diffchecker Desktopアプリを入手:あなたの差分はコンピューターから出ることはありません!
Desktopを入手
Untitled diff
作成日
9 年前
差分は期限切れになりません
クリア
エクスポート
共有
説明
6 削除
行
合計
削除
文字
合計
削除
この機能を引き続き使用するには、アップグレードしてください
Diff
checker
Pro
価格を見る
684 行
すべてコピー
7 追加
行
合計
追加
文字
合計
追加
この機能を引き続き使用するには、アップグレードしてください
Diff
checker
Pro
価格を見る
684 行
すべてコピー
"use strict";
"use strict";
var raidListUpdateInterval = 30000;
var raidListUpdateInterval = 30000;
var raidListUpdateBackoff = 1350;
var raidListUpdateBackoff = 1350;
var raidListUpdateCounter = 25;
var raidListUpdateCounter = 25;
var statusPanelUpdateIntervalSeconds = 30;
var statusPanelUpdateIntervalSeconds = 30;
var minimumBuffUpdateIntervalSeconds = 70;
var minimumBuffUpdateIntervalSeconds = 70;
var currentRaidListUpdateInterval = raidListUpdateInterval;
var currentRaidListUpdateInterval = raidListUpdateInterval;
var updateRaidsPanel = null, invalidateRaidList = null, doUpdateRaidsPanel = null, updateItemsPanel = null, invalidateItems = null, doUpdateItemsPanel = null;
var updateRaidsPanel = null, invalidateRaidList = null, doUpdateRaidsPanel = null, updateItemsPanel = null, invalidateItems = null, doUpdateItemsPanel = null;
var updateBuffsWhen = 0, isUpdatingBuffs = false;
var updateBuffsWhen = 0, isUpdatingBuffs = false;
var queuedRaidClick = null;
var queuedRaidClick = null;
var pendingRaidUpdate = null;
var pendingRaidUpdate = null;
var nextRaidUpdateWhen = null;
var nextRaidUpdateWhen = null;
var menuIconSize = 0;
var menuIconSize = 0;
var menuLeftEdge = 0;
var menuLeftEdge = 0;
var subpanelOffset = 0;
var subpanelOffset = 0;
var mostRecentItems = null;
var mostRecentItems = null;
var lastPlayerStatus = null;
var lastPlayerStatus = null;
var statusIntervalH, raidTimerIntervalH;
var statusIntervalH, raidTimerIntervalH;
var allBookmarks = {};
var allBookmarks = {};
function bookmarkNavigate(target, evt) {
function bookmarkNavigate(target, evt) {
var inNewWindow = false;
var inNewWindow = false;
if (evt) {
if (evt) {
inNewWindow = (evt.button === 1) ||
inNewWindow = (evt.button === 1) ||
!!evt.shiftKey;
!!evt.shiftKey;
}
}
if (inNewWindow) {
if (inNewWindow) {
// HACK: Fully resolve the URL
// HACK: Fully resolve the URL
var elt = document.createElement("a");
var elt = document.createElement("a");
elt.href = target;
elt.href = target;
chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href });
chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href });
}
}
else {
else {
chrome.runtime.sendMessage({ type: "setLastLocation", url: target });
chrome.runtime.sendMessage({ type: "setLastLocation", url: target });
window.location.href = target;
window.location.href = target;
}
}
}
}
;
;
function repeatLastQuest(evt, callback) {
function repeatLastQuest(evt, callback) {
chrome.runtime.sendMessage({ type: "getRecentQuest" }, function (recentQuestJson) {
chrome.runtime.sendMessage({ type: "getRecentQuest" }, function (recentQuestJson) {
if (!recentQuestJson) {
if (!recentQuestJson) {
if (callback)
if (callback)
callback(false, "No recent quest to attempt");
callback(false, "No recent quest to attempt");
else
else
return showBookmarkError("No recent quest to attempt.");
return showBookmarkError("No recent quest to attempt.");
}
}
var recentQuest;
var recentQuest;
try {
try {
recentQuest = JSON.parse(recentQuestJson);
recentQuest = JSON.parse(recentQuestJson);
}
}
catch (exc) {
catch (exc) {
if (callback)
if (callback)
callback(false, "No recent quest to attempt");
callback(false, "No recent quest to attempt");
else
else
return showBookmarkError("No recent quest to attempt.");
return showBookmarkError("No recent quest to attempt.");
}
}
var parts = splitQuestId(recentQuest.quest_id);
var parts = splitQuestId(recentQuest.quest_id);
var chapterId = parts[0];
var chapterId = parts[0];
var suffix = parts[1];
var suffix = parts[1];
var itemId = recentQuest.use_item_id;
var itemId = recentQuest.use_item_id;
if (itemId)
if (itemId)
itemId = parseInt(itemId);
itemId = parseInt(itemId);
else
else
itemId = undefined;
itemId = undefined;
var data = makeBookmarkCore(chapterId, suffix, recentQuest.quest_type, itemId, recentQuest.prefix);
var data = makeBookmarkCore(chapterId, suffix, recentQuest.quest_type, itemId, recentQuest.prefix);
checkQuestStart(data, function (ok, result, reason) {
checkQuestStart(data, function (ok, result, reason) {
if (ok) {
if (ok) {
bookmarkNavigate(data.targetUrl, evt);
bookmarkNavigate(data.targetUrl, evt);
setTimeout(function () {
setTimeout(function () {
if (callback)
if (callback)
callback(true);
callback(true);
window.location.reload();
window.location.reload();
}, 50);
}, 50);
}
}
else {
else {
if (callback)
if (callback)
callback(false, reason);
callback(false, reason);
else
else
return showBookmarkError(reason);
return showBookmarkError(reason);
}
}
});
});
});
});
}
}
;
;
function makeBookmarkCore(chapterId, questSuffix, questType, useItemId, urlPrefix) {
function makeBookmarkCore(chapterId, questSuffix, questType, useItemId, urlPrefix) {
var questId = String(chapterId) + String(questSuffix);
var questId = String(chapterId) + String(questSuffix);
if (!urlPrefix) {
if (!urlPrefix) {
urlPrefix = "/#quest";
urlPrefix = "/#quest";
}
}
var targetUrl = urlPrefix + "/supporter/" + questId + "/" + questType;
var targetUrl = urlPrefix + "/supporter/" + questId + "/" + questType;
if (useItemId)
if (useItemId)
targetUrl += "/0/" + useItemId;
targetUrl += "/0/" + useItemId;
var infoUrl = "/quest/treasure_raid/" + chapterId + "/" + questId;
var infoUrl = "/quest/treasure_raid/" + chapterId + "/" + questId;
// FIXME: The /1/ here is the raid type
// FIXME: The /1/ here is the raid type
var checkStartUrl = "/quest/check_quest_start/" + chapterId + "/1/" + questId;
var checkStartUrl = "/quest/check_quest_start/" + chapterId + "/1/" + questId;
return {
return {
chapterId: chapterId,
chapterId: chapterId,
questId: questId,
questId: questId,
targetUrl: targetUrl,
targetUrl: targetUrl,
infoUrl: infoUrl,
infoUrl: infoUrl,
checkStartUrl: checkStartUrl
checkStartUrl: checkStartUrl
};
};
}
}
;
;
function showBookmarkError(message, extra) {
function showBookmarkError(message, extra) {
showGamePopup({
showGamePopup({
title: "Bookmark",
title: "Bookmark",
body: message + (extra ? "<br>" + String(extra) : "")
body: message + (extra ? "<br>" + String(extra) : "")
});
});
}
}
;
;
function startRaid(data, evt) {
function startRaid(data, evt) {
log("Starting raid", data.targetUrl);
log("Starting raid", data.targetUrl);
bookmarkNavigate(data.targetUrl, evt);
bookmarkNavigate(data.targetUrl, evt);
}
}
;
;
function checkQuestStart_old(data, onSuccess) {
function checkQuestStart_old(data, onSuccess) {
checkQuestStart(data, function (ok, eligibility, reason) {
checkQuestStart(data, function (ok, eligibility, reason) {
if (ok)
if (ok)
onSuccess(data, eligibility);
onSuccess(data, eligibility);
else
else
showBookmarkError(reason);
showBookmarkError(reason);
});
});
}
}
function checkQuestStart(data, callback) {
function checkQuestStart(data, callback) {
log("Checking eligibility", data.checkStartUrl);
log("Checking eligibility", data.checkStartUrl);
doClientAjax(data.checkStartUrl, function (eligibility, error) {
doClientAjax(data.checkStartUrl, function (eligibility, error) {
if (!eligibility)
if (!eligibility)
return showBookmarkError("Failed to get information from server", error);
return showBookmarkError("Failed to get information from server", error);
switch (eligibility.result) {
switch (eligibility.result) {
case "ok":
case "ok":
callback(true, eligibility);
callback(true, eligibility);
return;
return;
case "error_cnt":
case "error_cnt":
callback(false, eligibility, "You have already attempted this raid the maximum number of times today.");
callback(false, eligibility, "You have already attempted this raid the maximum number of times today.");
return;
return;
case "other_quest_progress":
case "other_quest_progress":
callback(false, eligibility, "You cannot start this raid because another quest is in progress.");
callback(false, eligibility, "You cannot start this raid because another quest is in progress.");
return;
return;
case "error_level":
case "error_level":
callback(false, eligibility, "Your rank is too low to start this raid.");
callback(false, eligibility, "Your rank is too low to start this raid.");
return;
return;
default:
default:
try {
try {
var blob = JSON.parse(eligibility);
var blob = JSON.parse(eligibility);
if (blob.popup && blob.popup.body) {
if (blob.popup && blob.popup.body) {
callback(false, eligibility, blob.popup.body);
callback(false, eligibility, blob.popup.body);
return;
return;
}
}
}
}
catch (exc) {
catch (exc) {
callback(false, eligibility, "Unknown error");
callback(false, eligibility, "Unknown error");
}
}
}
}
});
});
}
}
;
;
function makeRaidBookmark(chapterId, questSuffix) {
function makeRaidBookmark(chapterId, questSuffix) {
var data = makeBookmarkCore(chapterId, questSuffix, 1);
var data = makeBookmarkCore(chapterId, questSuffix, 1);
return function (evt) {
return function (evt) {
checkQuestStart_old(data, function (data, eligibility) {
checkQuestStart_old(data, function (data, eligibility) {
startRaid(data, evt);
startRaid(data, evt);
});
});
};
};
}
}
;
;
function getRaidInfo(data, onSuccess) {
function getRaidInfo(data, onSuccess) {
log("Requesting raid info", data.infoUrl);
log("Requesting raid info", data.infoUrl);
doClientAjax(data.infoUrl, function (raidInfo, error) {
doClientAjax(data.infoUrl, function (raidInfo, error) {
if (!raidInfo)
if (!raidInfo)
return showBookmarkError("Failed to get information from server", error);
return showBookmarkError("Failed to get information from server", error);
onSuccess(data, raidInfo);
onSuccess(data, raidInfo);
});
});
}
}
;
;
function makeTreasureRaidBookmark(chapterId, questSuffix, itemId) {
function makeTreasureRaidBookmark(chapterId, questSuffix, itemId) {
var data = makeBookmarkCore(chapterId, questSuffix, 1, itemId);
var data = makeBookmarkCore(chapterId, questSuffix, 1, itemId);
return function (evt) {
return function (evt) {
getRaidInfo(data, function (data, raidInfo) {
getRaidInfo(data, function (data, raidInfo) {
var treasureIndex = raidInfo.treasure_id.indexOf(String(itemId));
var treasureIndex = raidInfo.treasure_id.indexOf(String(itemId));
if (treasureIndex < 0)
if (treasureIndex < 0)
return showBookmarkError("Item not found in raid info");
return showBookmarkError("Item not found in raid info");
var itemsNeeded = parseInt(raidInfo.consume[treasureIndex]);
var itemsNeeded = parseInt(raidInfo.consume[treasureIndex]);
var itemsHeld = raidInfo.num[treasureIndex];
var itemsHeld = raidInfo.num[treasureIndex];
if (itemsHeld < itemsNeeded)
if (itemsHeld < itemsNeeded)
return showBookmarkError(raidInfo.chapter_name + " requires " +
return showBookmarkError(raidInfo.chapter_name + " requires " +
itemsNeeded + " of " +
itemsNeeded + " of " +
raidInfo.treasure_name[treasureIndex] +
raidInfo.treasure_name[treasureIndex] +
", but you only have " + itemsHeld);
", but you only have " + itemsHeld);
checkQuestStart_old(data, function (data, eligibility) {
checkQuestStart_old(data, function (data, eligibility) {
startRaid(data, evt);
startRaid(data, evt);
});
});
});
});
};
};
/*
/*
{
{
"chapter_id":"30005",
"chapter_id":"30005",
"quest_id":"300051",
"quest_id":"300051",
"type":"1",
"type":"1",
"action_point":"50",
"action_point":"50",
"chapter_name":"Tiamat Omega Showdown",
"chapter_name":"Tiamat Omega Showdown",
"consume":["3"],
"consume":["3"],
"level":30,
"level":30,
"treasure_id":["18"],
"treasure_id":["18"],
"treasure_image_id":["18"],
"treasure_image_id":["18"],
"treasure_name":["Tiamat Omega Anima"],
"treasure_name":["Tiamat Omega Anima"],
"num":[26],
"num":[26],
"raid_name":"Lvl 50 Tiamat Omega",
"raid_name":"Lvl 50 Tiamat Omega",
"limit":90
"limit":90
}
}
*/
*/
}
}
;
;
function visitCurrentEvent(evt, tail) {
function visitCurrentEvent(evt, tail) {
chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) {
chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) {
if (!currentEvent)
if (!currentEvent)
showGamePopup({
showGamePopup({
title: "Error",
title: "Error",
body: "No event stored. Try visiting the main page."
body: "No event stored. Try visiting the main page."
});
});
else if (tail)
else if (tail)
bookmarkNavigate("/#" + currentEvent + tail, evt);
bookmarkNavigate("/#" + currentEvent + tail, evt);
else
else
bookmarkNavigate("/#" + currentEvent, evt);
bookmarkNavigate("/#" + currentEvent, evt);
});
});
}
}
;
;
function makeGuildWarBookmark(tail) {
function makeGuildWarBookmark(tail) {
return function (evt) {
return function (evt) {
bookmarkNavigate("/#event/" + guildWarName + (tail || ""), evt);
bookmarkNavigate("/#event/" + guildWarName + (tail || ""), evt);
};
};
}
}
;
;
function makeGuildWarRaidBookmark(chapterId, questSuffix, checkItem) {
function makeGuildWarRaidBookmark(chapterId, questSuffix, checkItem) {
var data = makeBookmarkCore(chapterId, questSuffix, 1);
var data = makeBookmarkCore(chapterId, questSuffix, 1);
var checkItemFn, checkStartFn, visitSupporterPageFn, checkMultiStart;
var checkItemFn, checkStartFn, visitSupporterPageFn, checkMultiStart;
checkItemFn = function (evt, onComplete) {
checkItemFn = function (evt, onComplete) {
if (window.location.href.indexOf("event/" + guildWarName) < 0) {
if (window.location.href.indexOf("event/" + guildWarName) < 0) {
if (onComplete)
if (onComplete)
onComplete(false);
onComplete(false);
return bookmarkNavigate("#event/" + guildWarName, evt);
return bookmarkNavigate("#event/" + guildWarName, evt);
}
}
data.targetUrl = data.targetUrl.replace("#quest/", "#event/" + guildWarName + "/") + "/0";
data.targetUrl = data.targetUrl.replace("#quest/", "#event/" + guildWarName + "/") + "/0";
var checkUrl = "/" + guildWarName + "/rest/top/check_item/" + data.questId;
var checkUrl = "/" + guildWarName + "/rest/top/check_item/" + data.questId;
doClientAjax(checkUrl, function (checkResult) {
doClientAjax(checkUrl, function (checkResult) {
if (checkResult && checkResult.result)
if (checkResult && checkResult.result)
return checkStartFn(evt, onComplete);
return checkStartFn(evt, onComplete);
else {
else {
if (onComplete)
if (onComplete)
onComplete(false);
onComplete(false);
return showBookmarkError("You do not have the necessary items to start this quest.");
return showBookmarkError("You do not have the necessary items to start this quest.");
}
}
});
});
};
};
checkStartFn = function (evt, onComplete) {
checkStartFn = function (evt, onComplete) {
checkQuestStart_old(data, function (data, eligibility) {
checkQuestStart_old(data, function (data, eligibility) {
if (eligibility.result === "ok")
if (eligibility.result === "ok")
checkMultiStart(evt, onComplete);
checkMultiStart(evt, onComplete);
else {
else {
if (onComplete)
if (onComplete)
onComplete(false);
onComplete(false);
return showBookmarkError("You are not eligible to start this quest. " + eligibility.result);
return showBookmarkError("You are not eligible to start this quest. " + eligibility.result);
}
}
});
});
};
};
checkMultiStart = function (evt, onComplete) {
checkMultiStart = function (evt, onComplete) {
var checkUrl = "/quest/check_multi_start";
var checkUrl = "/quest/check_multi_start";
doClientAjax(checkUrl, JSON.stringify({ quest_id: parseInt(data.questId) }), function (checkResult) {
doClientAjax(checkUrl, JSON.stringify({ quest_id: parseInt(data.questId) }), function (checkResult) {
if (checkResult && checkResult.result === "ok")
if (checkResult && checkResult.result === "ok")
return visitSupporterPageFn(evt, onComplete);
return visitSupporterPageFn(evt, onComplete);
else {
else {
if (onComplete)
if (onComplete)
onComplete(false);
onComplete(false);
return showBookmarkError("You cannot start a raid.");
return showBookmarkError("You cannot start a raid.");
}
}
});
});
};
};
visitSupporterPageFn = function (evt, onComplete) {
visitSupporterPageFn = function (evt, onComplete) {
if (window.location.href.indexOf("event/" + guildWarName) < 0) {
if (window.location.href.indexOf("event/" + guildWarName) < 0) {
if (onComplete)
if (onComplete)
onComplete(false);
onComplete(false);
return bookmarkNavigate("#event/" + guildWarName, evt);
return bookmarkNavigate("#event/" + guildWarName, evt);
}
}
else {
else {
if (onComplete)
if (onComplete)
onComplete(true);
onComplete(true);
startRaid(data, evt);
startRaid(data, evt);
}
}
};
};
if (!checkItem)
if (!checkItem)
return visitSupporterPageFn;
return visitSupporterPageFn;
return checkItemFn;
return checkItemFn;
}
}
;
;
function makeEventTreasureRaidBookmark(chapterId, questSuffix) {
function makeEventTreasureRaidBookmark(chapterId, questSuffix) {
return function (evt) {
return function (evt) {
chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) {
chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) {
if (!currentEvent)
if (!currentEvent)
showGamePopup({
showGamePopup({
title: "Error",
title: "Error",
body: "No event stored. Try visiting the main page."
body: "No event stored. Try visiting the main page."
});
});
var data = makeBookmarkCore(chapterId, questSuffix, 1);
var data = makeBookmarkCore(chapterId, questSuffix, 1);
data.targetUrl = data.targetUrl.replace("#quest/", "#" + currentEvent + "/");
data.targetUrl = data.targetUrl.replace("#quest/", "#" + currentEvent + "/");
checkQuestStart_old(data, function (data, eligibility) {
checkQuestStart_old(data, function (data, eligibility) {
startRaid(data, evt);
startRaid(data, evt);
});
});
});
});
};
};
}
}
;
;
var guildWarName = null;
var guildWarName = null;
var guildWarSubmenu = {
var guildWarSubmenu = {
"guild-war-home": makeGuildWarBookmark(),
"guild-war-home": makeGuildWarBookmark(),
"guild-war-gacha": makeGuildWarBookmark("/gacha/index"),
"guild-war-gacha": makeGuildWarBookmark("/gacha/index"),
"guild-war-reward": makeGuildWarBookmark("/reward"),
"guild-war-reward": makeGuildWarBookmark("/reward"),
//"guild-war-eye-vh": makeGuildWarRaidBookmark(71863, 1, false),
//"guild-war-eye-vh": makeGuildWarRaidBookmark(71863, 1, false),
コピー
コピー済み
コピー
コピー済み
"guild-war-dog-vh": makeGuildWarRaidBookmark(72
3
14, 1, false),
"guild-war-dog-vh": makeGuildWarRaidBookmark(72
2
14, 1, false),
"guild-war-dog-ex": makeGuildWarRaidBookmark(72
3
15, 1, false),
"guild-war-dog-ex": makeGuildWarRaidBookmark(72
2
15, 1, false),
"guild-war-dog-ex-plus": makeGuildWarRaidBookmark(72
3
16, 1, false),
"guild-war-dog-ex-plus": makeGuildWarRaidBookmark(72
2
16, 1, false),
"guild-war-hell-90": makeGuildWarRaidBookmark(72
3
17, 1, true),
"guild-war-hell-90": makeGuildWarRaidBookmark(72
2
17, 1, true),
"guild-war-hell-95": makeGuildWarRaidBookmark(72
3
18, 1, true),
"guild-war-hell-95": makeGuildWarRaidBookmark(72
2
18, 1, true),
};
};
var menuItems = {
var menuItems = {
"home": "/#mypage",
"home": "/#mypage",
"party": "/#party/index/0/npc/0",
"party": "/#party/index/0/npc/0",
"mystuff": {
"mystuff": {
"inventory": "/#list",
"inventory": "/#list",
"stash": "/#container",
"stash": "/#container",
"crate": "/#present",
"crate": "/#present",
"supplies": "/#item",
"supplies": "/#item",
},
},
"quest": {
"quest": {
"quest-all": "/#quest/index",
"quest-all": "/#quest/index",
"quest-special": "/#quest/extra",
"quest-special": "/#quest/extra",
"join-raid": "/#quest/assist",
"join-raid": "/#quest/assist",
"event": visitCurrentEvent,
"event": visitCurrentEvent,
"trial-battles": "/#trial_battle",
"trial-battles": "/#trial_battle",
"pending-raids": "/#quest/assist/unclaimed",
"pending-raids": "/#quest/assist/unclaimed",
},
},
"quest-repeat": repeatLastQuest,
"quest-repeat": repeatLastQuest,
コピー
コピー済み
コピー
コピー済み
"guild-war": guildWarSubmenu,
//
"guild-war": guildWarSubmenu,
"hard-raids": {
"hard-raids": {
"hard-tia": makeRaidBookmark(30004, 1),
"hard-tia": makeRaidBookmark(30004, 1),
"hard-colo": makeRaidBookmark(30009, 1),
"hard-colo": makeRaidBookmark(30009, 1),
"hard-levi": makeRaidBookmark(30015, 1),
"hard-levi": makeRaidBookmark(30015, 1),
"hard-yugu": makeRaidBookmark(30019, 1),
"hard-yugu": makeRaidBookmark(30019, 1),
"hard-chev": makeRaidBookmark(30022, 1),
"hard-chev": makeRaidBookmark(30022, 1),
"hard-cel": makeRaidBookmark(30025, 1)
"hard-cel": makeRaidBookmark(30025, 1)
},
},
"magna-raids": {
"magna-raids": {
"magna-tia": makeTreasureRaidBookmark(30005, 1, 18),
"magna-tia": makeTreasureRaidBookmark(30005, 1, 18),
"magna-colo": makeTreasureRaidBookmark(30010, 1, 19),
"magna-colo": makeTreasureRaidBookmark(30010, 1, 19),
"magna-levi": makeTreasureRaidBookmark(30016, 1, 20),
"magna-levi": makeTreasureRaidBookmark(30016, 1, 20),
"magna-yugu": makeTreasureRaidBookmark(30026, 1, 21),
"magna-yugu": makeTreasureRaidBookmark(30026, 1, 21),
"magna-chev": makeTreasureRaidBookmark(30027, 1, 26),
"magna-chev": makeTreasureRaidBookmark(30027, 1, 26),
"magna-cel": makeTreasureRaidBookmark(30028, 1, 31)
"magna-cel": makeTreasureRaidBookmark(30028, 1, 31)
},
},
"hl-raids": {
"hl-raids": {
"hl-tia": makeTreasureRaidBookmark(30044, 1, 32),
"hl-tia": makeTreasureRaidBookmark(30044, 1, 32),
"hl-colo": makeTreasureRaidBookmark(30049, 1, 47),
"hl-colo": makeTreasureRaidBookmark(30049, 1, 47),
"hl-levi": makeTreasureRaidBookmark(30051, 1, 48),
"hl-levi": makeTreasureRaidBookmark(30051, 1, 48),
"hl-yugu": makeTreasureRaidBookmark(30053, 1, 49),
"hl-yugu": makeTreasureRaidBookmark(30053, 1, 49),
"hl-chev": makeTreasureRaidBookmark(30056, 1, 50),
"hl-chev": makeTreasureRaidBookmark(30056, 1, 50),
"hl-cel": makeTreasureRaidBookmark(30058, 1, 51),
"hl-cel": makeTreasureRaidBookmark(30058, 1, 51),
"hl-rosequeen": makeTreasureRaidBookmark(30047, 1, 1204),
"hl-rosequeen": makeTreasureRaidBookmark(30047, 1, 1204),
},
},
"primal-raids": {
"primal-raids": {
"nataku": makeTreasureRaidBookmark(30042, 1, 1343),
"nataku": makeTreasureRaidBookmark(30042, 1, 1343),
"flame-glass": makeTreasureRaidBookmark(30041, 1, 1313),
"flame-glass": makeTreasureRaidBookmark(30041, 1, 1313),
"macula-marius": makeTreasureRaidBookmark(30038, 1, 1323),
"macula-marius": makeTreasureRaidBookmark(30038, 1, 1323),
"athena": makeTreasureRaidBookmark(30107, 1, 1313),
"athena": makeTreasureRaidBookmark(30107, 1, 1313),
"medusa": makeTreasureRaidBookmark(30039, 1, 1333),
"medusa": makeTreasureRaidBookmark(30039, 1, 1333),
"apollo": makeTreasureRaidBookmark(30043, 1, 1353),
"apollo": makeTreasureRaidBookmark(30043, 1, 1353),
"olivia": makeTreasureRaidBookmark(30040, 1, 1363),
"olivia": makeTreasureRaidBookmark(30040, 1, 1363),
"odin": makeTreasureRaidBookmark(30046, 1, 1353),
"odin": makeTreasureRaidBookmark(30046, 1, 1353),
},
},
"coop": {
"coop": {
"coop": "/#coopraid",
"coop": "/#coopraid",
// This makes it impossible to return to an existing room
// This makes it impossible to return to an existing room
// "coop-host": "/#coopraid/room/entry",
// "coop-host": "/#coopraid/room/entry",
"coop-join": "/#coopraid/offer",
"coop-join": "/#coopraid/offer",
"coop-shop": "/#coopraid/lineup"
"coop-shop": "/#coopraid/lineup"
},
},
"me": {
"me": {
"profile": "/#profile",
"profile": "/#profile",
"crew": "/#guild",
"crew": "/#guild",
"friends": "/#friend",
"friends": "/#friend",
"trophies": "/#title"
"trophies": "/#title"
},
},
"shop": {
"shop": {
"shop-mobacoins": "#shop/moba/0",
"shop-mobacoins": "#shop/moba/0",
"shop-crystals": "#shop/lupi/0",
"shop-crystals": "#shop/lupi/0",
"shop-points": "/#shop/exchange/points",
"shop-points": "/#shop/exchange/points",
"shop-trajectory": "#shop/exchange/trajectory",
"shop-trajectory": "#shop/exchange/trajectory",
"shop-moon": "#shop/exchange/moon",
"shop-moon": "#shop/exchange/moon",
"shop-treasure": "#shop/exchange/list",
"shop-treasure": "#shop/exchange/list",
"shop-whale-tears": "#shop/exchange/ceiling",
"shop-whale-tears": "#shop/exchange/ceiling",
"shop-weapon-series": "#archaic",
"shop-weapon-series": "#archaic",
},
},
"casino": {
"casino": {
"poker": "/#casino/list/poker",
"poker": "/#casino/list/poker",
"bingo": "/#casino/list/bingo",
"bingo": "/#casino/list/bingo",
"casino-shop": "/#casino/exchange"
"casino-shop": "/#casino/exchange"
},
},
};
};
var viramateMenuItems = {
var viramateMenuItems = {
"settings": function () {
"settings": function () {
var loc = chrome.extension.getURL("src/options_custom/index.html");
var loc = chrome.extension.getURL("src/options_custom/index.html");
var w = window.open(loc);
var w = window.open(loc);
},
},
"update-notes": function () {
"update-notes": function () {
var loc = chrome.extension.getURL("content/changelog.html");
var loc = chrome.extension.getURL("content/changelog.html");
var w = window.open(loc);
var w = window.open(loc);
}
}
};
};
function isHorizontalLayout() {
function isHorizontalLayout() {
return (isMobileSite() ||
return (isMobileSite() ||
!!currentSettings.horizontalBookmarks ||
!!currentSettings.horizontalBookmarks ||
!!document.getElementById("gree-game-container"));
!!document.getElementById("gree-game-container"));
}
}
;
;
function makeMenuHandler(name, value, tryCloseMenu) {
function makeMenuHandler(name, value, tryCloseMenu) {
var result;
var result;
if (typeof (value) === "string")
if (typeof (value) === "string")
result = function (evt) {
result = function (evt) {
if (evt) {
if (evt) {
evt.preventDefault();
evt.preventDefault();
evt.stopPropagation();
evt.stopPropagation();
}
}
tryCloseMenu();
tryCloseMenu();
bookmarkNavigate(value, evt);
bookmarkNavigate(value, evt);
};
};
else if (value && value.call && value.apply)
else if (value && value.call && value.apply)
result = function (evt) {
result = function (evt) {
if (evt) {
if (evt) {
evt.preventDefault();
evt.preventDefault();
evt.stopPropagation();
evt.stopPropagation();
}
}
tryCloseMenu();
tryCloseMenu();
value(evt);
value(evt);
};
};
else
else
return null;
return null;
allBookmarks[name] = result;
allBookmarks[name] = result;
return result;
return result;
}
}
;
;
function _updateIconSize(menuIcon) {
function _updateIconSize(menuIcon) {
if (isHorizontalLayout())
if (isHorizontalLayout())
menuIcon.style.left = menuLeftEdge.toFixed(0) + "px";
menuIcon.style.left = menuLeftEdge.toFixed(0) + "px";
else
else
menuIcon.style.left = "-6px";
menuIcon.style.left = "-6px";
var iconRect = menuIcon.getBoundingClientRect();
var iconRect = menuIcon.getBoundingClientRect();
if (isHorizontalLayout())
if (isHorizontalLayout())
menuIconSize = iconRect.width * getEffectiveZoom(menuIcon) * getEffectiveZoom(document.documentElement);
menuIconSize = iconRect.width * getEffectiveZoom(menuIcon) * getEffectiveZoom(document.documentElement);
else
else
menuIconSize = iconRect.height * getEffectiveZoom(menuIcon);
menuIconSize = iconRect.height * getEffectiveZoom(menuIcon);
}
}
;
;
function getColorForMenuItem(key) {
function getColorForMenuItem(key) {
switch (key) {
switch (key) {
case "hard-raids":
case "hard-raids":
return "#efc0ba";
return "#efc0ba";
case "magna-raids":
case "magna-raids":
return "#e8e8f1";
return "#e8e8f1";
case "hl-raids":
case "hl-raids":
return "#efe0ba";
return "#efe0ba";
}
}
var dashPos = key.lastIndexOf("-");
var dashPos = key.lastIndexOf("-");
var suffix = key.substr(dashPos + 1);
var suffix = key.substr(dashPos + 1);
switch (suffix) {
switch (suffix) {
case "tia":
case "tia":
return "#bfefbf";
return "#bfefbf";
case "yugu":
case "yugu":
return "#efdfa0";
return "#efdfa0";
case "colo":
case "colo":
return "#efbfbf";
return "#efbfbf";
case "levi":
case "levi":
return "#bfcfef";
return "#bfcfef";
case "cel":
case "cel":
return "#d890df";
return "#d890df";
}
}
return null;
return null;
}
}
;
;
function showViraButton() {
function showViraButton() {
if (isShutdown)
if (isShutdown)
return;
return;
injectStylesheet("sidebar-shadow.css", getUiContainer());
injectStylesheet("sidebar-shadow.css", getUiContainer());
var outImg = getResourceUrl('vira-small-smile.png');
var outImg = getResourceUrl('vira-small-smile.png');
var overImg = getResourceUrl('vira-small.png');
var overImg = getResourceUrl('vira-small.png');
var isCustomIcon = false;
var isCustomIcon = false;
try {
try {
if (currentSettings.bookmarksInactiveIcon)
if (currentSettings.bookmarksInactiveIcon)
outImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksInactiveIcon);
outImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksInactiveIcon);
if (currentSettings.bookmarksActiveIcon)
if (currentSettings.bookmarksActiveIcon)
overImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksActiveIcon);
overImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksActiveIcon);
isCustomIcon = (currentSettings.bookmarksActiveIcon || currentSettings.bookmarksInactiveIcon);
isCustomIcon = (currentSettings.bookmarksActiveIcon || currentSettings.bookmarksInactiveIcon);
}
}
catch (exc) {
catch (exc) {
log("Error decoding custom bookmarks icons", exc);
log("Error decoding custom bookmarks icons", exc);
}
}
var menuIcon = document.createElement("div");
var menuIcon = document.createElement("div");
var mainMenu = document.createElement("div");
var mainMenu = document.createElement("div");
menuIcon.className = "viramate-menu-icon";
menuIcon.className = "viramate-menu-icon";
// HACK: Why is this necessary?
// HACK: Why is this necessary?
menuIcon.style.backgroundRepeat = "no-repeat";
menuIcon.style.backgroundRepeat = "no-repeat";
menuIcon.style.backgroundImage = "url(" + outImg + ")";
menuIcon.style.backgroundImage = "url(" + outImg + ")";
menuIcon.setAttribute("title", "Viramate");
menuIcon.setAttribute("title", "Viramate");
var maxIconWidth = isCustomIcon ? 64 : 56;
var maxIconWidth = isCustomIcon ? 64 : 56;
// HACK: :after selectors don't work on img. html sucks.
// HACK: :after selectors don't work on img. html sucks.
var tempImage = document.createElement("img");
var tempImage = document.createElement("img");
tempImage.style.opacity = "0.0";
tempImage.style.opacity = "0.0";
tempImage.onload = function () {
tempImage.onload = function () {
var scale = 1.0;
var scale = 1.0;
if (tempImage.naturalWidth > maxIconWidth)
if (tempImage.naturalWidth > maxIconWidth)
scale = maxIconWidth / tempImage.naturalWidth;
scale = maxIconWidth / tempImage.naturalWidth;
menuIcon.style.width = (tempImage.naturalWidth * scale).toFixed(0) + "px";
menuIcon.style.width = (tempImage.naturalWidth * scale).toFixed(0) + "px";
menuIcon.style.height = (tempImage.naturalHeight * scale).toFixed(0) + "px";
menuIcon.style.height = (tempImage.naturalHeight * scale).toFixed(0) + "px";
uninjectElement(getUiContainer(), tempImage);
uninjectElement(getUiContainer(), tempImage);
_updateIconSize(menuIcon);
_updateIconSize(menuIcon);
_layoutPanels();
_layoutPanels();
};
};
tempImage.src = outImg;
tempImage.src = outImg;
injectElement(getUiContainer(), tempImage);
injectElement(getUiContainer(), tempImage);
var paddingSize = 100;
var paddingSize = 100;
if (typeof (currentSettings.bookmarksIconPadding) === "number")
if (typeof (currentSettings.bookmarksIconPadding) === "number")
paddingSize = currentSettings.bookmarksIconPadding;
paddingSize = currentSettings.bookmarksIconPadding;
if (isHorizontalLayout()) {
if (isHorizontalLayout()) {
menuIcon.style.paddingRight = Math.max(paddingSize - 12, 0).toFixed(0) + "px";
menuIcon.style.paddingRight = Math.max(paddingSize - 12, 0).toFixed(0) + "px";
}
}
else {
else {
menuIcon.style.paddingBottom = Math.max(paddingSize - 12, 0).toFixed(0) + "px";
menuIcon.style.paddingBottom = Math.max(paddingSize - 12, 0).toFixed(0) + "px";
}
}
mainMenu.className = "viramate-menu";
mainMenu.className = "viramate-menu";
if (typeof (currentSettings.bookmarksSize) === "number")
if (typeof (currentSettings.bookmarksSize) === "number")
menuIcon.style.transform = "scale(" + currentSettings.bookmarksSize.toFixed(1) + ")";
menuIcon.style.transform = "scale(" + currentSettings.bookmarksSize.toFixed(1) + ")";
if (typeof (currentSettings.bookmarksMenuSize) === "number")
if (typeof (currentSettings.bookmarksMenuSize) === "number")
mainMenu.style.transform = "scale(" + currentSettings.bookmarksMenuSize.toFixed(1) + ")";
mainMenu.style.transform = "scale(" + currentSettings.bookmarksMenuSize.toFixed(1) + ")";
// mainMenu.style.zoom = menuIcon.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2);
// mainMenu.style.zoom = menuIcon.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2);
var mouseIsOverIcon = false;
var mouseIsOverIcon = false;
var mouseIsOverMenu = 0;
var mouseIsOverMenu = 0;
var mouseIsOverSubmenu = 0;
var mouseIsOverSubmenu = 0;
var menuIsVisible = false;
var menuIsVisible = false;
var allMenus = [mainMenu];
var allMenus = [mainMenu];
var updateTimeout = 0;
var updateTimeout = 0;
var autoOpenDelay = isHorizontalLayout() ? 260 : 160;
var autoOpenDelay = isHorizontalLayout() ? 260 : 160;
var autoCloseDelay = currentSettings.openBookmarksOnClick ? 500 : 250;
var autoCloseDelay = currentSettings.openBookmarksOnClick ? 500 : 250;
var pamrklamr = function () {
var pamrklamr = function () {
return 5 * 1000 + (Math.random() * 1600 * 1000);
return 5 * 1000 + (Math.random() * 1600 * 1000);
};
};
var fmajrlialmsk;
var fmajrlialmsk;
fmajrlialmsk = function () {
fmajrlialmsk = function () {
if (isShutdown)
if (isShutdown)
return;
return;
if (isCustomIcon)
if (isCustomIcon)
return;
return;
if (!menuIsVisible) {
if (!menuIsVisible) {
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")";
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")";
window.setTimeout(function () {
window.setTimeout(function () {
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/qw3mkl/vqprlm.png') + ")";
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/qw3mkl/vqprlm.png') + ")";
}, 60);
}, 60);
window.setTimeout(function () {
window.setTimeout(function () {
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")";
menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")";
}, 950);
}, 950);
window.setTimeout(function () {
window.setTimeout(function () {
menuIcon.style.backgroundImage = "url(" + outImg + ")";
menuIcon.style.backgroundImage = "url(" + outImg + ")";
}, 1060);
}, 1060);
}
}
window.setTimeout(fmajrlialmsk, pamrklamr());
window.setTimeout(fmajrlialmsk, pamrklamr());
};
};
window.setTimeout(fmajrlialmsk, pamrklamr());
window.setTimeout(fmajrlialmsk, pamrklamr());
var showMenu = function (menu) {
var showMenu = function (menu) {
if (menu.className.indexOf("viramate-menu") === 0)
if (menu.className.indexOf("viramate-menu") === 0)
menu.style.left = menuLeftEdge.toFixed(0) + "px";
menu.style.left = menuLeftEdge.toFixed(0) + "px";
else
else
menu.style.left = "0px";
menu.style.left = "0px";
menu.style.opacity = "1.0";
menu.style.opacity = "1.0";
menu.style.pointerEvents = "all";
menu.style.pointerEvents = "all";
menuIsVisible = true;
menuIsVisible = true;
};
};
var showMenus = function () {
var showMenus = function () {
menuIcon.style.backgroundImage = "url(" + overImg + ")";
menuIcon.style.backgroundImage = "url(" + overImg + ")";
if (menuIcon.className.indexOf("open") < 0)
if (menuIcon.className.indexOf("open") < 0)
menuIcon.className += " open";
menuIcon.className += " open";
for (var i = 0; i < allMenus.length; i++) {
for (var i = 0; i < allMenus.length; i++) {
var elt = allMenus[i];
var elt = allMenus[i];
showMenu(elt);
showMenu(elt);
}
}
};
};
var hideMenu = function (menu) {
var hideMenu = function (menu) {
if (!isMobileSite()) {
if (!isMobileSite()) {
if (menu.className.indexOf("viramate-menu") === 0)
if (menu.className.indexOf("viramate-menu") === 0)
menu.style.left = (menuLeftEdge - 32).toFixed(0) + "px";
menu.style.left = (menuLeftEdge - 32).toFixed(0) + "px";
else
else
menu.style.left = "-32px";
menu.style.left = "-32px";
}
}
menu.style.opacity = "0.0";
menu.style.opacity = "0.0";
menu.style.pointerEvents = "none";
menu.style.pointerEvents = "none";
menuIsVisible = false;
menuIsVisible = false;
};
};
var hideMenus = function () {
var hideMenus = function () {
menuIcon.style.backgroundImage = "url(" + outImg + ")";
menuIcon.style.backgroundImage = "url(" + outImg + ")";
menuIcon.className = menuIcon.className.replace(" open", "");
menuIcon.className = menuIcon.className.replace(" open", "");
closeSubmenus();
closeSubmenus();
hideMenu(allMenus[0]);
hideMenu(allMenus[0]);
};
};
var closeSubmenus = function () {
var closeSubmenus = function () {
// Hide any other open submenus
// Hide any other open submenus
for (var i = 1; i < allMenus.length; i++) {
for (var i = 1; i < allMenus.length; i++) {
var submenu = allMenus[i];
var submenu = allMenus[i];
if (submenu.owner)
if (submenu.owner)
submenu.owner.className = submenu.owner.className.replace(" open", "");
submenu.owner.className = submenu.owner.className.replace(" open", "");
hideMenu(submenu);
hideMenu(submenu);
}
}
// Pop them off the list
// Pop them off the list
allMenus.length = 1;
allMenus.length = 1;
};
};
var openSubmenu = function (owner, submenu) {
var openSubmenu = function (owner, submenu) {
owner.className += " open";
owner.className += " open";
submenu.owner = owner;
submenu.owner = owner;
closeSubmenus();
closeSubmenus();
allMenus.push(submenu);
allMenus.push(submenu);
showMenus();
showMenus();
};
};
var updateMenu = function () {
var updateMenu = function () {
if (isShutdown)
if (isShutdown)
return;
return;
if (mouseIsOverIcon || (mouseIsOverMenu > 0)) {
if (mouseIsOverIcon || (mouseIsOverMenu > 0)) {
if (mouseIsOverSubmenu <= 0)
if (mouseIsOverSubmenu <= 0)
closeSubmenus();
closeSubmenus();
showMenus();
showMenus();
}
}
else
else
hideMenus();
hideMenus();
};
};
var scheduleUpdate = function (fast) {
var scheduleUpdate = function (fast) {
if (updateTimeout)
if (updateTimeout)
window.clearTimeout(updateTimeout);
window.clearTimeout(updateTimeout);
updateTimeout = window.setTimeout(updateMenu, fast ? autoOpenDelay : autoCloseDelay);
updateTimeout = window.setTimeout(updateMenu, fast ? autoOpenDelay : autoCloseDelay);
};
};
var makeSubmenuOverHandler = function (item, submenu) {
var makeSubmenuOverHandler = function (item, submenu) {
return function (evt) {
return function (evt) {
mouseIsOverSubmenu += 1;
mouseIsOverSubmenu += 1;
openSubmenu(item, submenu);
openSubmenu(item, submenu);
};
};
};
};
var makeSubmenuOutHandler = function (item, submenu) {
var makeSubmenuOutHandler = function (item, submenu) {
return function (evt) {
return function (evt) {
mouseIsOverSubmenu -= 1;
mouseIsOverSubmenu -= 1;
// TODO: Anything?
// TODO: Anything?
scheduleUpdate();
scheduleUpdate();
};
};
};
};
var tryCloseMenu = function () {
var tryCloseMenu = function () {
hideMenus();
hideMenus();
window.clearTimeout(updateTimeout);
window.clearTimeout(updateTimeout);
};
};
menuIcon.addEventListener("click", function () {
menuIcon.addEventListener("click", function () {
showMenus();
showMenus();
}, false);
}, false);
menuIcon.addEventListener("mouseover", function () {
menuIcon.addEventListener("mouseover", function () {
mouseIsOverIcon = true;
mouseIsOverIcon = true;
if (!isMobileSite() &&
if (!isMobileSite() &&
(currentSettings.openBookmarksOnClick !== true))
(currentSettings.openBookmarksOnClick !== true))
scheduleUpdate(true);
scheduleUpdate(true);
}, false);
}, false);
menuIcon.addEventListener("mouseout", function () {
menuIcon.addEventListener("mouseout", function () {
mouseIsOverIcon = false;
mouseIsOverIcon = false;
scheduleUpdate();
scheduleUpdate();
}, false);
}, false);
mainMenu.addEventListener("mouseover", function () {
mainMenu.addEventListener("mouseover", function () {
mouseIsOverMenu += 1;
mouseIsOverMenu += 1;
}, false);
}, false);
mainMenu.addEventListener("mouseout", function () {
mainMenu.addEventListener("mouseout", function () {
mouseIsOverMenu -= 1;
mouseIsOverMenu -= 1;
scheduleUpdate();
scheduleUpdate();
}, false);
}, false);
var isGuildWar = currentSettings.currentGuildWar &&
var isGuildWar = currentSettings.currentGuildWar &&
(currentSettings.currentGuildWar.indexOf("event/teamraid") === 0);
(currentSettings.currentGuildWar.indexOf("event/teamraid") === 0);
if (isGuildWar)
if (isGuildWar)
guildWarName = currentSettings.currentGuildWar.replace("event/", "");
guildWarName = currentSettings.currentGuildWar.replace("event/", "");
allBookmarks = {};
allBookmarks = {};
コピー
コピー済み
コピー
コピー済み
var
v
保存された差分
原文
ファイルを開く
"use strict"; var raidListUpdateInterval = 30000; var raidListUpdateBackoff = 1350; var raidListUpdateCounter = 25; var statusPanelUpdateIntervalSeconds = 30; var minimumBuffUpdateIntervalSeconds = 70; var currentRaidListUpdateInterval = raidListUpdateInterval; var updateRaidsPanel = null, invalidateRaidList = null, doUpdateRaidsPanel = null, updateItemsPanel = null, invalidateItems = null, doUpdateItemsPanel = null; var updateBuffsWhen = 0, isUpdatingBuffs = false; var queuedRaidClick = null; var pendingRaidUpdate = null; var nextRaidUpdateWhen = null; var menuIconSize = 0; var menuLeftEdge = 0; var subpanelOffset = 0; var mostRecentItems = null; var lastPlayerStatus = null; var statusIntervalH, raidTimerIntervalH; var allBookmarks = {}; function bookmarkNavigate(target, evt) { var inNewWindow = false; if (evt) { inNewWindow = (evt.button === 1) || !!evt.shiftKey; } if (inNewWindow) { // HACK: Fully resolve the URL var elt = document.createElement("a"); elt.href = target; chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href }); } else { chrome.runtime.sendMessage({ type: "setLastLocation", url: target }); window.location.href = target; } } ; function repeatLastQuest(evt, callback) { chrome.runtime.sendMessage({ type: "getRecentQuest" }, function (recentQuestJson) { if (!recentQuestJson) { if (callback) callback(false, "No recent quest to attempt"); else return showBookmarkError("No recent quest to attempt."); } var recentQuest; try { recentQuest = JSON.parse(recentQuestJson); } catch (exc) { if (callback) callback(false, "No recent quest to attempt"); else return showBookmarkError("No recent quest to attempt."); } var parts = splitQuestId(recentQuest.quest_id); var chapterId = parts[0]; var suffix = parts[1]; var itemId = recentQuest.use_item_id; if (itemId) itemId = parseInt(itemId); else itemId = undefined; var data = makeBookmarkCore(chapterId, suffix, recentQuest.quest_type, itemId, recentQuest.prefix); checkQuestStart(data, function (ok, result, reason) { if (ok) { bookmarkNavigate(data.targetUrl, evt); setTimeout(function () { if (callback) callback(true); window.location.reload(); }, 50); } else { if (callback) callback(false, reason); else return showBookmarkError(reason); } }); }); } ; function makeBookmarkCore(chapterId, questSuffix, questType, useItemId, urlPrefix) { var questId = String(chapterId) + String(questSuffix); if (!urlPrefix) { urlPrefix = "/#quest"; } var targetUrl = urlPrefix + "/supporter/" + questId + "/" + questType; if (useItemId) targetUrl += "/0/" + useItemId; var infoUrl = "/quest/treasure_raid/" + chapterId + "/" + questId; // FIXME: The /1/ here is the raid type var checkStartUrl = "/quest/check_quest_start/" + chapterId + "/1/" + questId; return { chapterId: chapterId, questId: questId, targetUrl: targetUrl, infoUrl: infoUrl, checkStartUrl: checkStartUrl }; } ; function showBookmarkError(message, extra) { showGamePopup({ title: "Bookmark", body: message + (extra ? "<br>" + String(extra) : "") }); } ; function startRaid(data, evt) { log("Starting raid", data.targetUrl); bookmarkNavigate(data.targetUrl, evt); } ; function checkQuestStart_old(data, onSuccess) { checkQuestStart(data, function (ok, eligibility, reason) { if (ok) onSuccess(data, eligibility); else showBookmarkError(reason); }); } function checkQuestStart(data, callback) { log("Checking eligibility", data.checkStartUrl); doClientAjax(data.checkStartUrl, function (eligibility, error) { if (!eligibility) return showBookmarkError("Failed to get information from server", error); switch (eligibility.result) { case "ok": callback(true, eligibility); return; case "error_cnt": callback(false, eligibility, "You have already attempted this raid the maximum number of times today."); return; case "other_quest_progress": callback(false, eligibility, "You cannot start this raid because another quest is in progress."); return; case "error_level": callback(false, eligibility, "Your rank is too low to start this raid."); return; default: try { var blob = JSON.parse(eligibility); if (blob.popup && blob.popup.body) { callback(false, eligibility, blob.popup.body); return; } } catch (exc) { callback(false, eligibility, "Unknown error"); } } }); } ; function makeRaidBookmark(chapterId, questSuffix) { var data = makeBookmarkCore(chapterId, questSuffix, 1); return function (evt) { checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }; } ; function getRaidInfo(data, onSuccess) { log("Requesting raid info", data.infoUrl); doClientAjax(data.infoUrl, function (raidInfo, error) { if (!raidInfo) return showBookmarkError("Failed to get information from server", error); onSuccess(data, raidInfo); }); } ; function makeTreasureRaidBookmark(chapterId, questSuffix, itemId) { var data = makeBookmarkCore(chapterId, questSuffix, 1, itemId); return function (evt) { getRaidInfo(data, function (data, raidInfo) { var treasureIndex = raidInfo.treasure_id.indexOf(String(itemId)); if (treasureIndex < 0) return showBookmarkError("Item not found in raid info"); var itemsNeeded = parseInt(raidInfo.consume[treasureIndex]); var itemsHeld = raidInfo.num[treasureIndex]; if (itemsHeld < itemsNeeded) return showBookmarkError(raidInfo.chapter_name + " requires " + itemsNeeded + " of " + raidInfo.treasure_name[treasureIndex] + ", but you only have " + itemsHeld); checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }); }; /* { "chapter_id":"30005", "quest_id":"300051", "type":"1", "action_point":"50", "chapter_name":"Tiamat Omega Showdown", "consume":["3"], "level":30, "treasure_id":["18"], "treasure_image_id":["18"], "treasure_name":["Tiamat Omega Anima"], "num":[26], "raid_name":"Lvl 50 Tiamat Omega", "limit":90 } */ } ; function visitCurrentEvent(evt, tail) { chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) { if (!currentEvent) showGamePopup({ title: "Error", body: "No event stored. Try visiting the main page." }); else if (tail) bookmarkNavigate("/#" + currentEvent + tail, evt); else bookmarkNavigate("/#" + currentEvent, evt); }); } ; function makeGuildWarBookmark(tail) { return function (evt) { bookmarkNavigate("/#event/" + guildWarName + (tail || ""), evt); }; } ; function makeGuildWarRaidBookmark(chapterId, questSuffix, checkItem) { var data = makeBookmarkCore(chapterId, questSuffix, 1); var checkItemFn, checkStartFn, visitSupporterPageFn, checkMultiStart; checkItemFn = function (evt, onComplete) { if (window.location.href.indexOf("event/" + guildWarName) < 0) { if (onComplete) onComplete(false); return bookmarkNavigate("#event/" + guildWarName, evt); } data.targetUrl = data.targetUrl.replace("#quest/", "#event/" + guildWarName + "/") + "/0"; var checkUrl = "/" + guildWarName + "/rest/top/check_item/" + data.questId; doClientAjax(checkUrl, function (checkResult) { if (checkResult && checkResult.result) return checkStartFn(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You do not have the necessary items to start this quest."); } }); }; checkStartFn = function (evt, onComplete) { checkQuestStart_old(data, function (data, eligibility) { if (eligibility.result === "ok") checkMultiStart(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You are not eligible to start this quest. " + eligibility.result); } }); }; checkMultiStart = function (evt, onComplete) { var checkUrl = "/quest/check_multi_start"; doClientAjax(checkUrl, JSON.stringify({ quest_id: parseInt(data.questId) }), function (checkResult) { if (checkResult && checkResult.result === "ok") return visitSupporterPageFn(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You cannot start a raid."); } }); }; visitSupporterPageFn = function (evt, onComplete) { if (window.location.href.indexOf("event/" + guildWarName) < 0) { if (onComplete) onComplete(false); return bookmarkNavigate("#event/" + guildWarName, evt); } else { if (onComplete) onComplete(true); startRaid(data, evt); } }; if (!checkItem) return visitSupporterPageFn; return checkItemFn; } ; function makeEventTreasureRaidBookmark(chapterId, questSuffix) { return function (evt) { chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) { if (!currentEvent) showGamePopup({ title: "Error", body: "No event stored. Try visiting the main page." }); var data = makeBookmarkCore(chapterId, questSuffix, 1); data.targetUrl = data.targetUrl.replace("#quest/", "#" + currentEvent + "/"); checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }); }; } ; var guildWarName = null; var guildWarSubmenu = { "guild-war-home": makeGuildWarBookmark(), "guild-war-gacha": makeGuildWarBookmark("/gacha/index"), "guild-war-reward": makeGuildWarBookmark("/reward"), //"guild-war-eye-vh": makeGuildWarRaidBookmark(71863, 1, false), "guild-war-dog-vh": makeGuildWarRaidBookmark(72314, 1, false), "guild-war-dog-ex": makeGuildWarRaidBookmark(72315, 1, false), "guild-war-dog-ex-plus": makeGuildWarRaidBookmark(72316, 1, false), "guild-war-hell-90": makeGuildWarRaidBookmark(72317, 1, true), "guild-war-hell-95": makeGuildWarRaidBookmark(72318, 1, true), }; var menuItems = { "home": "/#mypage", "party": "/#party/index/0/npc/0", "mystuff": { "inventory": "/#list", "stash": "/#container", "crate": "/#present", "supplies": "/#item", }, "quest": { "quest-all": "/#quest/index", "quest-special": "/#quest/extra", "join-raid": "/#quest/assist", "event": visitCurrentEvent, "trial-battles": "/#trial_battle", "pending-raids": "/#quest/assist/unclaimed", }, "quest-repeat": repeatLastQuest, "guild-war": guildWarSubmenu, "hard-raids": { "hard-tia": makeRaidBookmark(30004, 1), "hard-colo": makeRaidBookmark(30009, 1), "hard-levi": makeRaidBookmark(30015, 1), "hard-yugu": makeRaidBookmark(30019, 1), "hard-chev": makeRaidBookmark(30022, 1), "hard-cel": makeRaidBookmark(30025, 1) }, "magna-raids": { "magna-tia": makeTreasureRaidBookmark(30005, 1, 18), "magna-colo": makeTreasureRaidBookmark(30010, 1, 19), "magna-levi": makeTreasureRaidBookmark(30016, 1, 20), "magna-yugu": makeTreasureRaidBookmark(30026, 1, 21), "magna-chev": makeTreasureRaidBookmark(30027, 1, 26), "magna-cel": makeTreasureRaidBookmark(30028, 1, 31) }, "hl-raids": { "hl-tia": makeTreasureRaidBookmark(30044, 1, 32), "hl-colo": makeTreasureRaidBookmark(30049, 1, 47), "hl-levi": makeTreasureRaidBookmark(30051, 1, 48), "hl-yugu": makeTreasureRaidBookmark(30053, 1, 49), "hl-chev": makeTreasureRaidBookmark(30056, 1, 50), "hl-cel": makeTreasureRaidBookmark(30058, 1, 51), "hl-rosequeen": makeTreasureRaidBookmark(30047, 1, 1204), }, "primal-raids": { "nataku": makeTreasureRaidBookmark(30042, 1, 1343), "flame-glass": makeTreasureRaidBookmark(30041, 1, 1313), "macula-marius": makeTreasureRaidBookmark(30038, 1, 1323), "athena": makeTreasureRaidBookmark(30107, 1, 1313), "medusa": makeTreasureRaidBookmark(30039, 1, 1333), "apollo": makeTreasureRaidBookmark(30043, 1, 1353), "olivia": makeTreasureRaidBookmark(30040, 1, 1363), "odin": makeTreasureRaidBookmark(30046, 1, 1353), }, "coop": { "coop": "/#coopraid", // This makes it impossible to return to an existing room // "coop-host": "/#coopraid/room/entry", "coop-join": "/#coopraid/offer", "coop-shop": "/#coopraid/lineup" }, "me": { "profile": "/#profile", "crew": "/#guild", "friends": "/#friend", "trophies": "/#title" }, "shop": { "shop-mobacoins": "#shop/moba/0", "shop-crystals": "#shop/lupi/0", "shop-points": "/#shop/exchange/points", "shop-trajectory": "#shop/exchange/trajectory", "shop-moon": "#shop/exchange/moon", "shop-treasure": "#shop/exchange/list", "shop-whale-tears": "#shop/exchange/ceiling", "shop-weapon-series": "#archaic", }, "casino": { "poker": "/#casino/list/poker", "bingo": "/#casino/list/bingo", "casino-shop": "/#casino/exchange" }, }; var viramateMenuItems = { "settings": function () { var loc = chrome.extension.getURL("src/options_custom/index.html"); var w = window.open(loc); }, "update-notes": function () { var loc = chrome.extension.getURL("content/changelog.html"); var w = window.open(loc); } }; function isHorizontalLayout() { return (isMobileSite() || !!currentSettings.horizontalBookmarks || !!document.getElementById("gree-game-container")); } ; function makeMenuHandler(name, value, tryCloseMenu) { var result; if (typeof (value) === "string") result = function (evt) { if (evt) { evt.preventDefault(); evt.stopPropagation(); } tryCloseMenu(); bookmarkNavigate(value, evt); }; else if (value && value.call && value.apply) result = function (evt) { if (evt) { evt.preventDefault(); evt.stopPropagation(); } tryCloseMenu(); value(evt); }; else return null; allBookmarks[name] = result; return result; } ; function _updateIconSize(menuIcon) { if (isHorizontalLayout()) menuIcon.style.left = menuLeftEdge.toFixed(0) + "px"; else menuIcon.style.left = "-6px"; var iconRect = menuIcon.getBoundingClientRect(); if (isHorizontalLayout()) menuIconSize = iconRect.width * getEffectiveZoom(menuIcon) * getEffectiveZoom(document.documentElement); else menuIconSize = iconRect.height * getEffectiveZoom(menuIcon); } ; function getColorForMenuItem(key) { switch (key) { case "hard-raids": return "#efc0ba"; case "magna-raids": return "#e8e8f1"; case "hl-raids": return "#efe0ba"; } var dashPos = key.lastIndexOf("-"); var suffix = key.substr(dashPos + 1); switch (suffix) { case "tia": return "#bfefbf"; case "yugu": return "#efdfa0"; case "colo": return "#efbfbf"; case "levi": return "#bfcfef"; case "cel": return "#d890df"; } return null; } ; function showViraButton() { if (isShutdown) return; injectStylesheet("sidebar-shadow.css", getUiContainer()); var outImg = getResourceUrl('vira-small-smile.png'); var overImg = getResourceUrl('vira-small.png'); var isCustomIcon = false; try { if (currentSettings.bookmarksInactiveIcon) outImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksInactiveIcon); if (currentSettings.bookmarksActiveIcon) overImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksActiveIcon); isCustomIcon = (currentSettings.bookmarksActiveIcon || currentSettings.bookmarksInactiveIcon); } catch (exc) { log("Error decoding custom bookmarks icons", exc); } var menuIcon = document.createElement("div"); var mainMenu = document.createElement("div"); menuIcon.className = "viramate-menu-icon"; // HACK: Why is this necessary? menuIcon.style.backgroundRepeat = "no-repeat"; menuIcon.style.backgroundImage = "url(" + outImg + ")"; menuIcon.setAttribute("title", "Viramate"); var maxIconWidth = isCustomIcon ? 64 : 56; // HACK: :after selectors don't work on img. html sucks. var tempImage = document.createElement("img"); tempImage.style.opacity = "0.0"; tempImage.onload = function () { var scale = 1.0; if (tempImage.naturalWidth > maxIconWidth) scale = maxIconWidth / tempImage.naturalWidth; menuIcon.style.width = (tempImage.naturalWidth * scale).toFixed(0) + "px"; menuIcon.style.height = (tempImage.naturalHeight * scale).toFixed(0) + "px"; uninjectElement(getUiContainer(), tempImage); _updateIconSize(menuIcon); _layoutPanels(); }; tempImage.src = outImg; injectElement(getUiContainer(), tempImage); var paddingSize = 100; if (typeof (currentSettings.bookmarksIconPadding) === "number") paddingSize = currentSettings.bookmarksIconPadding; if (isHorizontalLayout()) { menuIcon.style.paddingRight = Math.max(paddingSize - 12, 0).toFixed(0) + "px"; } else { menuIcon.style.paddingBottom = Math.max(paddingSize - 12, 0).toFixed(0) + "px"; } mainMenu.className = "viramate-menu"; if (typeof (currentSettings.bookmarksSize) === "number") menuIcon.style.transform = "scale(" + currentSettings.bookmarksSize.toFixed(1) + ")"; if (typeof (currentSettings.bookmarksMenuSize) === "number") mainMenu.style.transform = "scale(" + currentSettings.bookmarksMenuSize.toFixed(1) + ")"; // mainMenu.style.zoom = menuIcon.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); var mouseIsOverIcon = false; var mouseIsOverMenu = 0; var mouseIsOverSubmenu = 0; var menuIsVisible = false; var allMenus = [mainMenu]; var updateTimeout = 0; var autoOpenDelay = isHorizontalLayout() ? 260 : 160; var autoCloseDelay = currentSettings.openBookmarksOnClick ? 500 : 250; var pamrklamr = function () { return 5 * 1000 + (Math.random() * 1600 * 1000); }; var fmajrlialmsk; fmajrlialmsk = function () { if (isShutdown) return; if (isCustomIcon) return; if (!menuIsVisible) { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")"; window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/qw3mkl/vqprlm.png') + ")"; }, 60); window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")"; }, 950); window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + outImg + ")"; }, 1060); } window.setTimeout(fmajrlialmsk, pamrklamr()); }; window.setTimeout(fmajrlialmsk, pamrklamr()); var showMenu = function (menu) { if (menu.className.indexOf("viramate-menu") === 0) menu.style.left = menuLeftEdge.toFixed(0) + "px"; else menu.style.left = "0px"; menu.style.opacity = "1.0"; menu.style.pointerEvents = "all"; menuIsVisible = true; }; var showMenus = function () { menuIcon.style.backgroundImage = "url(" + overImg + ")"; if (menuIcon.className.indexOf("open") < 0) menuIcon.className += " open"; for (var i = 0; i < allMenus.length; i++) { var elt = allMenus[i]; showMenu(elt); } }; var hideMenu = function (menu) { if (!isMobileSite()) { if (menu.className.indexOf("viramate-menu") === 0) menu.style.left = (menuLeftEdge - 32).toFixed(0) + "px"; else menu.style.left = "-32px"; } menu.style.opacity = "0.0"; menu.style.pointerEvents = "none"; menuIsVisible = false; }; var hideMenus = function () { menuIcon.style.backgroundImage = "url(" + outImg + ")"; menuIcon.className = menuIcon.className.replace(" open", ""); closeSubmenus(); hideMenu(allMenus[0]); }; var closeSubmenus = function () { // Hide any other open submenus for (var i = 1; i < allMenus.length; i++) { var submenu = allMenus[i]; if (submenu.owner) submenu.owner.className = submenu.owner.className.replace(" open", ""); hideMenu(submenu); } // Pop them off the list allMenus.length = 1; }; var openSubmenu = function (owner, submenu) { owner.className += " open"; submenu.owner = owner; closeSubmenus(); allMenus.push(submenu); showMenus(); }; var updateMenu = function () { if (isShutdown) return; if (mouseIsOverIcon || (mouseIsOverMenu > 0)) { if (mouseIsOverSubmenu <= 0) closeSubmenus(); showMenus(); } else hideMenus(); }; var scheduleUpdate = function (fast) { if (updateTimeout) window.clearTimeout(updateTimeout); updateTimeout = window.setTimeout(updateMenu, fast ? autoOpenDelay : autoCloseDelay); }; var makeSubmenuOverHandler = function (item, submenu) { return function (evt) { mouseIsOverSubmenu += 1; openSubmenu(item, submenu); }; }; var makeSubmenuOutHandler = function (item, submenu) { return function (evt) { mouseIsOverSubmenu -= 1; // TODO: Anything? scheduleUpdate(); }; }; var tryCloseMenu = function () { hideMenus(); window.clearTimeout(updateTimeout); }; menuIcon.addEventListener("click", function () { showMenus(); }, false); menuIcon.addEventListener("mouseover", function () { mouseIsOverIcon = true; if (!isMobileSite() && (currentSettings.openBookmarksOnClick !== true)) scheduleUpdate(true); }, false); menuIcon.addEventListener("mouseout", function () { mouseIsOverIcon = false; scheduleUpdate(); }, false); mainMenu.addEventListener("mouseover", function () { mouseIsOverMenu += 1; }, false); mainMenu.addEventListener("mouseout", function () { mouseIsOverMenu -= 1; scheduleUpdate(); }, false); var isGuildWar = currentSettings.currentGuildWar && (currentSettings.currentGuildWar.indexOf("event/teamraid") === 0); if (isGuildWar) guildWarName = currentSettings.currentGuildWar.replace("event/", ""); allBookmarks = {}; var populateSubmenu; populateSubmenu = function (container, items, isSubmenu, extraClassNames) { if (isSubmenu) { if (Object.keys(items).length > 4) container.style.columnCount = "2"; } for (var k in items) { if (!items.hasOwnProperty(k)) continue; var v = items[k]; // HACK: Only show guild war submenu during guild war if ((v === guildWarSubmenu) && !isGuildWar) continue; var elt = document.createElement("li"); elt.className = "viramate-menu-item"; if (extraClassNames) elt.className += " " + extraClassNames; elt.setAttribute("key", k); var label = i18n.get("m-" + k); elt.textContent = label; var color = getColorForMenuItem(k); if (color) elt.style.color = color; if (v && (typeof (v) === "object")) { // Submenu elt.className += " has-submenu"; var submenu = document.createElement("ul"); submenu.className = "viramate-submenu"; submenu.addEventListener("mouseover", function () { mouseIsOverSubmenu += 1; }, false); submenu.addEventListener("mouseout", function () { mouseIsOverSubmenu -= 1; scheduleUpdate(); }, false); elt.addEventListener("mouseover", makeSubmenuOverHandler(elt, submenu), false); elt.addEventListener("mouseout", makeSubmenuOutHandler(elt, submenu), false); hideMenu(submenu); populateSubmenu(submenu, v, true); container.appendChild(submenu); } else { // Item elt.addEventListener("mouseup", makeMenuHandler(k, v, tryCloseMenu), true); elt.addEventListener("tap", makeMenuHandler(k, v, tryCloseMenu), false); } container.appendChild(elt); } ; }; var ul = document.createElement("ul"); mainMenu.appendChild(ul); populateSubmenu(ul, menuItems, false); var langSelectorEn = document.createElement("li"); var langSelectorJp = document.createElement("li"); langSelectorEn.className = "language-menu-item en"; langSelectorJp.className = "language-menu-item jp"; langSelectorEn.textContent = "English"; langSelectorJp.textContent = "日本語"; langSelectorEn.title = langSelectorJp.title = i18n.get("m-set-language"); langSelectorEn.addEventListener("click", makeLanguageSetter(2), true); langSelectorJp.addEventListener("click", makeLanguageSetter(1), true); ul.appendChild(langSelectorEn); ul.appendChild(langSelectorJp); /* var showPopoutItem = document.createElement("li"); showPopoutItem.className = "viramate-menu-item"; showPopoutItem.textContent = "Open popout"; showPopoutItem.addEventListener("click", showPopout, true); ul.appendChild(showPopoutItem); */ var versionText = document.createElement("span"); versionText.className = "viramate-version"; ul.appendChild(versionText); populateSubmenu(ul, viramateMenuItems, false, "small"); hideMenus(); if (isHorizontalLayout()) { menuIcon.className += " horizontal"; mainMenu.className += " horizontal"; var trySpawn = function () { if (isShutdown) return true; var gameContainer = getGameContainer(); var wrapper = gameContainer.querySelector(".wrapper"); if (!gameContainer || !wrapper) return false; var effectiveZoom = getEffectiveZoom(gameContainer); var documentZoom = getEffectiveZoom(document.documentElement); menuLeftEdge = parseFloat(wrapper.parentNode.getAttribute("data-show-menubar-width")) || 0; var effectiveSidebarHeight = 48; if (isMobileSite()) { effectiveSidebarHeight /= documentZoom; getOverlayContainer().style.zoom = (1 / documentZoom).toFixed(3); } wrapper.style.marginTop = (effectiveSidebarHeight / effectiveZoom).toFixed(0) + "px"; return true; }; if (!trySpawn()) window.setTimeout(trySpawn, 500); } injectElement(getUiContainer(), menuIcon); injectElement(getUiContainer(), mainMenu); chrome.runtime.sendMessage({ type: "getVersion" }, function (version) { var text = "Viramate " + version; if (isMobileSite()) text += " (mobile)"; versionText.textContent = text; }); window.setTimeout(function () { if (isShutdown) return; _updateIconSize(menuIcon); getUserIdAndTabIdAsync(showStatusPanel); }, 25); } ; var primeHaloRequestIsPending = false; var primeHaloStartsWhen = null, primeHaloStartsWhenText = null; var needHaloPanelLayout = false; function navigateToExtraQuests() { window.location.href = "/#quest/extra"; } ; function updateClock(element) { var jstHourMinute = { timeZone: "Asia/Tokyo", hour12: false, hour: "2-digit", minute: "2-digit" }; var text = new Date().toLocaleString("ja-JP", jstHourMinute) + " JST"; var timeText = element.time; if (!timeText) { element.time = timeText = document.createElement("span"); element.appendChild(timeText); } var c = (currentSettings.clockBrightness * 255).toFixed(0); var ct = "rgb(" + c + ", " + c + ", " + c + ")"; timeText.style.color = ct; timeText.textContent = text; /* var haloText = element.halo; if (!haloText) { element.appendChild(document.createElement("br")); element.halo = haloText = document.createElement("span"); haloText.className = "halo-timer"; element.appendChild(haloText); haloText.addEventListener("click", navigateToExtraQuests, false); } if (primeHaloStartsWhen) { var now = Date.now(); if (!primeHaloStartsWhenText) { var temp = new Date(primeHaloStartsWhen); primeHaloStartsWhenText = temp.toLocaleString("ja-JP", jstHourMinute); } if (primeHaloStartsWhen < now) { // Prime halo is active c = (currentSettings.clockBrightness * 255).toFixed(0); var c2 = (currentSettings.clockBrightness * 210).toFixed(0); haloText.textContent = "\u2605 Halo" haloText.style.color = "rgb(" + c + ", " + c + ", " + c2 + ")"; haloText.style.fontWeight = "bold"; } else { // Prime halo starts soon c = (currentSettings.clockBrightness * 220).toFixed(0); haloText.textContent = "\u2605H " + primeHaloStartsWhenText; haloText.style.color = "rgb(" + c + ", " + c + ", " + c + ")"; haloText.style.fontWeight = "normal"; } } else { haloText.textContent = ""; } */ if (needHaloPanelLayout) { _layoutPanels(); needHaloPanelLayout = false; } } ; function showStatusPanel(uid) { var panel = document.createElement("div"); panel.className = "viramate-status-panel"; // panel.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); var clock = null; if (currentSettings.clockBrightness >= 0.05) { clock = document.createElement("span"); clock.className = "time"; panel.appendChild(clock); } if (currentSettings.statusPanel) { var meters = document.createElement("div"); meters.className = "meters"; var createMeter = function (name, withShadow) { var meter = document.createElement("div"); meter.className = "meter " + name + "-meter"; meter.title = name.toUpperCase(); var fill = document.createElement("div"); fill.className = "fill"; meter.fill = fill; meter.appendChild(fill); if (withShadow) { var shadow = document.createElement("div"); shadow.className = "fill shadow"; meter.shadow = shadow; meter.appendChild(shadow); } panel[name + "Meter"] = meter; meters.appendChild(meter); }; panel.appendChild(meters); createMeter("rp", false); createMeter("ap", true); createMeter("bp", true); if (currentSettings.statusPanelBuffs) { var buffsPanel = panel.buffs = document.createElement("div"); buffsPanel.className = "buffs"; panel.appendChild(buffsPanel); } } if (currentSettings.itemsPanel) { var itemsPanel = panel.items = document.createElement("div"); itemsPanel.className = "items"; if (currentSettings.largeItemsPanel) itemsPanel.className += " large-items"; panel.appendChild(itemsPanel); } if (clock) window.setInterval(function () { updateClock(clock); }, 1000); if (isHorizontalLayout()) panel.className += " horizontal"; injectElement(getUiContainer(), panel); if (currentSettings.raidsPanel) showRaidsPanel(uid); _layoutPanels(); invalidateStatus = function () { chrome.runtime.sendMessage({ type: "invalidateStatus", uid: uid }); }; if (currentSettings.itemsPanel) { invalidateItems = function (items) { _invalidateItems(panel, uid, items); }; updateItemsPanel = function () { _updateItemsPanel(panel, uid); }; doUpdateItemsPanel = function (items) { _doUpdateItemsPanel(panel, uid, items); }; } if (currentSettings.statusPanel) { updateStatusPanel = function (force, lazy) { if (isCombatPage(window.location.hash)) return; else if (window.location.hash.indexOf("result_") >= 0) return; else if (window.location.hash.indexOf("coopraid/room") >= 0) return; _updateStatusPanel(panel, uid, force, lazy); }; doUpdateStatusPanel = function (status) { _doUpdateStatusPanel(panel, status); }; doUpdateGuildSupportBuffs = function (buffs) { _doUpdateGuildSupportBuffs(panel, uid, buffs); }; doUpdatePersonalSupportBuffs = function (buffs) { _doUpdatePersonalSupportBuffs(panel, uid, buffs); }; invalidateSupportBuffs = function () { _invalidateSupportBuffs(panel, uid); }; var lazyUpdate = function () { if (isShutdown) { window.clearInterval(statusIntervalH); return; } updateStatusPanel(false, true); }; statusIntervalH = window.setInterval(lazyUpdate, statusPanelUpdateIntervalSeconds * 1000); // HACK: We need to delay this a bit so the page can finish loading window.setTimeout(lazyUpdate, 1250); } _layoutPanels(); } ; function _layoutPanels() { var uic = getUiContainer(); var statusPanel = uic.querySelector("div.viramate-status-panel"); var raidsPanel = uic.querySelector("div.viramate-raids-panel"); if (!statusPanel) return; if (isHorizontalLayout()) { subpanelOffset = menuIconSize + 4; statusPanel.style.left = (menuLeftEdge).toFixed(0) + "px"; statusPanel.style.paddingLeft = subpanelOffset.toFixed(0) + "px"; var meters = statusPanel.querySelector("div.meters"); var buffs = statusPanel.querySelector("div.buffs"); var items = statusPanel.querySelector("div.items"); if (meters) { meters.style.left = (subpanelOffset + 64).toFixed(0) + "px"; } if (buffs) { buffs.style.left = (subpanelOffset + 128 + 4).toFixed(0) + "px"; if (items) items.style.left = (subpanelOffset + 128 + buffs.clientWidth + 8).toFixed(0) + "px"; } else if (items) { items.style.left = (subpanelOffset + 128 + 4).toFixed(0) + "px"; } if (raidsPanel) { var bw = 0, iw = 0; if (buffs) bw = buffs.clientWidth; if (items) iw = items.clientWidth; if (bw) bw += 2; if (iw) iw += 2; if (buffs) raidsPanel.style.left = (128 + bw + iw + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; else if (meters) raidsPanel.style.left = (128 + iw + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; else raidsPanel.style.left = (64 + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; } } else { subpanelOffset = menuIconSize + 12; statusPanel.style.top = subpanelOffset.toFixed(0) + "px"; if (raidsPanel) raidsPanel.style.top = (statusPanel.clientHeight + subpanelOffset).toFixed(0) + "px"; } } ; function _roundDown(value, decimals) { var mult = Math.pow(10, decimals); value *= mult; value = Math.floor(value); value /= mult; return value.toFixed(decimals); } ; function _setWidth(elt, fraction) { if (fraction < 0) fraction = 0; else if (fraction > 1) fraction = 1; var newWidth = (fraction * 100).toFixed(2) + "%"; if (elt.style.width !== newWidth) elt.style.width = newWidth; } ; function _invalidateSupportBuffs(panel, uid) { var msg = { type: "invalidateBuffs", uid: uid }; chrome.runtime.sendMessage(msg); updateBuffsWhen = Date.now() + 2000; } ; function _doUpdatePersonalSupportBuffs(panel, uid, buffs) { if (isShutdown) return; var msg = { type: "updatePersonalBuffs", uid: uid, buffs: buffs }; chrome.runtime.sendMessage(msg); window.setTimeout(function () { _updateStatusPanel(panel, uid, false, true); }, 1000); } ; function _doUpdateGuildSupportBuffs(panel, uid, buffs) { if (isShutdown) return; var msg = { type: "updateGuildBuffs", uid: uid, buffs: buffs }; chrome.runtime.sendMessage(msg); window.setTimeout(function () { _updateStatusPanel(panel, uid, false, true); }, 1000); } ; function _doUpdateStatusPanel(panel, status) { lastPlayerStatus = status; var ap = status._precise_ap; var bp = status._precise_bp; panel.apMeter.setAttribute("text", _roundDown(ap, 1)); _setWidth(panel.apMeter.fill, Math.floor(ap) / parseInt(status.max_action_point)); _setWidth(panel.apMeter.shadow, ap / parseInt(status.max_action_point)); panel.bpMeter.setAttribute("text", _roundDown(bp, 0)); _setWidth(panel.bpMeter.fill, Math.floor(bp) / parseInt(status.max_battle_point)); _setWidth(panel.bpMeter.shadow, bp / parseInt(status.max_battle_point)); panel.rpMeter.setAttribute("text", status.levelGauge); panel.rpMeter.fill.style.width = status.levelGauge; if (currentSettings.statusPanelBuffs) _doUpdateBuffsPanel(panel, status); _layoutPanels(); } ; function _doUpdateBuffsPanel(panel, status) { var buffsPanel = panel.buffs; buffsPanel.textContent = ""; var buffs = status.buffs; if (!buffs || !buffs.length) return; var x = 0, y = 0; var count = 0; var nextBuffUpdateMinutes = null; for (var i = 0, l = buffs.length; i < l; i++) { var buff = buffs[i]; var elt = document.createElement("div"); elt.className = "viramate-buff"; elt.style.backgroundImage = "url('" + buff.imageUrl + "')"; elt.style.left = x.toFixed(0) + "px"; elt.style.top = y.toFixed(0) + "px"; var minutesLeft = ((buff.timeRemaining / 1000) / 60); if (nextBuffUpdateMinutes === null) nextBuffUpdateMinutes = minutesLeft; else nextBuffUpdateMinutes = Math.min(minutesLeft, nextBuffUpdateMinutes); if (minutesLeft < 90) elt.setAttribute("remaining", minutesLeft.toFixed(0)); else if (currentSettings.statusPanelExpiringBuffs) continue; if (minutesLeft > 60) { elt.title = buff.comment + " - " + (minutesLeft / 60).toFixed(1) + " hour(s) remaining"; } else { elt.title = buff.comment + " - " + minutesLeft.toFixed(0) + " minute(s) remaining"; } if (isHorizontalLayout()) { if (y >= 24) { y = 0; x += 24; } else { y += 24; } } else { if (x >= 32) { x = 0; y += 32; } else { x += 32; } } count++; buffsPanel.appendChild(elt); } if (nextBuffUpdateMinutes) { updateBuffsWhen = Math.max(updateBuffsWhen, Date.now() + ((nextBuffUpdateMinutes * 60 * 1000) + (59 * 1000))); var nextUpdateSeconds = (updateBuffsWhen - Date.now()) / 1000; if (nextUpdateSeconds <= 120) log("Updating buffs in " + nextUpdateSeconds.toFixed(0) + " second(s)"); } if (isHorizontalLayout()) { buffsPanel.style.width = (Math.ceil(count / 2) * 24).toFixed(0) + "px"; } else { buffsPanel.style.height = (Math.ceil(count / 2) * 32).toFixed(0) + "px"; } } ; function _maybeRequestBuffsFromServer() { if (!currentSettings.statusPanelBuffs) return; if (isUpdatingBuffs) return; var now = Date.now(); var shouldUpdateBuffs = now > updateBuffsWhen; if (!shouldUpdateBuffs) return; isUpdatingBuffs = true; updateBuffsWhen = now + (minimumBuffUpdateIntervalSeconds * 1000); var updateCounter = 2; doClientAjax("/guild_main/support_all_info/", function () { updateCounter--; if (updateCounter <= 0) isUpdatingBuffs = false; }); doClientAjax("/shop_exchange/activated_personal_supports/", function () { updateCounter--; if (updateCounter <= 0) isUpdatingBuffs = false; }); } ; function _updateStatusPanel(panel, uid, force, lazy) { if (isShutdown) return; var msg = { type: "getStatus", uid: uid, force: !!force, lazy: !!lazy }; chrome.runtime.sendMessage(msg, function (status) { if (status) { _doUpdateStatusPanel(panel, status); _maybeRequestBuffsFromServer(); _updateItemsPanel(panel, uid); } else log("Failed to get status"); }); } ; function showRaidsPanel(uid) { if (isShutdown) return; var panel = document.createElement("div"); panel.className = "viramate-raids-panel"; // panel.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); if (isHorizontalLayout()) panel.className += " horizontal"; var cdt = document.createElement("div"); panel.countdownTimer = cdt; cdt.className = "countdown-timer"; if (isHorizontalLayout()) { cdt.style.height = "0px"; } else { cdt.style.width = "0px"; } injectElement(getUiContainer(), panel); raidTimerIntervalH = window.setInterval(function () { if (isShutdown) { window.clearInterval(raidTimerIntervalH); return; } updateRaidTimer(panel); }, 750); updateRaidsPanel = function () { _updateRaidsPanel(panel, uid, false); }; invalidateRaidList = function (raids) { _invalidateRaidList(panel, uid, raids); }; doUpdateRaidsPanel = function (raids) { _doUpdateRaidsPanel(panel, raids); }; if (!pendingRaidUpdate) window.setTimeout(updateRaidsPanel, 1000); } ; function maybeScheduleNextRaidUpdate(panel) { if (isShutdown) return; if (pendingRaidUpdate) { updateRaidTimer(panel); return; } nextRaidUpdateWhen = null; if (!lastPlayerStatus) { pendingRaidUpdate = window.setTimeout(updateRaidsPanel, 3000); nextRaidUpdateWhen = Date.now() + 3000; } else if (raidListUpdateCounter-- >= 0) { currentRaidListUpdateInterval += raidListUpdateBackoff; // console.log("raid list update; next in " + (currentRaidListUpdateInterval / 1000).toFixed(1) + "s"); pendingRaidUpdate = window.setTimeout(updateRaidsPanel, currentRaidListUpdateInterval); nextRaidUpdateWhen = Date.now() + currentRaidListUpdateInterval; } else { log("raid list updates disabled because player is idle"); _doUpdateRaidsPanel(panel, null); } updateRaidTimer(panel); } ; function shouldShowRaidsPanel() { // return true; return !isCombatPage(window.location.hash) && (window.location.hash.indexOf("#coopraid/room") < 0) && (window.location.hash.indexOf("#result_") < 0) && (window.location.hash.indexOf("quest/supporter") < 0); } ; function updateRaidTimer(panel) { var ct = panel.countdownTimer; var remaining = nextRaidUpdateWhen - Date.now(); if (shouldShowRaidsPanel() && nextRaidUpdateWhen && (raidListUpdateCounter > 0)) { var total = currentRaidListUpdateInterval; var fraction = 1.0 - Math.max(Math.min(remaining / total, 1.0), 0.0); if (isHorizontalLayout()) ct.style.height = (fraction * 44).toFixed(1) + "px"; else ct.style.width = (fraction * 60).toFixed(1) + "px"; ct.title = "Next raid list update in " + (remaining / 1000).toFixed(1) + " second(s)"; } else { if (isHorizontalLayout()) ct.style.height = "0px"; else ct.style.width = "0px"; } } ; function isJoined(raid) { return raid["data-raid-type"] === 0; } ; function raidJoinHandler(evt) { doJoinRaid(evt, this); evt.preventDefault(); } ; function _doUpdateRaidsPanel(panel, _raids) { if (!panel) return; panel.innerHTML = ""; panel.appendChild(panel.countdownTimer); if (!_raids) { return; } var raids = _raids.assist_raids_data; if (!raids) return; for (var i = 0; i < raids.length; i++) { var raid = raids[i]; if (!raid) continue; var elt = document.createElement("div"); elt.className = "raid"; elt.title = raid.chapter_name; if (isJoined(raid)) elt.className += " joined"; if (raid.boss_image) { var imageUrl = "http://game-a1.granbluefantasy.jp/"; if (i18n.get("lang") === "en") imageUrl += "assets_en"; else imageUrl += "assets"; imageUrl += "/img/sp/assets/summon/qm/" + raid.boss_image + ".jpg"; elt.style.backgroundImage = "url('" + imageUrl + "')"; } else { elt.textContent = raid.chapter_name; } elt.addEventListener("mouseup", raidJoinHandler.bind(raid), false); var gauge = document.createElement("div"); gauge.className = "gauge"; var fill = document.createElement("div"); fill.className = "fill"; fill.style.width = raid.boss_hp_width + "%"; var memberCount = document.createElement("span"); memberCount.className = "member-count"; memberCount.textContent = raid.member_count; gauge.appendChild(fill); elt.appendChild(gauge); elt.appendChild(memberCount); panel.appendChild(elt); } } ; function _updateRaidsPanel(panel, uid, force) { if (isShutdown) return; pendingRaidUpdate = null; maybeScheduleNextRaidUpdate(panel); // HACK if (!shouldShowRaidsPanel()) { _doUpdateRaidsPanel(panel, null); return; } if (!lastPlayerStatus) return; if (currentSettings.raidsPanelBpFilter) { if (lastPlayerStatus && (lastPlayerStatus._precise_bp < 3)) { log("Not updating raids list because player only has " + lastPlayerStatus._precise_bp.toFixed(1) + " BP"); _doUpdateRaidsPanel(panel, null); return; } } var msg = { type: "getRaids", uid: uid, force: !!force }; chrome.runtime.sendMessage(msg, function (raids) { if (raids) _doUpdateRaidsPanel(panel, raids); else log("Failed to get raids"); }); } ; function _invalidateRaidList(panel, uid, raids) { if (!raids || (window.location.hash.indexOf("quest/assist") >= 0)) { if (pendingRaidUpdate) { window.clearTimeout(pendingRaidUpdate); pendingRaidUpdate = null; } raidListUpdateCounter = 45; currentRaidListUpdateInterval = raidListUpdateInterval; maybeScheduleNextRaidUpdate(panel); } var msg = { type: "invalidateRaids", uid: uid, raids: raids }; chrome.runtime.sendMessage(msg); } ; function _invalidateItems(panel, uid, items) { if (isShutdown) return; var msg = { type: "invalidateItems", uid: uid, items: items }; chrome.runtime.sendMessage(msg); if (items) { _doUpdateItemsPanel(panel, uid, items); } else { // HACK window.setTimeout(function () { _updateItemsPanel(panel, uid); }, 2000); } } ; function _updateItemsPanel(panel, uid) { // Only check for items if something is watched. chrome.runtime.sendMessage({ type: "getWatchedItems" }, function (watchedItems) { if (!currentSettings.itemsPanel) return; if (!watchedItems.items || !watchedItems.items.length) return; var msg = { type: "getItems", uid: uid, force: false }; chrome.runtime.sendMessage(msg, function (items) { mostRecentItems = items; _doUpdateItemsPanel(panel, uid, items); }); }); } ; function _doUpdateItemsPanel(_panel, uid, items) { var panel = _panel.items; if (!items) items = mostRecentItems; if (!items) { panel.textContent = ""; return; } var onWatchedItemIconContextMenu = function (evt) { evt.preventDefault(); }; var onWatchedItemIconMouseUp = function (evt) { evt.preventDefault(); var itemId = parseInt(evt.target.getAttribute("item-id")); var targetCount = parseInt(evt.target.getAttribute("target-count")); switch (evt.button) { case 0: log("Toggling item target count", itemId); var target = -1; if ((targetCount <= 0) || (typeof (targetCount) !== "number") || Number.isNaN(targetCount)) targetCount = parseInt(prompt("Set target number of " + evt.target.title)); else targetCount = -1; if (Number.isNaN(targetCount)) targetCount = -1; chrome.runtime.sendMessage({ type: "setItemWatchTarget", id: itemId, count: targetCount }); break; case 2: log("Removing watch on item", itemId); chrome.runtime.sendMessage({ type: "setItemWatchState", id: itemId, state: false }); break; } if (doUpdateItemsPanel) doUpdateItemsPanel(); }; chrome.runtime.sendMessage({ type: "getWatchedItems" }, function (obj) { var watchedItems = obj.items; var targetCounts = obj.counts; var x = 0, y = 0; var count = 0; panel.textContent = ""; for (var i = 0, l = watchedItems.length; i < l; i++) { var itemInfo = findItemInfo(function (item, id) { return item.item_id == id; }, watchedItems[i]); if (!itemInfo) continue; var elt = document.createElement("div"); elt.className = "viramate-item"; elt.style.backgroundImage = "url('http://game-a.granbluefantasy.jp/assets_en/" + "img/sp/assets/item/article/s/" + itemInfo.image + ".jpg')"; elt.style.left = x.toFixed(0) + "px"; elt.style.top = y.toFixed(0) + "px"; elt.title = itemInfo.name + " (Left-click to set goal, right-click to hide)"; elt.setAttribute("item-id", itemInfo.item_id); elt.addEventListener("contextmenu", onWatchedItemIconContextMenu, false); elt.addEventListener("mouseup", onWatchedItemIconMouseUp, false); var targetCount = targetCounts[itemInfo.item_id] || -1; var remaining = targetCount - itemInfo.number; if (targetCount > 0) elt.setAttribute("target-count", targetCount); if ((remaining > 0) && (targetCount > 0)) { elt.setAttribute("count", "-" + remaining); } else { elt.setAttribute("count", itemInfo.number); } count++; panel.appendChild(elt); if (isHorizontalLayout()) { if (currentSettings.largeItemsPanel) { y = 0; x += 48; } else if (y >= 24) { y = 0; x += 24; } else { y += 24; } } else { if (currentSettings.largeItemsPanel) { y += 64; x = 0; } else if (x >= 32) { x = 0; y += 32; } else { x += 32; } } } var iconSize, iconDivisor; if (isHorizontalLayout()) { iconDivisor = currentSettings.largeItemsPanel ? 1 : 2; iconSize = currentSettings.largeItemsPanel ? 48 : 24; panel.style.width = (Math.ceil(count / iconDivisor) * iconSize).toFixed(0) + "px"; } else { iconDivisor = currentSettings.largeItemsPanel ? 1 : 2; iconSize = currentSettings.largeItemsPanel ? 64 : 32; panel.style.height = (Math.ceil(count / iconDivisor) * iconSize).toFixed(0) + "px"; } _layoutPanels(); }); } ; function doJoinRaid(evt, raid) { var inNewWindow = false; if (evt) { inNewWindow = (evt.button === 1) || !!evt.shiftKey; } if (inNewWindow) { // HACK: Fully resolve the URL var elt = document.createElement("a"); elt.href = "/#quest/assist"; chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href }); } else { window.location.href = "/#quest/assist"; } } ; function findItemInfo(predicate, arg) { if (!mostRecentItems) return false; for (var i = 0, l = mostRecentItems.length; i < l; i++) { var item = mostRecentItems[i]; if (predicate(item, arg)) return item; } return false; } ; function makeLanguageSetter(languageId) { return function (e) { e.preventDefault(); doClientAjax("/setting/save", JSON.stringify({ special_token: null, language_type: String(languageId) }), function (result, error) { if (error) showGamePopup("Failed to set language"); else log("Language set successfully"); }); }; } ; //# sourceMappingURL=sidebar.js.map
変更されたテキスト
ファイルを開く
"use strict"; var raidListUpdateInterval = 30000; var raidListUpdateBackoff = 1350; var raidListUpdateCounter = 25; var statusPanelUpdateIntervalSeconds = 30; var minimumBuffUpdateIntervalSeconds = 70; var currentRaidListUpdateInterval = raidListUpdateInterval; var updateRaidsPanel = null, invalidateRaidList = null, doUpdateRaidsPanel = null, updateItemsPanel = null, invalidateItems = null, doUpdateItemsPanel = null; var updateBuffsWhen = 0, isUpdatingBuffs = false; var queuedRaidClick = null; var pendingRaidUpdate = null; var nextRaidUpdateWhen = null; var menuIconSize = 0; var menuLeftEdge = 0; var subpanelOffset = 0; var mostRecentItems = null; var lastPlayerStatus = null; var statusIntervalH, raidTimerIntervalH; var allBookmarks = {}; function bookmarkNavigate(target, evt) { var inNewWindow = false; if (evt) { inNewWindow = (evt.button === 1) || !!evt.shiftKey; } if (inNewWindow) { // HACK: Fully resolve the URL var elt = document.createElement("a"); elt.href = target; chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href }); } else { chrome.runtime.sendMessage({ type: "setLastLocation", url: target }); window.location.href = target; } } ; function repeatLastQuest(evt, callback) { chrome.runtime.sendMessage({ type: "getRecentQuest" }, function (recentQuestJson) { if (!recentQuestJson) { if (callback) callback(false, "No recent quest to attempt"); else return showBookmarkError("No recent quest to attempt."); } var recentQuest; try { recentQuest = JSON.parse(recentQuestJson); } catch (exc) { if (callback) callback(false, "No recent quest to attempt"); else return showBookmarkError("No recent quest to attempt."); } var parts = splitQuestId(recentQuest.quest_id); var chapterId = parts[0]; var suffix = parts[1]; var itemId = recentQuest.use_item_id; if (itemId) itemId = parseInt(itemId); else itemId = undefined; var data = makeBookmarkCore(chapterId, suffix, recentQuest.quest_type, itemId, recentQuest.prefix); checkQuestStart(data, function (ok, result, reason) { if (ok) { bookmarkNavigate(data.targetUrl, evt); setTimeout(function () { if (callback) callback(true); window.location.reload(); }, 50); } else { if (callback) callback(false, reason); else return showBookmarkError(reason); } }); }); } ; function makeBookmarkCore(chapterId, questSuffix, questType, useItemId, urlPrefix) { var questId = String(chapterId) + String(questSuffix); if (!urlPrefix) { urlPrefix = "/#quest"; } var targetUrl = urlPrefix + "/supporter/" + questId + "/" + questType; if (useItemId) targetUrl += "/0/" + useItemId; var infoUrl = "/quest/treasure_raid/" + chapterId + "/" + questId; // FIXME: The /1/ here is the raid type var checkStartUrl = "/quest/check_quest_start/" + chapterId + "/1/" + questId; return { chapterId: chapterId, questId: questId, targetUrl: targetUrl, infoUrl: infoUrl, checkStartUrl: checkStartUrl }; } ; function showBookmarkError(message, extra) { showGamePopup({ title: "Bookmark", body: message + (extra ? "<br>" + String(extra) : "") }); } ; function startRaid(data, evt) { log("Starting raid", data.targetUrl); bookmarkNavigate(data.targetUrl, evt); } ; function checkQuestStart_old(data, onSuccess) { checkQuestStart(data, function (ok, eligibility, reason) { if (ok) onSuccess(data, eligibility); else showBookmarkError(reason); }); } function checkQuestStart(data, callback) { log("Checking eligibility", data.checkStartUrl); doClientAjax(data.checkStartUrl, function (eligibility, error) { if (!eligibility) return showBookmarkError("Failed to get information from server", error); switch (eligibility.result) { case "ok": callback(true, eligibility); return; case "error_cnt": callback(false, eligibility, "You have already attempted this raid the maximum number of times today."); return; case "other_quest_progress": callback(false, eligibility, "You cannot start this raid because another quest is in progress."); return; case "error_level": callback(false, eligibility, "Your rank is too low to start this raid."); return; default: try { var blob = JSON.parse(eligibility); if (blob.popup && blob.popup.body) { callback(false, eligibility, blob.popup.body); return; } } catch (exc) { callback(false, eligibility, "Unknown error"); } } }); } ; function makeRaidBookmark(chapterId, questSuffix) { var data = makeBookmarkCore(chapterId, questSuffix, 1); return function (evt) { checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }; } ; function getRaidInfo(data, onSuccess) { log("Requesting raid info", data.infoUrl); doClientAjax(data.infoUrl, function (raidInfo, error) { if (!raidInfo) return showBookmarkError("Failed to get information from server", error); onSuccess(data, raidInfo); }); } ; function makeTreasureRaidBookmark(chapterId, questSuffix, itemId) { var data = makeBookmarkCore(chapterId, questSuffix, 1, itemId); return function (evt) { getRaidInfo(data, function (data, raidInfo) { var treasureIndex = raidInfo.treasure_id.indexOf(String(itemId)); if (treasureIndex < 0) return showBookmarkError("Item not found in raid info"); var itemsNeeded = parseInt(raidInfo.consume[treasureIndex]); var itemsHeld = raidInfo.num[treasureIndex]; if (itemsHeld < itemsNeeded) return showBookmarkError(raidInfo.chapter_name + " requires " + itemsNeeded + " of " + raidInfo.treasure_name[treasureIndex] + ", but you only have " + itemsHeld); checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }); }; /* { "chapter_id":"30005", "quest_id":"300051", "type":"1", "action_point":"50", "chapter_name":"Tiamat Omega Showdown", "consume":["3"], "level":30, "treasure_id":["18"], "treasure_image_id":["18"], "treasure_name":["Tiamat Omega Anima"], "num":[26], "raid_name":"Lvl 50 Tiamat Omega", "limit":90 } */ } ; function visitCurrentEvent(evt, tail) { chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) { if (!currentEvent) showGamePopup({ title: "Error", body: "No event stored. Try visiting the main page." }); else if (tail) bookmarkNavigate("/#" + currentEvent + tail, evt); else bookmarkNavigate("/#" + currentEvent, evt); }); } ; function makeGuildWarBookmark(tail) { return function (evt) { bookmarkNavigate("/#event/" + guildWarName + (tail || ""), evt); }; } ; function makeGuildWarRaidBookmark(chapterId, questSuffix, checkItem) { var data = makeBookmarkCore(chapterId, questSuffix, 1); var checkItemFn, checkStartFn, visitSupporterPageFn, checkMultiStart; checkItemFn = function (evt, onComplete) { if (window.location.href.indexOf("event/" + guildWarName) < 0) { if (onComplete) onComplete(false); return bookmarkNavigate("#event/" + guildWarName, evt); } data.targetUrl = data.targetUrl.replace("#quest/", "#event/" + guildWarName + "/") + "/0"; var checkUrl = "/" + guildWarName + "/rest/top/check_item/" + data.questId; doClientAjax(checkUrl, function (checkResult) { if (checkResult && checkResult.result) return checkStartFn(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You do not have the necessary items to start this quest."); } }); }; checkStartFn = function (evt, onComplete) { checkQuestStart_old(data, function (data, eligibility) { if (eligibility.result === "ok") checkMultiStart(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You are not eligible to start this quest. " + eligibility.result); } }); }; checkMultiStart = function (evt, onComplete) { var checkUrl = "/quest/check_multi_start"; doClientAjax(checkUrl, JSON.stringify({ quest_id: parseInt(data.questId) }), function (checkResult) { if (checkResult && checkResult.result === "ok") return visitSupporterPageFn(evt, onComplete); else { if (onComplete) onComplete(false); return showBookmarkError("You cannot start a raid."); } }); }; visitSupporterPageFn = function (evt, onComplete) { if (window.location.href.indexOf("event/" + guildWarName) < 0) { if (onComplete) onComplete(false); return bookmarkNavigate("#event/" + guildWarName, evt); } else { if (onComplete) onComplete(true); startRaid(data, evt); } }; if (!checkItem) return visitSupporterPageFn; return checkItemFn; } ; function makeEventTreasureRaidBookmark(chapterId, questSuffix) { return function (evt) { chrome.runtime.sendMessage({ type: "getCurrentEvent" }, function (currentEvent) { if (!currentEvent) showGamePopup({ title: "Error", body: "No event stored. Try visiting the main page." }); var data = makeBookmarkCore(chapterId, questSuffix, 1); data.targetUrl = data.targetUrl.replace("#quest/", "#" + currentEvent + "/"); checkQuestStart_old(data, function (data, eligibility) { startRaid(data, evt); }); }); }; } ; var guildWarName = null; var guildWarSubmenu = { "guild-war-home": makeGuildWarBookmark(), "guild-war-gacha": makeGuildWarBookmark("/gacha/index"), "guild-war-reward": makeGuildWarBookmark("/reward"), //"guild-war-eye-vh": makeGuildWarRaidBookmark(71863, 1, false), "guild-war-dog-vh": makeGuildWarRaidBookmark(72214, 1, false), "guild-war-dog-ex": makeGuildWarRaidBookmark(72215, 1, false), "guild-war-dog-ex-plus": makeGuildWarRaidBookmark(72216, 1, false), "guild-war-hell-90": makeGuildWarRaidBookmark(72217, 1, true), "guild-war-hell-95": makeGuildWarRaidBookmark(72218, 1, true), }; var menuItems = { "home": "/#mypage", "party": "/#party/index/0/npc/0", "mystuff": { "inventory": "/#list", "stash": "/#container", "crate": "/#present", "supplies": "/#item", }, "quest": { "quest-all": "/#quest/index", "quest-special": "/#quest/extra", "join-raid": "/#quest/assist", "event": visitCurrentEvent, "trial-battles": "/#trial_battle", "pending-raids": "/#quest/assist/unclaimed", }, "quest-repeat": repeatLastQuest, // "guild-war": guildWarSubmenu, "hard-raids": { "hard-tia": makeRaidBookmark(30004, 1), "hard-colo": makeRaidBookmark(30009, 1), "hard-levi": makeRaidBookmark(30015, 1), "hard-yugu": makeRaidBookmark(30019, 1), "hard-chev": makeRaidBookmark(30022, 1), "hard-cel": makeRaidBookmark(30025, 1) }, "magna-raids": { "magna-tia": makeTreasureRaidBookmark(30005, 1, 18), "magna-colo": makeTreasureRaidBookmark(30010, 1, 19), "magna-levi": makeTreasureRaidBookmark(30016, 1, 20), "magna-yugu": makeTreasureRaidBookmark(30026, 1, 21), "magna-chev": makeTreasureRaidBookmark(30027, 1, 26), "magna-cel": makeTreasureRaidBookmark(30028, 1, 31) }, "hl-raids": { "hl-tia": makeTreasureRaidBookmark(30044, 1, 32), "hl-colo": makeTreasureRaidBookmark(30049, 1, 47), "hl-levi": makeTreasureRaidBookmark(30051, 1, 48), "hl-yugu": makeTreasureRaidBookmark(30053, 1, 49), "hl-chev": makeTreasureRaidBookmark(30056, 1, 50), "hl-cel": makeTreasureRaidBookmark(30058, 1, 51), "hl-rosequeen": makeTreasureRaidBookmark(30047, 1, 1204), }, "primal-raids": { "nataku": makeTreasureRaidBookmark(30042, 1, 1343), "flame-glass": makeTreasureRaidBookmark(30041, 1, 1313), "macula-marius": makeTreasureRaidBookmark(30038, 1, 1323), "athena": makeTreasureRaidBookmark(30107, 1, 1313), "medusa": makeTreasureRaidBookmark(30039, 1, 1333), "apollo": makeTreasureRaidBookmark(30043, 1, 1353), "olivia": makeTreasureRaidBookmark(30040, 1, 1363), "odin": makeTreasureRaidBookmark(30046, 1, 1353), }, "coop": { "coop": "/#coopraid", // This makes it impossible to return to an existing room // "coop-host": "/#coopraid/room/entry", "coop-join": "/#coopraid/offer", "coop-shop": "/#coopraid/lineup" }, "me": { "profile": "/#profile", "crew": "/#guild", "friends": "/#friend", "trophies": "/#title" }, "shop": { "shop-mobacoins": "#shop/moba/0", "shop-crystals": "#shop/lupi/0", "shop-points": "/#shop/exchange/points", "shop-trajectory": "#shop/exchange/trajectory", "shop-moon": "#shop/exchange/moon", "shop-treasure": "#shop/exchange/list", "shop-whale-tears": "#shop/exchange/ceiling", "shop-weapon-series": "#archaic", }, "casino": { "poker": "/#casino/list/poker", "bingo": "/#casino/list/bingo", "casino-shop": "/#casino/exchange" }, }; var viramateMenuItems = { "settings": function () { var loc = chrome.extension.getURL("src/options_custom/index.html"); var w = window.open(loc); }, "update-notes": function () { var loc = chrome.extension.getURL("content/changelog.html"); var w = window.open(loc); } }; function isHorizontalLayout() { return (isMobileSite() || !!currentSettings.horizontalBookmarks || !!document.getElementById("gree-game-container")); } ; function makeMenuHandler(name, value, tryCloseMenu) { var result; if (typeof (value) === "string") result = function (evt) { if (evt) { evt.preventDefault(); evt.stopPropagation(); } tryCloseMenu(); bookmarkNavigate(value, evt); }; else if (value && value.call && value.apply) result = function (evt) { if (evt) { evt.preventDefault(); evt.stopPropagation(); } tryCloseMenu(); value(evt); }; else return null; allBookmarks[name] = result; return result; } ; function _updateIconSize(menuIcon) { if (isHorizontalLayout()) menuIcon.style.left = menuLeftEdge.toFixed(0) + "px"; else menuIcon.style.left = "-6px"; var iconRect = menuIcon.getBoundingClientRect(); if (isHorizontalLayout()) menuIconSize = iconRect.width * getEffectiveZoom(menuIcon) * getEffectiveZoom(document.documentElement); else menuIconSize = iconRect.height * getEffectiveZoom(menuIcon); } ; function getColorForMenuItem(key) { switch (key) { case "hard-raids": return "#efc0ba"; case "magna-raids": return "#e8e8f1"; case "hl-raids": return "#efe0ba"; } var dashPos = key.lastIndexOf("-"); var suffix = key.substr(dashPos + 1); switch (suffix) { case "tia": return "#bfefbf"; case "yugu": return "#efdfa0"; case "colo": return "#efbfbf"; case "levi": return "#bfcfef"; case "cel": return "#d890df"; } return null; } ; function showViraButton() { if (isShutdown) return; injectStylesheet("sidebar-shadow.css", getUiContainer()); var outImg = getResourceUrl('vira-small-smile.png'); var overImg = getResourceUrl('vira-small.png'); var isCustomIcon = false; try { if (currentSettings.bookmarksInactiveIcon) outImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksInactiveIcon); if (currentSettings.bookmarksActiveIcon) overImg = encoding.Base64.stringToImageURL(currentSettings.bookmarksActiveIcon); isCustomIcon = (currentSettings.bookmarksActiveIcon || currentSettings.bookmarksInactiveIcon); } catch (exc) { log("Error decoding custom bookmarks icons", exc); } var menuIcon = document.createElement("div"); var mainMenu = document.createElement("div"); menuIcon.className = "viramate-menu-icon"; // HACK: Why is this necessary? menuIcon.style.backgroundRepeat = "no-repeat"; menuIcon.style.backgroundImage = "url(" + outImg + ")"; menuIcon.setAttribute("title", "Viramate"); var maxIconWidth = isCustomIcon ? 64 : 56; // HACK: :after selectors don't work on img. html sucks. var tempImage = document.createElement("img"); tempImage.style.opacity = "0.0"; tempImage.onload = function () { var scale = 1.0; if (tempImage.naturalWidth > maxIconWidth) scale = maxIconWidth / tempImage.naturalWidth; menuIcon.style.width = (tempImage.naturalWidth * scale).toFixed(0) + "px"; menuIcon.style.height = (tempImage.naturalHeight * scale).toFixed(0) + "px"; uninjectElement(getUiContainer(), tempImage); _updateIconSize(menuIcon); _layoutPanels(); }; tempImage.src = outImg; injectElement(getUiContainer(), tempImage); var paddingSize = 100; if (typeof (currentSettings.bookmarksIconPadding) === "number") paddingSize = currentSettings.bookmarksIconPadding; if (isHorizontalLayout()) { menuIcon.style.paddingRight = Math.max(paddingSize - 12, 0).toFixed(0) + "px"; } else { menuIcon.style.paddingBottom = Math.max(paddingSize - 12, 0).toFixed(0) + "px"; } mainMenu.className = "viramate-menu"; if (typeof (currentSettings.bookmarksSize) === "number") menuIcon.style.transform = "scale(" + currentSettings.bookmarksSize.toFixed(1) + ")"; if (typeof (currentSettings.bookmarksMenuSize) === "number") mainMenu.style.transform = "scale(" + currentSettings.bookmarksMenuSize.toFixed(1) + ")"; // mainMenu.style.zoom = menuIcon.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); var mouseIsOverIcon = false; var mouseIsOverMenu = 0; var mouseIsOverSubmenu = 0; var menuIsVisible = false; var allMenus = [mainMenu]; var updateTimeout = 0; var autoOpenDelay = isHorizontalLayout() ? 260 : 160; var autoCloseDelay = currentSettings.openBookmarksOnClick ? 500 : 250; var pamrklamr = function () { return 5 * 1000 + (Math.random() * 1600 * 1000); }; var fmajrlialmsk; fmajrlialmsk = function () { if (isShutdown) return; if (isCustomIcon) return; if (!menuIsVisible) { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")"; window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/qw3mkl/vqprlm.png') + ")"; }, 60); window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + getResourceUrl('hfgk/askpmr/vxgkql.png') + ")"; }, 950); window.setTimeout(function () { menuIcon.style.backgroundImage = "url(" + outImg + ")"; }, 1060); } window.setTimeout(fmajrlialmsk, pamrklamr()); }; window.setTimeout(fmajrlialmsk, pamrklamr()); var showMenu = function (menu) { if (menu.className.indexOf("viramate-menu") === 0) menu.style.left = menuLeftEdge.toFixed(0) + "px"; else menu.style.left = "0px"; menu.style.opacity = "1.0"; menu.style.pointerEvents = "all"; menuIsVisible = true; }; var showMenus = function () { menuIcon.style.backgroundImage = "url(" + overImg + ")"; if (menuIcon.className.indexOf("open") < 0) menuIcon.className += " open"; for (var i = 0; i < allMenus.length; i++) { var elt = allMenus[i]; showMenu(elt); } }; var hideMenu = function (menu) { if (!isMobileSite()) { if (menu.className.indexOf("viramate-menu") === 0) menu.style.left = (menuLeftEdge - 32).toFixed(0) + "px"; else menu.style.left = "-32px"; } menu.style.opacity = "0.0"; menu.style.pointerEvents = "none"; menuIsVisible = false; }; var hideMenus = function () { menuIcon.style.backgroundImage = "url(" + outImg + ")"; menuIcon.className = menuIcon.className.replace(" open", ""); closeSubmenus(); hideMenu(allMenus[0]); }; var closeSubmenus = function () { // Hide any other open submenus for (var i = 1; i < allMenus.length; i++) { var submenu = allMenus[i]; if (submenu.owner) submenu.owner.className = submenu.owner.className.replace(" open", ""); hideMenu(submenu); } // Pop them off the list allMenus.length = 1; }; var openSubmenu = function (owner, submenu) { owner.className += " open"; submenu.owner = owner; closeSubmenus(); allMenus.push(submenu); showMenus(); }; var updateMenu = function () { if (isShutdown) return; if (mouseIsOverIcon || (mouseIsOverMenu > 0)) { if (mouseIsOverSubmenu <= 0) closeSubmenus(); showMenus(); } else hideMenus(); }; var scheduleUpdate = function (fast) { if (updateTimeout) window.clearTimeout(updateTimeout); updateTimeout = window.setTimeout(updateMenu, fast ? autoOpenDelay : autoCloseDelay); }; var makeSubmenuOverHandler = function (item, submenu) { return function (evt) { mouseIsOverSubmenu += 1; openSubmenu(item, submenu); }; }; var makeSubmenuOutHandler = function (item, submenu) { return function (evt) { mouseIsOverSubmenu -= 1; // TODO: Anything? scheduleUpdate(); }; }; var tryCloseMenu = function () { hideMenus(); window.clearTimeout(updateTimeout); }; menuIcon.addEventListener("click", function () { showMenus(); }, false); menuIcon.addEventListener("mouseover", function () { mouseIsOverIcon = true; if (!isMobileSite() && (currentSettings.openBookmarksOnClick !== true)) scheduleUpdate(true); }, false); menuIcon.addEventListener("mouseout", function () { mouseIsOverIcon = false; scheduleUpdate(); }, false); mainMenu.addEventListener("mouseover", function () { mouseIsOverMenu += 1; }, false); mainMenu.addEventListener("mouseout", function () { mouseIsOverMenu -= 1; scheduleUpdate(); }, false); var isGuildWar = currentSettings.currentGuildWar && (currentSettings.currentGuildWar.indexOf("event/teamraid") === 0); if (isGuildWar) guildWarName = currentSettings.currentGuildWar.replace("event/", ""); allBookmarks = {}; var populateSubmenu; populateSubmenu = function (container, items, isSubmenu, extraClassNames) { if (isSubmenu) { if (Object.keys(items).length > 4) container.style.columnCount = "2"; } for (var k in items) { if (!items.hasOwnProperty(k)) continue; var v = items[k]; // HACK: Only show guild war submenu during guild war if ((v === guildWarSubmenu) && !isGuildWar) continue; var elt = document.createElement("li"); elt.className = "viramate-menu-item"; if (extraClassNames) elt.className += " " + extraClassNames; elt.setAttribute("key", k); var label = i18n.get("m-" + k); elt.textContent = label; var color = getColorForMenuItem(k); if (color) elt.style.color = color; if (v && (typeof (v) === "object")) { // Submenu elt.className += " has-submenu"; var submenu = document.createElement("ul"); submenu.className = "viramate-submenu"; submenu.addEventListener("mouseover", function () { mouseIsOverSubmenu += 1; }, false); submenu.addEventListener("mouseout", function () { mouseIsOverSubmenu -= 1; scheduleUpdate(); }, false); elt.addEventListener("mouseover", makeSubmenuOverHandler(elt, submenu), false); elt.addEventListener("mouseout", makeSubmenuOutHandler(elt, submenu), false); hideMenu(submenu); populateSubmenu(submenu, v, true); container.appendChild(submenu); } else { // Item elt.addEventListener("mouseup", makeMenuHandler(k, v, tryCloseMenu), true); elt.addEventListener("tap", makeMenuHandler(k, v, tryCloseMenu), false); } container.appendChild(elt); } ; }; var ul = document.createElement("ul"); mainMenu.appendChild(ul); populateSubmenu(ul, menuItems, false); var langSelectorEn = document.createElement("li"); var langSelectorJp = document.createElement("li"); langSelectorEn.className = "language-menu-item en"; langSelectorJp.className = "language-menu-item jp"; langSelectorEn.textContent = "English"; langSelectorJp.textContent = "日本語"; langSelectorEn.title = langSelectorJp.title = i18n.get("m-set-language"); langSelectorEn.addEventListener("click", makeLanguageSetter(2), true); langSelectorJp.addEventListener("click", makeLanguageSetter(1), true); ul.appendChild(langSelectorEn); ul.appendChild(langSelectorJp); /* var showPopoutItem = document.createElement("li"); showPopoutItem.className = "viramate-menu-item"; showPopoutItem.textContent = "Open popout"; showPopoutItem.addEventListener("click", showPopout, true); ul.appendChild(showPopoutItem); */ var versionText = document.createElement("span"); versionText.className = "viramate-version"; ul.appendChild(versionText); populateSubmenu(ul, viramateMenuItems, false, "small"); hideMenus(); if (isHorizontalLayout()) { menuIcon.className += " horizontal"; mainMenu.className += " horizontal"; var trySpawn = function () { if (isShutdown) return true; var gameContainer = getGameContainer(); var wrapper = gameContainer.querySelector(".wrapper"); if (!gameContainer || !wrapper) return false; var effectiveZoom = getEffectiveZoom(gameContainer); var documentZoom = getEffectiveZoom(document.documentElement); menuLeftEdge = parseFloat(wrapper.parentNode.getAttribute("data-show-menubar-width")) || 0; var effectiveSidebarHeight = 48; if (isMobileSite()) { effectiveSidebarHeight /= documentZoom; getOverlayContainer().style.zoom = (1 / documentZoom).toFixed(3); } wrapper.style.marginTop = (effectiveSidebarHeight / effectiveZoom).toFixed(0) + "px"; return true; }; if (!trySpawn()) window.setTimeout(trySpawn, 500); } injectElement(getUiContainer(), menuIcon); injectElement(getUiContainer(), mainMenu); chrome.runtime.sendMessage({ type: "getVersion" }, function (version) { var text = "Viramate " + version; if (isMobileSite()) text += " (mobile)"; versionText.textContent = text; }); window.setTimeout(function () { if (isShutdown) return; _updateIconSize(menuIcon); getUserIdAndTabIdAsync(showStatusPanel); }, 25); } ; var primeHaloRequestIsPending = false; var primeHaloStartsWhen = null, primeHaloStartsWhenText = null; var needHaloPanelLayout = false; function navigateToExtraQuests() { window.location.href = "/#quest/extra"; } ; function updateClock(element) { var jstHourMinute = { timeZone: "Asia/Tokyo", hour12: false, hour: "2-digit", minute: "2-digit" }; var text = new Date().toLocaleString("ja-JP", jstHourMinute) + " JST"; var timeText = element.time; if (!timeText) { element.time = timeText = document.createElement("span"); element.appendChild(timeText); } var c = (currentSettings.clockBrightness * 255).toFixed(0); var ct = "rgb(" + c + ", " + c + ", " + c + ")"; timeText.style.color = ct; timeText.textContent = text; /* var haloText = element.halo; if (!haloText) { element.appendChild(document.createElement("br")); element.halo = haloText = document.createElement("span"); haloText.className = "halo-timer"; element.appendChild(haloText); haloText.addEventListener("click", navigateToExtraQuests, false); } if (primeHaloStartsWhen) { var now = Date.now(); if (!primeHaloStartsWhenText) { var temp = new Date(primeHaloStartsWhen); primeHaloStartsWhenText = temp.toLocaleString("ja-JP", jstHourMinute); } if (primeHaloStartsWhen < now) { // Prime halo is active c = (currentSettings.clockBrightness * 255).toFixed(0); var c2 = (currentSettings.clockBrightness * 210).toFixed(0); haloText.textContent = "\u2605 Halo" haloText.style.color = "rgb(" + c + ", " + c + ", " + c2 + ")"; haloText.style.fontWeight = "bold"; } else { // Prime halo starts soon c = (currentSettings.clockBrightness * 220).toFixed(0); haloText.textContent = "\u2605H " + primeHaloStartsWhenText; haloText.style.color = "rgb(" + c + ", " + c + ", " + c + ")"; haloText.style.fontWeight = "normal"; } } else { haloText.textContent = ""; } */ if (needHaloPanelLayout) { _layoutPanels(); needHaloPanelLayout = false; } } ; function showStatusPanel(uid) { var panel = document.createElement("div"); panel.className = "viramate-status-panel"; // panel.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); var clock = null; if (currentSettings.clockBrightness >= 0.05) { clock = document.createElement("span"); clock.className = "time"; panel.appendChild(clock); } if (currentSettings.statusPanel) { var meters = document.createElement("div"); meters.className = "meters"; var createMeter = function (name, withShadow) { var meter = document.createElement("div"); meter.className = "meter " + name + "-meter"; meter.title = name.toUpperCase(); var fill = document.createElement("div"); fill.className = "fill"; meter.fill = fill; meter.appendChild(fill); if (withShadow) { var shadow = document.createElement("div"); shadow.className = "fill shadow"; meter.shadow = shadow; meter.appendChild(shadow); } panel[name + "Meter"] = meter; meters.appendChild(meter); }; panel.appendChild(meters); createMeter("rp", false); createMeter("ap", true); createMeter("bp", true); if (currentSettings.statusPanelBuffs) { var buffsPanel = panel.buffs = document.createElement("div"); buffsPanel.className = "buffs"; panel.appendChild(buffsPanel); } } if (currentSettings.itemsPanel) { var itemsPanel = panel.items = document.createElement("div"); itemsPanel.className = "items"; if (currentSettings.largeItemsPanel) itemsPanel.className += " large-items"; panel.appendChild(itemsPanel); } if (clock) window.setInterval(function () { updateClock(clock); }, 1000); if (isHorizontalLayout()) panel.className += " horizontal"; injectElement(getUiContainer(), panel); if (currentSettings.raidsPanel) showRaidsPanel(uid); _layoutPanels(); invalidateStatus = function () { chrome.runtime.sendMessage({ type: "invalidateStatus", uid: uid }); }; if (currentSettings.itemsPanel) { invalidateItems = function (items) { _invalidateItems(panel, uid, items); }; updateItemsPanel = function () { _updateItemsPanel(panel, uid); }; doUpdateItemsPanel = function (items) { _doUpdateItemsPanel(panel, uid, items); }; } if (currentSettings.statusPanel) { updateStatusPanel = function (force, lazy) { if (isCombatPage(window.location.hash)) return; else if (window.location.hash.indexOf("result_") >= 0) return; else if (window.location.hash.indexOf("coopraid/room") >= 0) return; _updateStatusPanel(panel, uid, force, lazy); }; doUpdateStatusPanel = function (status) { _doUpdateStatusPanel(panel, status); }; doUpdateGuildSupportBuffs = function (buffs) { _doUpdateGuildSupportBuffs(panel, uid, buffs); }; doUpdatePersonalSupportBuffs = function (buffs) { _doUpdatePersonalSupportBuffs(panel, uid, buffs); }; invalidateSupportBuffs = function () { _invalidateSupportBuffs(panel, uid); }; var lazyUpdate = function () { if (isShutdown) { window.clearInterval(statusIntervalH); return; } updateStatusPanel(false, true); }; statusIntervalH = window.setInterval(lazyUpdate, statusPanelUpdateIntervalSeconds * 1000); // HACK: We need to delay this a bit so the page can finish loading window.setTimeout(lazyUpdate, 1250); } _layoutPanels(); } ; function _layoutPanels() { var uic = getUiContainer(); var statusPanel = uic.querySelector("div.viramate-status-panel"); var raidsPanel = uic.querySelector("div.viramate-raids-panel"); if (!statusPanel) return; if (isHorizontalLayout()) { subpanelOffset = menuIconSize + 4; statusPanel.style.left = (menuLeftEdge).toFixed(0) + "px"; statusPanel.style.paddingLeft = subpanelOffset.toFixed(0) + "px"; var meters = statusPanel.querySelector("div.meters"); var buffs = statusPanel.querySelector("div.buffs"); var itempanels = statusPanel.querySelectorAll("div.items"); if (meters) { meters.style.left = (subpanelOffset + 64).toFixed(0) + "px"; } if (buffs) { buffs.style.left = (subpanelOffset + 128 + 4).toFixed(0) + "px"; } if (itempanels) { var offset = subpanelOffset + 128 + 4; if (buffs){ offset+=(buffs.clientWidth + 4); } var runningtotal = offset; for (var i = 0; i<itempanels.length; i++) { itempanels[i].style.left = runningtotal.toFixed(0) + "px"; runningtotal += parseInt(itempanels[i].style.width,10); } } if (raidsPanel) { var bw = 0, iw = 0; if (buffs) bw = buffs.clientWidth; if (itempanels) var iw; for(var i=0; i<itempanels.length; i++){ iw+=(itempanels[i].clientWidth); } //iw-=4; //put raid panel flush against itemspanels if (bw) bw += 2; if (iw) iw += 2; if (buffs) { //console.log("buffs"); raidsPanel.style.left = (128 + bw + iw + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; } else if (meters){ //console.log("meters"); raidsPanel.style.left = (128 + iw + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; } else { //console.log("other"); raidsPanel.style.left = (64 + iw + menuLeftEdge + subpanelOffset + 8).toFixed(0) + "px"; } } } else { subpanelOffset = menuIconSize + 12; statusPanel.style.top = subpanelOffset.toFixed(0) + "px"; if (raidsPanel) raidsPanel.style.top = (statusPanel.clientHeight + subpanelOffset).toFixed(0) + "px"; var itempanels = statusPanel.querySelectorAll("div.items"); if (itempanels) { for (var i = 0; i<itempanels.length; i++) { } } } } ; function _roundDown(value, decimals) { var mult = Math.pow(10, decimals); value *= mult; value = Math.floor(value); value /= mult; return value.toFixed(decimals); } ; function _setWidth(elt, fraction) { if (fraction < 0) fraction = 0; else if (fraction > 1) fraction = 1; var newWidth = (fraction * 100).toFixed(2) + "%"; if (elt.style.width !== newWidth) elt.style.width = newWidth; } ; function _invalidateSupportBuffs(panel, uid) { var msg = { type: "invalidateBuffs", uid: uid }; chrome.runtime.sendMessage(msg); updateBuffsWhen = Date.now() + 2000; } ; function _doUpdatePersonalSupportBuffs(panel, uid, buffs) { if (isShutdown) return; var msg = { type: "updatePersonalBuffs", uid: uid, buffs: buffs }; chrome.runtime.sendMessage(msg); window.setTimeout(function () { _updateStatusPanel(panel, uid, false, true); }, 1000); } ; function _doUpdateGuildSupportBuffs(panel, uid, buffs) { if (isShutdown) return; var msg = { type: "updateGuildBuffs", uid: uid, buffs: buffs }; chrome.runtime.sendMessage(msg); window.setTimeout(function () { _updateStatusPanel(panel, uid, false, true); }, 1000); } ; function _doUpdateStatusPanel(panel, status) { lastPlayerStatus = status; var ap = status._precise_ap; var bp = status._precise_bp; panel.apMeter.setAttribute("text", _roundDown(ap, 1)); _setWidth(panel.apMeter.fill, Math.floor(ap) / parseInt(status.max_action_point)); _setWidth(panel.apMeter.shadow, ap / parseInt(status.max_action_point)); panel.bpMeter.setAttribute("text", _roundDown(bp, 0)); _setWidth(panel.bpMeter.fill, Math.floor(bp) / parseInt(status.max_battle_point)); _setWidth(panel.bpMeter.shadow, bp / parseInt(status.max_battle_point)); panel.rpMeter.setAttribute("text", status.levelGauge); panel.rpMeter.fill.style.width = status.levelGauge; if (currentSettings.statusPanelBuffs) _doUpdateBuffsPanel(panel, status); _layoutPanels(); } ; function _doUpdateBuffsPanel(panel, status) { var buffsPanel = panel.buffs; buffsPanel.textContent = ""; var buffs = status.buffs; if (!buffs || !buffs.length) return; var x = 0, y = 0; var count = 0; var nextBuffUpdateMinutes = null; for (var i = 0, l = buffs.length; i < l; i++) { var buff = buffs[i]; var elt = document.createElement("div"); elt.className = "viramate-buff"; elt.style.backgroundImage = "url('" + buff.imageUrl + "')"; elt.style.left = x.toFixed(0) + "px"; elt.style.top = y.toFixed(0) + "px"; var minutesLeft = ((buff.timeRemaining / 1000) / 60); if (nextBuffUpdateMinutes === null) nextBuffUpdateMinutes = minutesLeft; else nextBuffUpdateMinutes = Math.min(minutesLeft, nextBuffUpdateMinutes); if (minutesLeft < 90) elt.setAttribute("remaining", minutesLeft.toFixed(0)); else if (currentSettings.statusPanelExpiringBuffs) continue; if (minutesLeft > 60) { elt.title = buff.comment + " - " + (minutesLeft / 60).toFixed(1) + " hour(s) remaining"; } else { elt.title = buff.comment + " - " + minutesLeft.toFixed(0) + " minute(s) remaining"; } if (isHorizontalLayout()) { if (y >= 24) { y = 0; x += 24; } else { y += 24; } } else { if (x >= 32) { x = 0; y += 32; } else { x += 32; } } count++; buffsPanel.appendChild(elt); } if (nextBuffUpdateMinutes) { updateBuffsWhen = Math.max(updateBuffsWhen, Date.now() + ((nextBuffUpdateMinutes * 60 * 1000) + (59 * 1000))); var nextUpdateSeconds = (updateBuffsWhen - Date.now()) / 1000; if (nextUpdateSeconds <= 120) log("Updating buffs in " + nextUpdateSeconds.toFixed(0) + " second(s)"); } if (isHorizontalLayout()) { buffsPanel.style.width = (Math.ceil(count / 2) * 24).toFixed(0) + "px"; } else { buffsPanel.style.height = (Math.ceil(count / 2) * 32).toFixed(0) + "px"; } } ; function _maybeRequestBuffsFromServer() { if (!currentSettings.statusPanelBuffs) return; if (isUpdatingBuffs) return; var now = Date.now(); var shouldUpdateBuffs = now > updateBuffsWhen; if (!shouldUpdateBuffs) return; isUpdatingBuffs = true; updateBuffsWhen = now + (minimumBuffUpdateIntervalSeconds * 1000); var updateCounter = 2; doClientAjax("/guild_main/support_all_info/", function () { updateCounter--; if (updateCounter <= 0) isUpdatingBuffs = false; }); doClientAjax("/shop_exchange/activated_personal_supports/", function () { updateCounter--; if (updateCounter <= 0) isUpdatingBuffs = false; }); } ; function _updateStatusPanel(panel, uid, force, lazy) { if (isShutdown) return; var msg = { type: "getStatus", uid: uid, force: !!force, lazy: !!lazy }; chrome.runtime.sendMessage(msg, function (status) { if (status) { _doUpdateStatusPanel(panel, status); _maybeRequestBuffsFromServer(); _updateItemsPanel(panel, uid); } else log("Failed to get status"); }); } ; function showRaidsPanel(uid) { if (isShutdown) return; var panel = document.createElement("div"); panel.className = "viramate-raids-panel"; // panel.style.zoom = (1 / getEffectiveZoom(document.documentElement)).toFixed(2); if (isHorizontalLayout()) panel.className += " horizontal"; var cdt = document.createElement("div"); panel.countdownTimer = cdt; cdt.className = "countdown-timer"; if (isHorizontalLayout()) { cdt.style.height = "0px"; } else { cdt.style.width = "0px"; } injectElement(getUiContainer(), panel); raidTimerIntervalH = window.setInterval(function () { if (isShutdown) { window.clearInterval(raidTimerIntervalH); return; } updateRaidTimer(panel); }, 750); updateRaidsPanel = function () { _updateRaidsPanel(panel, uid, false); }; invalidateRaidList = function (raids) { _invalidateRaidList(panel, uid, raids); }; doUpdateRaidsPanel = function (raids) { _doUpdateRaidsPanel(panel, raids); }; if (!pendingRaidUpdate) window.setTimeout(updateRaidsPanel, 1000); } ; function maybeScheduleNextRaidUpdate(panel) { if (isShutdown) return; if (pendingRaidUpdate) { updateRaidTimer(panel); return; } nextRaidUpdateWhen = null; if (!lastPlayerStatus) { pendingRaidUpdate = window.setTimeout(updateRaidsPanel, 3000); nextRaidUpdateWhen = Date.now() + 3000; } else if (raidListUpdateCounter-- >= 0) { currentRaidListUpdateInterval += raidListUpdateBackoff; // console.log("raid list update; next in " + (currentRaidListUpdateInterval / 1000).toFixed(1) + "s"); pendingRaidUpdate = window.setTimeout(updateRaidsPanel, currentRaidListUpdateInterval); nextRaidUpdateWhen = Date.now() + currentRaidListUpdateInterval; } else { log("raid list updates disabled because player is idle"); _doUpdateRaidsPanel(panel, null); } updateRaidTimer(panel); } ; function shouldShowRaidsPanel() { // return true; return !isCombatPage(window.location.hash) && (window.location.hash.indexOf("#coopraid/room") < 0) && (window.location.hash.indexOf("#result_") < 0) && (window.location.hash.indexOf("quest/supporter") < 0); } ; function updateRaidTimer(panel) { var ct = panel.countdownTimer; var remaining = nextRaidUpdateWhen - Date.now(); if (shouldShowRaidsPanel() && nextRaidUpdateWhen && (raidListUpdateCounter > 0)) { var total = currentRaidListUpdateInterval; var fraction = 1.0 - Math.max(Math.min(remaining / total, 1.0), 0.0); if (isHorizontalLayout()) ct.style.height = (fraction * 44).toFixed(1) + "px"; else ct.style.width = (fraction * 60).toFixed(1) + "px"; ct.title = "Next raid list update in " + (remaining / 1000).toFixed(1) + " second(s)"; } else { if (isHorizontalLayout()) ct.style.height = "0px"; else ct.style.width = "0px"; } } ; function isJoined(raid) { return raid["data-raid-type"] === 0; } ; function raidJoinHandler(evt) { doJoinRaid(evt, this); evt.preventDefault(); } ; function _doUpdateRaidsPanel(panel, _raids) { if (!panel) return; panel.innerHTML = ""; panel.appendChild(panel.countdownTimer); if (!_raids) { return; } var raids = _raids.assist_raids_data; if (!raids) return; for (var i = 0; i < raids.length; i++) { var raid = raids[i]; if (!raid) continue; var elt = document.createElement("div"); elt.className = "raid"; elt.title = raid.chapter_name; if (isJoined(raid)) elt.className += " joined"; if (raid.boss_image) { var imageUrl = "http://game-a1.granbluefantasy.jp/"; if (i18n.get("lang") === "en") imageUrl += "assets_en"; else imageUrl += "assets"; imageUrl += "/img/sp/assets/summon/qm/" + raid.boss_image + ".jpg"; elt.style.backgroundImage = "url('" + imageUrl + "')"; } else { elt.textContent = raid.chapter_name; } elt.addEventListener("mouseup", raidJoinHandler.bind(raid), false); var gauge = document.createElement("div"); gauge.className = "gauge"; var fill = document.createElement("div"); fill.className = "fill"; fill.style.width = raid.boss_hp_width + "%"; var memberCount = document.createElement("span"); memberCount.className = "member-count"; memberCount.textContent = raid.member_count; gauge.appendChild(fill); elt.appendChild(gauge); elt.appendChild(memberCount); panel.appendChild(elt); } } ; function _updateRaidsPanel(panel, uid, force) { if (isShutdown) return; pendingRaidUpdate = null; maybeScheduleNextRaidUpdate(panel); // HACK if (!shouldShowRaidsPanel()) { _doUpdateRaidsPanel(panel, null); return; } if (!lastPlayerStatus) return; if (currentSettings.raidsPanelBpFilter) { if (lastPlayerStatus && (lastPlayerStatus._precise_bp < 3)) { log("Not updating raids list because player only has " + lastPlayerStatus._precise_bp.toFixed(1) + " BP"); _doUpdateRaidsPanel(panel, null); return; } } var msg = { type: "getRaids", uid: uid, force: !!force }; chrome.runtime.sendMessage(msg, function (raids) { if (raids) _doUpdateRaidsPanel(panel, raids); else log("Failed to get raids"); }); } ; function _invalidateRaidList(panel, uid, raids) { if (!raids || (window.location.hash.indexOf("quest/assist") >= 0)) { if (pendingRaidUpdate) { window.clearTimeout(pendingRaidUpdate); pendingRaidUpdate = null; } raidListUpdateCounter = 45; currentRaidListUpdateInterval = raidListUpdateInterval; maybeScheduleNextRaidUpdate(panel); } var msg = { type: "invalidateRaids", uid: uid, raids: raids }; chrome.runtime.sendMessage(msg); } ; function _invalidateItems(panel, uid, items) { if (isShutdown) return; var msg = { type: "invalidateItems", uid: uid, items: items }; chrome.runtime.sendMessage(msg); if (items) { _doUpdateItemsPanel(panel, uid, items); } else { // HACK window.setTimeout(function () { _updateItemsPanel(panel, uid); }, 2000); } } ; function _updateItemsPanel(panel, uid) { // Only check for items if something is watched. chrome.runtime.sendMessage({ type: "getWatchedItems" }, function (watchedItems) { if (!currentSettings.itemsPanel) return; if (!watchedItems.items || !watchedItems.items.length) return; var msg = { type: "getItems", uid: uid, force: false }; chrome.runtime.sendMessage(msg, function (items) { mostRecentItems = items; _doUpdateItemsPanel(panel, uid, items); }); }); } ; function _doUpdateItemsPanel(_panel, uid, items) { var panels = _panel.querySelectorAll("div.items"); //console.log(panels); var panel = panels[0].cloneNode(true); //prototypical panel panel.textContent = ""; if (!items) items = mostRecentItems; if (!items) { for (var i = 0; i < panels.length; i++) { panels[i].parentNode.removeChild(panels[i]); }; return; } var onWatchedItemIconContextMenu = function (evt) { evt.preventDefault(); }; var onWatchedItemIconMouseUp = function (evt) { evt.preventDefault(); var itemId = parseInt(evt.target.getAttribute("item-id")); var targetCount = parseInt(evt.target.getAttribute("target-count")); switch (evt.button) { case 0: log("Toggling item target count", itemId); var target = -1; if ((targetCount <= 0) || (typeof (targetCount) !== "number") || Number.isNaN(targetCount)) targetCount = parseInt(prompt("Set target number of " + evt.target.title)); else targetCount = -1; if (Number.isNaN(targetCount)) targetCount = -1; chrome.runtime.sendMessage({ type: "setItemWatchTarget", id: itemId, count: targetCount }); break; case 2: log("Removing watch on item", itemId); chrome.runtime.sendMessage({ type: "setItemWatchState", id: itemId, state: false }); break; } if (doUpdateItemsPanel) doUpdateItemsPanel(); }; var onWatchedItemIconDragStart = function (evt) { evt.dataTransfer.setData("text", evt.target.getAttribute("item-id")); }; var allowDrop = function (evt) { evt.preventDefault(); }; var onDroppedOn = function (evt) { evt.preventDefault(); var group = evt.target.getAttribute("group"); var itemId = evt.dataTransfer.getData("text"); if (group != "none"){ chrome.runtime.sendMessage({ type: "setItemGroup", id: itemId, group: group }); } else{ chrome.runtime.sendMessage({ type: "setItemGroup", id: itemId, group: "undefined" }); } doUpdateItemsPanel(); }; chrome.runtime.sendMessage({ type: "getWatchedItems" }, function (obj) { //Get info var watchedItems = obj.items; var targetCounts = obj.counts; var groups = obj.groups; //Remove old panels for (var i = 0; i < panels.length; i++) { panels[i].parentNode.removeChild(panels[i]); }; //Style variables var itemsize; var iconDivisor; if (isHorizontalLayout()){ if (currentSettings.largeItemsPanel) { itemsize = 48; iconDivisor = 1;} else {itemsize = 24; iconDivisor = 2;} } else{ if (currentSettings.largeItemsPanel) { itemsize = 64; iconDivisor = 1;} else {itemsize = 32; iconDivisor = 2;} } var spacing = 8; var borderthickness = 1; //Div styling var defaultPanel = panel.cloneNode(true); defaultPanel.style.marginTop = "0px"; defaultPanel.setAttribute("group", "-1"); defaultPanel.addEventListener("dragover", allowDrop, false); defaultPanel.addEventListener("drop", onDroppedOn, false); var borderdiv = document.createElement('div'); if (isHorizontalLayout()){ borderdiv.style.backgroundColor = "rgb(166,166,166)"; borderdiv.style.height = "38px"; borderdiv.style.width = borderthickness + "px"; borderdiv.style.marginTop = "5px"; borderdiv.style.marginBottom = "5px"; } else{ borderdiv.style.borderTop = borderthickness + "px solid rgb(166,166,166)"; borderdiv.style.marginLeft = "5px"; borderdiv.style.marginRight = "5px"; } var emptyPanel = defaultPanel.cloneNode(true); emptyPanel.setAttribute("group", "none"); emptyPanel.addEventListener("dragover", allowDrop, false); emptyPanel.addEventListener("drop", onDroppedOn, false); if (isHorizontalLayout()){ emptyPanel.style.width = (itemsize + spacing + borderthickness).toFixed(0) + "px"; } else{ emptyPanel.style.height = (itemsize + spacing + borderthickness).toFixed(0) + "px"; } var dropborderdiv = document.createElement("div"); dropborderdiv.style.border = borderthickness + "px dashed rgb(166,166,166)"; dropborderdiv.style.pointerEvents = "none"; if (isHorizontalLayout()) { dropborderdiv.style.margin = "4px"; dropborderdiv.style.position = "absolute"; //these numbers are related to other numbers... dropborderdiv.style.height = (itemsize+spacing+(borderthickness*2)).toFixed(0) + "px"; dropborderdiv.style.width = (itemsize).toFixed(0) + "px"; dropborderdiv.style.top = "0px"; dropborderdiv.style.left = "0px"; } else{ dropborderdiv.style.margin = "3px"; dropborderdiv.style.height = itemsize.toFixed(0) + "px"; } emptyPanel.appendChild(borderdiv.cloneNode(true)); emptyPanel.appendChild(dropborderdiv); //Reorganize groups var itemGroups = { "-1":[], }; for(id in groups){ //groups is actually key/value pairs of ids/groups. Because items can be in groups without being watched, itemGroups which associates group # with an array of ids is constructed here. if (watchedItems.includes(parseInt(id))){ // var group = groups[id]; if(itemGroups.hasOwnProperty(group)){ itemGroups[group].push(id); } else{ itemGroups[group] = [id];} } else{} //Do nothing } //Divs for each group var itemPanels = { "-1": defaultPanel,}; for(id in itemGroups){ var group = id; var groupPanel = defaultPanel.cloneNode(true); groupPanel.setAttribute("group", group); groupPanel.addEventListener("dragover", allowDrop, false); groupPanel.addEventListener("drop", onDroppedOn, false); itemPanels[group] = groupPanel; } //Add any item not in a group to the default group for (i = 0; i < watchedItems.length; i++){ var id = watchedItems[i]; if (!(id in groups)){ itemGroups[-1].push(id); } } //Fill each panel with its items var iconSize; for (var groupnumber in itemGroups) { itemPanels[groupnumber].appendChild(borderdiv.cloneNode(true)); var x = 0, y = 0; var count = 0; for (var i = 0, l = itemGroups[groupnumber].length; i < l; i++) { var itemInfo = findItemInfo(function (item, id) { return item.item_id == id; }, itemGroups[groupnumber][i]); if (!itemInfo) continue; var elt = document.createElement("div"); elt.className = "viramate-item"; elt.style.backgroundImage = "url('http://game-a.granbluefantasy.jp/assets_en/" + "img/sp/assets/item/article/s/" + itemInfo.image + ".jpg')"; if (isHorizontalLayout()){ elt.style.left = x + (spacing/2) + borderthickness + "px"; elt.style.top = y.toFixed(0) + "px"; } else{ elt.style.left = x.toFixed(0) + "px"; elt.style.top = y + (spacing/2) + borderthickness + "px"; } elt.title = itemInfo.name + " (Left-click to set goal, right-click to hide, drag to group)"; elt.setAttribute('draggable', true); elt.setAttribute("item-id", itemInfo.item_id); elt.setAttribute("group", groupnumber); elt.addEventListener("contextmenu", onWatchedItemIconContextMenu, false); elt.addEventListener("mouseup", onWatchedItemIconMouseUp, false); elt.addEventListener("dragstart", onWatchedItemIconDragStart, false); elt.addEventListener("dragover", allowDrop, false); elt.addEventListener("drop", onDroppedOn, false); var targetCount = targetCounts[itemInfo.item_id] || -1; var remaining = targetCount - itemInfo.number; if (targetCount > 0) elt.setAttribute("target-count", targetCount); if ((remaining > 0) && (targetCount > 0)) { elt.setAttribute("count", "-" + remaining); } else { elt.setAttribute("count", itemInfo.number); } count++; itemPanels[groupnumber].appendChild(elt); if (isHorizontalLayout()) { if (currentSettings.largeItemsPanel) { y = 0; x += itemsize; } else if (y >= itemsize) { y = 0; x += itemsize; } else { y += itemsize; } } else { if (currentSettings.largeItemsPanel) { y += itemsize; x = 0; } else if (x >= itemsize) { x = 0; y += itemsize; } else { x += itemsize; } } } if (isHorizontalLayout()) { itemPanels[groupnumber].style.width = (Math.ceil(count / iconDivisor) * itemsize + spacing + borderthickness).toFixed(0) + "px"; } else { itemPanels[groupnumber].style.height = (Math.ceil(count / iconDivisor) * itemsize + spacing + borderthickness).toFixed(0) + "px"; } } //Attach item panels if (itemGroups["-1"].length>0){_panel.appendChild(itemPanels["-1"]);} //Single this one out first, otherwise it'll be at the bottom which isn't wrong but feels unintuitive. delete itemPanels["-1"]; //(So it doesn't get added twice below) for (var groupnumber in itemPanels){ if (itemGroups[groupnumber].length>0){ _panel.appendChild(itemPanels[groupnumber]);} } _panel.appendChild(emptyPanel); _layoutPanels(); }); } ; function doJoinRaid(evt, raid) { var inNewWindow = false; if (evt) { inNewWindow = (evt.button === 1) || !!evt.shiftKey; } if (inNewWindow) { // HACK: Fully resolve the URL var elt = document.createElement("a"); elt.href = "/#quest/assist"; chrome.runtime.sendMessage({ type: "openNewTab", url: elt.href }); } else { window.location.href = "/#quest/assist"; } } ; function findItemInfo(predicate, arg) { if (!mostRecentItems) return false; for (var i = 0, l = mostRecentItems.length; i < l; i++) { var item = mostRecentItems[i]; if (predicate(item, arg)) return item; } return false; } ; function makeLanguageSetter(languageId) { return function (e) { e.preventDefault(); doClientAjax("/setting/save", JSON.stringify({ special_token: null, language_type: String(languageId) }), function (result, error) { if (error) showGamePopup("Failed to set language"); else log("Language set successfully"); }); }; } ; //# sourceMappingURL=sidebar.js.map
違いを見つける