2

我正在开发一个简单的基于 JavaScript 的插件架构,它允许来自任何框架(jQueryUI、ExtJS 等)的任何 JavaScript 控件。插入并在任何网页上重复使用。我下面的插件恰好使用 ExtJS 4。

第一个插件在第一个选项卡中呈现良好。但是,由于页面加载时第二个选项卡尚未呈现,因此第二个插件(也是一个网格)首先呈现到文档正文,然后在选项卡内正确呈现(HTMLElement/div 被移动)选项卡被选中。我希望在选项卡内呈现之前隐藏插件内容。另外,当它确实渲染时(选择选项卡时),除非我调整列大小,否则水平滚动条不会显示。

任何想法如何解决这一问题?

想法:使用 contentEl 以外的东西;利用各种 ExtJS 配置选项;改变我的架构。

这是插件代码:

(function(MyNamespace) {
  var gridDataStore = ...

  MyNamespace.Plugin.Chart = MyNamespace.Plugin.extend({
    return {
      initialize: function() {
        // ...
      },

      render: function() {
        var stockGrid = Ext.create('Ext.grid.Panel', {
          autoRender: true,
          autoShow: true,
          store: gridDataStore,
          header: false,
          stateId: 'stateGrid',
          columns: [
            {text: 'Symbol',      width: 75,  sortable: true, dataIndex: 'symbol'},
            {text: 'Description', width: 200, sortable: true, dataIndex: 'description'},
            {text: 'Quantity',    width: 75,  sortable: true, dataIndex: 'quantity'},
            {text: 'Last Price',  width: 85,  sortable: true, dataIndex: 'last_price'}
          ],
          viewConfig: {
            stripeRows: true,
            enableTextSelection: true
          }
        });

        return stockGrid.getEl().dom;
      }
    };
  }
})(MyNamespace);

这是使用插件的代码:

var chart = new MyNamespace.Plugin.Chart();
var anotherPlugin = new MyNamespace.Plugin.Another();

var stocksWindow = Ext.create('Ext.Window', {
  title: 'Stocks',
  width: 600,
  height: 450,
  layout: 'fit',
  items: [
    Ext.create('Ext.tab.Panel', {
      activeTab: 0,
      items: [{
        title: 'Chart',
        autoScroll: true,
        contentEl: chartPlugin.render()  // RENDER FIRST PLUGIN IN FIRST TAB
      },{
        title: 'Something Else',
        autoScroll: true,
        contentEl: anotherPlugin.render()  // RENDER SECOND PLUGIN IN SECOND TAB
      }]
    })
  ]
});

我可以将它添加到一个不可见的容器中,但这样做感觉很脏:

var container = document.createElement('div');
document.getElementsByTagName('body')[0].appendChild(container);
container.style.visibility = 'hidden';

var stockGrid = Ext.create('Ext.grid.Panel', {
  ...
  renderTo: container
  ...
});

这是一个例子

4

1 回答 1

1

这是您的代码的一些问题。

你所说的插件不是插件,它们只是Ext.grid.Panel. 插件是为 . 添加功能的东西Ext.Component,但这不是Stocks正在做的事情。这就是我们所说的预配置类。

这就是我要做的,只需将MyNamespace.Plugin.Stocks其设为 的子类Ext.grid.Panel,您现在可以轻松地将它们作为 a 的项目传递Ext.tab.Panel。确保重命名它,它不是插件。

通过为您的小部件子类提供alias: 'widget.stock-grid',您可以只使用对象定义来创建它们,而不必实例化它们,框架将只在需要时才渲染它(选项卡被激活)

        Ext.create('Ext.tab.Panel', {
            activeTab: 0,
            items: [{
                title: 'Stocks',
                autoScroll: true,
                xtype: 'stock-grid'
            },{
                title: 'Orders',
                autoScroll: true,
                xtype: 'stock-grid'
            }]
        })

使用托管布局时,您不能简单地将节点复制到另一个容器中,因为您复制到其中的节点不会有托管布局。

这是您的代码的修改版本,其编写方式更像 Ext-JS 的预期。http://jsfiddle.net/NVfRH/10/

您可以查看生成的 HTML,您会注意到订单下的网格仅在您激活该选项卡时才会呈现。

您还应该注意到您的网格没有正确调整自己的大小以填充窗口,我的代码修复了这个问题,因为它们正确放置在布局管道中并服从fit布局。

剩下的问题

  • 您的网格共享一个商店,请注意,当您对其中一个进行排序时,另一个也会进行排序,因此您不能将它们进行不同的排序。
  • 您正在使用 a stateId,但随后您创建了两个具有相同的实例stateId,所有 stateId 必须是唯一的

最后,我必须问,当查德约翰逊将他的名字改名为查德奥乔辛科时,你真的松了一口气吗?:)

于 2012-12-07T18:44:41.147 回答