ExtJs6学习(四)【组件和容器】

组件和容器

组件模型

XType和ComponentManager

  • XType
    定义:XType是一个纯JavaScript对象,包含一个xtype属性,属性的值是一个字符串,标识该XType对应的类。
    作用:Xtype允许组件延迟实例化,加速复杂用户界面的类的实例化,并大大提高代码的整洁度。
  • ComponentManager
    定义:ExtJs系统会自动将部件的XType注册到ComponentManager。
    作用:包含所有组件操作的方法。
使用方法
var myPanel = {
  xtype: 'panel',
  width: 100,
  height: 100,
  html: 'hello'
}

上面的代码相当于配置一个宽高分别为100px的Ext.Panel部件。由此可以看出,在ComponentManager中所有组件与一个唯一的字符串是一一对应的,相当于可以通过这个字符串获取所对应的组件类的引用。

自定义类注册XType
Ext.define('MyApp.CustomClass', {
  extend: 'Ext.panel.Panel',
  alias: 'widget.myCustomComponent'
});

// 使用
new Ext.Panel({
  ...
  items: {
    xtype: 'myCustomComponent',
    ...
  }
});

在初始化一个包含子元素的可视化组件时(如上代码中的Ext.Panel),它会检查自己是否有this.items,并检查this.items里是否有XType的配置对象。如果找到配置对象,会尝试用ComponentManager.create创建一个该组件的实例,如果没有定义,则可视化组件会在调用ComponentManager.create的时候定义它的defaultType属性。
如下代码,会创建两个panel:

var panel1 = {
  xtype : 'panel',
  title : 'Plain Panel',
  html  : 'Panel with an xtype specified'
};

var panel2 = {
  title : 'Plain Panel 2',
  html  : 'Panel with <b>no</b> xtype specified'
};

Ext.create('Ext.window.Window', {
  width        : 200,
  height       : 150,
  title        : 'Accordion window',
  layout       : 'accordion',
  border       : false,
  layoutConfig : {
      animate : true
  },
  items : [
      panel1,
      panel2
  ]
}).show();

组件渲染

直接渲染

通过renderTo或者applyTo属性实例化。

懒惰(按需)渲染

忽略renderTo和applyTo属性,在必要的时候调用该组件的render方法。

组件生命周期

ExtJs组件的生命周期主要被划分为三个阶段:初始化、渲染、销毁。

这里写图片描述

组件生命周期的每一阶段都要经历好几步,这是通过基类Ext.Component来控制的。

初始化

这里写图片描述

  1. 应用组件的配置
    当初始化一个组件的实例时,传递的组件配置对象包含了希望让组件拥有的所有功能,这些都是在Ext.Component基类的前几行代码完成的。

  2. 注册事件
    诸如enable/disable,show,hide,render,destory,state restore,state save等等事件,是所有继承于Ext.Component的组件都会默认拥有的基本事件,它们将会在执行某些行为之前或之后被触发。

  3. ComponentMgr注册组件实例
    在这里,每一个组件的实例都会生成一个字符串作为其ID值,供Ext.Cmp()方法来获得该实例的引用。在实例的配置中,可以通过配置id值给其传递ID值,不过如果设置了同样的ID值,Ext.Cmp()方法找到的实例引用将会是最后一个设置了该ID的组件。也就是说,最后设置的ID值将会覆盖前面的所有相同ID值。

  4. 调用initComponent()方法
    关于initComponent()方法,在直接或间接继承了Ext.Component基类的组件中,该方法会在Component的构造函数constructor中被调用。
    这里来看看其回调顺序:
    Ext.Window ==> Ext.Panel ==> Ext.Container ==> Ext.BoxComponent ==> Ext.Component
    在自定义组件时,一般都会覆盖父类的initComponent()方法,并且在最后用this.callParent()来回调父类函数,则在实例化组件的过程中,container的initComponent方法里的this已经变成了该实例对象本身。如果不这么做,譬如直接将itsms写入配置中,则在内部调用container的initComponent方法时,this所指的对象将不是目标实例化的对象。配置内的items的内容将残留在new的对象上,从而导致在连续实例化同一个自定义组件时,除了第一个实例,后面的实例都将失败的结果。
    于是在自定义组件的时候,最好将配置项写入initComponent方法中,并在配置项最后使用this.callParent()来回调其父类函数。有许多工作都会在initComponent方法里完成。例如注册自定义的事件、设定data stores、创建子控件等。initComponent可以看做constructor的补充,因此经常用于扩展组件的入口点。

  5. 加载插件和组件渲染
    如果在constructor的参数中传递了plugin对象,plugin的init方法将会被调用,同时会将父对象作为参数传递进init方法里。如果组件中配置了renderTo或者applyTo,则组件将马上被渲染,否则,它会被延迟渲染,直到组件被显式调用显示,或被它的容器所调用。

