I want to enable or disable checkboxes in EXTJS
dockedItems: [{
xtype: 'toolbar',
dock: 'top',
items: [{
xtype: 'radiofield',
id: 'all',
name: 'show',
boxLabel: 'All',
checked: true,
inputValue: 'all'
}, {
xtype: 'radiofield',
id: 'online',
name: 'show',
boxLabel: 'Online',
inputValue: 'online'
}, {
xtype: 'radiofield',
id: 'offline',
name: 'show',
boxLabel: 'Offline',
inputValue: 'offline'
}, {
xtype: 'checkboxfield',
id: 'cb1',
boxLabel: 'Sometimes',
checked: true,
inputValue: 'sometimes'
}, {
xtype: 'checkboxfield',
id: 'cb2',
boxLabel: 'Always',
checked: true,
inputValue: 'always'
}],
listeners: {
change: function (field, newValue, oldValue) {
var value = newValue.show;
if (value == 'all') {
var cb1 = Ext.getCmp('cb1');
var cb2 = Ext.getCmp('cb2');
cb1.disable();
cb2.disable();
}
if (value == 'online') {
var cb1 = Ext.getCmp('cb1');
var cb2 = Ext.getCmp('cb2');
cb1.disable();
cb2.disable();
}
if (value == 'offline') {
var cb1 = Ext.getCmp('cb1');
var cb2 = Ext.getCmp('cb2');
cb1.enable();
cb2.enable();
}
}
}
}]
How can I enable these checkboxes? They should be enabled when the user selects the offline option and disabled when the user selects other option.
Thanks for your help!
A couple errors I noticed:
The checkbox components cant be referred to by their id directly, you could call them with Ext.getCmp('id') though.
Your listener in the example above is attached to the toolbar, which doesn't have a change event. You need to attach it to the radio instead.
Actually, if you only want the checkboxes enabled when the 'offline' radio is filled then I would recommend adding a handler config to the 'offline' radio with a function to enable or disable the checkboxes depending on what value this radio is changed to. For example, this works:
dockedItems: [{
xtype: 'toolbar',
dock: 'top',
items: [{
xtype: 'radiofield',
id: 'all',
name: 'show',
boxLabel: 'All',
checked: true,
}, {
xtype: 'radiofield',
id: 'online',
name: 'show',
boxLabel: 'Online',
inputValue: 'online',
}, {
xtype: 'radiofield',
id: 'offline',
name: 'show',
boxLabel: 'Offline',
inputValue: 'offline',
handler: function(field, value) {
if (value) {
Ext.getCmp('cb1').enable();
Ext.getCmp('cb2').enable();
} else {
Ext.getCmp('cb1').disable();
Ext.getCmp('cb2').disable();
}
}
}, {
xtype: 'checkboxfield',
id: 'cb1',
boxLabel: 'Sometimes',
checked: true,
inputValue: 'sometimes',
disabled: true
}, {
xtype: 'checkboxfield',
id: 'cb2',
boxLabel: 'Always',
checked: true,
inputValue: 'always',
disabled: true
}]
}],
I suggest using handler config (as above) and not having a listener on the change event.
If you add a change listener it will override the default change handler used by ExtJS internally to deselect the other radio fields in the same name group. E.g. with a change listener on the 'offline' radio, when you select it, 'all' will remain selected.
In other words... just copy the example above and all will be well.
You can do the following you need to set ids for the checkboxs to look them up in this example:
if (value == 'offline') {
var cb1 = Ext.getCmp('cbox1');//look up by given checkbox ids
var cb2 = Ext.getCmp('cbox2');//look up by given checkbox ids
cb1.enable();
cb2.enable();
online
}
else {
var cb1 = Ext.getCmp('cbox1');//look up by given checkbox ids
var cb2 = Ext.getCmp('cbox2');//look up by given checkbox ids
cb1.disable();
cb2.disable();
}
A standard approach to enable / disable checkbox in ExtJS is to set configuration parameters disable: true or disable: false when creating component.
But as for ExtJS 4.2 - it has some inconvenience. Disabling or setting checkbox to readOnly makes component look very transparent. In classic framework design and maybe some others you won't even see a tick in the box if it's disabled or set to readOnly. As if it were empty.
The best solution we found is to create a project global css class for all ExtJS elements of this type. It shifts to a better tick sign in standard framework theme image and adds some opacity:
.x-form-readonly .x-form-checkbox {
background-image: url(/extjs/resources/ext-theme-classic/images/form/checkbox.gif);
opacity: 0.4;
}
Related
I have two components in my form which are "Source" and "Destination". And I want to give an option to change the order of those 2 components when clicked on "Swap" button.
Is this achievable in Extjs form ..?
https://fiddle.sencha.com/#view/editor&fiddle/3ej6
I attach here one possible solution: I removed both the fields and added them again with right indices.
listeners: {
click: function(){
const panel = this.up('panel');
const sourceForm = panel.query('combo[reference=source]');
const destinationForm = panel.query('combo[reference=destination]');
panel.remove(sourceForm)
panel.remove(destinationForm)
panel.insert(0, destinationForm)
panel.insert(1, sourceForm)
}
}
Here the link to working Fiddle.
---- EDIT -----
This is the new snippet to adapt the fiddle to your comment:
const panel = this.up('panel');
const sourceForm = panel.query('combo[reference=source]');
const destinationForm = panel.query('combo[reference=destination]');
const sourceIndex = panel.items.items.indexOf(sourceForm[0])
panel.remove(sourceForm)
panel.remove(destinationForm)
panel.insert(sourceIndex, destinationForm)
panel.insert(sourceIndex === 0 ? 1 : 0, sourceForm)
The working fiddle can be found at the same old link.
Different approach can be found here:
https://fiddle.sencha.com/#view/editor&fiddle/3em7
let combo1 = Ext.create({
xtype: 'combo',
name: 'source',
fieldLabel: 'source',
reference: 'source',
displayField: 'name',
valueField: 'abbr',
store: [{
abbr: 'AL',
name: 'Alabama'
}, {
abbr: 'AK',
name: 'Alaska'
}, {
abbr: 'AZ',
name: 'Arizona'
}, {
xtype: 'button',
}],
allowBlank: false // requires a non-empty value
})
let combo2 = Ext.create({
xtype: 'combo',
name: 'source1',
fieldLabel: 'dest',
reference: 'source1',
displayField: 'name',
valueField: 'abbr',
//hidden: true,
store: [{
abbr: 'AL',
name: 'Alabama'
}, {
abbr: 'AK',
name: 'Alaska'
}, {
abbr: 'AZ',
name: 'Arizona'
}, {
xtype: 'button',
}],
allowBlank: false // requires a non-empty value
})
let items = [combo1, combo2];
let wrapper = Ext.create({
xtype: 'container',
layout: 'vbox',
items: items
})
Ext.create('Ext.form.Panel', {
title: 'Contact Info',
width: 300,
bodyPadding: 10,
renderTo: Ext.getBody(),
items: [wrapper, {
xtype: 'button',
text: "Swap",
handler:(b)=> {
wrapper.removeAll(false);
wrapper.add(items.reverse());
}
}]
});
Technically, as far as i remember, items within a (container) component are managed using a mixed collection.
https://docs.sencha.com/extjs/6.5.3/classic/Ext.util.MixedCollection.html
You can try to change the order there and refresh the view.
I guess we missed the CSS only solution.
You can use ordinal-group to swap items. Just add a class, which adds a higher group number to the first combobox.
listeners: {
click: function () {
let view = this.up(),
sourceComp = view.down('combo[reference=source]');
sourceComp.toggleCls('box-reverse')
}
}
.box-reverse {
-webkit-box-ordinal-group: 3!important;
}
Here is your fiddle
I want to call change event only when we checked radio button but the change event are also calling when we set value...like this.
Ext.getCmp('2007').setValue({ '2007': 'NoAccess' });
Anyone can tell me how can we use custom checked event or any other event so we will call the change event only on checked(click) radio button.
I'm using Ext.Version 4.2.1.
Here is my code:-
{
xtype: 'radiogroup',
fieldLabel: ' Admin Notes',
labelStyle: 'font-size: 12px;color:#3399CC;',
margin: '0 0 0 3',
defaultType: 'radio',
id: '2007',
name: '2007',
defaults: {
flex: 1
},
items: [
{
boxLabel: 'Read and Update',
inputValue: 'ReadUpdate',
name: '2007'
}, {
boxLabel: 'Read Only',
margin: '0 0 0 20',
inputValue: 'ReadOnly',
name: '2007'
}, {
boxLabel: 'No Access',
inputValue: 'NoAccess',
name: '2007'
}
],
listeners: {
change: function() {
alert("True");
},
Before to use setValue() first you need to use following two methods of RadioGroup.
1). suspendEvent or suspendEvents to Suspends the firing of particular or all events.
2). radiogroup.setValue({name:'value'}) the radio with corresponding name and value will be set.
3). resumeEvent or resumeEvents to resumes firing of the named event or all events.
In this FIDDLE, I have created a demo using radiogroup. I hope it will help you to achieve your requirement.
Code Snippet
Ext.create('Ext.form.Panel', {
title: 'RadioGroup example with change event call when dyanmic value set.',
bodyPadding: 10,
renderTo: Ext.getBody(),
items: [{
xtype: 'radiogroup',
fieldLabel: 'Admin Notes',
defaultType: 'radio',
id: '2007',
defaults: {
name: '2007'
},
items: [{
boxLabel: 'Read and Update',
inputValue: 'ReadUpdate'
}, {
boxLabel: 'Read Only',
margin: '0 0 0 20',
inputValue: 'ReadOnly'
}, {
boxLabel: 'No Access',
inputValue: 'NoAccess'
}],
listeners: {
change: function (cmp, newValue) {
Ext.Msg.alert('Success', 'Checked value is :- ' + newValue['2007']);
}
}
}],
listeners: {
afterrender: function () {
var rb = Ext.getCmp('2007');
rb.suspendEvents();
rb.setValue({
'2007': 'NoAccess'
});
rb.resumeEvents();
}
}
});
I am using ExtJs 2.3.0.
I have a panel and inside it a radiogroup as follows
var testPanel = {
xtype: 'panel',
border: false,
items: [
{ fieldLabel: 'Please select ',
xtype: 'radiogroup',
id: 'id1',
columns: 2,
vertical: false
}
],
items: [
{ boxLabel: 'Yes', name: 'yes', inputValue: 'Yes', xtype: 'radio'},
{ boxLabel: 'No', name: 'no', inputValue: 'No', xtype: 'radio' }
]
}
The issue is-
The fieldLabel 'Please select' of radioBox is not displaying. I am able to see 'Yes'/ 'No' radiobuttons.
When I change xtype of testPanel to 'form', the label displays.
However, I can't use 'form' xtype. I want to use 'Panel' only.
Please let me know why the fieldLabel is not diaplying inside panel and any workaround for this.
For one thing, the individual radio buttons must be items of the radio group. Here, you've got the items keys that is duplicated in your config object, meaning you actually end up with 2 radios in your panel, but no radio group.
Then, simple panels do not have support for displaying labels. You must use a form panel for that.
Finally, you probably want to give all the radio in the group the same name, so that myForm.getForm().getValues() returns something like {myField: "Yes"} (the value will be taken from inputValue).
So here's what you're trying to do:
Ext.ComponentMgr.create({
xtype: 'form', // notice the changed xtype
renderTo: Ext.getBody(),
border: false,
items: [{
fieldLabel: 'Please select ',
xtype: 'radiogroup',
id: 'id1',
columns: 2,
vertical: false,
// radio buttons must be children of the radio group
items: [{
boxLabel: 'Yes',
// you probably want to give your radios the same name
name: 'myField',
inputValue: 'Yes'
}, {
boxLabel: 'No',
name: 'myField',
inputValue: 'No'
}]
}]
});
I get checked data string: "box0,box15,box30,box45"
Sencha docs says, I can set the value this way (checkboxes id and name are same like above)
// use comma separated string to set items with name to true (checked)
myCheckboxGroup.setValue('cb-col-1,cb-col-3');
I want to set true my boxes this way, but can't. Have you any idea about this?
This should work :
Ext.getCmp('MyCheckboxGroup').setValue({
cbxName: true,
cbxDescription: false
//cbxDescription: (condition) //you can always specify an condition here.
});
NOTE: cbxName, cbxDescription are the id's of checkboxes under MyCheckboxGroup, eg:
{
xtype: 'checkboxgroup',
fieldLabel: 'MyCheckboxGroup',
name: 'mycbxgrp',
columns: 2,
items: [
{ id: 'cbxName', boxLabel: 'Name', name: 'mycbxgrp', inputValue: 1 },
{ id: 'cbxDescription', boxLabel: 'Description', name: 'mycbxgrp', inputValue: 2 }
]
}
I'm not at work so i can't check my sources but i recall that it should be
cb-col-1 = Ext.getCmp(cb-col-1)
cb-col-3 = Ext.getCmp(cb-col-3)
myCheckboxGroup.setValue(cb-col-1 true);
myCheckboxGroup.setValue(cb-col-3, true);
if it is a component, and
Ext.get('cb-col-1').dom.value = true;
Ext.get('cb-col-3').dom.value = true;
if it is an element
When using setValue with a checkboxgroup you need to pass the checkbox field name:
Ext.create('Ext.form.CheckboxGroup', {
id: 'MyGroup',
items: [{
xtype:'checkbox',
name: 'check1'
},{
xtype: 'checkbox',
name: 'check2'
},{
xtype: 'checkbox',
name: 'checkset',
inputValue: 'val1'
},{
xtype: 'checkbox',
name: 'checkset',
inputValue: 'val2'
}]
});
Ext.getCmp('MyGroup').setValue({
check1: true,
check2: false,
checkset: ['val1', 'val2']
});
Literally lifted from the Sencha Docs
I have a form where i have a radiogroup 'yes', 'no'.
When i click on 'yes' i got a textfield added to a fieldset on the form with the config option: allowBlank: false. So there is validation on the field. When I click on 'no' all fields are removed from the fieldset that is present on the form.
The problem is when the validation is active, so when you go inside the textfield and you click away from it without entering any characters into it and i click on the radiobutton 'no' the textfield disappears and gives me the following error when i catch it:
Element.alignToXY with an element that doesn't exist
When i click afterwards on the radiobutton 'yes', the textfield is shown again BUT i get an error:
TypeError: dom is undefined
I could catch these errors and do nothing with it because in fact the form seems to be working, the textfields got added and removed like it should, there are only errors present and i don't like the concept of it. Does anyone has a clue why this error occurs and how to get rid of it so it's working 100% properly?
Here is an example of the code:
var radiogroup = new Ext.form.RadioGroup({
fieldLabel: 'Radio group test',
allowBlank: false,
anchor: '85%',
items: [{
boxLabel: 'Yes',
name: 'radio',
inputValue: 1
}, {
boxLabel: 'No',
name: 'radio',
inputValue: 2
}],
listeners: {
change: function (rg, radio) {
if (radio.inputValue == 1) {
var textfield_test = new Ext.form.TextField({
fieldLabel: 'Test',
allowBlank: false,
id: 'test',
name: 'test',
anchor: '85%',
width: 320,
helpText: 'test'
});
textfield_fieldset.insert(textfield_fieldset.items.length, textfield_test);
} else {
try {
txt_test = Ext.getCmp('test');
if (txt_test) {
textfield_fieldset.remove(txt_test);
}
textfield_fieldset.doLayout();
} catch (err) {
alert(err);
}
}
}
}
});
I've done this successfully not just for one textbox, but for an entire panel, and it works pretty well. In my case, any number of panel can be added and removed dynamically and it works pretty well. The relevant code that I used were:
panel.insert(medIndex,getNewPanel());
panel.doLayout();
And for remove i used,
var cmp = Ext.getCmp('Panel-' + Id);
if (cmp) {
treatment.remove(cmp, true); // True is the autoDestroy option.
}
These two in combination works for me. Though I would suggest that if you're doing this only for one textbox, then convert it into a hidden field and disable it. When you disable a field, it does not get submitted in a post, or ajax post request.
Hope this helps.
first, why did you re-add/re-remove a component like that?,..
if i was you... i will use the hide / show method of textfield class..
after read your code, i assuming that you are make a formPanel with 2 items (radiogroup and fieldset) where in the fieldset, there is a textfield... so, guestly.. mybe like this ??
var radiogroup = new Ext.form.RadioGroup({
fieldLabel: 'Radio group test',
allowBlank: false,
anchor: '85%',
items: [
{
boxLabel: 'Yes',
name: 'radio',
inputValue: 1},
{
boxLabel: 'No',
name: 'radio',
inputValue: 2}
],
listeners: {
change : function(a,b){
if (b.inputValue==1){
Ext.getCmp("textfield").enable();
Ext.getCmp("textfield").show();
}else{
Ext.getCmp("textfield").disable(); // set disable to prevent send empty data
Ext.getCmp("textfield").hide();
}
}
}
});
var formPanel = new Ext.form.FormPanel({
url : 'www.google.com',
method : "GET",
layout:'column',
frame :true,
border : false,
items : [
radiogroup,
{
xtype:'fieldset',
id : 'test',
title: 'Fieldset',
collapsible: true,
height : 200,
width : 350,
items :[{
xtype : "textfield",
id : 'textfield',
fieldLabel : "input data",
name : "text",
hidden:true,
disabled:true
}]
}
]
});
var win = new Ext.Window({
title : "holla",
width : 400,
height: 300,
border : false,
layout:'fit',
items : [formPanel]
});
win.show();
I created a jsfiddle to answer this question. The textfield seemed to get added / removed properly there: http://jsfiddle.net/jaycode/PGSb7/4/
Cheers.
Edit: For completeness, I guess I'll just post the code here as well
HTML
<div id="radios"></div>
<div id="textfield_fieldset"></div>
JS
var textfield_fieldset = new Ext.form.FieldSet({
renderTo: 'textfield_fieldset',
});
var radiogroup = new Ext.form.RadioGroup({
renderTo: 'radios',
width: 200,
height: 60,
fieldLabel: 'Radio group test',
allowBlank: false,
layout: {
type: 'vbox'
},
items: [
{
boxLabel: 'Yes',
name: 'radio',
inputValue: 1
},
{
boxLabel: 'No',
name: 'radio',
inputValue: 2
}
],
listeners: {
change: function(rg, radio) {
if (rg.lastValue.radio == 1) {
var textfield_test = new Ext.form.TextField({
fieldLabel: 'Test',
allowBlank: false,
id: 'test',
name: 'test',
anchor: '85%',
width: 320,
helpText: 'test'
});
textfield_fieldset.insert(textfield_fieldset.items.length, textfield_test);
} else {
txt_test = Ext.getCmp('test');
if (txt_test) {
textfield_fieldset.remove(txt_test);
}
textfield_fieldset.doLayout();
}
}
}
});