Fill the combo ExtJS by the custom data - arrays

I have Combo ExtJS, that should be filled by the data from Spring MVC - like this:
var LongRecord = Ext.data.Record.create([
{name: 'id', mapping: 'id'}
]);
var comboStore = new MyDataStore.data.Store({
proxy: new MyDataStore.data.DwrProxy({
invoker: function(params, arg, cb) {
// data from server
AssetScreener.getEntityOwnerIds(cb);
console.log("invoker has been called");
}
}),
reader: new Ext.data.ArrayReader({}, LongRecord),
listeners: {
'load': function(s, recs) {
alert("!");
}
}
});
Combo code:
new Ext.form.ComboBox({
store: comboStore,
typeAhead: true,
triggerAction: 'all',
editable: false,
width: 100,
displayField: 'id',
valueField: 'id'
});
Problem is that data, that I'm getting from server, looks like this
'5','0',["1","8","133"]
I need to slice the array ["1","8","133"] and show this in combo (change backend java-code is unwishable way).
In combo after this code is executed I see the three empty items. Need hints, please.

In the load event, you'll get the ["1","8","133"] from the recs parameter after slicing. Use store.loadData() to replace the current store records with the correct ones.
You can create a model out of the array to feed the store like so:
var i, item, feed = [];
for(i=0; i<array.length; i++)
{
item = array[i];
feed.push(Ext.create('com.your.Model', {
id : item
}));
}
store.loadData(feed);

Related

Extjs Combobox store value from another object

I have a object that has some values that i want to display in a combobox that i am adding to a form panel inside a for loop.
this is the contents of the object object
but in my combobox i get data as [object Object]
here is what i am currently doing
for(var i = 0; i < data.length ; i++)
{
console.log('ad');
var storeStates = new Ext.data.ArrayStore({
fields: ['optionText'],
data : [data[i].data.selectOptions.list[i].optionText]
});
var cb = new Ext.form.ComboBox({
fieldLabel: data[i].data.name,
hiddenName: 'fieldTypeName',
id: data[i].data.name.toString(),
valueField: 'optionText',
displayField: 'optionText',
typeAhead: true,
allowBlank: false,
mode: 'local',
selectOnFocus: true,
triggerAction: 'all',
emptyText: 'Survey Field Type',
disabled: this.existingField,
width: 190,
store: storeStates,
listeners: {
'select': function (combo, newValue, oldValue) {
}
}
});
Ext.getCmp('survey-field-form').add(cb);
//Ext.getCmp('survey-field-form').doLayout();
console.log('added');
}
You need to change your store definition from Ext.data.ArrayStore to Ext.data.Store & data as data[i].data.selectOptions.list
var storeStates = new Ext.data.Store({
fields: ['optionText'],
data : data[i].data.selectOptions.list
});
I think you need to define your store like that to get the correct display:
var storeStates = new Ext.data.JsonStore({
data: data[i].data.selectOptions.list,
fields: [{name: "optionText", type: "string"}]
});
I solved it by creating a reader and a store and pushing data into the store and then loading the store like this
// create a Record constructor:
var rt = Ext.data.Record.create([
{name: 'optionValue'},
{name: 'optionText'}
]);
var myStore = new Ext.data.Store({
// explicitly create reader
reader: new Ext.data.ArrayReader(
{
idIndex: 0 // id for each record will be the first element
},
rt // recordType
)
});
var myData = [];
for(var j = 0; j < data[i].data.selectOptions.list.length; j++)
{
var optionText = data[i].data.selectOptions.list[j].optionText.toString();
var optionValue = data[i].data.selectOptions.list[j].optionValue.toString();
myData.push([optionValue, optionText]);
}
myStore.loadData(myData);
Hope this helps someone else

Preselect items in EXT JS 4.2 Grid

