Binding

Overview

Each component has the bind() method, which allows to define their source of data.

There are 3 groups of component

  • single value controls - buttons, inputs, labels - all of them can store only single variable of data
  • set of data controls - form, toolbar, template - all of them can store single data object, which can contain multiple variables
  • collection based controls - list, grid - they can store multiple data objects

Loading data in inputs ( single value controls )

  • Value of input is equal to the value of some other input
//each time, when value in input2 changed, 
//value in input1 will be set to the value of input2
$$('input1').bind('input2');
  • Value of input is equal to the some property from the different form
//each time, when value in form1@field_name changed, 
//value in input1 will be set to the value of form1@field_name
$$('input1').bind('form1','field_name');
  • Value of input taken from selected element of list
//each time, when item in list "mylist" selected
//value in input1 will be set to the property of selected item
$$('input1').bind('mylist','property_name');

Loading data in form ( record based controls )

  • Some field in form set from external input
//each time, when value in input1 changed, 
//value of "field_name" in "form1" will be set to the value of input1
$$('form1').bind('input1', 'field_name');
  • Template loaded from some form
//each time, when any value in form2 changed, 
//template will take all values from form2 and will update self
$$('template').bind('form1');
  • Form loaded from selected item in list
//each time, when item in list "mylist" selected
//form1 will take all values from selected item
$$('form1').bind('mylist');

Loading data in list ( collection based controls )

  • List filtration based on some input
//each time, when value in input1 changed, 
//list will be filtered, based on defined logic
$$('mylist').bind('input1', function(list_data, input_data){
	return list_data.some_property == input_data;
});
  • List filtration based on some form
//each time, when some value in form changed, 
//list will be filtered, based on defined logic
$$('mylist').bind('form1', function(list_data, form_data){
	if (!form_data) return false;
	return list_data.some_property == form_data.some_property;
});
  • List filtration based on selection in some other list
//each time, when selection in the first list is changed, 
//the second list will be filtered, based on defined logic
$$('mylist').bind('mylist2', function(list_data, list2_data){
	if (!list2_data) return false;
return list_data.some_property == list2_data.some_property;
});

Related sample: 10_server/01_loading/05_list_list_client.html

Syncing data collection

Below logic allows to sync two copy all, or part of data from one DataCollection to another. Slave collection will automatically update self, each time when master is updated.

  • List loaded with same data as some other collection
$$('slave_list').data.sync('master_list');
  • List loaded with filtered set of data
$$('slave_list').data.sync('master_list', function(){
	this.filter(function(data){
		return data.name.length < 6;
	});
});

Related sample: 10_server/01_loading/09_list_fill.html

  • List loaded with grouped set of data
dhx.extend($$('slave_list').data, dhx.GroupStore);
$$('slave_list').data.sync('master_list', function(){
	this.group({
		by:"#name#",
		map:{ name:["#name#"]}
	});
});

Related sample: 10_server/01_loading/09_list_fill.html

Non-UI data objects

Additionally, there are 3 non-ui objects which can be used in data binding. Those objects haven't got any graphical representation, and can be used only for data storing.

  • DataValue ( single value )
  • DataRecord ( single record )
  • DataCollection ( collection of records )

For all of them you can use the same API as shown above:

var data = new DataCollection({ 
	url:"some_data.json" 
});
$$('myform').bind(data);

Pushing data back

If you have form which is bound to the list ( common edit scenario ), after values in form changed by user, you may need to push that updated data back to the master list, to do so, just call

$$('myform').bind('list');
$$('saveButton').attachEvent('onItemClick', function(){
	$$('myform').save(); //will push updates back to the master list
});

Related sample: 06_grid/03_edit.html

If you have 2 forms bound to a DataStore object ( dhx.DataStore() ), sequential saving their changes can provoke data loss. In this case, use the saveBatch() method to provide simultaneous saving and prevent losses.

$$('myform1').bind('myStore');
$$('myform2').bind('myStore');
 
$$('myStore').saveBatch(function(){
        $$('myform1').save();
        $$('myform2').save();
});

Binding to server side data

You can use data binding with server side feeds, just define dataFeed property for the component and it will load new data from the server, instead of the master component.

  • Reloading list from server side
//each time when item in master list selected, 
//slave list will be reloaded from the server side
//some.php?dhx_filter[paramName]={master.name}
$$('slave_list').define("dataFeed", "some.php");
$$('slave_list').bind("master_list", function(master, filter){
		filter.paramName = master.name;
});

Related sample: 10_server\01_loading\06_list_list_server.html

  • Reloading template from server side
//each time when item in master list selected, 
//template will be reloaded from the server side
//some.php?action=get&id={master.id}
$$('template').define("dataFeed", "some.php");
$$('template').bind("master_list");

Related sample: 10_server/01_loading/12_list_to_template_server.html

Concept of cursor

List based controls, which are used as source of bind operation receives few extra events and API commands, which allows to push data in slave components.

You can use

$$('list').setCursor(id)

to force loading of necessary data in all components, which are using list as master control.

For getting cursor you can use the method getCursor():

var itemId = $$('list').getCursor();

Data scheme

You can define the default values for the DataCollection or list, by using

$$('list').data.scheme({
	name:"Default name",
	age:16
});
$$('list').add();		//will add {name:"Default name", age:16} record

also, for more complex init, you can use a function

$$('list').data.scheme({
	$init:function(obj){
		obj.name = "Default name";
		obj.age = 16;
	}
});