使用python在多窗口之间做桥接
parent
1f2273150c
commit
80872e0678
|
@ -8,15 +8,19 @@ from gi.repository import GObject, Gtk, Gdk, WebKit2, GLib, Gio, GdkPixbuf
|
|||
|
||||
|
||||
def create_same_window(origin, req):
|
||||
WebEngine = type(origin)
|
||||
w, h = origin.window.get_size()
|
||||
win = Gtk.Window()
|
||||
win.set_default_size(w, h)
|
||||
web = WebKit2.WebView.new_with_related_view(origin)
|
||||
|
||||
web = WebEngine(win, origin)
|
||||
web.set_zoom_level(origin.get_zoom_level())
|
||||
web.set_settings(origin.get_settings())
|
||||
web.load_request(req)
|
||||
|
||||
win.add(web)
|
||||
win.show_all()
|
||||
return web
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -47,11 +51,8 @@ def create_custom_window(origin, options):
|
|||
|
||||
|
||||
|
||||
web = WebEngine(win)
|
||||
# web = WebEngine(win, origin)
|
||||
# web = WebKit2.WebView.new_with_related_view(origin)
|
||||
# web = WebEngine.new_with(win, origin)
|
||||
# web.window = win
|
||||
|
||||
web = WebEngine(win, origin)
|
||||
web.set_root(origin.root, True)
|
||||
web.set_zoom_level(origin.get_zoom_level())
|
||||
web.set_settings(origin.get_settings())
|
||||
|
|
|
@ -13,6 +13,7 @@ from gi.repository import WebKit2
|
|||
class Inject:
|
||||
def __init__(self, webview, env = {}):
|
||||
|
||||
self.webview = webview
|
||||
self.manager = webview.get_user_content_manager()
|
||||
|
||||
script_data = open(self.abspath('./inject.js'), 'r').read()
|
||||
|
|
|
@ -75,12 +75,14 @@ class WebEngine(WebKit2.WebView):
|
|||
|
||||
root = None
|
||||
window = None
|
||||
opener = None
|
||||
custom_bridge = None
|
||||
|
||||
def __init__(self, win):
|
||||
def __init__(self, win, opener = None):
|
||||
|
||||
WebKit2.WebView.__init__(self)
|
||||
|
||||
self.opener = opener
|
||||
self.window = win
|
||||
|
||||
if win.get_title() is None:
|
||||
|
@ -106,6 +108,8 @@ class WebEngine(WebKit2.WebView):
|
|||
|
||||
self.connect('create', self.create_new_window)
|
||||
|
||||
# 允许前端 widnow.close() 关闭窗口
|
||||
self.connect('close', lambda w: win.close())
|
||||
|
||||
|
||||
|
||||
|
@ -182,7 +186,7 @@ class WebEngine(WebKit2.WebView):
|
|||
# 退出app
|
||||
case 'quit':
|
||||
self.window.close()
|
||||
# self.emit('quit')
|
||||
self.emit('quit')
|
||||
|
||||
# 读取图片, 返回图片像素数据
|
||||
case 'image':
|
||||
|
@ -212,6 +216,16 @@ class WebEngine(WebKit2.WebView):
|
|||
elif params['action'] == 'remove':
|
||||
pass
|
||||
|
||||
case 'opener':
|
||||
callback = 'opener_message'
|
||||
output = params.get('data')
|
||||
scripts = 'native.$emit("opener_message", ' + json.dumps(output) + ')'
|
||||
if self.opener is None:
|
||||
self.evaluate_javascript(scripts, -1)
|
||||
else:
|
||||
self.opener.evaluate_javascript(scripts, -1)
|
||||
return
|
||||
|
||||
case 'window':
|
||||
_error, output = self._window_setting(params)
|
||||
|
||||
|
@ -399,6 +413,9 @@ class WebEngine(WebKit2.WebView):
|
|||
case 'create':
|
||||
self.new_window_by_custom(params.get('options'))
|
||||
|
||||
case 'close':
|
||||
self.window.close()
|
||||
|
||||
case 'fullscreen':
|
||||
self.window.fullscreen()
|
||||
|
||||
|
|
|
@ -45,6 +45,9 @@ const KEYS_MAP = {
|
|||
super: '<Super>'
|
||||
}
|
||||
|
||||
const NO_CALLBACK = false
|
||||
const CALL_ONCE = true
|
||||
|
||||
function defer() {
|
||||
let obj = {}
|
||||
obj.promise = new Promise((resolve, reject) => {
|
||||
|
@ -58,22 +61,23 @@ function rand(prefix = 'cb_') {
|
|||
return prefix + Math.random().toString().slice(2)
|
||||
}
|
||||
|
||||
function handler(event, data = {}, once = true) {
|
||||
function handler(event, data = {}, need = CALL_ONCE) {
|
||||
let _ = defer()
|
||||
let callback
|
||||
|
||||
if (typeof once === 'boolean') {
|
||||
if (need === NO_CALLBACK) {
|
||||
_.resolve(true)
|
||||
} else {
|
||||
callback = rand()
|
||||
native[once ? '$once' : '$on'](callback, (err, res) => {
|
||||
native.$once(callback, (err, res) => {
|
||||
if (err) {
|
||||
_.reject(err)
|
||||
} else {
|
||||
_.resolve(res)
|
||||
}
|
||||
})
|
||||
} else {
|
||||
_.resolve(true)
|
||||
}
|
||||
|
||||
window.webkit.messageHandlers.app.postMessage({
|
||||
event,
|
||||
data,
|
||||
|
@ -188,11 +192,13 @@ class EventEmitter {
|
|||
|
||||
window.native = new EventEmitter()
|
||||
|
||||
native.$on('opener_message', data => window.postMessage(data))
|
||||
|
||||
Object.assign(native, {
|
||||
env: '{{env}}',
|
||||
|
||||
quit() {
|
||||
return handler('quit', {}, null)
|
||||
return handler('quit', {}, NO_CALLBACK)
|
||||
},
|
||||
fs: {
|
||||
access(filepath, mode = 'r') {
|
||||
|
@ -250,7 +256,7 @@ Object.assign(native, {
|
|||
return handler('clipboard', { action: 'wait_for_text' })
|
||||
},
|
||||
writeText(value) {
|
||||
return handler('clipboard', { action: 'set_text', value }, null)
|
||||
return handler('clipboard', { action: 'set_text', value }, NO_CALLBACK)
|
||||
},
|
||||
readImage() {
|
||||
return handler('clipboard', { action: 'wait_for_image' }).then(r =>
|
||||
|
@ -262,10 +268,10 @@ Object.assign(native, {
|
|||
if (typeof value === 'object') {
|
||||
value = value.toJSON()
|
||||
}
|
||||
return handler('clipboard', { action: 'set_image', value }, null)
|
||||
return handler('clipboard', { action: 'set_image', value }, NO_CALLBACK)
|
||||
},
|
||||
clear() {
|
||||
return handler('clipboard', { action: 'clear' })
|
||||
return handler('clipboard', { action: 'clear' }, NO_CALLBACK)
|
||||
}
|
||||
},
|
||||
screen: {
|
||||
|
@ -338,51 +344,74 @@ Object.assign(native, {
|
|||
return handler('tray', { action: 'set_status', value: status })
|
||||
}
|
||||
},
|
||||
opener: {
|
||||
//
|
||||
postMessage(data = {}) {
|
||||
return handler('opener', { action: 'postmessage', data }, NO_CALLBACK)
|
||||
}
|
||||
},
|
||||
window: {
|
||||
create(options = {}) {
|
||||
return handler('window', { action: 'create', options })
|
||||
},
|
||||
|
||||
close() {
|
||||
return handler('window', { action: 'close' })
|
||||
},
|
||||
|
||||
isVisible() {
|
||||
return handler('window', { action: 'is_visible' })
|
||||
},
|
||||
toggleVisible() {
|
||||
handler('window', { action: 'toggle_visible' }, null)
|
||||
handler('window', { action: 'toggle_visible' }, NO_CALLBACK)
|
||||
},
|
||||
hide() {
|
||||
handler('window', { action: 'hide' }, null)
|
||||
handler('window', { action: 'hide' }, NO_CALLBACK)
|
||||
},
|
||||
show() {
|
||||
handler('window', { action: 'show' }, null)
|
||||
handler('window', { action: 'show' }, NO_CALLBACK)
|
||||
},
|
||||
fullscreen() {
|
||||
handler('window', { action: 'fullscreen' }, null)
|
||||
handler('window', { action: 'fullscreen' }, NO_CALLBACK)
|
||||
},
|
||||
unfullscreen() {
|
||||
handler('window', { action: 'unfullscreen' }, null)
|
||||
handler('window', { action: 'unfullscreen' }, NO_CALLBACK)
|
||||
},
|
||||
maximize() {
|
||||
handler('window', { action: 'maximize' }, null)
|
||||
handler('window', { action: 'maximize' }, NO_CALLBACK)
|
||||
},
|
||||
unmaximize() {
|
||||
handler('window', { action: 'unmaximize' }, null)
|
||||
handler('window', { action: 'unmaximize' }, NO_CALLBACK)
|
||||
},
|
||||
setTitle(title = '') {
|
||||
handler('window', { action: 'set_title', value: title }, null)
|
||||
handler('window', { action: 'set_title', value: title }, NO_CALLBACK)
|
||||
},
|
||||
resize(width = 0, height = 0) {
|
||||
handler('window', { action: 'resize', value: { width, height } }, null)
|
||||
handler(
|
||||
'window',
|
||||
{ action: 'resize', value: { width, height } },
|
||||
NO_CALLBACK
|
||||
)
|
||||
},
|
||||
move(x = 0, y = 0) {
|
||||
handler('window', { action: 'move', value: { x, y } }, null)
|
||||
handler('window', { action: 'move', value: { x, y } }, NO_CALLBACK)
|
||||
},
|
||||
setOpacity(opacity = 1) {
|
||||
handler('window', { action: 'set_opacity', value: opacity }, null)
|
||||
handler('window', { action: 'set_opacity', value: opacity }, NO_CALLBACK)
|
||||
},
|
||||
alwayOnTop(setting = true) {
|
||||
handler('window', { action: 'set_keep_above', value: setting }, null)
|
||||
handler(
|
||||
'window',
|
||||
{ action: 'set_keep_above', value: setting },
|
||||
NO_CALLBACK
|
||||
)
|
||||
},
|
||||
alwayOnBotttom(setting = true) {
|
||||
handler('window', { action: 'set_keep_below', value: setting }, null)
|
||||
handler(
|
||||
'window',
|
||||
{ action: 'set_keep_below', value: setting },
|
||||
NO_CALLBACK
|
||||
)
|
||||
}
|
||||
},
|
||||
notify({ title, summary, icon, progress = 0, urgency = 0, callback }) {
|
||||
|
@ -394,7 +423,7 @@ Object.assign(native, {
|
|||
handler(
|
||||
'notify',
|
||||
{ title, summary, icon, progress, urgency, callback: eventName },
|
||||
null
|
||||
NO_CALLBACK
|
||||
)
|
||||
},
|
||||
|
||||
|
@ -404,13 +433,13 @@ Object.assign(native, {
|
|||
|
||||
proxy: {
|
||||
disable() {
|
||||
return handler('proxy', { action: 'disable' })
|
||||
return handler('proxy', { action: 'disable' }, NO_CALLBACK)
|
||||
},
|
||||
system() {
|
||||
return handler('proxy', { action: 'system' })
|
||||
return handler('proxy', { action: 'system' }, NO_CALLBACK)
|
||||
},
|
||||
custom(url = '', ignore = null) {
|
||||
return handler('proxy', { action: 'enable', url, ignore })
|
||||
return handler('proxy', { action: 'enable', url, ignore }, NO_CALLBACK)
|
||||
}
|
||||
},
|
||||
|
||||
|
|
Loading…
Reference in New Issue