Marionette没有't在第二次显示父视图时渲染子视图

Marionette doesn't render the sub-views when the parent is shown the second time

本文关键字:视图 显示 第二次 没有 Marionette      更新时间:2023-09-26

我想重用应用程序中的视图(以前打开的屏幕),但区域内容消失了。如何防止Marionette这样做?

  var app = new Backbone.Marionette.Application();
  window.app = app;
  app.addRegions({
    root: 'body'
  });
  var View1 = Marionette.LayoutView.extend({
    template: _.template('<div>View1<div class="sub"></div></div>'),
      regions: {
        sub: '.sub'
      }
  });
  var View2 = Marionette.ItemView.extend({
    template: _.template('<div>View2</div>')
  });
  var SubView = Marionette.ItemView.extend({
    template: _.template('<div>SubView</div>')
  });
  var view1 = new View1();
  var view2 = new View2();
  var subView = new SubView();
  app.root.show(view1, { preventDestroy: true });
  view1.sub.show(subView, { preventDestroy: true });
  setTimeout(function() {
    app.root.show(view2, { preventDestroy: true });
    setTimeout(function() {
      app.root.show(view1, { preventDestroy: true });
    }, 500);
  }, 500);

或者小提琴http://jsfiddle.net/ndr7262y/

因此preventDestroy不会停止区域内的子视图被销毁,而只是实际区域本身。Marionette在设计上试图鼓励破坏视图并重新初始化它们,以便正确处理清理。不过,解决这一问题的一种方法是在显示视图时收听,然后显示子

app.listenTo(view1, "show", function () {
          view1.sub.show(subView)
});

唯一的问题是子视图仍在被销毁,因此您可以覆盖子视图的销毁方法以不销毁视图,这会让跟踪变得有点棘手,尽管现在您必须手动确保绑定正确应用/删除

  var SubView = Marionette.ItemView.extend({
      template: _.template('<div>SubView</div>'),
      destroy: function () {
          if (this.isDestroyed) {
              return;
          }
          var args = [].slice.call(arguments);
          this.triggerMethod.apply(this, ['before:destroy'].concat(args));
          // mark as destroyed before doing the actual destroy, to
          // prevent infinite loops within "destroy" event handlers
          // that are trying to destroy other views
          this.isDestroyed = false;
          this.triggerMethod.apply(this, ['destroy'].concat(args));
          // unbind UI elements????? well its not beng destoryed so probably don;t wantto do this
          //unless you manually handle rebind the events
          //this.unbindUIElements();
          return this;
      }
  });

最终结果http://jsfiddle.net/ndr7262y/2/

但这里更好的方法是当视图1显示时重新对子视图进行分类

app.listenTo(view1, "show", function () {
           var subView = new SubView();
          view1.sub.show(subView)
});

而现在你却没有;不必担心清理或覆盖destroy方法。http://jsfiddle.net/ndr7262y/4/