52

同じページに複数のテンプレートを使用して、ノックアウトforeachバインディングを実装しました。ここに例の1つを示します。興味のあることは、ブロックがレンダリングを終了するタイミングを見つけることです。試してみafterRenderましafterAddたが、それぞれに対して実行されると思います。要素であり、ループ全体が終了した後ではありません。

<ul data-bind="foreach: {data: Contacts, afterAdd: myPostProcessingLogic}">
  <li>
    <div class="list_container gray_bg mrgT3px">
      <div class="list_contact_icon"></div>
      <div class="contact_name"><span data-bind="text: first_name"></span> <span data-bind="text: last_name"></span></div>
      <div class="contact_number"><span data-bind="text: value"></span></div>
      <div class="callsms_container">
        <a href="#notification-box" class="notifcation-window">
          <div class="hover_btn tooltip_call">
            <div class="hover_call_icon"></div>
            <span>Call</span></div>
        </a>
        <a class="sendsms" href="#sendsms" rel="#sendsms">
          <div class="hover_btn tooltip_sms">
            <div class="hover_sms_icon"></div>
            <span>SMS</span></div>
        </a>
        <a href="#">
          <div class="hover_more_btn"></div>
        </a>
      </div>
      <!-- close callsms container -->
      <div id="notification-box" class="notification-popup">
        <a href="#" class="close"><img class="btn_close" src="images/box_cross.png" /></a> <img class="centeralign" src="images/notification_call.png" /> <span>Calling... +44 7401 287366</span> </div>
      <!-- close notification box -->
      <!-- close list gray bg -->
      <div class="tooltip_description" style="display:none" id="disp"> asdsadaasdsad </div>
    </div>
  </li>
</ul>

ループがレンダリングを終了したときの成功コールバックだけを見つけることに興味があります。

これが私のafterAdd関数です。これは基本的にいくつかのjQueryイベントを添付しますが、それほど多くはありません。

myPostProcessingLogic = function(elements) { 
  $(function(){
      $(".list_container_callog").hover(function(){  
          $(".callsms_container", this).stop().animate({left:"0px"},{queue:false,duration:800});
      }, function() {
          $(".callsms_container", this).stop().animate({left:"-98%"},{queue:false,duration:800});
      });
  });
}

事前に感謝し、成功のコールバックがあることを教えてください:)

4

8 に答える 8

71

afterRenderコールバックがありますknockout.js

foreach: { data: myItems, afterRender: renderedHandler }

ここにドキュメントがあります。

ハンドラー内で、レンダリングされたコレクションの長さがアイテムコレクションの長さと等しいかどうかを確認します。そうでない場合は、使用する予定の完全にレンダリングされたロジックを実行しないでください。

renderedHandler: function (elements, data) {
    if ($('#containerId').children().length === this.myItems().length) {
        // Only now execute handler
    }
}
于 2013-01-10T09:19:48.037 に答える
12

でラッピングしてみてulください

<div data-bind='template: {afterRender: myPostProcessingLogic }'>

テンプレート内のすべてが初めてレンダリングされたときにのみ機能します。ただし、myPostProcessingLogicへの呼び出しは1回だけです。これがフィドルです

<div data-bind='template: {afterRender: myPostProcessingLogic }'>
  <ul data-bind="foreach: Contacts">
    <li>
      <div class="list_container gray_bg mrgT3px">
        <div class="list_contact_icon"></div>
        <div class="contact_name"><span data-bind="text: first_name"></span> <span data-bind="text: last_name"></span></div>
        <div class="contact_number"><span data-bind="text: value"></span></div>
        <div class="callsms_container">
          <a href="#notification-box" class="notifcation-window">
            <div class="hover_btn tooltip_call">
              <div class="hover_call_icon"></div>
              <span>Call</span></div>
          </a>
          <a class="sendsms" href="#sendsms" rel="#sendsms">
            <div class="hover_btn tooltip_sms">
              <div class="hover_sms_icon"></div>
              <span>SMS</span></div>
          </a>
          <a href="#">
            <div class="hover_more_btn"></div>
          </a>
        </div>
        <!-- close callsms container -->
        <div id="notification-box" class="notification-popup">
          <a href="#" class="close"><img class="btn_close" src="images/box_cross.png" /></a> <img class="centeralign" src="images/notification_call.png" /> <span>Calling... +44 7401 287366</span> </div>
        <!-- close notification box -->
        <!-- close list gray bg -->
        <div class="tooltip_description" style="display:none" id="disp"> asdsadaasdsad </div>
      </div>
    </li>
  </ul>
</div>
于 2014-04-11T15:19:21.257 に答える
5

上記のチャックシュナイダーの答えは最高です。foreachはtbody要素にあるため、コンテナーレスコントロールを使用する必要がありました。

<!-- ko template: {afterRender: SetupCheckboxes } -->
<tbody data-bind="foreach: selectedItems" id="gridBody">
  <tr>
    <td>
      <input type="checkbox" />
    </td>
  </tr>
