Речь пойдет об использовании i-bem.js. Предположим у меня есть декларация блока 'input' с методами disable и enable, которые устанавливают модификатор disabled соответствено в true или false. Для классов input_disabled_true и input_disabled_false у меня заготовлены css-свойства, что-то делающие с внешним видом инпута.
Далее, я создаю декларацию блока superInput, укзаывая, что он является наследником input. Я хочу использовать методы disable и enable из базового класса. Только вот они устанавливают класс superInput_disabled_{true|false}. Для решения задачи приходится делать новый блок, не наследуя его от input, в html делать микс блоков superInput и input на отдом элементе (можно вложенными), а в скрипте декларации блока искать на текущем блоке(superInput) блок input, у которого можно вызвать disable и enable.
Очень хочется в таком случае воспользоваться наследованием в javascript, но по факту это оказывается неудобно.
Пример немного искуственный, но подобные задачи появляются. Как рекомендуется решать такие проблемы? Все же наследованием или отдельной декларацией (я про javascript)
Распишу поподробнее варианты. Исходим из того, что у нас есть blocks/input/input.js, в котором реализовано базовое поведение,
1. Переопределения на уровнях
Если нам нужно, на некоторой странице иметь некий superInput, который чем-то отличается от базового input, то нам не обязательно именно придумывать новое имя и новый блок. Можно создать pages/index/blocks/input/input.js и положить туда BEM.DOM.decl('input', ... тут декларация полей и методов ...), эта декларация будет себя вести в точности как наследник базового blocks/input/input.js, т.е. будут доступны правильные this.__base() и this.__self.
2. Модификаторы
Поведение superInput базирующееся на базовом input можно представить как модификатор, например с именем type и значением super. В файле blocks/input/_type/input_type_super.js (который, кстати, можно создать командой bem create mod -l blocks -b input type -v super -T js) нужно написать BEM.DOM.decl({ block: 'input', modName: 'type', modVal: 'super'}, ... тут декларация полей и методов ...). Декларация полей и методов для модификатора также ведёт себя как наследник от базового класса, т.е. в методах доступны правильные this.__base() и this.__self.
3. Миксы
Мы можем выражать поведение элементов на странице с помощью смешивания нескольких БЭМ-сущностей на одной DOM-ноде. В HTML-е это будет выглядеть примерно так: . В BEMJSON так: { block: 'input', mix: [ { block: 'super-input' } ] }. После этого в коде блока blocks/super-input/super-input.js нет необходимости делать baseBlock, зато можно получить доступ к input с помощью метода this.findBlockOn('input') (документация в JSDoc).
4. Композиция блоков
Наконец можно просто использовать блок в составе другого блока, тут больше подходит пример с input и superForm. Можно вложить input внутрь superForm и из кода blocks/super-form/super-form.js можно будет получить доступ к input с помощью метода this.findBlockInside('input') (документация в JSDoc) и this.findBlocksInside('input') (документация в JSDoc).
Наследование в i-bem.js с помощью baseBlock мы реализовали скорее для полноты API и для того, чтобы было удобно делат некоторые i-* блоки, т.е. для функциональности внутри технологии JS. Этот способ не очень подходит для повторного использования БЭМ-сущностей в пределах всех технологий.
P.S. Так же рекомендую почитать критику объектно-ориентированного подхода вообще, например http://habrahabr.ru/post/143620/ .
1. Переопределение на уровнях. Не совсем понял, почему на уровне переопределения input будет являться наследником input из библиотеки блоков.
2. Модификаторы. Похоже, что в данном случае мне лучше всего подойдет именно это.
3. Миксы. Они удобны, но не в случае, когда нужно доопределить блок, потому что выглядит это как костыль. Может быть это просто замыленность взглядов, но ...
4. Композиция блоков. Да, да, это понятно, но случай не тот )
P.S. Статью прочитал и по ссылкам походил. Было полезно.
P.P.S. Большое спасибо за развернутый ответ!