Cef3中js与C++交互(四)——CefV8Accessor

JS对象可选择使用一个与之关联的CefV8Accessor以提供一个源生的getting和setting值的实现

套路:

CefRefPtr<CefV8Accessor> accessor =;
CefRefPtr<CefV8Value> obj = CefV8Value::CreateObject(accessor);

接下来就是继承CefV8Accessor,重写Get和Set接口

class MyV8Accessor : public CefV8Accessor {
public:
  MyV8Accessor() {}

  virtual bool Get(const CefString& name,
                   const CefRefPtr<CefV8Value> object,
                   CefRefPtr<CefV8Value>& retval,
                   CefString& exception) OVERRIDE {
    if (name == "myval") {
      // Return the value.
      retval = CefV8Value::CreateString(myval_);
      return true;
    }

    // Value does not exist.
    return false;
  }

  virtual bool Set(const CefString& name,
                   const CefRefPtr<CefV8Value> object,
                   const CefRefPtr<CefV8Value> value,
                   CefString& exception) OVERRIDE {
    if (name == "myval") {
      if (value->IsString()) {
        // Store the value.
        myval_ = value->GetStringValue();
      } else {
        // Throw an exception.
        exception = "Invalid value type";
      }
      return true;
    }

    // Value does not exist.
    return false;
  }

  // Variable used for storing the value.
  CefString myval_;

  // Provide the reference counting implementation for this class.
  IMPLEMENT_REFCOUNTING(MyV8Accessor);
};

In order for a value to be passed to the accessor it must be set using
the SetValue() method variant that accepts AccessControl and
PropertyAttribute arguments.

翻译:

为了将值传递给accessor,必须设置SetValue()方法,并且需要设置AccessControl和PropertyAttribute 参数。

obj->SetValue("myval", V8_ACCESS_CONTROL_DEFAULT, 
    V8_PROPERTY_ATTRIBUTE_NONE);

官网的介绍就这么多,怎么用呢?

我用Qt写了个demo
MyV8Accessor.h

#ifndef MYV8ACCESSOR_H
#define MYV8ACCESSOR_H

#include "include/cef_v8.h"

class MyV8Accessor : public CefV8Accessor
{
public:
  MyV8Accessor();

  virtual bool Get(const CefString& name,
                   const CefRefPtr<CefV8Value> object,
                   CefRefPtr<CefV8Value>& retval,
                   CefString& exception) OVERRIDE;

  virtual bool Set(const CefString& name,
                   const CefRefPtr<CefV8Value> object,
                   const CefRefPtr<CefV8Value> value,
                   CefString& exception) OVERRIDE;

private:
  // Variable used for storing the value.
  CefString myval_ = "ha ha";

  // Provide the reference counting implementation for this class.
  IMPLEMENT_REFCOUNTING(MyV8Accessor);
};

#endif // MYV8ACCESSOR_H

MyV8Accessor.cpp

#include "MyV8Accessor.h"

#include <QMessageBox>

MyV8Accessor::MyV8Accessor()
{

}

bool MyV8Accessor::Get(const CefString &name, const CefRefPtr<CefV8Value> object, CefRefPtr<CefV8Value> &retval, CefString &exception)
{
    if (name == "myval")
    {
        QMessageBox::information(nullptr, "title", "MyV8Accessor Get");

        // Return the value.
        retval = CefV8Value::CreateString(myval_);
        return true;
    }

    // Value does not exist.
    return false;
}

bool MyV8Accessor::Set(const CefString &name, const CefRefPtr<CefV8Value> object, const CefRefPtr<CefV8Value> value, CefString &exception)
{
    if (name == "myval")
    {
        if (value->IsString())
        {
            QMessageBox::information(nullptr, "title", "MyV8Accessor Set");

            // Store the value.
            myval_ = value->GetStringValue();
        } else {
            // Throw an exception.
            exception = "Invalid value type";
        }
        return true;
    }

    // Value does not exist.
    return false;
}

simple_app.h

#pragma once

#include "include/cef_app.h"

class SimpleApp
    : public CefApp
    , public CefBrowserProcessHandler
    , public CefRenderProcessHandler
{
public:
    SimpleApp(void);
    virtual ~SimpleApp() OVERRIDE;

public:
    virtual CefRefPtr<CefBrowserProcessHandler> GetBrowserProcessHandler() OVERRIDE;
    virtual CefRefPtr<CefRenderProcessHandler> GetRenderProcessHandler() OVERRIDE;
    virtual void OnContextCreated(CefRefPtr<CefBrowser> browser, CefRefPtr<CefFrame> frame,CefRefPtr<CefV8Context> context) OVERRIDE;

protected:
    IMPLEMENT_REFCOUNTING(SimpleApp);
};

simple_app.cc

// Copyright (c) 2013 The Chromium Embedded Framework Authors. All rights
// reserved. Use of this source code is governed by a BSD-style license that
// can be found in the LICENSE file.

#include "simple_app.h"

#include <string>

#include "include/cef_browser.h"
#include "include/cef_command_line.h"
#include "include/views/cef_browser_view.h"
#include "include/views/cef_window.h"
#include "include/wrapper/cef_helpers.h"
#include "simple_handler.h"

#include "MyV8Accessor.h"

SimpleApp::SimpleApp()
{
}

SimpleApp::~SimpleApp()
{
}

CefRefPtr<CefBrowserProcessHandler> SimpleApp::GetBrowserProcessHandler()
{
    return this;
}

CefRefPtr<CefRenderProcessHandler> SimpleApp::GetRenderProcessHandler()
{
    return this;
}

void SimpleApp::OnContextCreated(CefRefPtr<CefBrowser> browser, CefRefPtr<CefFrame> frame, CefRefPtr<CefV8Context> context)
{
    CEF_REQUIRE_RENDERER_THREAD()

    CefRefPtr<CefV8Value> window = context->GetGlobal();

    CefRefPtr<CefV8Accessor> accessor = new MyV8Accessor();
    CefRefPtr<CefV8Value> obj = CefV8Value::CreateObject(accessor, nullptr);
    obj->SetValue("myval", V8_ACCESS_CONTROL_DEFAULT, V8_PROPERTY_ATTRIBUTE_NONE);

    window->SetValue("MyValObj", obj, V8_PROPERTY_ATTRIBUTE_NONE);
}

index.html

<!DOCTYPE HTML>
<html>
	<head>
		<meta charset="utf-8" />
		<script type="text/javascript" >
			function getMethod()
			{
				try{
					alert("MyValObj.myval: " + MyValObj.myval);
				}catch(err){
					alert("error message: " + err.message);
				}
			}
			function setMethod()
			{
				try{
					MyValObj.myval = "hello world"
				}catch(err){
					alert("error message: " + err.message);
				}
			}
		</script>
	</head>
	<body style="width:100%;height:100%;background-color:green;">
		<p>这是c++与JS交互测试脚本</p>
		<div >
			<button onclick="getMethod();">Get方法</button>
			<button onclick="setMethod();">Set方法</button>
		</div>
	</body>
</html>

运行结果:
我让它弹了两个框,第一个是Qt的QMessageBox,判断MyV8Accessor的Get方法是否被调用,第二个是网页上的弹框,获取值。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
惯例,全部的代码,如果跑不起来,则参考前面的环境配置和目录结构

链接:https://pan.baidu.com/s/1SsX4w92v2IzV4czEmH2low
提取码:w12c

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值