渲染

这里写图片描述

  1. 触发beforeRender事件
    这是在组件被render渲染前被调用的。用以提供处理函数或者阻止组件的继续渲染。

  2. 设置容器
    如果没有父容器被指定,默认它的父对象被指定为它的容器。

  3. 调用onReader方法
    这是为子类执行呈现工作的一个非常重要的方法,这是一个模板方法,在子类中可以根据需来重写它的实现逻辑。直接被创建的类的 onRender 首先被调用,然后它可以通过superclass.onRender 来调用基类的 onRender 方法。这个方法很容易被重新实现,如果需要你可以在继承关系的任意类中重写这个方法。  

  4. 不隐藏组件
    默认,大多数组件都会通过设置像 x-hidden 这个样式来使它隐藏。当 autoShow 设置为true 时,这个隐藏功能的样式会被移除。

  5. 应用自定义样式
    所有的 Component 子类都支持指定 cls 配置属性,通过它可以为 Component 所呈现的HTML 元素指定 CSS 样式。通过添加组件的 cls 属性,使用标准的样式规则,是一个自定义可视组件显示效果的非常完美的方法。

  6. render 方法被触发
    简单的通知组件已经被成功的呈现了。

  7. 调用afterRender
    这是另一个模板方法,子类根据逻辑需要可以重新实现或覆盖该方法。所有的子类可以通过调 superclass.afterRender.来调用父类的方法。

  8. 组件隐藏或不可用
    根据配置选项的值来设置。

  9. 状态事件被初始化
    可以状态化的组件会定义一些事件来指定状态的初始化和保存。如果提供,这些事件会被添加。

销毁

这里写图片描述

  1. 触发beforedestroy
    这是一个可取消的事件,如果需要,可能通过提供事件代理来阻止组件被销毁。   

  2. 调用beforeDestroy方法
    又一个模板方法,在子类中可以重新实现和调用父类的方法。   

  3. 移除事件监听者(代理)
    如果组件已被呈现,则移除它底层的 HTML 元素的事件监听列表,然后将元素从 DOM中移除。

  4. onDestroy被调用
    这个还是一个模板方法,在子类可以重新实现。这里需要注意的是,容器类提供了一个默认的 onDestroy 实现,它会循环销毁它的成员组。

  5. 组件实例从ComponentManager中反注册
    不可以再通过Ext.getCmp获取到对象实例。

  6. destroy事件被触发
    这只是一个简单的提醒,表示组件销毁成功。

  7. 移除Component上的事件代理
    组件可以独立于元素,自己拥有事件代理,如果存在则移除它们。

容器

Container是一个幕后组件类,它为组件管理其子元素提供了基础

处理子元素

Ext.getCmp('myWin').add({
  title: 'Appended Panel',
  id: 'addedPanel',
  html: 'hello'
});

如上代码可以在myWin容器中新增一个id为addedPanel的panel组件。

Ext.getCmp('myWin').insert(1, {
  title: 'Inserted Panel',
  id: 'insertPanel',
  html: 'hello'
});

如上代码可以在myWin容器下标为1的位置插入一个id为insertPanel的panel组件。

查询组件

ExtJs 4.0开始带有一个ComponentQuery类,它有一个选择器引擎。ComponentQuery是模仿浏览器的选择器引擎设计的,所以可以以任何源节点为根执行查询操作。

查询组件与CSS的查询规则类似。例如:

Ext.ComponentQuery.query('#myDiv');

可以查询出一个id为myDiv的元素。
:不管找到多少元素,ComponentQuery返回的都将是一个数组,因此如果想要测试查询是否成功需要判断返回的数组长度是否大于0,同时如果想要获取元素,必须用下标访问。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值