Processing.getInstanceById (id);对一个函数有效,对另一个函数未定义

Processing.getInstanceById(id); works with one function, undefined for another?

本文关键字:函数 有效 未定义 一个 另一个 getInstanceById id Processing      更新时间:2023-09-26

以下是http://processingjs.org/articles/PomaxGuide.html用于在网页上使用处理草图,我的一个函数完美地利用了这一点:

function drawSomething() {
  // some calculations
  var pjs = Processing.getInstanceById('canvasID');
  var number = 5 // placeholder result of calculations
  pjs.drawText(number);
}

然而,对于另一个函数,drawSomethingElse,相同的pjs变量定义日志:

TypeError: pjs is undefined

所有的代码都被封装在docReady和drawSomething();在页面加载时调用:

$(document).ready(function(){
  // do lots of stuff
  drawSomethingElse();
}

javascript中的作用域是这样工作的。如果你在另一个函数中声明varfunction它只在这个函数中可见

function outerScope(){
   var outerVariable = "is defined in outer scope";
   function innerScope(){
      var innerVariable = "is defined in inner scope";
      console.log(outervariable); //innerScope can see outerVariable (through a closure)
   }
   console.log(innerVariable) //=undefined outerScope can't see innerVariable
   console.log(outerVariable) //outerScope can still see outerVariable
}
console.log(outerScope) //= function, global scope can see outerScope
console.log(outerVariable) //=undefined but global scope can't see inside outerScope
console.log(innerScope) //= undefined, therefore it can't see innerScope
console.log(innerVariable) //=undefined and of course not into inner scope

这对所有函数都是正确的,包括jQuery函数,它们也不例外。所以这就是为什么你必须在你想要使用它的作用域"层"中定义一个var。为了不污染全局作用域你把东西包装到这些匿名函数中,只需要添加一个作用域"layer"

这个模型总是适用的,不管你添加了多少层。你总是能够理解行为。(btw 总是检查console.log中所有你不确定的东西,这有助于追踪bug。你越能准确地回答你的解决方案的问题,你就越能更好地知道如何修复它)

适应你对范围的了解,因为你没有在当前范围内定义Processing,所以你知道它,因此必须在全局范围内,这意味着你可以打开你的浏览器控制台,只是console.log(Processing),也许在控制台几次调用Processing.getInstanceById()方法。也许它不是画布id,也许它是定义实例名称的草图的名称。试一试。

既然你现在知道你的。pde草图没有加载的时候,你想通过javascript获得实例,你有几个选项。最简单的方法是将草图作为文档的一部分,这样$(document).ready()只在加载处理和草图时触发并执行javascript。

通常处理检查画布上的自定义data-processing-sources属性,并为文件(您的草图)发送异步请求。但由于它是异步的,它不是你的文档加载的一部分,所以文档已经准备好了,但你的草图还没有。

如果你把草图代码放在文档内的script标签中,那么文档在加载之前不会准备好。您还需要设置mime类型,否则浏览器会认为这是javascript并抛出错误。它不会改变任何其他东西,它只是另一种方式来设置你的处理草图。

<script type="text/processing" data-processing-target="canvasID"> 
    //your sketch code
</script>
<canvas id="canvasID"></canvas>

对于你来说,仍然能够从外部加载你的草图,这里有稍微令人困惑的第三种方法来设置你的草图。删除整个script标签和草图。

跳过data-processing-target和data-processing-sources属性,而不是pjs = Processing.getInstanceById

$(document).ready(function(){
    var xhr = new XMLHttpRequest();
    xhr.open("GET", "yourSketch.pde");
    xhr.onload = function(){
        var code = xhr.response;
        var canvas = document.getElementById("canvasID")
         pjs = new Processing(canvas,code);
         //rest of your code
   }
   xhr.send();
});

注意:如果你从文件://protocol

本地查看你的网站,这项技术将不起作用。

pjs的作用域是drawSomething函数在不同的函数中使用它改变你的代码像这样

(function() {
  var pjs = Processing.getInstanceById('canvasID');
  function drawSomething() {
    var number = 5 // placeholder result of calculations
    pjs.drawText(number);
  }
  function someotherfunction() {
     drawSomething();
  }
}());

现在你可以在这个匿名函数的任何地方使用PJS