-
Notifications
You must be signed in to change notification settings - Fork 4
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
15 changed files
with
1,401 additions
and
23 deletions.
There are no files selected for viewing
File renamed without changes.
File renamed without changes.
File renamed without changes.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,134 @@ | ||
'use strict'; | ||
|
||
const tabIdToContentType = {}; | ||
|
||
// Populate the extension's context menu with relevant items. Right-click on the | ||
// page action icon to open it. | ||
chrome.storage.local.get(['disabled', 'theme'], function(state) { | ||
const theme = state['theme']; | ||
|
||
addNormalMenu(getDisabledStateLabel(state['disabled']), 'disabled'); | ||
addMenuSeparator('separator1'); | ||
addRadioMenu('Light Theme', 'vs', theme === 'vs'); | ||
addRadioMenu('Dark Theme', 'vs-dark', theme === 'vs-dark'); | ||
addRadioMenu('High Contrast Theme', 'hc-black', theme === 'hc-black'); | ||
addMenuSeparator('separator2'); | ||
addNormalMenu('Homepage', 'homepage'); | ||
addNormalMenu('License', 'license'); | ||
addMenuSeparator('separator3'); | ||
}); | ||
|
||
chrome.runtime.onMessage.addListener(function(request, sender, sendResponse) { | ||
console.log('message:', request) | ||
if (typeof sender !== 'undefined') { | ||
if (request.action === 'show_page_action') { | ||
chrome.pageAction.show(sender.tab.id); | ||
} else if (request.action === 'get_content_type') { | ||
sendResponse({ | ||
contentType: tabIdToContentType[sender.tab.id] | ||
}); | ||
} else if (request.action === 'download_content') { | ||
chrome.tabs.query({ | ||
active: true, | ||
currentWindow: true | ||
}, | ||
function(tabs) { | ||
// Encode contents and prepare for local download. | ||
const blob = new Blob([request.content], { type: 'text/plain' }); | ||
const downloadUrl = URL.createObjectURL(blob); | ||
const tabUrl = tabs[0].url; | ||
chrome.downloads.download({ | ||
url: downloadUrl, | ||
filename: tabUrl.substr(tabUrl.lastIndexOf('/') + 1) | ||
}); | ||
} | ||
); | ||
} | ||
} | ||
}); | ||
|
||
// Store the content-types headers, which will help us select the editor's | ||
// language. Note: this feature requires a persistent background in | ||
// manifest.json until declarativeWebRequest goes stable or support for event | ||
// pages is added to webRequest. | ||
chrome.webRequest.onHeadersReceived.addListener( | ||
function(details) { | ||
for (const header of details.responseHeaders) { | ||
if (header.name.toLowerCase() === 'content-type') { | ||
tabIdToContentType[details.tabId] = header.value; | ||
return; | ||
} | ||
} | ||
}, { | ||
urls: ['<all_urls>'], | ||
types: ['main_frame'] | ||
}, ['responseHeaders'] | ||
); | ||
|
||
chrome.contextMenus.onClicked.addListener(function(event) { | ||
if (event.menuItemId === 'homepage') { | ||
window.open('https://github.com/Ludonope/BFPortalUnleashed'); | ||
} else if (event.menuItemId === 'license') { | ||
window.open('https://github.com/Ludonope/BFPortalUnleashed/blob/master/LICENSE'); | ||
} else if (event.menuItemId === 'disabled') { | ||
chrome.storage.local.get('disabled', function(state) { | ||
const newState = state['disabled'] === 'true' ? 'false' : 'true'; | ||
// Persist new state and update action label in context menu. | ||
chrome.storage.local.set({ | ||
disabled: newState | ||
}); | ||
chrome.contextMenus.update('disabled', { | ||
title: getDisabledStateLabel(newState) | ||
}); | ||
}); | ||
} | ||
}); | ||
|
||
chrome.runtime.onInstalled.addListener(function(details) { | ||
if (details.reason === 'update') { | ||
chrome.notifications.create('update_notification', { | ||
title: 'Extension update', | ||
message: `Portal Unleashed updated to version ${chrome.runtime.getManifest().version}`, | ||
type: 'basic', | ||
iconUrl: 'images/portal_unchained_logo.png' | ||
}); | ||
} | ||
}); | ||
|
||
function selectTheme(info, tab) { | ||
chrome.storage.local.set({ | ||
theme: info.menuItemId | ||
}); | ||
chrome.tabs.sendMessage(tab.id, { action: 'set_theme', content: info.menuItemId }); | ||
} | ||
|
||
function addNormalMenu(menuTitle, menuId) { | ||
chrome.contextMenus.create({ | ||
title: menuTitle, | ||
id: menuId, | ||
contexts: ['page_action'] | ||
}); | ||
} | ||
|
||
function addRadioMenu(menuTitle, menuId, checked) { | ||
chrome.contextMenus.create({ | ||
title: menuTitle, | ||
type: 'radio', | ||
checked: checked, | ||
id: menuId, | ||
contexts: ['page_action'], | ||
onclick: selectTheme | ||
}); | ||
} | ||
|
||
function addMenuSeparator(separatorId) { | ||
chrome.contextMenus.create({ | ||
type: 'separator', | ||
id: separatorId, | ||
contexts: ['page_action'] | ||
}); | ||
} | ||
|
||
function getDisabledStateLabel(state) { | ||
return `${state === 'true' ? 'Enable' : 'Disable'} extension`; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,144 @@ | ||
'use strict'; | ||
|
||
if (shouldLaunchEditor(document.body)) { | ||
const interval = setInterval(() => { | ||
const app = document.getElementsByClassName('app')[0]; | ||
if (app) { | ||
clearInterval(interval); | ||
prepareEditorLaunch(app); | ||
} | ||
}, 100); | ||
} | ||
|
||
const req = document.createElement('script') | ||
req.src = 'require.js' | ||
document.body.appendChild(req) | ||
|
||
function prepareEditorLaunch(app) { | ||
// Hide contents to avoid flickering while the rest of the script loads | ||
// asynchronously. | ||
// element.style.setProperty('display', 'none', ''); | ||
chrome.storage.local.get('disabled', function(state) { | ||
if (state['disabled'] === 'true') { | ||
// element.style.removeProperty('display'); | ||
} else { | ||
listenToEditorMessages(app); | ||
toggleEditor(app); | ||
} | ||
}); | ||
// Notify the background to show the page action for the current tab. | ||
chrome.runtime.sendMessage({ | ||
action: 'show_page_action' | ||
}); | ||
} | ||
|
||
function shouldLaunchEditor(body) { | ||
// Only handle documents with a unique <pre> element. | ||
return true; | ||
// return body && body.getElementsByTagName('pre').length === 1 && body.childNodes.length === 1; | ||
} | ||
|
||
function listenToEditorMessages(element) { | ||
window.addEventListener('message', function(message) { | ||
// Wait for editor frame to signal that it has loaded. | ||
if (message.data === 'loaded') { | ||
// element.parentNode.removeChild(element); | ||
const response = { | ||
code: `import * as portal from 'portal-unleashed' | ||
import { logic, eventPayloads, gameplay } from 'portal-unleashed' | ||
const mod = new portal.Mod() | ||
mod.onPlayerDied({ | ||
name: 'New Rule', | ||
conditions: [ | ||
logic.Equals(portal.MeleeAlexandria.Knife_BF3, eventPayloads.EventPlayer()), | ||
logic.Equals(portal.Factions.Alexandria_RU, eventPayloads.EventPlayer()), | ||
], | ||
actions: (player, otherPlayer) => { | ||
return [ | ||
portal.player.EnableAllInputRestrictions(player, new portal.BBoolean(true)), | ||
gameplay.UnspawnPlayer(otherPlayer), | ||
logic.While(portal.logic.Equals(portal.Factions.Alexandria_RU, player), [ | ||
portal.player.EnableAllInputRestrictions(player, new portal.BBoolean(false)), | ||
gameplay.UnspawnPlayer(otherPlayer) | ||
]) | ||
] | ||
} | ||
})`, | ||
filename: 'main.ts' | ||
}; | ||
message.source.postMessage(response, chrome.runtime.getURL('')); | ||
} else if (message.data.startsWith('run+')) { | ||
console.log(message) | ||
let source = `import * as __portal from '${chrome.runtime.getURL('../lib/portal-unleashed/dist/unleash.js')}'\n` + | ||
message.data.substring(4).replaceAll("portal-unleashed", chrome.runtime.getURL('../lib/portal-unleashed/dist/unleash.js')) | ||
var s = document.createElement('script'); | ||
s.type = 'module' | ||
s.innerHTML = ` | ||
import prettier from "https://unpkg.com/[email protected]/esm/standalone.mjs"; | ||
import parserBabel from "https://unpkg.com/[email protected]/esm/parser-babel.mjs"; | ||
import * as __portal from '${chrome.runtime.getURL('../lib/portal-unleashed/dist/unleash.js')}' | ||
const code = prettier.format(__portal.preprocess(${JSON.stringify(source)}), { | ||
parser: "babel", | ||
plugins: [parserBabel], | ||
}) | ||
console.log('generated code:', code) | ||
var s = document.createElement('script'); | ||
s.type = 'module' | ||
s.innerHTML = \`\${code} | ||
setTimeout(function() { | ||
_Blockly.Xml.clearWorkspaceAndLoadFromXml(_Blockly.Xml.textToDom(mod.toXML()), _Blockly.mainWorkspace) | ||
}, 0);\` | ||
s.onload = function() { | ||
this.remove() | ||
}; | ||
(document.head || document.documentElement).appendChild(s); | ||
`; | ||
s.onload = function() { | ||
this.remove(); | ||
}; | ||
(document.head || document.documentElement).appendChild(s); | ||
} | ||
}); | ||
} | ||
|
||
function getFilename() { | ||
let filename = location.href; | ||
// Remove path. | ||
let index = filename.lastIndexOf('/'); | ||
if (index !== -1) { | ||
filename = filename.substring(index + 1); | ||
} | ||
// Remove fragment identifier. | ||
index = filename.indexOf('#'); | ||
if (index !== -1) { | ||
filename = filename.substring(0, index); | ||
} | ||
// Remove query parameters. | ||
index = filename.indexOf('?'); | ||
if (index !== -1) { | ||
filename = filename.substring(0, index); | ||
} | ||
return filename; | ||
} | ||
|
||
function toggleEditor(app) { | ||
const checkMonaco = document.getElementById('unleashed-editor'); | ||
console.log(`app ${app}`); | ||
console.log(`checkMonaco ${checkMonaco}`); | ||
if (checkMonaco) { | ||
app.style.gridTemplateColumns = '1fr'; | ||
app.removeChild(checkMonaco); | ||
} else { | ||
app.style.gridTemplateColumns = '1fr 1fr'; | ||
|
||
const iframe = document.createElement('iframe'); | ||
iframe.id = 'unleashed-editor'; | ||
iframe.setAttribute('src', chrome.runtime.getURL('editor/editor.html')); | ||
iframe.setAttribute('style', 'border: 0px none; width: 100%; height: 100%; grid-row: 1;'); | ||
app.appendChild(iframe); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
<!DOCTYPE html> | ||
<html> | ||
|
||
<head> | ||
<meta http-equiv="Content-Type" content="text/html;charset=utf-8"> | ||
</head> | ||
|
||
<body> | ||
<div id="container" style="position: fixed; top: 0; left: 0; right: 0; bottom: 0"></div> | ||
<script src="../lib/monaco-editor/min/vs/loader.js"></script> | ||
<script src="../lib/requirejs/require.js"></script> | ||
<script src="editor.js"></script> | ||
</body> | ||
|
||
</html> |
Oops, something went wrong.