mirror of
https://gitee.com/energye/energy.git
synced 2024-11-29 18:28:06 +08:00
A: JS ipc.on options: mode
This commit is contained in:
parent
05a7690506
commit
cad0352bde
86
cef/ipc.go
86
cef/ipc.go
@ -14,6 +14,8 @@ package cef
|
||||
|
||||
import (
|
||||
"github.com/energye/energy/v2/cef/internal/ipc"
|
||||
ipcArgument "github.com/energye/energy/v2/cef/ipc/argument"
|
||||
"github.com/energye/energy/v2/cef/ipc/types"
|
||||
"github.com/energye/energy/v2/cef/process"
|
||||
"sync"
|
||||
"time"
|
||||
@ -70,11 +72,13 @@ type ipcOnHandler struct {
|
||||
|
||||
// ipc.emit 回调结果
|
||||
type ipcCallback struct {
|
||||
isSync bool //同否同步 true:同步 false:异步, 默认false
|
||||
resultType result_type //返回值类型 0:function 1:variable 默认:0
|
||||
variable *ICefV8Value //回调函数, 根据 resultType
|
||||
function *ICefV8Value //回调函数, 根据 resultType
|
||||
name *ICefV8Value //事件名称
|
||||
isSync bool //同否同步 true:同步 false:异步, 默认false
|
||||
resultType result_type //返回值类型 0:function 1:variable 默认:0
|
||||
variable *ICefV8Value //回调函数, 根据 resultType
|
||||
function *ICefV8Value //回调函数, 根据 resultType
|
||||
name *ICefV8Value //事件名称
|
||||
mode types.Mode //监听模式
|
||||
asyncHandler *asyncGoExecuteJSHandler //监听模式为 MAsync
|
||||
}
|
||||
|
||||
// IPC 内部定义使用 key 不允许使用
|
||||
@ -193,3 +197,75 @@ func (m *ipcOnHandler) clear() {
|
||||
}
|
||||
m.callbackList = make(map[string]*ipcCallback)
|
||||
}
|
||||
|
||||
// JS: ipc.on 异步模式完成事件处理
|
||||
type asyncGoExecuteJSHandler struct {
|
||||
handler *ICefV8Handler
|
||||
callback *ICefV8Value
|
||||
}
|
||||
|
||||
// 返回一个新的 asyncGoExecuteJSHandler
|
||||
func newAsyncGoExecuteJSHandler() *asyncGoExecuteJSHandler {
|
||||
asyncHandler := &asyncGoExecuteJSHandler{
|
||||
handler: V8HandlerRef.New(),
|
||||
}
|
||||
// 创建处理器函数, 在异步监听模式时使用
|
||||
asyncHandler.handler.Execute(asyncHandler.asyncHandler)
|
||||
asyncHandler.callback = V8ValueRef.NewFunction("callback", asyncHandler.handler)
|
||||
asyncHandler.callback.SetCanNotFree(true)
|
||||
return asyncHandler
|
||||
}
|
||||
|
||||
func (m *asyncGoExecuteJSHandler) free() {
|
||||
if m.callback != nil {
|
||||
m.callback.Free()
|
||||
m.callback = nil
|
||||
}
|
||||
}
|
||||
|
||||
// Js: ipc.on 异步监听模式完成处理器
|
||||
func (m *asyncGoExecuteJSHandler) asyncHandler(name string, object *ICefV8Value, arguments *TCefV8ValueArray, retVal *ResultV8Value, exception *ResultString) bool {
|
||||
idValue := object.GetValueByKey("id")
|
||||
defer idValue.Free()
|
||||
messageId := idValue.GetIntValue()
|
||||
size := arguments.Size()
|
||||
result := make([]interface{}, size)
|
||||
for i := 0; i < size; i++ {
|
||||
tempVal := arguments.Get(i)
|
||||
if !tempVal.IsValid() {
|
||||
result[i] = nil
|
||||
continue
|
||||
}
|
||||
isObject := tempVal.IsObject() || tempVal.IsArray()
|
||||
callbackArgsBytes := ValueConvert.V8ValueToProcessMessageArray(tempVal)
|
||||
tempVal.Free()
|
||||
if isObject {
|
||||
result[i] = callbackArgsBytes
|
||||
} else {
|
||||
if val, ok := callbackArgsBytes.([]interface{}); ok && len(val) == 1 {
|
||||
result[i] = callbackArgsBytes.([]interface{})[0]
|
||||
} else {
|
||||
result[i] = nil
|
||||
}
|
||||
}
|
||||
}
|
||||
replayGoExecuteJSEvent(messageId, result)
|
||||
return true
|
||||
}
|
||||
|
||||
func replayGoExecuteJSEvent(messageId int32, callbackArgsBytes interface{}) {
|
||||
if messageId != 0 {
|
||||
callbackMessage := &ipcArgument.List{
|
||||
Id: messageId,
|
||||
BId: ipc.RenderChan().BrowserId(),
|
||||
Name: internalIPCGoExecuteJSEventReplay,
|
||||
}
|
||||
if callbackArgsBytes != nil {
|
||||
callbackMessage.Data = callbackArgsBytes //json.NewJSONArray(callbackArgsBytes).Data()
|
||||
}
|
||||
// send ipc message
|
||||
// send bytes data to browser ipc
|
||||
ipc.RenderChan().IPC().Send(callbackMessage.Bytes())
|
||||
callbackMessage.Reset()
|
||||
}
|
||||
}
|
||||
|
@ -18,6 +18,7 @@ import (
|
||||
ipcArgument "github.com/energye/energy/v2/cef/ipc/argument"
|
||||
"github.com/energye/energy/v2/cef/ipc/context"
|
||||
"github.com/energye/energy/v2/cef/ipc/target"
|
||||
"github.com/energye/energy/v2/cef/ipc/types"
|
||||
"github.com/energye/energy/v2/consts"
|
||||
"github.com/energye/energy/v2/pkgs/json"
|
||||
"time"
|
||||
@ -47,9 +48,10 @@ func (m *ipcRenderProcess) clear(frameId int64) {
|
||||
|
||||
// JS ipc.on 监听事件
|
||||
func (m *ipcOnHandler) jsOnEvent(name string, object *ICefV8Value, arguments *TCefV8ValueArray, retVal *ResultV8Value, exception *ResultString) (result bool) {
|
||||
var size int
|
||||
if name != internalIPCOn {
|
||||
return
|
||||
} else if arguments.Size() != 2 { //必须是2个参数
|
||||
} else if size = arguments.Size(); !(size >= 2 && size <= 3) { //必须是2 | 3个参数
|
||||
exception.SetValue("ipc.on parameter should be 2 quantity")
|
||||
arguments.Free()
|
||||
return
|
||||
@ -73,11 +75,37 @@ func (m *ipcOnHandler) jsOnEvent(name string, object *ICefV8Value, arguments *TC
|
||||
arguments.Free()
|
||||
return
|
||||
}
|
||||
//监听选项, 第三个参数
|
||||
options := arguments.Get(2)
|
||||
if size == 3 && !options.IsObject() {
|
||||
exception.SetValue("ipc.on event options should be a object")
|
||||
arguments.Free()
|
||||
return
|
||||
}
|
||||
retVal.SetResult(V8ValueRef.NewBool(true))
|
||||
onCallback.SetCanNotFree(true)
|
||||
onNameValue = onName.GetStringValue()
|
||||
//ipc on
|
||||
m.addCallback(onNameValue, &ipcCallback{function: V8ValueRef.UnWrap(onCallback), name: V8ValueRef.UnWrap(onName)})
|
||||
|
||||
callback := &ipcCallback{
|
||||
function: V8ValueRef.UnWrap(onCallback),
|
||||
name: V8ValueRef.UnWrap(onName),
|
||||
}
|
||||
|
||||
// 监听模式,JS: ipc.on 监听事件 options 模式(mode)值是 MAsync(1)时,在回调函数的参数列表最后一个参数 complete 对象
|
||||
if size == 3 && options.IsValid() {
|
||||
modeValue := options.GetValueByKey("mode")
|
||||
if modeValue.IsValid() {
|
||||
callback.mode = types.Mode(modeValue.GetIntValue())
|
||||
modeValue.Free()
|
||||
}
|
||||
options.Free()
|
||||
if callback.mode == types.MAsync {
|
||||
callback.asyncHandler = newAsyncGoExecuteJSHandler()
|
||||
}
|
||||
}
|
||||
|
||||
//ipc on, 添加到维护集合
|
||||
m.addCallback(onNameValue, callback)
|
||||
result = true
|
||||
return
|
||||
}
|
||||
@ -139,6 +167,17 @@ func (m *ipcRenderProcess) ipcGoExecuteJSEvent(browser *ICefBrowser, frame *ICef
|
||||
//bytes to v8array value
|
||||
argsArray, err = ValueConvert.BytesToV8ArrayValue(argumentList.Bytes())
|
||||
}
|
||||
// MAsync: 异步模式
|
||||
if callback.mode == types.MAsync {
|
||||
if argsArray == nil {
|
||||
argsArray = V8ValueArrayRef.New()
|
||||
}
|
||||
complete := V8ValueRef.NewObject(nil)
|
||||
complete.SetValueByKey("callback", callback.asyncHandler.callback, consts.V8_PROPERTY_ATTRIBUTE_READONLY)
|
||||
complete.SetValueByKey("id", V8ValueRef.NewInt(messageId), consts.V8_PROPERTY_ATTRIBUTE_READONLY)
|
||||
argsArray.Add(complete)
|
||||
}
|
||||
// 执行事件函数
|
||||
if argsArray != nil && err == nil {
|
||||
// parse v8array success
|
||||
ret = callback.function.ExecuteFunctionWithContext(ctx, nil, argsArray)
|
||||
@ -147,7 +186,8 @@ func (m *ipcRenderProcess) ipcGoExecuteJSEvent(browser *ICefBrowser, frame *ICef
|
||||
// parse v8array fail
|
||||
ret = callback.function.ExecuteFunctionWithContext(ctx, nil, nil)
|
||||
}
|
||||
if ret != nil && ret.IsValid() && messageId != 0 { // messageId != 0 callback func args
|
||||
// MSync: 同步模式
|
||||
if callback.mode == types.MSync && ret != nil && ret.IsValid() && messageId != 0 { // messageId != 0 callback func args
|
||||
// v8value to process message bytes
|
||||
callbackArgsBytes = ValueConvert.V8ValueToProcessMessageArray(ret)
|
||||
ret.Free()
|
||||
@ -158,19 +198,9 @@ func (m *ipcRenderProcess) ipcGoExecuteJSEvent(browser *ICefBrowser, frame *ICef
|
||||
ctx.Exit()
|
||||
}
|
||||
ctx.Free()
|
||||
if messageId != 0 { //messageId != 0 callback func
|
||||
callbackMessage := &ipcArgument.List{
|
||||
Id: messageId,
|
||||
BId: ipc.RenderChan().BrowserId(),
|
||||
Name: internalIPCGoExecuteJSEventReplay,
|
||||
}
|
||||
if callbackArgsBytes != nil {
|
||||
callbackMessage.Data = callbackArgsBytes //json.NewJSONArray(callbackArgsBytes).Data()
|
||||
}
|
||||
// send ipc message
|
||||
// send bytes data to browser ipc
|
||||
ipc.RenderChan().IPC().Send(callbackMessage.Bytes())
|
||||
callbackMessage.Reset()
|
||||
// MSync: 同步模式
|
||||
if callback.mode == types.MSync {
|
||||
replayGoExecuteJSEvent(messageId, callbackArgsBytes)
|
||||
}
|
||||
}
|
||||
return
|
||||
|
Loading…
Reference in New Issue
Block a user