Skip to content

Instantly share code, notes, and snippets.

@priyajeet
Last active December 20, 2019 21:01
Show Gist options
  • Save priyajeet/5d9666233d28a183dcbb to your computer and use it in GitHub Desktop.
Save priyajeet/5d9666233d28a183dcbb to your computer and use it in GitHub Desktop.
/*
Personally the way I understood them was that behaviors are similar-ish to mixins to a module.
They are however not mixins. They are used to extract out common things needed in multiple modules.
As an example that we use within Box's webapp:
Say you have 2 modules - Foo and Bar. Both of these modules need a simple drop down menu showing some items.
The items shown are different for Foo and Bar, likewise when you click on an item, the action they perform
are also different for Foo and Bar.
If the items in the menu were exactly the same always and performed the same action always,
then we could essentially use a service to create this menu as a widget and re-use it everywhere.
So a service widget in that case. Internally we use the typical factory pattern for widgets.
But since the items differ and their action differ, behavior might be better for this particular use case.
Foo knows about its menu items and their actions. Bar knows about its own menu items and their actions.
So the only common thing between them end up being the opening/closing of a menu popup.
That essentially is a menu behavior while keeping what's shown in the menu and their corresponding
actions encapsulated in their respective modules Foo and Bar.
*/
<div data-module="foo">
<button data-menu-toggler='foo-menu1'>Foo</button>
...
<menu data-menu-name='foo-menu1'>
<menuitem data-type="foo-item-1">Foo Item 1</menutiem>
<menuitem data-type="foo-item-2">Foo Item 2</menutiem>
...
</menu>
</div>
<div data-module="bar">
<a data-menu-toggler='bar-menu1'>Bar</a>
...
<ul data-menu-name="bar-menu1">
<li data-type="bar-item-1">Bar Item 1</menutiem>
<li data-type="bar-item-2">Bar Item 2</menutiem>
...
</ul>
</div>
Box.Application.addBehavior('menu-toggler', function(context) {
function render(menu, toggler) {
// use them to create UI
// attach events for the menu itself, not its items
}
return {
init: function() {
// gets handle to the referencing module's dom node
var el = context.getElement();
// find what activates a menu within that module's dom
var toggler = el.querySelector('[data-menu-toggler]');
// find the menu itself within that module's dom
var menu = el.querySelector('[data-menu-name=' + toggler.dataset.menuToggler + ']');
render(menu, toggler);
}
};
});
Box.Application.addModule('foo', function(context) {
return {
behaviors: [ 'menu-toggler' ],
onclick: function(event, element, elementType) {
switch (elementType) {
case 'foo-item-1':
// do something
break;
case 'foo-item-2':
// do something
break;
...
}
}
};
});
Box.Application.addModule('bar', function(context) {
return {
behaviors: [ 'menu-toggler' ],
onclick: function(event, element, elementType) {
switch (elementType) {
case 'bar-item-1':
// do something
break;
case 'bar-item-2':
// do something
break;
...
}
}
};
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment