2011-04-11 25 views
1

我正在开发一款游戏,我希望有多个脚本都可以实现相同的结构。每个脚本需要在自己的范围内运行,以便代码不会与其他脚本重叠。例如:使用javax.script运行多个脚本的有效方法

structure.js

function OnInit() { 
    // Define resources to load, collision vars, etc. 
} 

function OnLoop() { 
    // Every loop 
} 

function ClickEvent() { 
    // Someone clicked me 
} 

// Other fun functions 

现在,可以说我有: “BadGuy.js”, “ReallyReallyBadGuy.js”, “OtherBadGuy.js” - 他们看起来都像上述在结构方面。在游戏中,每当发生事件时,我想调用相应的函数。

问题归结为效率和速度。我通过为每个脚本实例创建一个引擎(使用getEngineByName)找到了一个工作解决方案,但这对我来说似乎并不理想。

如果没有更好的解决方案,我可能会求助于每个脚本都有自己独特的类/函数名称。即

BadGuy.js

var BadGuy = new Object(); 

BadGuy.ClickEvent = function() { 
} 

回答

-1

我不认为你需要创建一个新的ScriptEngine为每一个 “人”。您可以在一台引擎中管理它们。所以先前道歉屠杀你的游戏场景.....

  1. 获取犀牛引擎的一个实例。
  2. 发出eval(脚本)语句以将新的JS对象添加到引擎,以及您希望这些对象支持的不同行为(或函数)。
  3. 对于每个人都有不同的选择,但只要每个“人”具有唯一的名称,就可以始终引用它们的名称并调用一个名为的方法。
  4. 对于更多性能敏感的操作(也许某种基于轮的事件循环),您可以在同一个引擎中预编译脚本,然后可以执行该脚本而无需重新评估源。

下面是我在Groovy中编写的示例。

import javax.script.*; 
sem = new ScriptEngineManager(); 
engine = sem.getEngineByExtension("js"); 
engine.getBindings(ScriptContext.ENGINE_SCOPE).put("out", System.out); 
eventLoop = "for(guy in allGuys) { out.println(allGuys[guy].Action(action)); }; " 
engine.eval("var allGuys = []"); 
engine.eval("var BadGuy = new Object(); allGuys.push(BadGuy); BadGuy.ClickEvent = function() { return 'I am a BadGuy' }; BadGuy.Action = function(activity) { return 'I am doing ' + activity + ' in a BAD way' }"); 
engine.eval("var GoodGuy = new Object(); allGuys.push(GoodGuy); GoodGuy.ClickEvent = function() { return 'I am a GoodGuy' }; GoodGuy.Action = function(activity) { return 'I am doing ' + activity + ' in a GOOD way' }"); 
CompiledScript executeEvents = engine.compile(eventLoop); 
println engine.invokeMethod(engine.get("BadGuy"), "ClickEvent"); 
println engine.invokeMethod(engine.get("GoodGuy"), "ClickEvent"); 
engine.getBindings(ScriptContext.ENGINE_SCOPE).put("action", "knitting"); 
executeEvents.eval();