khusamov,
Там надо много людей плюсануть чтобы повторно можно было, человек 10 наверное, точно не считал |
Цитата:
Цитата:
Цитата:
Цитата:
Ext.define('Foo', { config: { blerg: { frobbe: 'throbbe' } } }); Ext.define('Bar', { extend: 'Foo', config: { blerg: { qux: 'xyzzy' } }); var beer = new Bar({ blerg: { foo: 42 } }); console.log(beer.getBlerg()); // { // foo: 42, // frobbe: 'throbbe', // qux: 'xyzzy' // } var gurgle = new Bar({ blerg: { frobbe: 'zingbong' } }); console.log(gurgle.getBlerg()); // { // frobbe: 'zingbong', // qux: 'xyzzy' // } Ну, я малость разошёлся с именами метапеременных, но надеюсь, что понятно всё же будет. ;) |
Цитата:
|
о как, конфиг теперь рекурсивно обрабатывается???
раньше такого не было. |
Ээээ, ну, не совсем рекурсивно… Там всё чуть сложнее. :) Эта система притащена в Ext JS 5.0 из Sencha Touch и (гхм) слегка допилена по месту. Делать с ней можно много весёлых штук для фана и профита, но лучше ограничиться документированным применением, примерно как я показал выше.
Ещё ньюанс: с массивами в конфигах надо быть осторожнее. Они, конечно, формально тоже объекты, но с массивами связка по прототипу не работает, и результат может быть непредсказуем. Это можно обойти, но я не уверен, что эти инструменты входят в публичное API. |
Цитата:
|
Если вы не помещаете массивы в свойства блока config, то никакой специальной магии к ним применяться не будет. Это будут простые свойства объекта, которые совершенно одинаковым образом работают на чтение - при этом неважно, где именно свойство находится, на экземпляре объекта или на прототипе. Сюрпризы могут быть, как вы уже выяснили, если пытаться в такие свойства записывать; но мы же о конфигах говорим, правильно? Конфиги по определению должны только читаться.
Если же вам надо помещать массивы в свойства блока config, то специальную магию надо будет слегка подправить напильничком, чтобы она работала как надо. Если не подправить, то из коробки может и не заработать. Со свойствами-объектами всё достаточно просто, их связывают по прототипной цепочке и они "просто работают". С массивами такого очевидного варианта нет. |
Цитата:
Я все этим методы активню пользуюсь, а теперь выясняется что нельзя? Они только для чтения??? |
Цитата:
|
Цитата:
Система конфигурации в Ext JS 5 имеет основной целью конфигурирование экземпляров объектов. Конфигурация каждого экземпляра может динамически меняться, при этом конфигурация других объектов того же класса изменяться не должна. Отсюда логически следует, что конфигурационные свойства классов должны быть доступны только для чтения, в отличие от объектов. В теории это всё звучит хорошо, но на практике у нас есть JavaScript и только одна схема наследования, прототипная. Это означает, что наследование конфигов можно сделать двумя способами: либо связывая конфиги-объекты по прототипной цепочке с соответствующими конфигами классов, либо тупо копируя все свойства для каждого нового экземпляра. Второй способ отпал по причине низкой производительности, поэтому остаётся первый. Если конфигурационные объекты по прототипу не связывать, то для каждого экземпляра объекта будут доступны только те свойства, которые содержатся в конфиге самого экземпляра - наследованные свойства доступны не будут. Именно так это работало в Ext JS 4: Ext.define('Bar', { blerg: { frobbe: 'throbbe' } }); var beer = new Bar({ blerg: { qux: 'dux' } }); console.log(beer.blerg); // { // qux: 'dux' // } Как видите, никакого наследования быть не может, т.к содержимое переменной beer это объект, прототипом которого является объект Bar. У каждого из этих объектов есть свойство blerg, и использоваться будет "верхнее" значение в прототипной цепочке. Блок config в Ext JS 5 работает по-другому и свойства-объекты связываются по прототипу, чтобы обеспечить наследование конфигов. Заметьте, что все эти пространные рассуждения никак не относятся к тривиальным значениям конфигов: строкам, числам, etc. С ними всё просто. Но объекты наследуются: Ext.define('Foo', { config: { blerg: { zilch: 42 } }, // Это нужно только в данном примере; // в обычном случае initConfig уже вызывается // родительским классом (Ext.Component, etc) constructor: function(config) { this.initConfig(config); } }); var foo = new Foo({ blerg: { bar: 'qux', zilch: 43 } }); console.log(foo.getBlerg()); // { // bar: 'qux', // zilch: 43 // } В этом примере объект в переменной foo имеет прототипом объект Foo, оба имеют конфиг blerg. Этот конфиг, в свою очередь, это тоже объект, прототипом которого является объект конфига blerg в объекте Foo. Свойство zilch имеется в обоих конфигах, но "верхнее" в цепочке принадлежит конфигу foo, поэтому оно и используется; свойство bar в конфиге Foo отсутствует и есть только в конфиге foo. Поскольку конфиги динамические, то их можно менять, но только для экземпляра объекта: foo.setBlerg({ zilch: 44 }); foo.getBlerg(); // { // zilch: 44 // } Если вы проинспектируете конфиг объекта Foo, то увидите, что он не изменился. Конфигурация происходит только на уровне экземпляра, но не класса. Что касается массивов, то с ними связывание по прототипу не работает, поэтому тоже будет использоваться "верхнее" значение в цепочке, так же как и с тривиальными типами данных: Ext.define('Baz', { config: { qux: [42] }, constructor: function(cfg) { this.initConfig(cfg); } }); var bazz = new Baz(); bazz.getQux(); // [42] var brazz = new Baz({ qux: [-1] }); brazz.getQux(); // [-1] Специальная магия нужна в случае, если вы хотите, чтобы массив был объединением элементов из наследованных конфигов с элементами из массива на экземпляре: Ext.define('MagicParent', { config: { qux: { $value: [42], merge: function(newValue, oldValue) { // Пристёгиваем новые элементы к старым return (oldValue || []).concat(newValue); } }, constructor: function(cfg) { this.initConfig(cfg); } }); Ext.define('MagicChild', { extend: 'MagicParent', config: { qux: [43] } }); var magic = new MagicChild({ qux: [44] }); magic.getQux(); // [42, 43, 44] // Значения, переданные в setter, считаются полными // и через цепочку связываний не проходят: magic.setQux([-1]); magic.getQux(); // [-1] Надеюсь, теперь будет понятнее. В целом система конфигов не безобразно сложна к пониманию, но имеет некоторые особенности, поэтому и остаётся большей частью приватной. Если разобраться, можно творить чудесатые чудеса. :) |
Часовой пояс GMT +3, время: 06:31. |