PDA

View Full Version : Add Items to Panel



irfaniqbal
26 Jan 2011, 2:31 AM
Hi all,
I have a main panel in my App. That panel contains one item and i want to add some other panel items to my Main panel. I have tried this but doesn't help me.



app.add(newPanel); // app is main panel of my Application and newPanel is a new panel which i want to add
app.doLayout();
app.setActiveItem(1); //After adding newPanel i want to set it as Active Item

Any help is my pleasure. thanks in advance.

Stoot98
26 Jan 2011, 5:01 AM
Have you set the app panel as a card layout?

irfaniqbal
26 Jan 2011, 6:05 AM
yeh i have set it to Card Layout.

AndreaCammarata
26 Jan 2011, 6:34 AM
Hi all,
I have a main panel in my App. That panel contains one item and i want to add some other panel items to my Main panel. I have tried this but doesn't help me.



app.add(newPanel); // app is main panel of my Application and newPanel is a new panel which i want to add
app.doLayout();
app.setActiveItem(1); //After adding newPanel i want to set it as Active Item

Any help is my pleasure. thanks in advance.

Hi infaniqbal.
Try this example I develop



Ext.setup({
onReady: function() {

var pnlToAdd = new Ext.Panel({
html: 'This is a new Panel'
});

var pnlMain = new Ext.Panel({
fullscreen: true,
layout: 'card',
cardSwitchAnimation: {
type: 'flip'
},
dockedItems: [{
xtype: 'toolbar',
title: 'Example',
items: [{
text: 'Add Item',
handler: function(){
pnlMain.add(pnlToAdd);
pnlMain.setActiveItem(2);
}
}]
}],
items: [{
xtype: 'panel',
html: 'First Panel'
},{
xtype: 'panel',
html: 'Second Panel'
}]
});
}
});


This works great for me on 1.0.1a.

Hope this helps.

irfaniqbal
26 Jan 2011, 9:43 AM
thanks andrea for your reply. it helps me but one more thing that the panel which i want to add, has multiple items and i want to add all items to Main panel. i want something like this:


app.add(allPanels.items[0]);
app.add(allPanels.items[1]);
app.add(allPanels.items[2]);but it give me following error: Cannot read property 'isComponent' of undefined
Any idea how can i do it? thanks

AndreaCammarata
26 Jan 2011, 1:44 PM
thanks andrea for your reply. it helps me but one more thing that the panel which i want to add, has multiple items and i want to add all items to Main panel. i want something like this:


app.add(allPanels.items[0]);
app.add(allPanels.items[1]);
app.add(allPanels.items[2]);but it give me following error: Cannot read property 'isComponent' of undefined
Any idea how can i do it? thanks

Hi infaniqbal.
Why you want add each panel one by one?
If you look at the example I post you a little bit edited in the red part



Ext.setup({
onReady: function() {

var pnlToAdd = new Ext.Panel({
html: 'This is a new Panel',
items: [{
html: 'SubPanel 1'
},{
html: 'SubPanel 2'
},{
html: 'SubPanel 3'
}]
});

var pnlMain = new Ext.Panel({
fullscreen: true,
layout: 'card',
cardSwitchAnimation: {
type: 'flip'
},
dockedItems: [{
xtype: 'toolbar',
title: 'Example',
items: [{
text: 'Add Item',
handler: function(){
pnlMain.add(pnlToAdd);
pnlMain.setActiveItem(2);
}
}]
}],
items: [{
xtype: 'panel',
html: 'First Panel'
},{
xtype: 'panel',
html: 'Second Panel'
}]
});
}
});


You will see that every panel defined as item inside the panel you are going to add, will be added by default because they are part of "pnlToAdd". You don't need to add them one by one.

Hope this helps.

gcallaghan
26 Jan 2011, 1:48 PM
app.add(allPanels.items[0]);

if allPanels is a sencha container, then the syntax is allPanels.items.get(0)

see Ext.util.MixedCollection in the api docs for more info

irfaniqbal
27 Jan 2011, 2:23 AM
thank Andrea & gcallaghan.
@gcallaghan: No allPanels is not a container. its a Panel and items it contains are also panels.

Actually, items of allPanels are different panels and i want to set one of these items as ActiveItem in different conditions one by one. So, how could i get a particular item of allPanels after adding it to main panel (app) and then set it as ActiveItem? thanks

AndreaCammarata
27 Jan 2011, 2:54 AM
Is this what you mean?



Ext.setup({
onReady: function() {

var allPanels = new Ext.Panel({
layout: 'card',
items: [{
html: 'SubPanel 1'
},{
html: 'SubPanel 2'
},{
html: 'SubPanel 3'
}]
});

var pnlMain = new Ext.Panel({
fullscreen: true,
layout: 'card',
cardSwitchAnimation: {
type: 'flip'
},
dockedItems: [{
xtype: 'toolbar',
title: 'Example',
items: [{
text: 'Add allPanels',
handler: function(){
//Let's adding allPanels to main app Panel
pnlMain.add(allPanels);
//Set the allPanels as active item
pnlMain.setActiveItem(2);
}
},{
text: 'Set SubPanel 2 as Active',
handler: function(){
//Thi set the 'SubPanel 2' as the active item of allPanel
pnlMain.getComponent(allPanels).setActiveItem(1);
}
}]
}],
items: [{
xtype: 'panel',
html: 'First Panel'
},{
xtype: 'panel',
html: 'Second Panel'
}]
});
}
});


Pressing the 'Add allPanels' buttons all the panels will be added as item of your main app panel, and, by default, the "subPanel1" will set as active.
Pressing the "Set SubPanel 2 as Active", the "subPanel2" will be set as active.

Hope this helps.

AndreaCammarata
27 Jan 2011, 3:16 AM
Otherwise, if you don't want to add allPanel to you main app panel, but only one subPanel of allPanel you can do



Ext.setup({
onReady: function() {

var allPanels = new Ext.Panel({
items: [{
html: 'SubPanel 1'
},{
html: 'SubPanel 2'
},{
html: 'SubPanel 3'
}]
});

var pnlMain = new Ext.Panel({
fullscreen: true,
layout: 'card',
cardSwitchAnimation: {
type: 'flip'
},
dockedItems: [{
xtype: 'toolbar',
title: 'Example',
items: [{
text: 'Set SubPanel 2 as Active',
handler: function(){
//Let's adding "Sub Panel 2" to main app Panel
pnlMain.add(allPanels.getComponent(1));
//Set the "Sub Panel 2" as active item
pnlMain.setActiveItem(2);
}
}]
}],
items: [{
xtype: 'panel',
html: 'First Panel'
},{
xtype: 'panel',
html: 'Second Panel'
}]
});
}
});
Hope this helps.

irfaniqbal
27 Jan 2011, 4:39 AM
thanks again Andrea, but the problem is still there. here is the code for allPanel:


Application.views.AllPanels = Ext.extend(Ext.Panel, {
id: 'allPanels',
activeItem: 0,
dockedItems: dockedItems ,
initComponent: function() {
this.homeScreen = new Application.views.home();
this.supplementsScreen = new Application.views.supplements();
this.nutritionScreen = new Application.views.nutrition();

this.items = [this.homeScreen];
Application.views.AllPanels.superclass.initComponent.call(this);
}
});
and the code for main Panel is:


Application.App = Ext.extend(Ext.Panel, {
fullscreen: true,
layout: 'card',
activeItem: 0,
id: 'mainPanel',
initComponent: function() {
this.startScreen = new Application.views.login({
flex: 1
});
this.items = [this.startScreen];
Application.App.superclass.initComponent.call(this);
},
});
Now i am adding allPanel to main panel like this:


allPanels = new Application.views.AllPanels();
app.add(allPanels);
app.getComponent(allPanels).setActiveItem(1); //I have tried both ways of setting the active item but nothing works.
//app.setActiveItem(1);
hope i have described my problem well. thanks

AndreaCammarata
27 Jan 2011, 5:42 AM
I think now I understand your problem.
Try this example




new Ext.Application({
name: 'Application',

launch: function() {

var app, allPanels;

Application.views.AllPanels = Ext.extend(Ext.Panel, {
layout: 'card',
initComponent: function() {

this.homeScreen = new Ext.Panel({
html: 'Home Panel'
});

this.supplementsScreen = new Ext.Panel({
html: 'Supplements Panel',
dockedItems: [{
xtype: 'toolbar',
title: 'Supplements',
dock: 'top'
}]
});

this.items = [this.homeScreen, this.supplementsScreen];
Application.views.AllPanels.superclass.initComponent.call(this);
}
});

Application.App = Ext.extend(Ext.Panel, {
fullscreen: true,
layout: 'card',
activeItem: 0,
initComponent: function() {

this.startScreen = new Ext.Panel({
html: 'Start Screen',
dockedItems: [{
xtype: 'toolbar',
title: 'Example',
dock: 'top',
items: [{
text: 'Show Supplements',
handler: function(){

//Let's add allPanels
app.add(allPanels);

//You have to set allPanels as active before
app.setActiveItem(allPanels);

//Set Supplements as active
app.getComponent(allPanels).setActiveItem(1);
}
}]
}]
});

this.items = [this.startScreen];
Application.App.superclass.initComponent.call(this);
},
});

app = new Application.App();

allPanels = new Application.views.AllPanels();

}
});


Notice that you have to set the allPanel layout before everything and add all your panel as items of your appPanel.
Than, after adding your "allPanel" to your "app" you have to set it as active before set as active a panel item placed inside "allPanel".
I fon't know if this is clear.
Notice that my code if for example purpose, obviously it's better if you create a .js for every view you have.

