2012-03-14 1 views
0

У меня возникли проблемы с пониманием синтаксиса двухсторонних привязок в ember.jsСвязывания между двумя произвольными объектами в ember.js

У меня есть два объекта, которые я хотел бы, чтобы связать вместе, вот что я пытался :

App = Ember.Application.create({}); 

App.MyPoint = Ember.Object.extend({ 
    x: 0, 
    y: 0, 
    init: function() 
    { 
    } 
}); 

App.PointView = Ember.Object.extend({ 
    point: null, 
    cx: 0, 
    cy: 0, 
    init: function() 
    { 
    } 
}); 


var aPoint = App.MyPoint.create(); 

var aPointView = App.PointView.create({point: aPoint, cxBinding: "aPoint.x", cyBinding: "aPoint.y"}); 

console.log("Expect 0, 0: ", aPointView.get('cx'), aPointView.get('cy')); 

aPoint.set('x', 10); 
console.log("Expect 10, 0: ", aPointView.get('cx'), aPointView.get('cy')); // But I get 0, 0 ... 

jsfiddle: http://jsfiddle.net/W9qtF/

в идеале, я бы даже предпочел, чтобы создать привязку в PointView Init(), так что PointView.create ({точка: aPoint}) устанавливает все правильно. Это возможно?

+0

спасибо тому, кто downvoted без комментариев ... тем более, что я принял ответ некоторое время назад. – Taum

ответ

3

Я создал JSFiddle, где вы можете играть со связями, см. http://jsfiddle.net/hVGwV/. Я вызываю Ember.run.sync() в примере, чтобы принудительно синхронизировать все привязки.

JavaScript:

var get = Ember.get; 
var view; 
var point; 

var flushAndDebug = function(msg) { 
    if (msg) { console.log(msg); } 
    Ember.run.sync(); 
    point.debug(); 
    view.debug(); 
    console.log('--------------'); 
}; 

Point = Ember.Object.extend({ 
    x: 0, 
    y: 0, 
    debug: function() { 
     console.log('point: %@/%@'.fmt(get(this, 'x'), get(this, 'y'))); 
    } 
}); 

PointView = Ember.Object.extend({ 
    point: null, 
    cxBinding: 'point.x', 
    cyBinding: 'point.y', 
    debug: function() { 
     console.log('view: %@/%@'.fmt(get(this, 'cx'), get(this, 'cy'))); 
    } 
}); 

point = Point.create(); 
view = PointView.create(); 

flushAndDebug('point and view created'); 

view.set('point', point); 
flushAndDebug('after point has been set on view'); 

point.set('x', 50); 
flushAndDebug('x of point has been updated'); 

view.set('cy', 100); 
flushAndDebug('y of view has been updated'); 

view.set('point', null); 
flushAndDebug('point of view is set to null'); 

view.set('cx', '200'); 
flushAndDebug('x of view is updated'); 

view.set('point', point); 
flushAndDebug('point has been reassigned to view'); 

var newPoint = Point.create({ 
    x: 400, 
    y: 400 
}); 
view.set('point', newPoint); 
flushAndDebug('new created point has been set as point on view'); 

point.set('x', 42); 
flushAndDebug('original point has been updated'); 

Выход:

point and view created 
point: 0/0 
view: (null)/(null) 
-------------- 
after point has been set on view 
point: 0/0 
view: 0/0 
-------------- 
x of point has been updated 
point: 50/0 
view: 50/0 
-------------- 
y of view has been updated 
point: 50/100 
view: 50/100 
-------------- 
point of view is set to null 
point: 50/100 
view: (null)/(null) 
-------------- 
x of view is updated 
point: 50/100 
view: 200/(null) 
-------------- 
point has been reassigned to view 
point: 50/100 
view: 50/100 
-------------- 
new created point has been set as point on view 
point: 50/100 
view: 400/400 
-------------- 
original point has been updated 
point: 42/100 
view: 400/400 
-------------- 
+0

Так что привязки обновлены в Ember.sync.run(), теперь это объясняет, почему все мои тесты в jsfiddle, где не работает;) Спасибо большое! – Taum

