EXTJS - Load Mask - javascript

I want to present the source code, which is taken from inside a div with jQuery, inside an Ext.Window. I have managed to do that, but my problem is that sometimes the source code is huge, since it contains encoded images and the Ext.Window takes some time to appear in the screen after it is triggered via click event. I would like to present the Ext.Window but with a loading icon until the data is ready.
win = new Ext.Window ({
title:'Source Code',
width:800,
height:300,
items: [{
xtype : 'textarea',
readOnly: true,
value: sourceCode
}]
});
win.show();

Try with a undefined function and a setTimeout function. Do not forget the config layout: 'fit'.
Ext.application({
name : 'Fiddle',
launch : function() {
var win = Ext.create('Ext.window.Window', {
title:'Source Code',
width:800,
height:300,
layout: 'fit',
items: [{
xtype : 'textarea',
readOnly: true,
value: 'test'
}]
});
win.show(undefined, function(){
win.getEl().mask('Loading...');
setTimeout(function() {
win.getEl().unmask();
}, 3000);
});
}
});
Or
Ext.application({
name : 'Fiddle',
launch : function() {
Ext.create('Ext.window.Window', {
title:'Source Code',
width:800,
height:300,
layout: 'fit',
items: [{
xtype : 'textarea',
readOnly: true,
value: 'test'
}]
}).show(undefined, function(){
win.getEl().mask('Loading...');
setTimeout(function() {
win.getEl().unmask();
}, 3000);
});
}
});
TRY
win.show(undefined, function(){
win.getEl().mask('Loading...');
win.suspendEvents();
win.down('textarea').setValue(sourceCode);
win.down('textarea').focus();
win.resumeEvents();
setTimeout(function() {
win.getEl().unmask();
}, 2000);
});

What you can try is to set the value only after the window is already displayed:
win = new Ext.Window ({
title:'Source Code',
width:800,
height:300,
items: [{
xtype : 'textarea',
readOnly: true
}],
listeners: {
afterrender: function(sourceWindow) {
sourceWindow.down('textarea').setValue(sourceCode)
}
}
});
win.show();
Then you can add josei's mask/unmask approach on top of that, although I would recommend that you search some event that happens after the value has been set to remove the mask (you can try the change event on the textarea), because that way your wait wouldn't be a fixed amount of time, but related to the time it takes to render the textarea value.

Related

ExtJS drag event listeners work differently on Chrome and Firefox

I have added an input field to Window's title bar (header). On Chrome selecting and editing the input field works, and I can still drag the window around. On Firefox I can drag the window around the viewport, but I am unable to select the input field and edit it. How should I correct this code so that it would work on both browsers?
Quick'n'dirty demonstration of the problem:
Ext.define('Demo.DemoWindow', {
extend: 'Ext.window.Window',
xtype: 'demowindow',
height: 300,
width: 400,
title: 'Window',
autoShow: true,
items: [{
xtype: 'button',
text : 'Press!',
listeners: {
click: function() {
var win = this.up('window');
var header = win.getHeader();
header.setTitle('');
var killDrag = false;
var dragEvent = win.dd.on({
beforedragstart: function(dd, e) {
if (killDrag) {
return false;
}
}
});
var field = Ext.create('Ext.form.field.Text', {
name: 'Title',
allowBlank: false,
value: 'Type here something!',
listeners: {
el: {
delegate: 'input',
mouseout: function() {
killDrag = false;
},
mouseenter: function() {
killDrag = true;
}
}
}
});
header.insert(0, field);
}
}
}]
});
Ext.application({
name: 'Demo',
launch: function() {
Ext.create('Ext.container.Viewport', {
layout: 'absolute',
items: [
{
xtype: 'demowindow',
x: 20,
y: 20,
}
]
});
}
});
Using the mouseover event instead of mouseenter seems to work well with both.

Editor cannot disappear after closing Window