Hope this helps.

irfaniqbal
27 Jan 2011, 8:02 AM
thanks Andrea. This solution works fine for me :) . I did not use it exactly but i fetch my solution out of it. :)

I really appreciate your help and services for this community. Keep it up.

AndreaCammarata
27 Jan 2011, 8:08 AM
thanks Andrea. This solution works fine for me :) . I did not use it exactly but i fetch my solution out of it. :)

I really appreciate your help and services for this community. Keep it up.

Thank you infaniqbal :).
I'm glad to give a hand ;)

irfaniqbal
27 Jan 2011, 8:13 AM
one correction for you :P my name is 'irfan iqbal' not 'infaniqbal' {plz correct the spell :) }

And one more question. As you know my application's structure, please suggest me how can i achieve Back Button functionality in it. so that i can move across the panels. thanks

gcallaghan
27 Jan 2011, 9:12 AM
Sencha should support this using Ext.Application and Ext.Routes. This isn't terribly well documented at the moment. I've implemented something in the meantime by overriding the setActiveItem function of my container panel.



listeners:{
...
goBack:function(){
if (this.history.length > 0){
this.setActiveItem(
this.history.pop(),
{type:'slide',reverse:true},
{back:true}
);
}
},
...
},
setActiveItem:function(card, animation, cfg){
var cfg = cfg ? cfg:{};
var anim = animation == undefined ? 'slide':animation;
if (cfg.back) {
this.future.push(current_card);
}
else {
if (!cfg.forward) {
this.future = [];
}
this.history.push(current_card);
}
MyPanel.superclass.setActiveItem.call(this, card, anim);


},


In this code I have a history array that I push cards onto every time I callSetActiveItem. When the goBack event is fired, I pop the last card off the history stack and call setActiveItem with that card and an extra config specifying that this is a back event. I also keep a future stack to use when going back.

gcallaghan
27 Jan 2011, 10:44 AM
thank Andrea & gcallaghan.
@gcallaghan: No allPanels is not a container. its a Panel and items it contains are also panels.


a Panel "is a" Sencha container in the OOP sense. sot the "items.get(0)" syntax still stands. For when you need it in the future ;-)

AndreaCammarata
27 Jan 2011, 12:27 PM
one correction for you :P my name is 'irfan iqbal' not 'infaniqbal' {plz correct the spell :) }
Opsss...sorry irfan ;)



And one more question. As you know my application's structure, please suggest me how can i achieve Back Button functionality in it. so that i can move across the panels. thanks

Does gcallaghan reply to your question?

irfaniqbal
28 Jan 2011, 1:55 AM
Does gcallaghan reply to your question?

yeh i have received gcallaghan solution. and now i will try it in my app. thanks

irfaniqbal
28 Jan 2011, 3:10 AM
Sencha should support this using Ext.Application and Ext.Routes. This isn't terribly well documented at the moment. I've implemented something in the meantime by overriding the setActiveItem function of my container panel.



listeners:{
...
goBack:function(){
if (this.history.length > 0){
this.setActiveItem(
this.history.pop(),
{type:'slide',reverse:true},
{back:true}
);
}
},
...
},
setActiveItem:function(card, animation, cfg){
var cfg = cfg ? cfg:{};
var anim = animation == undefined ? 'slide':animation;
if (cfg.back) {
this.future.push(current_card);
}
else {
if (!cfg.forward) {
this.future = [];
}
this.history.push(current_card);
}
MyPanel.superclass.setActiveItem.call(this, card, anim);


},
In this code I have a history array that I push cards onto every time I callSetActiveItem. When the goBack event is fired, I pop the last card off the history stack and call setActiveItem with that card and an extra config specifying that this is a back event. I also keep a future stack to use when going back.

thanks gcallaghan, will you please elaborate that where do i call goBack function? here is the main Panel of my App.


Application.App = Ext.extend(Ext.Panel, {
fullscreen: true,
layout: 'card',
activeItem: 0,
id: 'mainPanel',
initComponent: function() {
this.startScreen = new Application.views.login();

this.items = [this.startScreen];
Application.App.superclass.initComponent.call(this);
},
setActiveItem:function(card, animation, cfg){
this.history = new Array();
this.future = new Array();
var cfg = cfg ? cfg:{};
var anim = animation == undefined ? 'slide':animation;
if (cfg.back) {
this.future.push(app.getActiveItem());
}
else {
if (!cfg.forward) {
this.future = [];
}
this.history.push(app.getActiveItem());
}
Application.App.superclass.setActiveItem.call(this, card, anim);
},
listeners: {
goBack:function(){
if (this.history.length > 0){
this.setActiveItem(
this.history.pop(),
{type:'slide',reverse:true},
{back:true}
);
}
}
}

});
i have inserted your code in this panel. is it ok ? thanks