一、介绍

谷歌浏览器和CEF使用V8JavaScript Engine作为内容的JavaScript实现。在浏览器中的每个窗口都有它自己在的JS上下文提供作用域和在窗口中安全的执行JS代码。CEF暴露大量JS功能集成在客户端应用程序。
CEF3的Webkit和JS在单独的渲染进程中运行。在渲染进程的主线程中使用TID_RENDERER 作为唯一标识。所有V8的执行必须放置在这个线程中。
与JS执行相关的回调函数被暴露是通过CefRenderProcessHandler接口实现。当一个新的渲染进程被初始化时通过CefApp::GetRenderProcessHandler()函数获取这个接口。

二、执行JavaScript

在客户端应用程序中简单的方式执行JS使用CefFrame::ExecuteJavaScript()函数,这个函数在浏览进程一和渲染进程中都可用。在一个JS上下文外可安全使用。

CefRefPtr<CefBrowser> browser = ...;
CefRefPtr<CefFrame> frame = browser->GetMainFrame(); 
frame->ExecuteJavaScript("alert('ExecuteJavaScript works!');", frame->GetURL(), 0);

上面的引起alert('ExecuteJavaScript works!')在浏览器的主窗口中执行。

在窗口的JS上下文中ExecuteJavaScript函数可用于函数和变量交互。是为了从JS到客户端应用程序返回值使用窗口绑定和扩展。

三、窗口绑定

窗口绑定允许客户端应用程序系上一个值到窗口的window对象上,窗口绑定的实现使用CefRenderProcessHandler::OnContextCreated()函数。

如:

void MyRenderProcessHandler::OnContextCreated(
CefRefPtr<CefBrowser> browser,
CefRefPtr<CefFrame> frame,
CefRefPtr<CefV8Context> context) {
// Retrieve the context's window object.
CefRefPtr<CefV8Value> object = context->GetGlobal(); // Create a new V8 string value. See the "Basic JS Types" section below.
CefRefPtr<CefV8Value> str = CefV8Value::CreateString("My Value!"); // Add the string to the window object as "window.myval". See the "JS Objects" section below.
object->SetValue("myval", str, V8_PROPERTY_ATTRIBUTE_NONE);
}

JavaScript框架可以与之交互的窗口绑定。

<script language="JavaScript">
alert(window.myval); // Shows an alert box with "My Value!"
</script>

窗口绑定是每次重新加载一个框架加载给客户端应用程序在必要时更改绑定的机会。例如,不同的框架通过修改绑定框架的窗口对象值可以访问不同的特性。

四、扩展

扩展像window绑定一样除了为每个框架 加载到上下文之外,一旦加载就不能修改,当一个扩展已经加载并试图在扩展加载中访问DOM就会出现DOM不存在的crash。扩展应该在CefRenderProcessHandler::OnWebKitInitialized()函数中使用CefRegisterExtension函数注册。

void MyRenderProcessHandler::OnWebKitInitialized() {
// Define the extension contents.
std::string extensionCode =
"var test;"
"if (!test)"
" test = {};"
"(function() {"
" test.myval = 'My Value!';"
"})();"; // Register the extension.
CefRegisterExtension("v8/test", extensionCode, NULL);
}

通过extensionCode描述的字符串可以是任何有效的代码,JS框架可以和扩展代码进行交互

<script language="JavaScript">
alert(test.myval); // Shows an alert box with "My Value!"
</script>

五、基本JS类型

CEF支持基本数据类型的创建,包括:undefined, null, bool, int, double, date 和 string.这些基本数据类型使用CefV8Value::Create*()系列静态函数创建。如创建一个JS字符串:CefRefPtr<CefV8Value> str = CefV8Value::CreateString("My Value!");

基本数据类型可在任何地方创建和在所关联的上下文中不用初始化。如:

CefRefPtr<CefV8Value> val = ...;
if (val.IsString())
{ // The value is a string. }

使用Get*Value()系列函数获取值:CefString strVal = val.GetStringValue();

六、JS数组

使用CefV8Value::CreateArray()静态函数并传递一个长度作为参数创建数组。数组只能在上下文内部创建并使用。如:

CefRefPtr<CefV8Value> arr = CefV8Value::CreateArray(2);

值赋给一个数组使用SetValue()方法的变体,以一个索引作为第一个参数。
arr->SetValue(0, CefV8Value::CreateString("My First String!"));
arr->SetValue(1, CefV8Value::CreateString("My Second String!"));

IsArray()函数测试CefV8Value是否为数组,GetArrayLength()函数获取数据的长度,从数组中获取一个值使用GetValue()变体函数。

七、JS对象

使用CefV8Value::CreateObject静态函数可带一个可选的CefV8Accessor参数创建JS对象。对象也只能在js上下文中创建并使用。

CefRefPtr<CefV8Value> obj = CefV8Value::CreateObject(NULL);

使用SetValue()变体函数并以字符串key作为第一参数给对象分配值。

八、对象的访问者

JS对象可选择使用一个与之关联的CefV8Accessor以提供一个源生的getting和setting值的实现。
CefRefPtr<CefV8Accessor> accessor = …;
CefRefPtr<CefV8Value> obj = CefV8Value::CreateObject(accessor);

CefV8Accessor接口的一个实现,必须由客户端应用程序提供。

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);
};

