PDA

View Full Version : Asynchronous Tree State Plugin/Example by Saki



jsakalos
4 Apr 2009, 4:50 PM
Hi all.

There is a question: "How do I keep the state of tree?" asked over and over in forums. So I coded the plugin that you can just stick to your existing tree and it becomes stateful.

See the example/demo at http://examples.extjs.eu/?ex=treestate

Enjoy!

MaxT
8 Apr 2009, 1:02 PM
When a node is collapased, the state of its descendents is not restored when the page is reloaded. Is this intentional?

Max

jsakalos
8 Apr 2009, 1:09 PM
Yes, it is trade off between usability and simplicity.

skay_v13
1 May 2009, 7:47 AM
in your blog http://examples.extjs.eu/?ex=treestate

there is no Php file for Treestate

Where is 'get-tree.php' ??

can u give me php source??

jsakalos
1 May 2009, 10:33 AM
The example is about tree state not about backend. BTW, the backend is proprietary so it will never be published.

skay_v13
2 May 2009, 4:14 AM
but can u give me example of PHP Source for tree??

because i don't know how to make tree dinamicly...

jsakalos
2 May 2009, 1:51 PM
Sorry, I have no example, only the backend mentioned above.

kisjonnk
7 May 2009, 1:17 AM
Hey Saki

This plugin doesn't seem to work! I've tested your example (http://examples.extjs.eu/?ex=treestate) in Firefox, Chrome and IE8.

The other state plugins (accordion, tab and window) works well.

jsakalos
7 May 2009, 10:20 AM
The example runs in iframe so if you reload iframe at the right side only it works. You can also repeatedly click "Run example" on the left tree. I have no idea yet why it doesn't restore state when the whole page is reloaded.

Bulle Bas
13 Jun 2009, 5:38 AM
I can confirm that tree state is not saved when the complete page is refreshed. Caching problem?

jsakalos
13 Jun 2009, 12:14 PM
Most likely. Try to right click on the right and select "Show only this frame".

Bulle Bas
14 Jul 2009, 4:58 AM
Most likely. Try to right click on the right and select "Show only this frame".
Yeah, that way it works.

Romanitch
11 Sep 2009, 2:30 AM
It is posible make work your plugin after tree.root.reload() ???

jsakalos
11 Sep 2009, 2:22 PM
You could try to call tree.applyState(tree.state) before root reload

boston-george
11 Dec 2010, 6:00 AM
Hi saki!

how can i display new form when i click on leaf node?

i have this code:



MyViewportUi = Ext.extend(Ext.Viewport, {
layout: 'border',
initComponent: function() {
this.items = [
{
xtype: 'panel',
title: '',
region: 'north',
layout: 'absolute',
height: 77
},
{
xtype: 'panel',
title: '',
region: 'south',
layout: 'absolute',
height: 51
},
{
xtype: 'treepanel',
title: 'Menu',
region: 'west',
width: 188,
rootVisible: false,
root: {
text: 'Menu',
id: 'menus'

},
loader: {
//url: 'rtvmenu.js'
url: 'rtvmenu.php'
}
},
{
xtype: 'panel',
title: 'Selezione',
region: 'center',
layout: 'absolute'
}
];
MyViewportUi.superclass.initComponent.call(this);
}
});


and



MyViewport = Ext.extend(MyViewportUi, {
initComponent: function() {
MyViewport.superclass.initComponent.call(this);

}

});


thank you so much!!

jsakalos
11 Dec 2010, 2:24 PM
How does your question relate to tree state?

Generally: you listen to an event and you take the appropriate action in the listener.

bauyrzhan
21 Feb 2011, 10:37 PM
Hi Saki. I used your plugin but it doesn't work. Shows this mistake. Am I don't understand anything?Please, help me. (and sorry for my English X))
Uncaught TypeError: Object #<an Object> has no method 'push'

jsakalos
22 Feb 2011, 3:56 AM
That's too little information to help you. First of all, make this example (http://examples.extjs.eu/?ex=treestate) to work at your server, then modify it to suit your needs.

Note: Hope you're not using IE for development, do you? Firefox/Firebug is the must for developers.

bauyrzhan
22 Feb 2011, 7:55 PM
No, Saki, I'm using Google Chrome. It has his own debugger. Does GChrome works with your example? I fixed my last problem, but your plugin does not work.
Does following works?
My tree panel:

