![]()
Важно.
Если вы этого еще не сделали, обязательно прочитайте первую часть и вторую часть этой статьи. Без этого будет очень трудно объяснить (или даже невозможно), а для вас понять, что написано в этой части.
Вступление.
Помогая на форуме, и читая код людей, которые делали ошибки при наследовании ExtJS классов, я обратил внимание на ошибки, которые пользователи обычно делают. Поэтому я решил написать эту статью, в которой буду собирать эти ошибки, и объяснять как их решать. Я имею ввиду что я не буду создавать больше частей этой статьи, а буду добавлять найденные ошибки сюда, вместо того чтобы бесконечно создавать части 4, 5 и т.д.
Наиболее распространенными источниками ошибок являются:
- Ненужное наследование.
- Добавление объектов к прототипу.
- Жесткая привязка к id.
Ненужное наследование.
Основными причинами наследования являются:
- Повторное использование.
- Добавление функциональности.
- И то и другое.
поэтому мы наследуем, если нам необходимо создать компонент для многократного использования или нам нужно добавить новый функционал классу (новые методы) или и то и другое. Если мы говорим о повторном использовании, наследование может быть простым:
MyPortlet = Ext.extend(Ext.Panel, {
anchor:'100%'
,draggable:true
,defaultType:'mygraph'
});
Вы видите что получается ? Мы будем использовать класс MyPortlet много раз, поэтому вместо того что писать каждый раз в приложении в 10000 строк эти строчки, мы просто 100 раз вызовем пред настроенный объект и сэкономим 297 строк кода.
Другая польза этого метода состоит в том, что если мы хотим изменить тип с ‘mygraph’ на ‘mygraph_new’, нам надо лишь поменять код в классе, который мы используем, это избавит нас от поиска и замены это же параметра в 100 мест кода.
(Ну 100 раз это конечно преувеличение, но экономия все равно будет).
Если говорить о добавлении нового функционала, то вот простой пример:
MyPanel = Ext.extend(Ext.Panel, {
onRender:function() {
MyPanel.superclass.onRender.apply(this, arguments);
alert('Rendered');
}
});
Здесь мы добавили новую логику к Ext.Panel, теперь у нашего класса больше возможностей, чем раньше.
Во всех других случаях использовать наследование нет необходимости.
Добавление объектов к прототипу.
Для начала выполним следующий код:
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<link rel="stylesheet" type="text/css" href="ext/resources/css/ext-all.css">
<script type="text/javascript" src="ext/adapter/ext/ext-base.js"></script>
<script type="text/javascript" src="ext/ext-all-debug.js"></script>
<title id="page-title">Extending Error: Object in prototype</title>
<script type="text/javascript">
Ext.BLANK_IMAGE_URL = 'ext/resources/images/default/s.gif';
Ext.onReady(function() {
MyPanel = Ext.extend(Ext.Panel, {
layout:'fit'
,panelConfig: {
bodyBg:'red'
}
,initComponent:function() {
var config = {
bodyStyle:'background-color:' + this.panelConfig.bodyBg
}; // eo config object
// apply config
Ext.apply(this, Ext.apply(this.initialConfig, config));
MyPanel.superclass.initComponent.apply(this, arguments);
} // eo function initComponent
,applyBackground:function(color) {
this.panelConfig.bodyBg = color;
this.body.applyStyles({'background-color':color});
} // eo function applyBackground
}); // eo extend
var p1 = new MyPanel({
title:'Panel with Blue Background'
,renderTo:Ext.getBody()
,width:240
,height:160
});
p1.applyBackground('blue');
var p2 = new MyPanel({
title:'Panel with Red Background'
,renderTo:Ext.getBody()
,width:240
,height:160
});
});
</script>
</head>
<body></body>
</html>
Чего мы ожидаем ? Это написано в title панелей: Верхняя панель (p1) должна быть с синим бэкграундом, потому что мы установили ей этот параметр после того как создали объект. А у нижней панели (p2) должен быть красный бэкграунд, потому что он стоит по умолчанию в классе MyPanel.
Но она получается тоже голубой!!! Почему ? Причина проста panelConfig это объект, который создается при определении класса и он добавляется к прототипу MyPanel. Объекты (массивы тоже) доступны по ссылке, получается что p1 и p2 используют один и тот же panelConfig. Устанавливая свойство bodyBg в методе applyBackground мы изменяем panelConfig. Поэтому мы создаем панель p2 с таким же голубым цветом.
Здесь вы сразу увидели ошибку, но устранение этой ошибки может занят у вас недели в реальных приложениях. Представьте например, что у вас прототип класса store.
Жесткая привязка к id.
Очень простой, но смертельной ошибкой является жесткая привязка наследуемого класса или его items, tollbars, buttons объектов к определенному id. Если мы жестко привязываемся к определенному id, мы не сможем создать несколько экземпляров нашего класса, ведь так ?
Вместо заключения.
Это пока все, но если я найду еще какие-либо ошибки, я обязательно добавлю их выше.
Оставайтесь с нами!
Источник: http://blog.extjs.eu/know-how/writing-a-big-application-in-ext-part-3/