7

アイテムが選択された後に左にアニメーション化するアニメーションを実装しようとしています。次のコードは機能します。しかし、約80%の確率でしかありません。

JS

//myItem
Template.myItem.rendered = function(){
  if(Session.get("selected_item") === this.data._id){
    $(this.firstNode).addClass("selected");
  } else {
    $(this.firstNode).removeClass("selected");
  }
};

Template.myItem.events({
  "click .myItem": function(evt, template){
    Session.set("selected_item", this._id);
  }
});


//myItemList
Template.myItemList.helpers({
  items: function(){
    return Items.find();
  }
});

テンプレート

<template name="myItem">
  <div class="myItem">{{name}}</div>
</template>

<template name="myItemList">
  {{#each items}}
    {{> myItem}}
  {{/each}}
</template>

CSS

.myItem { transition: all 200ms 0ms ease-in; }
.selected { left: -20px; }

また、コードを にラップしてMeteor.defer()、実際にすべてがアニメーションを実行する準備ができていることを確認しようとしました。

Template.myItem.rendered = function(){
  Meteor.defer(function() {
    if(Session.get("selected_item") === this.data._id){
      $(this.firstNode).addClass("selected");
    } else {
      $(this.firstNode).removeClass("selected");
    }
  });
};

しかし、それはこの種のエラーになります:

Exception from defer callback: TypeError {}

毎回アニメーションを機能させる方法についてのアイデアを見るのは素晴らしいことです.

アップデート

クラブは正しい答えを得ました。例外はthis参照から来ていました。詳細を追加したいと思います。そこで、アニメーションの実行方法に関する 2 つの作業バージョンを次に示します。

Meteor.defer()

Template.myItem.rendered = function(){
  var instance = this;
  if(Session.get("selected_item") === this.data._id){
    Meteor.defer(function() {  
      $(instance.firstNode).addClass("selected"); //use "instance" instead of "this"
    });
  }
};

selected(アイテムを再描画すると meteor がクラスを削除するため、実際にはここで else ブロックは必要ありません。)

または$().animate()

Template.myItem.rendered = function(){
  if(Session.get("selected_item") === this.data._id){
    $(this.firstNode).animate({
      left: "-20px"
    }, 300);
  }
};

jQuery アプローチを使用する場合は、CSS コードを削除する必要があります。

.myItem { transition: all 200ms 0ms ease-in; }
.selected { left: -20px; }

4

1 に答える 1