</tbody>
<!-- /ko -->
于 2016-09-06T05:15:00.957 に答える
4

次のようなKnockoutのcontainerlessメソッドを使用して、foreachを別のforeachループにラップするだけです。

<!-- ko foreach:{data: Contacts, afterRender: myPostProcessingLogic }-->
<ul data-bind="foreach: $data}">
  <li>
    <div class="list_container gray_bg mrgT3px">
      <div class="list_contact_icon"></div>
      <div class="contact_name"><span data-bind="text: first_name"></span> <span data-bind="text: last_name"></span></div>
      <div class="contact_number"><span data-bind="text: value"></span></div>
      <div class="callsms_container">
        <a href="#notification-box" class="notifcation-window">
          <div class="hover_btn tooltip_call">
            <div class="hover_call_icon"></div>
            <span>Call</span></div>
        </a>
        <a class="sendsms" href="#sendsms" rel="#sendsms">
          <div class="hover_btn tooltip_sms">
            <div class="hover_sms_icon"></div>
            <span>SMS</span></div>
        </a>
        <a href="#">
          <div class="hover_more_btn"></div>
        </a>
      </div>
      <!-- close callsms container -->
      <div id="notification-box" class="notification-popup">
        <a href="#" class="close"><img class="btn_close" src="images/box_cross.png" /></a> <img class="centeralign" src="images/notification_call.png" /> <span>Calling... +44 7401 287366</span> </div>
      <!-- close notification box -->
      <!-- close list gray bg -->
      <div class="tooltip_description" style="display:none" id="disp"> asdsadaasdsad </div>
    </div>
  </li>
</ul>
<!-- /ko -->
于 2014-06-13T08:09:49.430 に答える
1

上記の解決策はうまく機能します。さらに、foreachの「as」オプションを使用する必要がある場合は、次のように実行できます。

data-bind="foreach: { data: myItems, afterRender: renderedHandlet, as: 'myItem'}">
于 2014-02-10T20:22:08.330 に答える
1

バージョン3.5では、Knockoutは、ノードのコンテンツがバインドされたことを通知するイベントを提供します

HTML

<div data-bind="childrenComplete: bindingComplete">...</div>

JavaScript

function bindingComplete(){
...
}

すべての子データバインディング式をカプセル化するDOM内のポイントでイベントバインディング式を作成する場合、それはページバインディングの完全なイベントに相当します。

参照 https://knockoutjs.com/documentation/binding-lifecycle-events.html

于 2019-10-15T19:46:27.750 に答える
0

私は最近、ノックアウトを使用してプルリクエストを行い、バインディングで定義する2つのイベントを追加し、アンラップしてから、アイテムをレンダリングする前とすべてのアイテムがレンダリングされた後に正しいスポットを呼び出しました。私は彼らから何も返事をもらっていませんが、これはあなたがやりたいことを正確に実行しますが、それを機能させるためにハッキーなコードを書く必要はありません。これまで誰もこのリクエストをしていないことに驚いています。ソースに追加したこれらのコールバックを使用して、ノックアウトバインドされたjqueryデータテーブルを破棄して再初期化しました。これが最も簡単な解決策でした。私はそれを別の方法で試みる多くの試みをオンラインで見ましたが、これは最も簡単な解決策です。

プルリクエスト:-> pr 1856

ko.bindingHandlers.DataTablesForEach = {

  init: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
    var nodes = Array.prototype.slice.call(element.childNodes, 0);
    ko.utils.arrayForEach(nodes, function(node) {
      if (node && node.nodeType !== 1) {
        node.parentNode.removeChild(node);
      }
    });
    return ko.bindingHandlers.foreach.init(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext);
  },
  update: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {

    var value = ko.unwrap(valueAccessor()),
      key = "DataTablesForEach_Initialized";

    var newValue = function() {
      return {
        data: value.data || value,
        beforeRenderAll: function(el, index, data) {

          if (ko.utils.domData.get(element, key)) {

            $(element).closest('table').DataTable().destroy();
          }
        },
        afterRenderAll: function(el, index, data) {
          $(element).closest('table').DataTable(value.options);
        }
      };
    };

    ko.bindingHandlers.foreach.update(element, newValue, allBindingsAccessor, viewModel, bindingContext);

    //if we have not previously marked this as initialized and there is currently items in the array, then cache on the element that it has been initialized
    if (!ko.utils.domData.get(element, key) && (value.data || value.length)) {
      ko.utils.domData.set(element, key, true);
    }

    return {
      controlsDescendantBindings: true
    };
  }
};

ノックアウトデータテーブルJSFiddle

于 2015-06-05T17:41:28.377 に答える
0

afterRenderAllknockout.jsでコールバックを試してください:

foreach:{データ:myItems、afterRenderAll:myPostProcessingLogic}

于 2017-12-17T22:07:28.550 に答える