我正在使用Adobe CEP(它使开发人员可以为Adobe CC产品创建窗口式扩展)。我的代码大部分是现代JavaScript(该平台使用Chromium 57,Node.js 7.7.4)。 但是,为了访问DOM,我需要在Adobe ExtendScript中编写一些函数并从普通JS执行它们。唯一的方法是使用脚本提供的csInterface.evalScript(script, callback)
执行脚本。 script
必须是字符串,就我而言,这是一个转换为字符串的函数调用。 我希望能够通过evalScript
与ExtendScript进行传递,但是evalScript
仅接受并返回一个字符串。
当前,我将每个对象属性作为其自变量传递。这很麻烦,但是有效。
虽然我的第一个是JSON.stringify()
,但是不幸的是ExtendScript是ECMAScript 3的方言,这意味着不支持JSON.parse()
。
我不能只将对象参数合并到脚本函数调用中,因为这样字符串的值将为foo([object Object])
。
我已经看到eval()
/ uneval()
或Object.toSource()
之类的功能,但Chromium不支持这些功能。
这是一个示例,类似于我当前的方法:
functions.js (ES3 / ExtendScript)
function drawCircle(x, y, name) {
// pick a layer
var layer = app.activeDocument.layers[0];
var diameter = 10;
var top = y + diameter / 2;
var left = x - diameter / 2;
// draw ellipse in layer
var circle = layer.pathItems.ellipse(top, left, diameter, diameter);
circle.name = name;
circle.filled = true;
return true;
}
app.js (ES6)
const csInterface = new CSInterface(); // provided by Adobe
async function circle() {
const dataObject = {x: 10, y: 10, name: 'Hello world!'};
// the script to call
// evaluates to drawCircle(10,10,'Hello world!');
const script = "drawCircle(" + dataObject.x + "," + dataObject.y + ",'" + dataObject.name + "');";
return new Promise((resolve, reject) => {
csInterface.evalScript(script, (result) => {
resolve(result);
});
});
}
正如预期的那样,circle()
调用drawCircle()
很好,并且在我正在处理的文档中出现一个椭圆。但是,通过串联执行脚本/调用函数感觉很错误。所以总而言之,
dataObject
转换为字符串并通过drawCircle()
传递给evalScript()
,dataObject
返回drawCircle()
并将其作为对象接收。当前,返回对象仅导致"[object Object]"
作为返回值。答案 0 :(得分:1)
将对象从Javascript传递到ExtendScript的唯一方法是使用JSON.stringify()
将其作为JSON字符串发送。
是的,关于JSON.parse()
的支持,您是正确的,但是,您不需要。
您仍然可以发送字符串化的对象,并将作为对象到达ExtendScript。
const dataObject = {x: 10, y: 10, name: 'Hello world!'};
const script = "drawCircle(" + JSON.stringify(dataObject) + ")";
然后在ExtendScript中,您可以执行以下操作:
function drawCircle(obj) {
var layer = app.activeDocument.layers[0];
var radius = 10;
var top = obj.y + 5;
var left = obj.x - 5;
var circle = layer.pathItems.ellipse(top, left, radius, radius);
circle.name = obj.name;
circle.filled = true;
return true;
}
您将需要此ExtendScript模块,将其复制到与jsx相同的文件夹中
Link to Indiscripts ExtendScript JSON module
然后将其与jsx顶部的#include 'json.jsx';
(或//@include 'json.jsx'
以避免棉绒错误)一起包含。这将添加一个提供两个方法的JSON全局函数:JSON.eval()
和JSON.lave()
。
我们需要的方法是lave()
,它允许您将对象字符串化为Javascript。认为它是JSON.stringify()
的更友好版本。
function drawCircle(obj) {
var layer = app.activeDocument.layers[0];
var radius = 10;
var top = obj.y + 5;
var left = obj.x - 5;
// draw ellipse in layer
var circle = layer.pathItems.ellipse(top, left, radius, radius);
circle.name = obj.name;
circle.filled = true;
return JSON.lave(circle);
}
然后在javascript中可以再次解析为对象:
const dataObject = {x: 10, y: 10, name: 'Hello world!'};
const script = "drawCircle(" + JSON.stringify(dataObject) + ")";
csInterface.evalScript(script, (result) => {
console.log(JSON.parse(result));
});
我在最新的CEP运行时版本(v9)中对此进行了测试。