You can create a custom component from any of the existing ones, assigning properties, methods and events to it.
The library allows extending functionality of any component by adding building modules to it (however, most components feature all the necessary functionality by default) as well as creating a totally custom component that inherits from the basic view.
Simply put, the technique uses the protoUI(); command to construct the new component with it own name, properties and functions. All the new components must be based on existing ones.
webix.protoUI({
name:"newComponent", // the name of a new component
$init:function(config){
thid.load(data.xml)
//functions executed on component initialization
},
defaults:
{width:200}
on:{'onItemClick', function(){}}, //attached events
custom_func:function(){..function description..}, //any custom function
$getSize: function(){..},
$setSize:function(){..},
}, webix.Movable, // extended functionality
webix.ui.list); //the name of the base component
As a result, we get a custom component that
Later on, the component is inserted into the app the same way you do with library components:
webix.ui({
view:"newComponent",
..config options..
})
The must-have elements for such constructor are new component's name and the component it inherits from. Additional functionality can be included to your choice.
Editable List
webix.protoUI({
name:"editlist",
},
webix.EditAbility, webix.ui.list);
The protoUI constructor eliminates the need of repeated usage of the extend(); method each time you want to initialize a new instance of your custom component. Read more about extended component functionality.
Before we describe how the mentioned technique works, it will be helpful to summarize the main methods and properties you may use while developing a component.
this.$ready.push(...);
In this method you add HTML elements, specify event handlers.
As a parameter the method takes the object 'config' that contains all the properties which a user set in the constructor.
Inside the method you can refer to the HTML object of the component through this.$view.
Note, the method doesn't take properties set in the method 'defaults'.
They are available just after initialization is finished completely (i.e. $init and all the property setters are executed).
The method returns the array [gravW;width;gravH;height] (width gravity, fixed width, height gravity, fixed height).
The values of the array conform to the following rules:
The possible scenarios:
Sc.1 You want the parent container to set the size automatically (autosizing).
Solution: don't redefine the function or return [1;-1;1;-1]
Sc.2 You want to set relative width(height).
Solution:
a)for relative width return [yourValue;-1;1;-1]
b)for relative height return [1;-1;yourValue;-1]
Sc.3 You want to set fixed width(height).
Solution:
a)for fixed width return [1;yourValue;1;-1]
b)for fixed height return [1;-1;1;yourValue]
Let's consider some existing component, for example, window. It has a header and a body. Assume, you hide the header. The body of the window will keep the previous size but instead of the header you'll see empty space. To prevent this, you should specify a logic defining behaviour of the elements in such the situation. The appropriate logic must be specified in the method $setSize.
Fully custom components inherit from view, as a rule, which is an empty container for library components. Basic modules are also included into your component to support app-user interaction.
Let's see how can we create a multi-colored header for a three-column app.
webix.protoUI({
name:custom",
..configuration..},
webix.MouseEvents, webix.EventSystem, webix.ui.view);
1 . For a component you can set CSS classes with the help of the className(); method defined for $view property that points to an HTML container of the component. It is included into the $init function alongside with the innerHTML method to set containers for component items.
$init:function(config){
this.$view.className = "my_control";
this.$view.innerHTML = "<div class='item1'></div><div class='item2'></div>
<div class='item3'></div>";
}
2 . Define default properties:
defaults:{ controlHeight:50 }
3 . Create component items by defining item setter functions:
item1_setter:function(value){
if(value)
this.$view.childNodes[0].innerHTML = value;
return value;
}
These functions are used in the component code to set inner HTML for component items:
webix.ui({
view:"custom",
item1:"Reg Form",
item2:"Filmset",
item3:"Details"
})
4 . Size the component. Here two methods are used:
Both of them are used for inner logic. To size and resize existing components refer to the dedicated article.
$getSize:function(){
return [1,100000,this.config.controlHeight,this.config.controlHeight,1];
},
$setSize:function(x,y){
if (webix.ui.view.prototype.$setSize.call(this,x,y)){
var itemWidth = Math.round(this.$width/3);
for(var i=0;i<3;i++){
this.$view.childNodes[i].style.width = (i==2?this.$width-
(itemWidth*2):itemWidth) +"px";
this.$view.childNodes[i].style.height = this.$height+"px";
}
}
}
5 . Attach events to the component
on: {'onMouseOver': function(){...);}}
As a result, we've got a multi-colored header template within a three-columnn design and 'elastic' sizing, which means that the app can adjust its size to the current window size.
Related sample: Custom Component
Back to top