I am creating a toolbar in my code below. What I'm wondering is how to place these inside a panel?
var toptoolbar = Ext.create('Ext.toolbar.Toolbar', {
id: 'ttool',
width: '100%',
items: [
{ text : 'MetaCenter',
menu : {
items: [
{ text : 'Wiki' },
{ text : 'JIRA' },
{ text : 'SVN' },
{ text : 'Sharepoint',
menu : {
items: [
{text : 'text 1'},
{text : 'text 2'}
]
}
}]
}
}
]
});
What I want to do is something like:
Ext.create.('Ext.panel.Panel', {
id: 'panel',
tbar: { //code to create the toptoolbar }
....
EDIT:
What I want to have is a very extensive drop down menu with sub menus on a toolbar, I'm trying to avoid putting all of that code to create that toolbar inside of my application. Instead I want to be able to call it from a variable (or better yet, a class?). Kind of like abstraction/encapsulation.
Is this a standard way of component instantiation or are there more-efficient methods?
Cheers!
Check out the ExtJS docs for dockedItems, they give exactly this scenario as an example: http://docs.sencha.com/extjs/4.2.1/#!/api/Ext.panel.Panel-cfg-dockedItems
You can define the toolbar in the initComponent method of the panel.
Ext.define('MyApp.view.MyPanel', {
extend: 'Ext.panel.Panel',
height: 250,
width: 400,
title: 'My Panel',
initComponent: function() {
var me = this;
Ext.applyIf(me, {
dockedItems: [
{
xtype: 'toolbar',
dock: 'top'
}
]
});
me.callParent(arguments);
}
});
Related
Afterrender event not work for my tabpanel component.
code of my tabpanel:
Ext.define('Admin.view.tabs.Tabs', {
extend: 'Ext.tab.Panel',
shadow: true,
cls: 'demo-solid-background',
tabBar: {
layout: {
pack: 'center'
}
},
activeTab: 1,
defaults: {
scrollable: true
},
items: [
{
title: 'Tab 1',
html : 'By default, tabs are aligned to the top of a view.',
cls: 'card'
},
{
title: 'Tab 2',
html : 'A TabPanel can use different animations by setting <code>layout.animation.</code>',
cls: 'card'
}
],
listeners: {
afterrender: function(corpse) {
console.log('afterrender');
}
}});
This tab panel I use in view formpanel that added in main view like this:
doCompose: function (to) {
var me = this,
composer = me.composer,
view = me.getView(),
viewModel = me.getViewModel(),
toField;
me.hideActions();
if (!composer) {
me.composer = composer = view.add(
{
xtype: 'compose',
flex: 1
});
if (to) {
toField = me.lookupReference('toField');
toField.setValue(to);
}
viewModel.set('composing', true);
}
}
Compose it's my formpanel which contain tabpanel.
I try use example from official templates ExtJs Sencha.
View for mobile profile compose email https://github.com/syscobra/extjs-admin-dashboard-template/tree/master/modern/src
As i said Ext-JS 6 modern TabPanel has not afterrender event.Instead you can use painted, heres the
FIDDLE
listeners: {
painted: function () {
//your code
}
}
I'm trying to use controller in my program.Controller name is "Main" and code is given below.
refs: [
{
ref: 'navigation',
selector: 'navigation'
},
{
ref: 'ContentPanel',
selector: 'ContentPanel'
},
{
ref: 'viewport',
selector: 'viewport'
}
]
and i have a view port with following code.
Ext.define('MyApp.view.MyViewport', {
extend: 'Ext.container.Viewport',
requires: [
'MyApp.view.Header',
'MyApp.view.Navigation',
'MyApp.view.ContentPanel'
],
layout: {
type: 'border'
},
initComponent: function() {
var me = this;
Ext.applyIf(me, {
items: [
{
xtype: 'header',
height: 136,
region: 'north'
},
{
xtype: 'navigation',
width: 207,
region: 'west'
},
{
xtype: 'ContentPanel',
width: 431,
flex: 2,
region: 'center'
}
]
});
now my problem is i have to get an object of ContentPanel when i click on naviagation(tree panel). i tried using
var content= this.getContentPanel();
i have one more form panel add i want to add that to the controller. and i want to get the instance of the form and put it inside the content panel and display.
var form= this.getMyform();// i didnt add Myform to the controller yet because i dont know to add reference properly
content.add(form);
My main problem is that i cant instantiate the content panel and form in ItemClick event of navigation(tree panel)
thank you
A ref should start with a lower case letter. The same is valid for xtypes. ref: 'contentPanel' will define a getter getContentPanel. Since contentPanelis different from ContentPanel, I'm not sure, if in your case the getter is created or not.
I'm new in extjs.
Currently a panel have been created and set to north region.
Ext.create('Ext.panel.Panel', {
layout: {
type: 'border'
},
bodyStyle: 'background: yellow;',
height : 700,
width : '100%',
renderTo: Ext.get("example"),
items : [{
title: 'navigationBar',
header: false,
region: 'north',
xtype: 'panel',
//margins: '5,5,5,5',
items: [
MenuBar
]
}
And I also create a toolbar in my child class, which ready to call from my parent class and place to the north region panel.
Ext.define('adminInterface', {
extend: 'Ext.toolbar.Toolbar',
items: [{
xtype: 'tbbutton',
text: 'Button',
},{
xtype: 'tbbutton',
text: 'Button1',
menu: [{
text: 'Good',
},{
text: 'Better',
},{
text: 'Best',
}]}]
});
Once I execute the code, the toolbar variable from child class was call, but it not show out the interface.
Thanks for anyone share their information.
Hi refer my sample example
Ext.create('Ext.panel.Panel', {
title: 'Hello',
width: 200,
html: '<p>World!</p>',
renderTo: Ext.getBody(),
tbar: new Ext.Toolbar({
//your Toolbar config options
})
});
Still we can able to see more sample from existing post as shown below
How do i add a toolbar to my layout in extjs?
Extjs 4 add toolbar to panel dockeditems run-time
var myBtnHandler = function(btn) {
Ext.MessageBox.alert('You Clicked', btn.text);
},
fileBtn = Ext.create('Ext.button.Button', {
text : 'File',
handler : myBtnHandler
}),
editBtn = Ext.create('Ext.button.Button', {
text : 'Edit',
handler : myBtnHandler
}),
tbFill = new Ext.toolbar.Fill();
var myTopToolbar = Ext.create('Ext.toolbar.Toolbar', {
items : [
fileBtn,
tbFill,
editBtn
]
});
var myBottomToolbar = [
{
text : 'Save',
handler : myBtnHandler
},
'-',
{
text : 'Cancel',
handler : myBtnHandler
},
'->',
'<b>Items open: 1</b>'
];
var myPanel = Ext.create('Ext.panel.Panel', {
width : 200,
height : 150,
title : 'Ext Panels rock!',
collapsible : true,
renderTo : Ext.getBody(),
tbar : myTopToolbar,
bbar : myBottomToolbar,
html : 'My first Toolbar Panel!'
});
how to reuse the same item in multiple tab so that when that item change, other tab will reflect the changes
i try this code but the label in first tab not shown:
var label = Ext.create('Ext.form.Label', {
text : 'mylabel'
});
Ext.onReady(function() {
Ext.create('Ext.tab.Panel', {
width : 200,
height : 200,
renderTo : Ext.getBody(),
items : [{
title : 'tab1',
items : [label, {
xtype : 'button',
handler : function() {
label.setText('changed from tab1');
}
}]
}, {
title : 'tab2',
items : [label, {
xtype : 'button',
handler : function() {
label.setText('changed from tab2');
}
}]
}]
});
});
i'm sorry, what i mean is to use the label globally(like global variable) so that the same instance of label can be displayed and changed from every tab
you can define your label component:
Ext.define('MyLabel', {
extend: 'Ext.form.Label',
alias: 'widget.mylabel',
text : 'mylabel'
});
the alias property is an alias for the class name (in this case MyLabel) and that is why you can use "mylabel" as an xtype
in this way you can reuse the component, like this
var panel = Ext.create('Ext.tab.Panel', {
width : 200,
height : 200,
renderTo : Ext.getBody(),
items : [{
title : 'tab1',
items : [{
xtype: 'mylabel',
itemId: 'item1'
}, {
xtype : 'button',
handler : function(button) {
panel.down('#item2').setText('changed from tab1');
}
}]
}, {
title : 'tab2',
items : [{
xtype: 'mylabel',
itemId: 'item2'
}, {
xtype : 'button',
handler : function(button) {
panel.down('#item1').setText('changed from tab2');
}
}]
});
You can't do exactly what you want here. You see, when you create a label, it has underlying DOM, and naturally that DOM can only exist in one place (so it can't show the same thing on both tabs).
If there is a component that you are wanting to show on both tabs, it seems like it is "higher up" from a data hierarchical perspective. Perhaps it belongs outside the tab panel?
If the label truly belongs in both tabs and should be "the same", you are either going to need to fake it or manually move it between the tabs.
Option 1: Fake It
You can get the most code reuse here by creating a custom Label class, like laurac posted. You still need to keep the label text in sync, so you are going to need to update one when the other's text is changed:
var label1 = Ext.create('Ext.form.Label', {
text : 'mylabel'
});
var label2 = Ext.create('Ext.form.Label', {
text : 'mylabel'
});
Ext.onReady(function() {
Ext.create('Ext.tab.Panel', {
width : 200,
height : 200,
renderTo : Ext.getBody(),
items : [{
title : 'tab1',
items : [label1, {
xtype : 'button',
handler : function() {
label1.setText('changed from tab1');
label2.setText('changed from tab1');
}
}]
}, {
title : 'tab2',
items : [label2, {
xtype : 'button',
handler : function() {
labe2.setText('changed from tab2');
labe1.setText('changed from tab2');
}
}]
}]
});
});
Clearly that doesn't feel to "clean".
Option 2: Manual Control
This might be hacky, but slightly less hacky than option 1. Basic idea is to move the label between to two tabs when they are activated:
var label = Ext.create('Ext.form.Label', {
text : 'mylabel'
});
Ext.onReady(function() {
Ext.create('Ext.tab.Panel', {
width : 200,
height : 200,
renderTo : Ext.getBody(),
items : [{
title : 'tab1',
items : [{
xtype : 'button',
handler : function() {
label.setText('changed from tab1');
}
}],
listeners: {
scope: this,
activate: function(panel) {
panel.insert(0, label);
panel.doLayout();
}
}
}, {
title : 'tab2',
items : [{
xtype : 'button',
handler : function() {
label.setText('changed from tab2');
}
}],
listeners: {
scope: this,
activate: function(panel) {
panel.insert(0, label);
panel.doLayout();
}
}
}]
});
});
Note: I haven't started using Ext4 yet, so some of the code I added might need to be changed for Ext4 (I think maybe doLayout went away?).
Anyway, those are the only two ways I can think of to solve your problem.
Good luck!
in a Extjs application I have a Grid and a Tabs line over it. Content of the Grid depends on the selected Tab.
Say tabs has Jan-Feb-Mar-... values. Clicking of the Tab I would reload grid's store
Question: is it possible to avoid duplicating of the 12 grid components in favor to have one shared instance?
Thanks
Disclaimer: searching at the sencha's forum, google, stackoverflow was not successful :(
It is, but it would require more effort than it is worth. Just create a prototype for your component, so that you can create new instances really quickly.
I haven't tried this myself, but I imagine that you could create a TabPanel with empty tabs and size the TabPanel so that only the tab strip is visible. Under that (using the appropriate layout, border, vbox, etc.) create your GridPanel and use the TabPanel's activate event to reload the grid based on the currently-active tab.
Hope the following implementation meet your needs
1. Create your custom grid and register it
2. place it tab panel
As the grid is created using xtype, it would not create 12 instances when you change tabs.
Application.PersonnelGrid = Ext.extend(Ext.grid.GridPanel, {
border:false
,initComponent:function() {
Ext.apply(this, {
store:new Ext.data.Store({...})
,columns:[{...}, {...}]
,plugins:[...]
,viewConfig:{forceFit:true}
,tbar:[...]
,bbar:[...]
});
Application.PersonnelGrid.superclass.initComponent.apply(this, arguments);
} // eo function initComponent
,onRender:function() {
this.store.load();
Application.PersonnelGrid.superclass.onRender.apply(this, arguments);
} // eo function onRender
});
Ext.reg('personnelgrid', Application.PersonnelGrid);
var panel = new Ext.TabPanel({
items:[{
title:'Jan',
items: [{xtype:'personnelgrid'}]
}, {
title: 'Feb',
items: [{xtype:'personnelgrid'}]
}
....
{
title: 'Dec',
items: [{xtype:'personnelgrid'}]
}]
})
Since this is the only place discussed about this until now, I share what I just found.
The trick is use dockedItems in ExtJs 4 (Not sure either grid can be added into tbar in ExtJs 3)
When changing the active tab, only body will be change but not the docked item. Just set the grid height equal to the body during boxready and resize so that we can't see the body anymore.
This is the code for ExtJs 4.2 MVC that also make use of refs.
Ext.define('app.controller.Notification', {
extend: 'Ext.app.Controller',
views: ['notification.List'],
stores: ['Notification'],
models: ['Notification'],
refs: [{
ref: 'pnlNotif',
selector: 'pnlNotif'
}, {
ref: 'notifList',
selector: 'notifList'
}],
init: function () {
this.control({
'dbPnlNotif': {
added: this.pnlNotifAdded,
boxready: this.calcNotifListSize,
resize: this.calcNotifListSize,
tabchange: this.pnlNotifTabChange
}
});
},
pnlNotifAdded: function (pnlNotif) {
pnlNotif.add({ title: '1', html: '1' });
pnlNotif.add({ title: '2', html: '2' });
pnlNotif.add({ title: '3', html: '3' });
},
calcNotifListSize: function (pnlNotif) {
// calc the notification list height to make sure it use the whole body
// This way we can use only one instance of list to display for each tabs
// because the list is rendered as dockedItems
var height = pnlNotif.getHeight();
var headerHeight = pnlNotif.getDockedItems()[0].getHeight();
var tabBarHeight = pnlNotif.getDockedItems()[1].getHeight();
height = height - headerHeight - tabBarHeight;
if (this.getNotifList().getHeight() !== height) {
this.getNotifList().setHeight(height - 1);// - 1 to include border bottom
}
},
pnlNotifTabChange: function (pnlNotif, newTab) {
// do something to filter the list based on selected tab.
}
});
Ext.define('ML.view.Notification', {
extend: 'Ext.tab.Panel',
alias: ['widget.pnlNotif'],
title: 'Notification',
dockedItems: [{
xtype: 'notifList'
}]
});
Ext.define('ML.view.notification.List', {
extend: 'Ext.grid.Panel',
alias: 'widget.notifList',
dock: 'top',
store: 'Notification',
initComponent: function () {
this.columns = [
...
];
this.callParent(arguments);
}
});
Try this
var gridJanName = Ext.create('Ext.grid.Panel', {
enableColumnHide: false,
autoScroll:true,
store: storeJanNameGroup,
border:true,
stripeRows: true,
columnLines:false,
loadMask: true,
tbar:tbgridTools,
margin: '1 1 1 1',
pageSize: 100,
maxWidth:700,
features: [groupFeature],
selModel: {
mode: 'MULTI'
},
columns: [
{xtype:'rownumberer',width:50},
{dataIndex:'id', hidden:true},
//etc
]
});
var gridFebName = Ext.create('Ext.grid.Panel', {
enableColumnHide: false,
autoScroll:true,
store: storeJanNameGroup,
border:true,
stripeRows: true,
columnLines:false,
loadMask: true,
tbar:tbgridTools,
margin: '1 1 1 1',
pageSize: 100,
maxWidth:700,
features: [groupFeature],
selModel: {
mode: 'MULTI'
},
columns: [
{xtype:'rownumberer',width:50},
{dataIndex:'id', hidden:true},
//etc
]
});
//
//etc grid
//
var JanPanel = Ext.create('Ext.panel.Panel', {
title:'Jan',
bodyPadding: 5,
Width:780,
layout: {
type: 'hbox',
align: 'stretch'
},
items: [gridJanName]
});
var FebPanel = Ext.create('Ext.panel.Panel', {
title:'Feb',
bodyPadding: 5,
Width:780,
layout: {
type: 'hbox',
align: 'stretch'
}
//,items: [gridFebName]
});
var MarPanel = Ext.create('Ext.panel.Panel', {
title:'Mar',
bodyPadding: 5,
Width:780,
layout: {
type: 'hbox',
align: 'stretch'
}
//,items: [gridMarName]
});
//etc
var eachMonthstabs = Ext.create('Ext.tab.Panel', {
minTabWidth: 130,
tabWidth:150,
//Width:750,
scroll:false,
autoHeight: true,
id:'timestabs',
enableTabScroll:true,
items: [
{
xtype:JanPanel
},
{
xtype:FebPanel
},
{
xtype:MarPanel
}
///etc
]
});
For me good solution was to use a left toolbar called lbar with list of buttons and a single grid instead of tabpanel