I got a problem on Ext 4.1.0 and Ext 4.1.1
Double click first cell to edit it and then click window close button, the editor still floats on the page.But it is ok for last cell.
Anyone met this problem before? Thanks
Ext.onReady(function(){
Ext.create('Ext.data.Store', {
storeId:'simpsonsStore',
fields:['name', 'email', 'phone'],
data:{'items':[
{ 'name': 'Lisa', "email":"lisa#simpsons.com", "phone":"1224" },
{ 'name': 'Bart', "email":"bart#simpsons.com", "phone":"1234" },
{ 'name': 'Homer', "email":"home#simpsons.com", "phone":"1244" },
{ 'name': 'Marge', "email":"marge#simpsons.com", "phone":"1254" }
]},
proxy: {
type: 'memory',
reader: {
type: 'json',
root: 'items'
}
}
});
var table = Ext.create('Ext.grid.Panel', {
title: 'Simpsons',
store: Ext.data.StoreManager.lookup('simpsonsStore'),
columns: [
{
text: 'Name',
dataIndex: 'name',
editor: { xtype: 'textfield', toFrontOnShow: false }
},
{
text: 'Email',
dataIndex: 'email',
flex: 1
},
{
text: 'Phone',
dataIndex: 'phone',
editor: {
xtype: 'numberfield',
hideTrigger: true,
validateOnChange : false
}
}
],
height: 200,
width: 400,
plugins:[ Ext.create('Ext.grid.plugin.CellEditing', {
clicksToEdit: 2
})]
});
var window = new Ext.Window({
id: 'abc',
title :'abc',
modal : true,
layout: 'border',
resizable : true,
draggable : true,
closable : true,
closeAction : 'hide',
width :410,
height :210,
items : [table]
});
window.show();
});
The easiest way to handle this for you, would be to listen to the window's beforeclose event and cancel any editing in this event using the celleditor's cancelEdit method as described here in the docs.
For example, here is your window object (from your code above) with the listener applied:
var window = new Ext.Window({
id: 'abc',
title :'abc',
modal : true,
layout: 'border',
resizable : true,
draggable : true,
closable : true,
closeAction : 'hide',
width :410,
height :210,
items : [ table],
// add this listener to your window
listeners: {
beforeclose: function(panel) {
var view = panel.down('gridview');
if (view && view.editingPlugin) {
view.editingPlugin.cancelEdit();
}
}
}
});
Reply to comment:
Here's an override that would do the same thing. You would have to include this override in each app after ExtJS initialization though.
Of course it is also possible to replace the init function in the Ext.grid.plugin.Editor source code with this one (then you wouldn't have to include the override in the app) but I wouldn't recommend doing that for a number of reasons.
Ext.override(Ext.grid.plugin.Editor, {
init: function(grid) {
// the normal init code (below) must be included in the override
var me = this;
me.grid = grid;
me.view = grid.view;
me.initEvents();
me.mon(grid, 'reconfigure', me.onReconfigure, me);
me.onReconfigure();
grid.relayEvents(me, [
'beforeedit',
'edit',
'validateedit',
'canceledit'
]);
grid.isEditable = true;
grid.editingPlugin = grid.view.editingPlugin = me;
// additional code to cancel editing before a grid is hidden
grid.on('beforehide', function(grid) {
var view = grid.view;
if (view && view.editingPlugin) {
view.editingPlugin.cancelEdit();
}
});
// additional code to cancel editing before a grid is destroyed
grid.on('beforedestroy', function(grid) {
var view = grid.view;
if (view && view.editingPlugin) {
view.editingPlugin.cancelEdit();
}
});
}
});
I would also recommend looking into MVC architecture, it would make handling things like this alot easier for you.

Event triggered on tab load, or loading a tab with ajax?

How do I fire an event when a tab is loaded in Sencha Touch? I want to AJAX in some content that isn't important enough to be loaded immediately, and Sencha Touch seems to miss the autoLoad property of ExtJS.
What can I bind to on a panel to detect that the panel has been activated?
You can listen for the event activate in the panel itself or for the event cardswitch in the TabPanel.
The cardswitch event only fires after the first card has been set, so if you want an action to trigger on initialization, add a listener for the activate event on the TabPanel.
Ext.setup({
icon: 'icon.png',
tabletStartupScreen: 'tablet_startup.png',
phoneStartupScreen: 'phone_startup.png',
glossOnIcon: false,
onReady: function() {
var tabpanel = new Ext.TabPanel({
tabBar: {
dock: 'bottom',
layout: {
pack: 'center'
}
},
fullscreen: true,
ui: 'light',
cardSwitchAnimation: {
type: 'slide',
cover: true
},
//
// Listen for cardswitch event in TabPanel
//
listeners: {
cardswitch: function(comp, newCard, oldCard, index, animated) {
console.log(newCard.title, oldCard.title, index, animated);
}
},
defaults: {
scroll: 'vertical'
},
items: [{
title: 'About',
html: '<h1>Bottom Tabs</h1><p>Docking tabs to the bottom will automatically change their style. The tabs below are type="light", though the standard type is dark. Badges (like the 4 & Long title below) can be added by setting <code>badgeText</code> when creating a tab/card or by using <code>setBadge()</code> on the tab later.</p>',
iconCls: 'info',
cls: 'card1',
//
// Listen for activate event in panel
//
listeners: {
activate: function(comp){
console.log(comp.title);
//
// Ajax Request
//
Ext.Ajax.request({
url: 'your_url_here.json',
success: function(response, opts) {
//
// Update panel html with ajax response
//
comp.update(response.responseText);
},
failure: function(response, opts) {
console.log('server-side failure with status code ' + response.status);
}
});
}
}
}, {
title: 'Favorites',
html: '<h1>Favorites Card</h1>',
iconCls: 'favorites',
cls: 'card2',
badgeText: '4'
}, {
title: 'Downloads',
id: 'tab3',
html: '<h1>Downloads Card</h1>',
badgeText: 'Text can go here too, but it will be cut off if it is too long.',
cls: 'card3',
iconCls: 'download'
}, {
title: 'Settings',
html: '<h1>Settings Card</h1>',
cls: 'card4',
iconCls: 'settings'
}, {
title: 'User',
html: '<h1>User Card</h1>',
cls: 'card5',
iconCls: 'user'
}]
});
}
});
More info on the Sencha Touch Docs:
http://dev.sencha.com/deploy/touch/docs/?class=Ext.TabPanel
http://dev.sencha.com/deploy/touch/docs/?class=Ext.Panel

How to completely hide the dockedItems toolbar

I'm able to hide items among the dockedItems of a TabPanel, but am wanting to temporarily hide the entire dock, because the toolbar itself still takes up space and the rest of the content does not fill the screen.
So far, I do like so:
myApp.views.productList.dockedItems.items[0].removeAll(true);
myApp.views.productList.doComponentLayout();
Alternatively:
myApp.views.productList.getComponent('search').removeAll(true);
myApp.views.productList.doComponentLayout();
But neither removes the dockedItems toolbar itself.
I've even tried to give the dockedItems individually and collectively an id: to remove the whole component, but without luck. I've also tried moving the toolbar in question out from the docked items and into the items: property of the containing panel, but this breaks other things in my app that I'd rather not change at present.
Any clues on how to do this?
If I understand you correctly you want to temporally remove tabBar from a tabPanel. I was able to accomplish this through giving and id to my tabBar and then using removeDocked and addDocked methods. I'm new to sencha-touch so most likely there is a better way of doing this
The code below removes tabBar from tabPanel and then adds it back again.
Ext.setup({
onReady: function() {
var tabpanel = new Ext.TabPanel({
ui : 'dark',
sortable : true,
tabBar:{
id: 'tabPanelTabBar'
},
items: [
{title: 'Tab 1',html : '1',cls : 'card1'},
{title: 'Tab 2',html : '2',cls : 'card2'},
{title: 'Tab 3',html : '3',cls : 'card3'}
]
});
var paneltest = new Ext.Panel({
fullscreen: true,
dockedItems:[
{
xtype: 'button',
text: 'Disable TabBar',
scope: this,
hasDisabled: false,
handler: function(btn) {
console.log(btn);
if (btn.hasDisabled) {
tabpanel.addDocked(Ext.getCmp('tabPanelTabBar'), 0);
btn.hasDisabled = false;
btn.setText('Disable TabBar');
} else {
tabpanel.removeDocked(Ext.getCmp('tabPanelTabBar'), false)
btn.hasDisabled = true;
btn.setText('Enable TabBar');
}
}}
],
items:[tabpanel]
});
paneltest.show()
}
})
в dockedItems добавить button, которая будет обращаться к элементу panel.dockedItems и изменять/скрывать сам dockedItems
function f_create_accord(P_el_id, P_el_params) {
P_el = Ext.create
(
'Ext.panel.Panel',
{
id: P_el_id
, border: false
, x: P_el_params.left
, y: P_el_params.top
, id_el: P_el_params.id_el
, layout: 'accordion'
, dockedItems: [{
xtype: 'toolbar',
dock: 'bottom',
items: [{
P_el_id: P_el_id,
xtype: 'button',
text: 'добавить',
}, {
id_el: P_el_id,
xtype: 'button',
text: 'скрыть',
vision: true,
listeners: {
click: function (el, v2, v3) {
if (el.vision) {
Ext.getCmp(el.id_el).dockedItems.items[0].setHeight(5);
Ext.getCmp(el.id_el).dockedItems.items[0].items.items[0].hide();
Ext.getCmp(el.id_el).dockedItems.items[0].items.items[1].setWidth(Ext.getCmp(el.id_el).getWidth());
el.vision = false
}
else {
Ext.getCmp(el.id_el).dockedItems.items[0].setHeight('15px');
Ext.getCmp(el.id_el).dockedItems.items[0].items.items[0].show();
Ext.getCmp(el.id_el).dockedItems.items[0].items.items[1].setWidth(60);
el.vision = true
}
// Ext.getCmp(el.id_el).dockedItems.items[i].hide();
}
}
}]
}]
}
);
P_el.setStyle('position', 'absolute');
P_el.setStyle('box-shadow', ' 0px 0px 0px 1px green');
P_el.setStyle('background', 'border-box');
return P_el;
}

Ext js FormPanel is not showing panel items when toolbar is present

I seem to be having a weird issue here. An extended component has the following code:
MyApp.panels.RelationshipDetails = Ext.extend(Ext.FormPanel, {
closable: true,
relationshipId: null,
documentId: null,
title: 'Relationship',
initComponent: function () {
if (!this.verifyRequiredData()) {
MyApp.panels.RelationshipDetails.superclass.initComponent.call(this);
return;
}
// Build components
this.tbar = this.buildToolbar();
this.items = this.buildDetailItemArray();
MyApp.panels.RelationshipDetails.superclass.initComponent.call(this);
},
verifyRequiredData: function () {
// Verification code here
},
buildDetailItemArray: function () {
return [{
xtype: 'fieldset',
title: 'Details',
collapsible: true,
autoHeight: true,
items: [{
xtype: 'hidden',
name: 'Id'
}, {
xtype: 'textfield',
fieldLabel: 'Name',
name: 'Name'
}, {
xtype: 'textfield',
fieldLabel: 'Description',
name: 'Description'
}, {
xtype: 'button',
text: 'Save',
name: 'saveButton'
}]
}];
},
buildToolbar: function () {
return new Ext.Toolbar({
// Toolbar Config
});
}
});
The issue is that when this panel renders, the toolbar is the only thing that renders. Through debugging I can see that BuildDetailItemArray() is being called correctly and returning the correct result.
It gets even weirder when I comment out the this.tbar = line, because when the toolbar is not present, the fieldset and field renders correctly. This occurs even if I extend Panel instead of FormPanel. I also tried abstracting out the form fields into it's own component, and the same thing occurs.
Anyone have any idea why this doesn't seem to work?
What sort of layout are you trying to put this panel into? Also, are you setting a height for this panel?
Often, if you aren't specifying a height for the component to be added (in your case, this panel), or you're not setting an anchor if using an AnchorLayout, component content won't be shown, but the toolbar still will.
It'd be good to know the context of this panel in your overall layout.

Categories