I have some ExtJS forms containing radiogroups.
And each of these radioGroups have 2 radios having inputValues as true and false.
But when I set form values using form.setValues(values), if radioButton value I want to set is false, respective radio is not getting selected. This works in case my value is true.
Here is link for fiddle
This works if you change booleanRadio: true.
My Code:
Ext.define('myView', {
extend: 'Ext.panel.Panel',
xtype: 'myView',
id: 'myViewContainer',
layout: 'vbox',
width: '100%',
initComponent: function() {
var me = this;
var allItems = [];
allItems.push(me.getMyForm());
Ext.applyIf(me, {
items: allItems
});
me.callParent(arguments);
},
getMyForm: function() {
var me = this;
var currentForm = {
xtype: 'form',
cls: 'y-form',
id: 'myForm',
trackResetOnLoad: true,
items: [
{
xtype: 'radiogroup',
fieldLabel: 'is Sponsored',
labelSeparator: '',
layout: 'hbox',
items: [
{
xtype: 'radiofield',
name: 'isSponsored',
boxLabel: 'Yes',
inputValue: true
},
{
xtype: 'radiofield',
name: 'isSponsored',
boxLabel: 'No',
inputValue: false
}
]
}
]
};
return currentForm;
}
});
Ext.define('myController', {
extend: 'Ext.app.Controller',
init: function() {
this.control({
'panel#myViewContainer': {
afterrender: this.retrieveFormValues
}
});
},
retrieveFormValues: function() {
var me = this;
var data = {isSponsored: false};
if (data != null && !Ext.Object.isEmpty(data)) {
var myFormContainer = Ext.getCmp('myViewContainer');
myFormContainer.getForm().setValues(data);
}
}
});
if you change the inputValues of radiobuttons to 0 or 1, and adjust values var accordingly, the desired radio button will be set. I have updated the fiddle.
items: [{
boxLabel: 'Item 1',
name: 'booleanRadio',
inputValue: 1,
}, {
boxLabel: 'Item 2',
name: 'booleanRadio',
inputValue: 0,
}],
listeners: {
afterrender: function(radioGroupForm) {
var values = {
booleanRadio: 0
}
Ext.getCmp('radioGroupFormPanel').getForm().setValues(values);
}
}
If you send false to radiobutton, it unchecks the radio. That's why your 'true' is working and 'false' is not.
Related
I have a form panel with a radiogroup, and depending on the radiogroup selection, it will show some other components. If a radiofield is not selected, then its items will be hidden, as they're not part of the active card.
Now, if I have allowblank: false set on a field (and it's empty) within the hidden card, my form is still considered invalid. Being hidden means the user would not like to use it, so it should not be considered as part of the form. Here's an example.
In the example, I have 2 forms... the top form is the one that I'm curious about... is there a way to get this working without having to bind to disabled? I tried looking at hideMode, but that wasn't what I was looking for.
Ideally, I wouldn't have to create a formula for each card that I add... that seems silly. I realize I could create a generic formula, but once again, that just seems extraneous. Another option could be ditching the card layout, and binding each card to hidden and disabled, but I'm creating more formulas. Is there some sort of property I'm missing?
Ext.application({
name: 'Fiddle',
launch: function() {
Ext.define('MyController', {
extend: 'Ext.app.ViewController',
alias: 'controller.myview',
onValidityChange: function(form, isValid, eOpts) {
this.getViewModel().set('isFormValid', isValid);
}
});
Ext.define('MyViewModel', {
extend: 'Ext.app.ViewModel',
alias: 'viewmodel.myview',
data: {
activeItem: {
myInput: 0
}
},
formulas: {
activeCardLayout: function(getter) {
var myInput = getter('activeItem.myInput');
console.log(myInput);
return parseInt(myInput);
}
}
});
Ext.define('MyForm', {
extend: 'Ext.form.Panel',
title: 'My Form',
controller: 'myview',
viewModel: {
type: 'myview'
},
layout: {
type: 'hbox'
},
listeners: {
validitychange: 'onValidityChange'
},
dockedItems: [{
xtype: 'toolbar',
dock: 'top',
layout: {
type: 'hbox'
},
items: [{
xtype: 'button',
text: 'Save',
reference: 'saveButton',
disabled: true,
bind: {
disabled: '{!isFormValid}'
}
}]
}],
items: [{
xtype: 'radiogroup',
vertical: true,
columns: 1,
bind: {
value: '{activeItem}'
},
defaults: {
name: 'myInput'
},
items: [{
boxLabel: 'None',
inputValue: '0'
}, {
boxLabel: 'Something',
inputValue: '1'
}]
}, {
xtype: 'container',
layout: 'card',
flex: 1,
bind: {
activeItem: '{activeCardLayout}'
},
items: [{
xtype: 'container',
layout: 'fit'
}, {
xtype: 'container',
layout: 'fit',
items: [{
xtype: 'textfield',
fieldLabel: 'hello',
allowBlank: false
}]
}]
}]
});
Ext.define('MyViewModel2', {
extend: 'Ext.app.ViewModel',
alias: 'viewmodel.myview2',
data: {
activeItem: {
myInput: 0
}
},
formulas: {
disableSomethingCard: function(getter) {
return getter('activeItem.myInput') !== '1';
},
activeCardLayout: function(getter) {
var myInput = getter('activeItem.myInput');
console.log(myInput, 'here');
return parseInt(myInput);
}
}
});
Ext.define('MyForm2', {
extend: 'MyForm',
title: 'My Form 2 (works)',
viewModel: {
type: 'myview2'
},
items: [{
xtype: 'radiogroup',
vertical: true,
columns: 1,
bind: {
value: '{activeItem}'
},
defaults: {
name: 'myInput'
},
items: [{
boxLabel: 'None',
inputValue: '0'
}, {
boxLabel: 'Something',
inputValue: '1'
}]
}, {
xtype: 'container',
layout: 'card',
flex: 1,
bind: {
activeItem: '{activeCardLayout}'
},
items: [{
xtype: 'container',
layout: 'fit'
}, {
xtype: 'container',
layout: 'fit',
bind: {
disabled: '{disableSomethingCard}'
},
items: [{
xtype: 'textfield',
fieldLabel: 'hello',
allowBlank: false
}]
}]
}]
});
Ext.create('MyForm', {
renderTo: Ext.getBody()
});
Ext.create('MyForm2', {
renderTo: Ext.getBody()
});
}
});
I have a listContainer and on tap of any item in the list, I open another page known as editContainer with the record from list. In the edit page, I want to disable a dropdown based on the value of another field, is there any way I can get the values in record in the initialize function of editContainer? Here is my code:-
onListItemTap:function(dataview,index,target,record,e,eOpts)
{
if(record)
this.editContainer = Ext.create('myApp.view.EditContainer',{title:'Edit Data'});
this.editContainer.setRecord(record);
this.getMainNav().push(this.editContainer);
}
Above code opens editContainer when a list item is selected. Below is my EditContainer
Ext.define('myApp.view.EditContainer', {
extend: 'Ext.Container',
requires: [
'Ext.form.Panel',
'Ext.form.FieldSet',
'Ext.field.Select'
],
config: {
id: 'editContainer',
autoDestroy: false,
layout: 'fit',
items: [
{
xtype: 'formpanel',
id: 'editFormPanel',
padding: 10,
styleHtmlContent: true,
autoDestroy: false,
layout: 'fit',
items: [
{
xtype: 'fieldset',
id: 'nameFieldSet',
autoDestroy: false,
items: [
{
xtype: 'textfield',
id: 'siteName',
itemId: 'mytextfield',
label: 'Name',
labelWidth: '35%',
name: 'name'
},
{
xtype: 'selectfield',
id: 'role',
itemId: 'myselectfield4',
label: 'Role',
labelWidth: '35%',
name: 'role',
options: [
{
text: 'Unassigned',
value: 'Unassigned'
},
{
text: 'Role1',
value: 'role1'
}
]
},
{
xtype: 'selectfield',
id: 'type',
label: 'Type',
labelWidth: '35%',
name: 'type',
options: [
{
text: 'Default',
value: 'Default'
},
{
text: 'Custom',
value: 'custom'
}
]
},
{
xtype: 'selectfield',
id: 'roleValue',
label: 'Role Value',
labelWidth: '35%',
name: 'rolevalue',
options: [
{
text: 'value1',
value: 'value1'
},
{
text: 'value2',
value: 'value2'
},
{
text: 'value3',
value: 'value3'
}
]
}
]
}
]
}
],
listeners: [
{
fn: 'onTextfieldKeyup',
event: 'keyup',
delegate: 'textfield'
},
{
fn: 'onSelectfieldChange',
event: 'change',
delegate: 'selectfield'
}
]
},
onTextfieldKeyup: function(textfield, e, eOpts) {
this.fireEvent('change', this);
},
onSelectfieldChange: function(selectfield, newValue, oldValue, eOpts) {
this.fireEvent('change', this);
},
initialize: function() {
this.callParent();
var record;
//Code to disable roleValue selectfield if Role is unassigned.
},
updateRecord: function(newRecord) {
var me = this,
myPanel = me.down('#editFormPanel');
if(myPanel)
myPanel.setRecord(newRecord);
},
saveRecord: function() {
var me =this,
myStore = Ext.data.StoreManager.lookup('MyStore');
var formPanel = me.down('#editFormPanel'),
record = formPanel.getRecord();
formPanel.updateRecord(record);
return record;
}
});
Since creating your editContainer and setting its data are two different steps in your code you can't use the initialize method of the editContainer.
But you can override the setRecord method of the editContainer, so it additionally disables the dropdown.
Since you push the editContainer onto a navigation view you could also use the activate event of the editContainer to disable the dropdown.
Maybe you can create a quick store on the fly, as a place to have a reference to that data...
//in your controller where you set the record
var mod = Ext.define('app.model.PanelDataModel', {
extend: 'Ext.data.Model',
config: {
fields: [
'roleValue'
]
}
});
var sto = Ext.create('Ext.data.Store', {
model: mod,
id:'PanelDataStore'
});
sto.add({
roleValue: record.roleValue
});
sto.sync();
//Now in your panel's initialize method:
var pstore = Ext.getStore('PanelDataStore');
pstore.load();
if(pstore.data.all[0].data.roleValue == 'unassigned'){
Ext.getCmp('roleValue').setDisabled(true);
}
Here is my view:
Ext.define('NG.view.order.Header', {
extend: 'Ext.form.Panel',
alias: 'widget.orderheader',
scroll: 'vertical',
layout: 'column',
defaults: {
columnWidth: .33,
border: false
},
config: {
order: null
},
constructor: function (config) {
var me = this;
me.items = me.createItems();
me.callParent(arguments);
me.setOrder(config.order);
},
// creates this view items.
createItems: function () {
var items = [{
//column 1
layout: 'form',
defaultType: 'displayfield',
defaults: {
margin:'0 0 15 0'
},
items: [{
fieldLabel: 'No',
name: 'orderNumber'
}, {
fieldLabel: 'Ver',
name: 'version'
}, {
fieldLabel: 'Date',
name: 'orderDate',
renderer: Ext.util.Format.dateRenderer(Date.patterns.defaultFormat)
}, {
fieldLabel: 'Amount',
name: 'totalAmount'
}]
}, {
//column 2
layout: 'form',
defaultType: 'displayfield',
items: [{
fieldLabel: 'Supplier',
name: 'vendorName'
}, {
fieldLabel: 'Supplier No',
name: 'vendorDuns'
}, {
fieldLabel: 'Customer',
name: 'customerName'
}, {
fieldLabel: 'Buyer',
name: 'orderBuyerName'
}]
}]
return items;
}
});
As you can see I have set a margin on the first column fields.
Its seems this value is ignored .
Is this a known issue ??
Is there a workaround?
I have a checkbox group with somany checkboxes in it. I want to check all of them once when a button clicked. These checkboxes are created dynamically.
var json = result.responseText;
var temp = JSON.parse(json);
for(var i=0;i<Object.keys(temp[newValue]).length;i++){
menuArray.push({
xtype: 'checkboxfield',
boxLabel: (temp[newValue][i]).split("_").join(" "),
name: temp[newValue][i],
id:temp[newValue][i],
inputValue: 'true',
uncheckedValue: 'false',
formBind: false
});
}
checkboxGroup = new Ext.form.CheckboxGroup({
xtype: 'checkboxgroup',
fieldLabel: '',
id:'moduleCheckboxGroup',
columns: 1,
items: menuArray
});
permissionPanel.removeAll();
permissionPanel.add(checkboxGroup);
Thanks in advance!
you can use "query" method to search childs with "isCheckbox".
Ext.create('Ext.form.CheckboxGroup', {
renderTo: Ext.getBody(),
id: 'mycheckboxgroup',
columns: 1,
items: [{
xtype: 'checkboxfield',
boxLabel: 'Test1',
name: 'test1',
inputValue: 'true',
uncheckedValue: 'false',
formBind: false
}, {
xtype: 'checkboxfield',
boxLabel: 'Test2',
name: 'test2',
inputValue: 'true',
uncheckedValue: 'false',
formBind: false
}, {
xtype: 'checkboxfield',
boxLabel: 'Test3',
name: 'test3',
inputValue: 'true',
uncheckedValue: 'false',
formBind: false
}]
});
Ext.create('Ext.Button', {
renderTo: Ext.getBody(),
text: 'Check all',
handler: function () {
var checkboxes = Ext.getCmp('mycheckboxgroup').query('[isCheckbox]');
Ext.Array.each(checkboxes, function (checkbox) {
checkbox.setValue(1);
});
}
});
Jsfiddle example
I would create a button which holds a reference to a checkbox group and then store states to toggle select and de-select on click. Here is a live demo of the code below.
App
var group = Ext.create('App.DynamicCheckboxGroup', {
id: 'mycheckboxgroup',
count : 9,
columns : 3,
width: 180,
renderTo: Ext.getBody()
});
Ext.create('App.CheckboxGroupButton', {
checkboxGroup: group,
renderTo: Ext.getBody()
});
DynamicCheckboxGroup
Ext.define('App.DynamicCheckboxGroup', {
extend : 'Ext.form.CheckboxGroup',
config : {
count : 3
},
initComponent : function() {
var me = this;
var items = [];
for (var i = 1; i <= me.count; i++) {
items.push({
xtype: 'checkbox',
boxLabel: 'Test' + i,
name: 'test' + i,
inputValue: 'true',
uncheckedValue: 'false',
formBind: false
});
}
me.items = items;
me.callParent(arguments);
}
});
CheckboxGroupButton
Ext.define('App.CheckboxGroupButton', {
extend: 'Ext.Button',
config : {
checkboxGroup : null,
states : [{
text : 'Deselect All',
value : 1
}, {
text: 'Select All',
value : 0
}]
},
initComponent : function() {
var me = this;
me.setText(me.states[1].text);
me.callParent(arguments);
},
handler : function (button, e) {
var me = this;
var newState = me.states.reduce(function(result, state) {
return state.text !== button.getText() ? state : result;
}, {});
Ext.Array.each(me.checkboxGroup.getBoxes(), function (checkbox) {
checkbox.setValue(newState.value);
});
button.setText(newState.text);
}
});
In ExtJS 4.x there is a shortcut for Eldono's solution:
var checkBoxes = checkboxGroup.getBoxes()
Sencha docs: Ext.form.CheckboxGroupView.getBoxes
I need to access a PropertyGrid of a created NewPerson window.
NewPerson window is composed of a propertygrid and a toolbar.
When a user fill in the propertygrid and hits 'Save' button, a new
person should be created with the attributes present in the
propertygrid.
the problem is that a user should be able to create as many NewPerson windows as he needs, so how can I access the propertygrid of a window? Thanks.
NewPerson Window View:
Ext.define('MyApp.view.ui.NewPerson', {
extend: 'Ext.window.Window',
height: 180,
width: 524,
resizable: false
,
layout: {
type: 'fit'
},
title: 'New Person',
initComponent: function() {
var me = this;
Ext.applyIf(me, {
dockedItems: [
{
xtype: 'newpersontoolbar',
dock: 'bottom'
}
],
items: [
{
xtype: 'newpersongrid'
}
]
});
me.callParent(arguments);
}
});
NewPersonGrid View:
Ext.define('MyApp.view.ui.NewPersonGrid', {
extend: 'Ext.grid.property.Grid',
border: 0,
id: 'newpersongrid',
forceFit: true,
initComponent: function() {
var me = this;
Ext.applyIf(me, {
source: {
'Property 1': 'String',
'Property 2': true,
'Property 3': '2012-02-20T19:22:06',
'Property 4': 123
},
listeners: {
afterlayout: {
fn: me.onPropertyAfterLayout,
scope: me
}
}
});
me.callParent(arguments);
},
onPropertyAfterLayout: function(abstractcontainer, layout, options) {
}
});
NewPersonToolbar View:
Ext.define('MyApp.view.ui.NewPersonToolbar', {
extend: 'Ext.toolbar.Toolbar',
initComponent: function() {
var me = this;
Ext.applyIf(me, {
items: [
{
xtype: 'savebutton'
}
]
});
me.callParent(arguments);
}
});
SaveButton View:
Ext.define('MyApp.view.ui.SaveButton', {
extend: 'Ext.button.Button',
text: 'Save person',
initComponent: function() {
var me = this;
Ext.applyIf(me, {
listeners: {
click: {
fn: me.onButtonClick,
scope: me
}
}
});
me.callParent(arguments);
},
onButtonClick: function(button, e, options) {
// GRID = code here to access propertygrid
Ext.create('MyApp.model.Person', Ext.encode(GRID.getSource()));
}
});
Since your MyApp.view.ui.NewPerson is a component that contains both the property grid and a save button, it makes sense to put the logic that binds the two there:
Ext.define('MyApp.view.ui.NewPerson', {
extend: 'Ext.window.Window',
...
initComponent: function() {
var me = this;
Ext.applyIf(me, {
dockedItems: [
{
xtype: 'newpersontoolbar',
dock: 'bottom'
}
],
items: [
{
xtype: 'newpersongrid'
}
]
});
me.callParent(arguments);
me.down('#savePersonButton').handler = function(button, e) {
me.down('#newpersongrid').doSomething();
}
}
});
You will need to add itemId = 'savePersonButton' and itemId = 'newpersongrid' property to both your button and grid respectively (since it is not an id it can be used in many instances of component, but will be scoped to one container each time.