.....
var tree = new Ext.tree.TreePanel({
title: 'Навигатор по группам показателей',
autoScroll: true,
animate: true,
enableDD: false,
containerScroll: true,
loader: {
url: 'Get/get-catalog-nodes.aspx'
, baseParams: {
cmd: 'getChildren'
, treeTable: 'tree2'
, treeID: 1
}
},
width: 450,
height: 600,
root: {
nodeType: 'async',
text: 'Показатели',
draggable: false,
id: '-1'
},
listeners: {
click: function (node, event) {
store.baseParams.pid = node.id;
store.load({ params: { start: 1, limit: 24} });
//alert(node.id);
node.expand();
},
expandnode: function (node) {
var t = node.getPath();
},
collapsenode: function (node) {
}
},
plugins: [new Ext.ux.state.TreePanel()]
});

.....

included script to the aspx file

.....

<script type="text/javascript" src="Scripts/Catalog.js"></script>
<script type="text/javascript" src="Scripts/Ext.ux.state.TreePanel.js"></script>

....

I did this, but no results. My treepanel not save the state(

jsakalos
22 Feb 2011, 11:51 PM
Does Catalog.js contain the tree? If so, you must include the plugin before the tree. Normally, you include all extensions and plugins right after the ExtJS Library. Your code is included last.

bauyrzhan
23 Feb 2011, 3:07 AM
Does Catalog.js contain the tree? If so, you must include the plugin before the tree. Normally, you include all extensions and plugins right after the ExtJS Library. Your code is included last.

Of course in catalog.js. Let me explain
Catalog.aspx header code:
..
...
<asp:Content ID="Content1" ContentPlaceHolderID="head" Runat="Server">

<link rel="stylesheet" type="text/css" href="Scripts/ext-3.3.0/resources/css/ext-all.css" />
<link rel="stylesheet" href="Styles/Site.css" type="text/css" />
<link rel="stylesheet" href="Styles/dropdown.css" type="text/css" />
<link rel="stylesheet" href="Styles/NewsDataView.css" type="text/css" />

<script type="text/javascript" src="Scripts/ext-3.3.0/adapter/ext/ext-base.js"></script>
<script type="text/javascript" src="Scripts/ext-3.3.0/ext-all-debug.js"> </script>
<script type="text/javascript" src="Scripts/dropdown.js"></script>
<script type="text/javascript" src="Charts/amline/swfobject.js"></script>

<script type="text/javascript" src="Scripts/Ext.ux.state.TreePanel.js"></script>
<script type="text/javascript" src="Scripts/Catalog.js"></script>


<link rel="stylesheet" href="Widgets/LiveSearch/combos.css" type="text/css" />
<script type="text/javascript" src="Widgets/LiveSearch/LiveSearchWidget.aspx"></script>

</asp:Content>
....

My TreePanel in Catalog.js:

....
...
var tree = new Ext.tree.TreePanel({
title: 'Навигатор по группам показателей',
autoScroll: true,
animate: true,
enableDD: false,
containerScroll: true,
loader: {
url: 'Get/get-catalog-nodes.aspx'
, baseParams: {
cmd: 'getChildren'
, treeTable: 'tree2'
, treeID: 1
}
},
width: 450,
height: 600,
root: {
nodeType: 'async',
text: 'Показатели',
draggable: false,
id: '-1'
},
listeners: {
click: function (node, event) {
store.baseParams.pid = node.id;
store.load({ params: { start: 1, limit: 24} });
//alert(node.id);
node.expand();

},
expandnode: function (node) {
var t = node.getPath();
},
collapsenode: function (node) {

}
},
plugins: [new Ext.ux.state.TreePanel()]
});
....

Does not work(

jsakalos
23 Feb 2011, 3:49 AM
Do you setup a state provider early in your code?

bauyrzhan
23 Feb 2011, 3:59 AM
Yes. Better, see full code of Catalog.js:


Ext.ns('Ext.ux.tree');

Ext.state.Manager.setProvider(new Ext.state.CookieProvider());

Ext.onReady(function () {

var path = new Array();
var count;

// create the data store
var store = new Ext.data.JsonStore({
totalProperty: 'total', // total data, see json output
root: 'results', // see json output
url: 'Get/get-catalog-page-grid-data.aspx',
baseParams: { pid: '-1' },
fields: [
{ name: 'IndicatorId', type: 'int' }
, { name: 'Name', type: 'text' }
, { name: 'No', type: 'int' }
, { name: 'IsLink', type: 'int' }
],
listeners: {
'load': store_load
}
});

function store_load() {
if (store.getTotalCount() == 0) {
grid.setTitle('Список показателей');
} else {
var node = tree.getSelectionModel().getSelectedNode();
grid.setTitle(node.text);
}
}

// create the Grid
var grid = new Ext.grid.GridPanel({
store: store,
columns: [
{ id: 'No', header: "№", width: 30, sortable: true, dataIndex: 'No' },
{ header: 'Наименование показателя', width: 390, sortable: true, dataIndex: 'Name', renderer: renderTopic, id: 'Name' }
],
stripeRows: true,
height: 600,
width: 450,
title: 'Список показателей',

bbar: new Ext.PagingToolbar({
pageSize: 24, // data to display
store: store,
displayInfo: true,
displayMsg: 'Показаны {0} - {1} из {2}',
emptyMsg: "Список пуст"
})
});

// render functions
function renderTopic(value, p, record) {
if (record.get('IsLink') == '0')
return String.format('<b>{1}</b>', record.data.IndicatorId, record.data.Name);
else
return String.format('<a href="Indicator.aspx?id={0}"><b>{1}</b></a>', record.data.IndicatorId, record.data.Name);
}

var tree = new Ext.tree.TreePanel({
title: 'Навигатор по группам показателей',
autoScroll: true,
animate: true,
enableDD: false,
containerScroll: true,
loader: {
url: 'Get/get-catalog-nodes.aspx'
, baseParams: {
cmd: 'getChildren'
, treeTable: 'tree2'
, treeID: 1
}
},
width: 450,
height: 600,
root: {
nodeType: 'async',
text: 'Показатели',
draggable: false,
id: '-1'
},
listeners: {
click: function (node, event) {
store.baseParams.pid = node.id;
store.load({ params: { start: 1, limit: 24} });
//alert(node.id);
node.expand();

},
expandnode: function (node) {
var t = node.getPath();
},
collapsenode: function (node) {

}
},
plugins: [new Ext.ux.state.TreePanel()]
});

// render this grid to paging-grid element
grid.render('paging-grid');

// render the tree
tree.render('tree-div');

tree.getRootNode().expand();

//tree.expandPath('/-1/5998/6278/6328/6351');
// load data from the url ( get-data-page-grid.aspx ) and add start and limit parameter
store.load({ params: { start: 1, limit: 24} });

});

jsakalos
23 Feb 2011, 9:57 AM
Look, "does not work" is not enough to find out where the problem is. The following works:


<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<link rel="stylesheet" type="text/css" href="ext/resources/css/ext-all.css" />
<link id="theme" rel="stylesheet" type="text/css" href="css/empty.css" />
<link rel="stylesheet" type="text/css" href="css/icons.css" />
<link rel="stylesheet" type="text/css" href="css/formloadsubmit.css" />
<link rel="shortcut icon" href="img/extjs.ico" />
<script type="text/javascript" src="ext/adapter/ext/ext-base.js"></script>
<script type="text/javascript" src="ext/ext-all-debug.js"></script>
<script type="text/javascript" src="js/Ext.ux.state.TreePanel.js"></script>
<script type="text/javascript" src="treestate.js"></script>
<title id="page-title">Asynchronous Tree State by Saki</title>
</head>
<body>
</body>
</html>


and


Ext.ns('Ext.ux.tree');

Ext.state.Manager.setProvider(new Ext.state.CookieProvider());

var tree = new Ext.tree.TreePanel({
id:'tree'
,autoScroll:true
// ,rootVisible:false
,root:{
nodeType:'async'
,id:'root'
,text:'Solar System'
,expanded:true
}
,loader: {
url:'get-tree.php'
,baseParams:{
cmd:'getChildren'
,treeTable:'tree2'
,treeID:1
}
}
,plugins:[new Ext.ux.state.TreePanel()]
}); // eo tree

// main entry point
Ext.onReady(function() {

// create and show window
var win = new Ext.Window({
id:'combo-win'
,title:Ext.fly('page-title').dom.innerHTML
,layout:'fit'
,width:280
,height:360
,closable:false
,border:false
,items:tree
});

win.show();

}); // eo onReady



I've tested it with Ext 3.3.1 and I found no problems.

bauyrzhan
24 Feb 2011, 9:00 PM
Thanks, Saki. I wrote saving state by using cookie)