0

Ember полагается на некоторые соглашения. Один из них заключается в том, что все объекты/классы должны находиться в одном пространстве имен приложений. То есть что-то вроде window.App = Ember.Application.create().

я переписал свой пример, чтобы жить под тем же именем пространства - а затем он работает:

http://jsfiddle.net/phGeP/1/

App = Ember.Application.create(); 

App.MyPoint = Ember.Object.extend({ 
    x: 0, 
    y: 0 
}); 

App.PointView = Ember.Object.extend({ 
    point: null, 
    cxBinding: "point.x", 
    cyBinding: "point.y" 
}); 


App.aPoint = App.MyPoint.create(); 

App.aPointView = App.PointView.create({point: App.aPoint}); 

console.log("Expect 0, 0: ", App.aPointView.get('cx'), App.aPointView.get('cy')); 

App.aPoint.set('cx', 10); 
console.log("Expect 10, 0: ", App.aPointView.get('cx'), App.aPointView.get('cy')); 
​ 
+0

Эта скрипка не работает должным образом в моем браузере: эхо "undefined undefined" ... Что-то не так? –

+0

«Все объекты/классы должны находиться под одним и тем же пространством имен приложений». Это действительно так? У моего приложения, очевидно, будет много точек (и много точек зрения), я не могу просто использовать App.aPoint: как вы справляетесь с этим делом? – Taum

0

Вот версия, которая работа:

MyPoint = Ember.Object.extend({ 
    x: 0, 
    y: 0 
}); 

PointView = Ember.Object.extend({ 
    point: null, 

    cx: function() { 
     return this.point.x; 
    }.property('point'), 

    cy: function() { 
     return this.point.y; 
    }.property('point') 
}); 

aPoint = MyPoint.create(); 

aPointView = PointView.create({ 
    point: aPoint 
}) 

console.log("Expect 0, 0: ", aPointView.get('cx'), aPointView.get('cy')); 

aPoint.set('x', 10); 
console.log("Expect 10, 0: ", aPointView.get('cx'), aPointView.get('cy')); // But I get 0, 0 ... 

Я изменил cx & cy свойства, которые должны вычисляться в соответствии с текущим значением.

Тогда, когда вы изменяете значение aPoint, вы должны использовать x property, так как cx является собственностью компании PointView.

+0

Но если я делаю aPointView.set ('cx', 10), aPoint.get ('x') по-прежнему 0 (значит, это просто наблюдатель, а не двусторонняя привязка?) – Taum

+0

Вы можете увидеть мою второй ответ для двунаправленности ... –

0

Вот двунаправленная пример:

Шаблон:

<script type="text/x-handlebars" data-template-name="point-view"> 
    Point: ({{point.x}}, {{point.y}}) 

    <p> 

    {{view Ember.TextField valueBinding="point.x"}} 
    {{view Ember.TextField valueBinding="point.y"}} 
    {{#view Ember.Button target="App.pointController" action="resetCoordinates"}}Reset coordinates{{/view}} 
</script> 

JS:

App = Ember.Application.create() 

App.Point = Ember.Object.extend({ 
    x: 0, 
    y: 0, 

    reset: function() { 
     this.set('x', 0); 
     this.set('y', 0); 
    } 
}); 

App.PointView = Ember.View.extend({ 
    templateName: 'point-view', 
    pointBinding: 'App.pointController.point' 
}); 

App.pointController = Ember.Object.create({ 
    point: null, 

    init: function() { 
     this.set('point', App.Point.create()); 
    }, 

    resetCoordinates: function() { 
     this.point.reset(); 
    } 
}) 

App.PointView.create().append(); 
+0

Спасибо за внимание, но я не хочу выводить HTML. Я на самом деле пытаюсь создать объект-оболочку вокруг пути Рафаэля и хочу привязать координаты точки в моей модели данных к координатам точки на пути объекта Рафаэля. Мне удалось сделать это с помощью примера pangratz выше tho и использовать рассчитанные свойства для манипулирования объектом Raphael :) – Taum

Смежные вопросы