我有Kinetic.Group
并在其属性中添加了变量actualstatus
。 actualstatus
由其他一些JavaScript动态更改为“1”或“0”(1 = ON 0 = OFF
)。
现在,我正在尝试做的事情是用KineticJS显示实际状态(打开或关闭)。当我使用自定义Kinetic.Shape
时,我可以这样做:
var shape = new Kinetic.Shape({
actualstatus: "",
drawFunc: function(canvas){
var ctx = canvas.getContext();
ctx.beginPath();
if(this.actualstatus == "1") ctx.fillStyle = "yellow";
else if(this.actualstatus == "0") ctx.fillStyle = "lightgrey";
ctx.fillRect(0,0,50,50);
ctx.closePath();
}
});
它完美无缺,但无法在其上监听事件并使用多个ctx.beginPath()
ctx.closePath()
来绘制复杂的小部件。
正因为如此,我只使用非自定义动力学形状重建它,这解决了我的事件和复杂的绘图问题,但现在,它不再根据{{1}更改其颜色或文本} -property of the group,包含所有形状。
所以我的问题:每次actualstatus
- 属性发生变化时,有没有办法用新颜色等重绘形状?或者有没有办法听取actualstatus
- 更改?
我希望你能以某种方式得到我上面说的有点复杂的形象:)当然,任何帮助都非常感激;)
答案 0 :(得分:3)
您可以“监听”“actualstatus”的值何时更改并相应更改颜色
您可以使用javascript getters和setter来完成此操作。
这两个函数与属性(actualstatus)相关联,并且只要请求属性值(getter)和分配属性值(setter)时就会触发。
// this will trigger the getter function
var test = actualstatus;
// this will trigger the setter function
actualstatus=”1”;
这一点的重要性在于您可以使用setter函数来更改actualstatus值... AND ...您还可以触发更改形状颜色。
以下是setter函数的样子:
function (newValue) {
// change the current value to the new value
this.currentValue = newValue;
// and also change the rectangle’s color based on the newValue
switch(value){
case "0":
myKineticRect.setFill('lightgrey');
break;
case "1":
myKineticRect.setFill('yellow');
break;
default:
myKineticRect.setFill('red');
break;
}
layer.draw();
}
让getter / setter工作:
首先,声明一个包含我们想要“监听”的所有变量的对象。
// create a container object for all the Vars we want to "listen" to
var WatchedVars=function(){};
接下来告诉WatchedVars添加一个名为“actualstatus”的变量,它将有一个getter和一个setter:
// "listen" for gets and sets on "actualstatus"
Object.defineProperty(WatchedVars.prototype,"actualstatus",{
// this is a "private" property that holds the current value of actualstatus
privateValue: "X",
// on get: just return the current value (privateValue)
get: function(){ return(this.privateValue); },
// on set: set the current value
// ...AND(!)... execute the callback handler (actualstatusSetHandler)
set: function(newValue){
this.privateValue=newValue;
actualstatusSetHandler(this.privateValue);
}
});
因此,每当您更改actualstatus的值时,都会调用setter。
// assigning w.actualstatus a value of "1" triggers its setter function
w.actualstatus=”1”;
setter将actualstatus的当前值更改为“1”
setter还调用actualstatusSetHandler(),用黄色填充矩形。
这是每次actualstatus值发生变化时都会执行的回调:
// this handler will get called every time the value of actualstatus changes
// in this case, we change the fill color of a kinetic shape (rect)
function actualstatusSetHandler(value,isTrue){
switch(value){
case "0":
rect.setFill('lightgrey');
break;
case "1":
rect.setFill('yellow');
break;
default:
rect.setFill('red');
break;
}
layer.draw();
}
这就是如何“监听”javascript中的变量!
这是代码和小提琴:http://jsfiddle.net/m1erickson/Uw4Ht/
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Prototype</title>
<script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script>
<script src="http://d3lp1msu2r81bx.cloudfront.net/kjs/js/lib/kinetic-v4.5.1.min.js"></script>
<style>
#container{
border:solid 1px #ccc;
margin-top: 10px;
width:200px;
}
</style>
<script>
$(function(){
// create a container object for all the Vars we want to "listen" to
var WatchedVars=function(){};
// "listen" for gets and sets on "actualstatus"
Object.defineProperty(WatchedVars.prototype,"actualstatus",{
// this is a "private" property that holds the current value of actualstatus
privateValue: "X",
// on get: just return the current value (privateValue)
get: function(){ return(this.privateValue); },
// on set: set the current value
// ...AND(!)... execute the callback handler (actualstatusSetHandler)
set: function(newValue){
this.privateValue=newValue;
actualstatusSetHandler(this.privateValue);
}
});
// this handler will get called every time the value of actualstatus changes
// in this case, we change the fill color of a kinetic shape (rect)
function actualstatusSetHandler(value,isTrue){
switch(value){
case "0":
rect.setFill('lightgrey');
break;
case "1":
rect.setFill('yellow');
break;
default:
rect.setFill('red');
break;
}
layer.draw();
}
// just normal Kinetic stuff
// create stage & layer, add a rectangle
var stage = new Kinetic.Stage({
container: 'container',
width: 200,
height: 200
});
var layer = new Kinetic.Layer();
stage.add(layer);
var rect = new Kinetic.Rect({
x: 30,
y: 30,
width: 100,
height: 30,
fill: "green",
stroke: "gray",
strokeWidth: 3
});
layer.add(rect);
layer.draw();
// create an instance of WatchedVars
var w=new WatchedVars();
// testing...just change the value of actualstatus
$("#set0").click(function(){ w.actualstatus="0"; });
$("#set1").click(function(){ w.actualstatus="1"; });
}); // end $(function(){});
</script>
</head>
<body>
<div id="container"></div>
<button id="set0">actualstatus==0</button>
<button id="set1">actualstatus==1</button>
</body>
</html>
答案 1 :(得分:1)
@markE感谢您的帮助和精彩的代码片段。我想使用KineticJS函数,现在可以使用activestate
方法设置.setAttrs()
:
rect.setAttrs({
activestate: "0" //or "1"
});
如果您使用.setAttrs()
更改属性,则可以使用KineticJS提供的attrs-listener:
rect.on('activestateChange', function(){
if(activestate == "1")
rect.setFill('yellow');
else if(activestate == "0")
rect.setFill('grey');
});