NativeScript运行时与元数据解析

Viewed 0

NativeScript是一个跨平台解决方案,允许使用JavaScript编写原生Android、iOS和即将支持的Windows应用程序。与基于WebView的方案不同,它直接调用系统原生API,提供更接近原生应用的体验。

NativeScript

NativeScript是一个运行时环境,支持用通用JavaScript代码构建原生应用。它具备JavaScript对象与原生UI组件双向绑定、CSS样式原生应用等功能,但最突出的是能直接访问本地平台的原生API。

例如,以下Android应用程序代码:

var time = new android.text.format.Time();
time.set(1, 0, 2015);
console.log(time.format("%D"));

这段JavaScript实例化Java的android.text.format.Time对象,调用其方法后输出"01/01/15"。类似地,在iOS中:

var alert = new UIAlertView();
alert.message = "Hello world!";
alert.addButtonWithTitle("OK");
alert.show();

这实例化Objective-C的UIAlertView类并显示警告框。

NativeScript运行时

NativeScript运行时的架构基于JavaScript虚拟机:在Android上使用V8,在iOS上使用JavaScriptCore。因此,所有访问原生API的代码都遵循JavaScript语法,并支持ES6等现代特性。关键是如何让虚拟机识别原生API。以Android为例,代码var time = new android.text.format.Time();在V8中运行,但V8通过NativeScript注入的全局对象知道android.text.format.Time。这是利用V8的Context API实现的,类似Node.js注入全局require()的机制。

元数据(Metadata)

NativeScript依赖反射来调用平台API。为提升性能,它在预编译过程中生成并嵌入元数据,描述API结构。当JavaScript调用new android.text.format.Time()时,NativeScript通过元数据知道需实例化对应Java对象。

调用本地代码

当JavaScript函数调用发生时,V8会触发回调,允许NativeScript用C++代码拦截并执行相应操作。在Android上,通过JNI(Java Native Interface)桥接C++和Java;在iOS上,C++可直接调用Objective-C API。例如,对于time.set(1, 0, 2015);,NativeScript通过代理对象将调用转发到Java对象的set()方法。代理对象维持JavaScript对象与本地平台对象的映射,确保方法调用正确传递。

TNS模块

TNS(Telerik NativeScript)模块遵循CommonJS规范,类似Node.js模块,允许抽象平台特定代码为统一API。例如,文件系统操作在Android和iOS上实现不同,但通过TNS模块可一致使用:

var fs = require("file-system");
var file = new fs.File(path);

开发者还可编写自定义TNS模块,例如获取设备操作系统版本:

// 在iOS上
exports.version = UIDevice.currentDevice().systemVersion;

// 在Android上
exports.version = android.os.Build.VERSION.RELEASE;

使用方式与Node.js模块相同:

var device = require("./device");
console.log(device.version);

TNS模块降低了跨平台开发的复杂度,让Web开发者能更轻松地处理原生功能。通过这种方式,NativeScript实现了用JavaScript高效开发原生应用,结合了JavaScript的灵活性和原生应用的性能。

0 Answers