I am trying to preselect items in my EXT grid based on the value of one of the items in the data store.
In my data store I fetch 7 items, the last item I grab 'installed' is a BOOLEAN and I would like to use that to preselect items in my grid.
Here is the code I have so far that is not working...
Ext.require([
'Ext.grid.*',
'Ext.data.*',
'Ext.selection.CheckboxModel'
]);
Ext.onReady(function(){
Ext.QuickTips.init();
var sb = $('#sb_id').val();
// Data store
var data = Ext.create('Ext.data.JsonStore', {
autoLoad: true,
fields: [ 'name', 'market', 'expertise', 'id', 'isFull', 'isPrimary', 'installed'],
proxy: {
type: 'ajax',
url: '/opsLibrary/getLibraryJsonEdit',
extraParams: {
sb_id: sb
},
actionMethods: 'POST'
},
sorters: [{
property: 'market',
direction: 'ASC'
}, {
property: 'expertise',
direction: 'ASC'
}]
});
data.on('load',function(records){
Ext.each(records,function(record){
var recs = [];
Ext.each(record, function(item, index){
console.log(item.data);
if (item.data['installed'] == true) {
console.log('Hi!');
recs.push(index);
}
});
//data.getSelectionModel().selectRows(recs);
})
});
// Selection model
var selModel = Ext.create('Ext.selection.CheckboxModel', {
columns: [
{xtype : 'checkcolumn', text : 'Active', dataIndex : 'id'}
],
listeners: {
selectionchange: function(value, meta, record, row, rowIndex, colIndex){
var selectedRecords = grid4.getSelectionModel().getSelection();
var selectedParams = [];
// Clear input and reset vars
$('#selected-libraries').empty();
var record = null;
var isFull = null;
var isPrimary = null;
// Loop through selected records
for(var i = 0, len = selectedRecords.length; i < len; i++){
record = selectedRecords[i];
// Is full library checked?
isFull = record.get('isFull');
// Is this primary library?
isPrimary = record.get('isPrimary');
// Build data object
selectedParams.push({
id: record.getId(),
full: isFull,
primary: isPrimary
});
}
// JSON encode object and set hidden input
$('#selected-libraries').val(JSON.stringify(selectedParams));
}}
});
I was trying to use an on.load method once the store was populated to go back and preselect my items but am not having any luck.
Im a Python guy and don't get around JS too much so sorry for the noobness.
Any help would be appreciated.
Thanks again!
You should be able to do something like:
//create selModel instance above
data.on('load', function(st, recs) {
var installedRecords = Ext.Array.filter(recs, function(rec) {
return rec.get('installed');
});
//selModel instance
selModel.select(installedRecords);
});
Select can take an array of records.
http://docs.sencha.com/extjs/4.2.1/#!/api/Ext.selection.Model-method-select
//data.getSelectionModel().selectRows(recs);
Didn't work because store's don't have a reference to selection models it is the other way around. You can get a selection model from a grid by doing grid.getSelectionModel() or
you can just use the selModel instance you created
var selModel = Ext.create('Ext.selection.CheckboxModel', {

Extjs Grid - Delete all record has a conditional

I have a grid and a button will delete in http://jsfiddle.net/9zB8R/
My field like fields: ['id', 'name', 'type']. If type == delete i will delete it.
I init data like:
var simpleData = [];
var store = new Ext.data.ArrayStore({
fields: ['id', 'name', 'type'],
data: simpleData
});
for (i = 0; i < 20; i++) {
simpleData.push({id:''+i+'', name: 'name'+i, type: 'delete'});
}
//this record will not delete
simpleData.push({id:'20', name: 'enable', type: 'enable'});
store.loadData(simpleData);
I have a tbar like below but that can't delete all record have type == delete. How can i fix that. Thanks.
tbar:[
{
text:'Delete all type = delete',
handler:function(){
store.each(function(item, idx) {
if (item && item.get('type')=='delete') {
store.removeAt(idx);
}
});
}
}
]
The problem is with the "each" loop. Removing items in the loop is changing store size and hence only some of the items are getting deleted.
To get around it, you can loop through the store in reverse order and then delete as below:
var grid = new Ext.grid.GridPanel({
width: 400,
height: 600,
store: store,
loadMask: true,
renderTo: Ext.getBody(),
tbar:[
{
text:'Delete all type = delete',
handler:function(){
var i = store.getCount()-1;
for (i; i>=0; i--) {
if (store.getAt(i).get('type')=='delete') {
store.removeAt(i);
}
}
}
}
],

Updating a value on an Ext.form.Panel

The following should be trivial, but I cannot get it to work:
I have the following Ext.form.Panel:
Ext.define('EvaluateIt.view.SiteEvaluationForm', {
extend: 'Ext.form.Panel',
alias : 'widget.siteEvaluationForm',
id: 'evaluationId',
requires: [
'Ext.form.Panel',
'Ext.form.FieldSet',
'Ext.field.Url',
'Ext.field.Select',
'Ext.field.Hidden'
],
config: {
// We give it a left and top property to make it floating by default
left: 0,
top: 0,
// Make it modal so you can click the mask to hide the overlay
modal: true,
hideOnMaskTap: true,
// Set the width and height of the panel
//width: 400,
//height: 330,
width: Ext.os.deviceType == 'Phone' ? screen.width : 300,
height: Ext.os.deviceType == 'Phone' ? screen.height : 500,
scrollable: true,
layout: {
type: 'vbox'
},
defaults: {
margin: '0 0 5 0',
labelWidth: '40%',
labelWrap: true
},
items: [
{
xtype: 'textfield',
name: 'address',
label: 'Address',
itemId: 'address'
},
{
xtype: 'hiddenfield',
itemId: 'imageUriId',
name: 'imageUri'
},
{
xtype: 'button',
itemId: 'siteImage',
text: 'Take Photo'
},
{
xtype: 'button',
itemId: 'save',
text: 'Save'
}
]
}
});
Which gets opened from an onItemDisclosure in a list view, and thus has a record bound to it.
When the 'siteImage' button is tapped, the user selects an image from the photo gallery and the uri is written to a temporary store for processing. This part works just fine.
What I need to do: When 'save' in the above form is tapped I need to take the uri from the temporary store and write it to the same store that all of the values from the above form get saved to.
To do this, I have the following method:
onSaveSiteEvaluation: function(button) {
console.log('Button Click for Save');
//var form = button.up('panel');
var form = Ext.getCmp('evaluationId');
//get the record
var record = form.getRecord();
//get the form values
//var values = form.getValues();
// return a clone for updating of values
var values = Ext.clone(form.getValues());
//if a new siteEvaluation
if(!record){
var newRecord = new EvaluateIt.model.SiteEvaluation(values);
Ext.getStore('SiteEvaluations').add(newRecord);
}
//existing siteEvaluation
else {
// get image uri from temp store
var images = Ext.create('EvaluateIt.store.ImageQueue');
images.queryBy(function(record,id){
images = Ext.getStore(images);
if (images.getCount() > 0) {
var uri = record.get('src');
// image = Ext.getCmp('imageUri');
//image = form.setValue(uri);
//form.getCmp('imageId').setValue(uri);
console.log('URI: ' + uri);
// THIS DOES NOT WORK!!
form.setValues({
imageUri: uri
})
//record.set('imageUri',uri)
console.log('imageUri: '+ record.get('imageUri'));
}
});
// do stuff
record.set(values);
}
form.hide();
//save the data to the Web local Storage
Ext.getStore('SiteEvaluations').sync();
},
Everything in this method works EXCEPT where I write the value of the uri to the form
form.setValues({
imageUri: uri
})
I've tried making 'uriImage' as an xType of hiddenfield and textfield, I've tried cloning the values from the form, etc. all with absolutely no luck in updating the actual attribute imageUri in the store (NOTE: All other form values are updated just fine). What am I missing? Thanks!
UPDATE
This works:
images.queryBy(function(iRecord,id){
images = Ext.getStore(images);
if (images.getCount() > 0) {
var uri = iRecord.get('src');
// update store with URI
form.setValues({
imageUri: uri
})
values = form.getValues();
record = form.getRecord();
}
});
// do stuff
record.set(values);
All's well that ends well!
Because Ext.form.Panel doesn't have setValue method. You first need to get basic form out of it:
form.getForm().setValue();
UPDATE: My bad, I was looking at the ExtJs docs and not Sencha Touch. your form does have setValue method.
After you call setValues(), can you go getRecord() again? Also looks like your record internal variable is defined twice. That should not be an issue, but...

How to pass parameter for selected value of Combobox and get values for the parameter from database

I am using ext js.
I have combo box where I am selecting a value and using this value as parameter to get other values (two values). Now I want this to be added to a variable so I can use it in other places other than the combobox. How can I do this?
var txtEP=new Ext.form.ComboBox({
renderTo: "txtEP",
fieldLabel: 'End Point',
triggerAction: "all",
forceSelection: true,
mode:'local',
autoScroll: true,
allowBlank: false,
autoShow: true,
typeAhead:true,
store: genres,
valueField:'pincode',
displayField:'pincode',
emptyText:'Select a Start Point',
selectOnFocus:true,
listeners : {
'select' : function(){
var selVal = this.getValue();
//endpt(Global Variable) is the variable where i am trying to get this value.
endpt=store.load({url:'./genres1.php', params: {pincode: selVal}});
alert(endpt);
}
}
//valueField: 'X,Y'
});
You would have to assign it in a callback as a config of store.load this is because when you assign it right away the store does not contain any data. Something like this:
var txtEP = new Ext.form.ComboBox({
renderTo: "txtEP",
fieldLabel: 'End Point',
triggerAction: "all",
forceSelection: true,
mode:'local',
autoScroll: true,
allowBlank: false,
autoShow: true,
typeAhead:true,
store: genres,
valueField:'pincode',
displayField:'pincode',
emptyText:'Select a Start Point',
selectOnFocus:true,
listeners : {
'select' : function(){
var selVal = this.getValue();
store.load({
url:'./genres1.php',
params: {pincode: selVal},
callback: function(records) {
endpt = records; // here is where it is assigned
}
});
}
}
});
Realize also, that "endpt" will now contain an array of Ext.data.Model objects so you can use the methods given here to extract whatever values you need from them.
To answer your comment:
Ext.data.Model has a get method. You pass it the name of the field you want to get values with. In your case, you mentioned somewhere that /genres.php returns two values, if the data is returned as one record with two different columns like this:
column header: | value1 | value2
row 1: | 'data1' | 'data2'
You could assign the two returned data values to variables in your callback function like this, say you named your variables firstValue and secondValue:
firstValue = endpt[0].get('value1');
secondValue = endpt[0].get('value2');
If instead, your /genres.php returns the data as two different rows with only one column header like this:
column header: value
row 1: 'data1'
row 2: 'data2'
You could assign the data to variables like this:
firstValue = endpt[0].get('value');
secondValue = endpt[1].get('value');

Resources