为了将值传递给访问者必须使用SetValue()变体函数设置,接受AccessControl和PropertyAttribute参数

九、JS函数

CEF支持JS函数创建和本地实现,

CEF3研究(四)之javascript集成的更多相关文章

  1. 第四章 JavaScript操作DOM对象

    第四章   JavaScript操作DOM对象 一.DOM操作 DOM是Document Object Model的缩写,即文档对象模型,是基于文档编程的一套API接口,1988年,W3C发布了第一级 ...

  2. JavaScript DOM编程艺术第四章 — JavaScript图片库案例研究

    这一章通过JavaScript图片库案例,学习了一些DOM属性. HTML代码 <!DOCTYPE html> <html> <head> <meta cha ...

  3. CEF3研究(三)

    一.Off-Screen Rendering 脱屏绘制 CEF的脱屏渲染并不创建源生的浏览器窗口,而是CEF提供主应用程序在无效区域和像素buffer里渲染,然后主应用程序通过鼠标.键盘和焦点事件通知 ...

  4. CEF3研究(二)

    应用程序结构 每个CEF3应用程序都有一个相同的结构: 提供一个入口函数以初始化CEF和运行每个子进程逻辑和CEF消息处理 提供一个CefApp子类处理某个进程的回调 提供一个CefClinet子类处 ...

  5. 王爽-汇编语言-综合研究四-不使用main函数编程

    (一) 研究目的 使用C语言编程,我们一定要使用main函数么? (二) 研究过程 1) 最初的程序 首先,我们编写一个不写main函数的C语言程序. 程序如下: 在编译的过程中,没有发现错误.在链接 ...

  6. 四种JavaScript隐式类型转换的总结

    一般存在四种情况,JavaScript会对变量的数据类型进行转换. 目录 * if中的条件会被自动转为Boolean类型 * 会被转为false的数据 * 会被转为true的数据 * 参与+运算都会被 ...

  7. python自动化开发-[第十四天]-javascript(续)

    今日概要: 1.数据类型 2.函数function 3.BOM 4.DOM 1.运算符 算术运算符: + - * / % ++ -- 比较运算符: > >= < <= != = ...

  8. JQuery制作网页—— 第四章JavaScript对象及初识面向对象

    1.对象:在JavaScript中,所有事物都是对象,如字符串.数值.数组.函数等. JavaScript中的基本数据类型: number(数值类型)   string(字符串类型)  boolean ...

  9. Chrome自带恐龙小游戏的源码研究(四)

    在上一篇<Chrome自带恐龙小游戏的源码研究(三)>中实现了让游戏昼夜交替,这一篇主要研究如何绘制障碍物. 障碍物有两种:仙人掌和翼龙.仙人掌有大小两种类型,可以同时并列多个:翼龙按高. ...

随机推荐

  1. 1-3 编程基础 makefile工程管理

    GNU make Linux程序员必须学会使用GNU make来构建和管理自己的软件工程.GNU的make能够使整个工程的编译.链接只需要一个命令就可以完成. makefile make在执行时,需要 ...

  2. CSS继承inherit | elementUI NavMenu vertical竖版 加 A标记 外联 不能继承上层color,需要手写下color:inherit;

    <li data-v-576b9cf5="" role="menuitem" tabindex="0" class="el- ...

  3. Asp.Net Core 入门(二)——Startup.cs做了什么

    上篇介绍了Program.cs中Main做了什么,这篇我们来讨论下Startup.cs它又做了什么呢? 我们新建一个Asp.Net Core Mvc项目,先来开一下Startup的代码 public ...

  4. caffe layer注册机制

    Caffe内部维护一个注册表用于查找特定Layer对应的工厂函数(Layer Factory的设计用到了设计模式里的工厂模式).Layer_factory的主要作用是负责Layer的注册,已经注册完事 ...

  5. 微信公众号:theTree20181123

    哈哈哈哈~我开通了一个微信公众号,以后的文章会发在公众号内啦~走过路过的小伙伴们过来围观一下呀~~ 主要是分为三个模块:视觉SLAM,ACM,变美树洞 这里面写下来的文章都是我再读研阶段的所学所想当然 ...

  6. kotlin - Parcelable implementations generator

    本文摘自——https://kotlinlang.org/docs/tutorials/android-plugin.html Android Extensions plugin provides P ...

  7. 【传智播客】Libevent学习笔记(五):基本类型和函数

    目录 00. 目录 01. 基本类型 1.1 evutil_socket_t类型 1.2 标准类型 1.3 各种兼容性类型 02. 可移植的定时器函数 03. 套接字API兼容性 04. 可移植的字符 ...

  8. python基础:函数传参、全局变量、局部变量、内置函数、匿名函数、递归、os模块、time模块

    ---恢复内容开始--- 一.函数相关: 1.1位置参数: ef hello(name,sex,county='china'): pass #hello('hh','nv') #位置参数.默认参数 1 ...

  9. android问题

    http://www.cnblogs.com/tianjian/category/330793.html

  10. 获得Dictionary所有key和value值

    Dictionary<string, string> dc = new Dictionary<string, string>(); dc.Add("code" ...