Thursday, January 20, 2011

AS3 DataGrid component: Part 15

In this tutorial we will create an editable DataGrid and restrict characters in it by creating a custom CellRenderer class.

Here's how it is going to look like:


In the example, you can only edit the first column and you can only enter numbers in it.

Here is the code in the .fla:

import fl.data.DataProvider;
import fl.controls.dataGridClasses.DataGridColumn;

myGrid.move(10,10);
myGrid.setSize(300, 200);

var col_id:DataGridColumn = new DataGridColumn("ID");
myGrid.addColumn(col_id);
col_id.cellRenderer = loaderCellRenderer;
loaderCellRenderer._stage = this;
col_id.sortOptions = Array.NUMERIC;

var col_desc:DataGridColumn = new DataGridColumn("Name");
myGrid.addColumn(col_desc);

var textFormat1:TextFormat = new TextFormat();
textFormat1.size = 16;
textFormat1.color = 0x333333;
textFormat1.bold = true;
textFormat1.font = "Arial";

myGrid.setStyle("headerTextFormat", textFormat1);

var textFormat2:TextFormat = new TextFormat();
textFormat2.size = 10;
textFormat2.font = "Verdana";

myGrid.setRendererStyle("textFormat", textFormat2);

var myData:Array = [{Name: "John", ID: "1002"},
{Name: "Ralph", ID: "1003"},
{Name: "Ted", ID: "1004"},
{Name: "Bob", ID: "1005"}
];

myGrid.dataProvider = new DataProvider(myData);
myGrid.rowHeight = 26;
myGrid.rowCount = myGrid.length;

As I said before, we will be using a custom loaderCellRenderer class for this. The class will extend TextInput component, and we will able to use the restrict property to allow only numbers to be entered in the field.

Here is the full code:

package 
{

import fl.controls.TextInput;
import flash.events.Event;
import fl.controls.listClasses.ListData;
import fl.controls.listClasses.ICellRenderer;

public class loaderCellRenderer extends TextInput implements ICellRenderer
{
protected var _data:Object;
protected var _listData:ListData;
protected var _selected:Boolean;
public static var _stage;

public function loaderCellRenderer()
{
super();
restrict = "0-9";
addEventListener(Event.CHANGE, textChange);
}

public function textChange(Event):void{
_data.ID = text;
}

public function get data():Object
{
return _data;
}

public function set data(value:Object):void
{
_data = value;
text = value.ID
}

public function get listData():ListData
{
return _listData;
}

public function set listData(value:ListData):void
{
_listData = value;
}

public function get selected():Boolean
{
return _selected;
}

public function set selected(value:Boolean):void
{
_selected = value;
}

public function setMouseState(state:String):void
{
}

}
}

When the data is set, we want to get the information from the ID property of the data object (in the array) the CellRenderer belongs to and display it as text. The "text = value.ID" in set data makes sure of that.

However, we should also be able to change the data and when we do, the ID value in the array should change too. Thats why we add an Event.CHANGE listener and apply the text to the ID property using "_data.ID = text".

Now we have a DataGrid table which allows us to edit the first column with numbers only.

Thanks for reading!

Related:

AS3 DataGrid component: Part 1
AS3 DataGrid component: Part 2
AS3 DataGrid component: Part 3
AS3 DataGrid component: Part 4
AS3 DataGrid component: Part 5
AS3 DataGrid component: Part 6
AS3 DataGrid component: Part 7
AS3 DataGrid component: Part 8
AS3 DataGrid component: Part 9
AS3 DataGrid component: Part 10
AS3 DataGrid component: Part 11
AS3 DataGrid component: Part 12
AS3 DataGrid component: Part 13
AS3 DataGrid component: Part 14
AS3 DataGrid component: Part 16

1 comment:

jc said...

Great Tutorial,

Any clues on how to make this a bit more dynamic? As the value.ID is hard coded?

I am using this in a datagrid with 12 columns.

Having 12 loaderCellRenderer[0-11] is a bit wasteful.

Any way to make it so that the current column of
ID, Name, Make, Model, Discount, Features, etc.

Without using the 12 files right now, I get null reference errors or change data in a different column than the intended.

Post a Comment