Main view file
Ext.define('DemoApp1.view.Main', {
extend: 'Ext.tab.Panel',
xtype: 'main',
requires: [
'Ext.form.FieldSet',
'Ext.field.Text',
'Ext.field.Email',
'Ext.field.Password',
'Ext.field.DatePicker',
'Ext.TitleBar',
'Ext.Button'
],
config: {
tabBarPosition: 'bottom',
items: [
{
xtype: 'container',
title: 'Login',
autoDestroy: false,
layout: {
type: 'vbox',
pack: 'center',
align: 'center'
},
iconCls: 'user',
items: [
// login user
{
xtype: 'fieldset',
id: 'login-user-field-set',
width: 500,
title: 'Login Here!',
items: [
{
xtype: 'emailfield',
label: 'Email',
name: 'user'
},
{
xtype: 'passwordfield',
label: 'Password',
name: 'password'
}
]
},
{
xtype: 'button',
id: 'login-button',
text: 'Login',
ui: 'confirm',
width: 150
}
]
},
{
autoDestroy: false,
xtype: 'container',
title: 'Register',
layout: 'vbox',
scrollable: true,
iconCls: 'add',
items: [
{
xtype: 'titlebar',
title: 'Register New User',
docked: 'top'
},
{
// register new user
xtype: 'fieldset',
id: 'reg-items-field-set',
items: [
{
xtype: 'textfield',
label: 'Email',
allowBlank: false,
name: 'reg_user'
},
{
xtype: 'passwordfield',
label: 'Password',
name: 'reg_password'
},
{
xtype: 'passwordfield',
label: 'Confirm Password',
name: 'reg_cpassword'
},
{
xtype: 'textfield',
label: 'User Name',
name: 'reg_user_name'
},
{
xtype: 'datepickerfield',
picker: {
yearFrom: 1975,
yearTo: 2005
},
label: 'DOB',
name: 'reg_dob'
},
{
xtype: 'selectfield',
label: 'Gender',
name: 'reg_gender',
options: [
{text: 'Male', value: 'male'},
{text: 'Female', value: 'female'}
]
}
]
},
{
xtype: 'container',
layout: {
type: 'hbox',
align: 'center',
pack: 'center'
},
items: [
{
xtype: 'button',
id: 'register-button',
text: 'Register',
ui: 'confirm',
width: 200
},
{
xtype: 'spacer',
width: 50
},
{
xtype: 'button',
id: 'reset-button',
text: 'Reset',
ui: 'decline',
width: 200
}
]
}
]
}
]
}
});
Controller file
Ext.define('DemoApp1.controller.MainController', {
extend: 'Ext.app.Controller',
requires: [
'Ext.form.FieldSet',
'Ext.Button'
],
config: {
refs: {
loginButton: '#login-button',
regFieldSet: '#reg-items-field-set',
regNewUserButton: '#register-button',
regFormResetButton: '#reset-button',
loginUserFieldSet: '#login-user-field-set'
},
control: {
loginButton: {
tap: 'loginButtonTapped'
},
regFormResetButton: {
tap: 'regFormResetButtonTapped'
},
regNewUserButton: {
tap: 'regNewUserButtonTapped'
}
},
loginButtonTapped: function(self, e) {
console.log('loginButtonTapped');
},
regFormResetButtonTapped: function(self, e) {
console.log('regFormResetButtonTapped');
},
regNewUserButtonTapped: function(self, e) {
console.log('regNewUserButtonTapped');
}
}
});
on click on any button it logging the below
Uncaught TypeError: Cannot read property 'apply' of undefined
what wrong in it???
thanks in advance...
Your methods should not go in the config block. loginButtonTapped, regFormResetButtonTapped and regNewUserButtonTapped. They should come out one level into the class definition, because they are class methods, not configurations.
Related
I'm working on creating a user profile view in my ext.js (and sencha touch) application. I have my routes set up and I have my data model in my data.js. I also created a form to show the data in. However, I'm having issues getting the user data to render on the front end.
index.js code:
// User Profile
var userProfileToolbar = {
xtype: 'toolbar',
id: 'userProfileToolbar',
title: 'UserProfile',
style: settings_sz2,
ui: 'light',
docked: 'top',
items: gen_top_buttons
};
var userprofile_tabbar = {
xtype: 'tabbar',
id: 'userprofile_tabbar',
style: dark_tabbar_sz,
ui: 'light',
docked: 'top',
items: all_discover_buttons
};
var profileForm = {
items: [
{
xtype: 'textfield',
name : 'email',
label: 'Email',
labelWidth: '35%'
},
{
xtype: 'textfield',
name : 'disp_name',
label: 'Display Name',
labelWidth: '35%',
listeners: {
check: {
fn: function() {
account.get('disp_name');
account.set("disp_name", disp_name);
account.setDirty();
store.sync();
}
}
}
},
{
xtype: 'urlfield',
name : 'url',
label: 'Website',
labelWidth: '35%'
},
{
xtype: 'textfield',
name : 'location',
label: 'Location',
labelWidth: '35%'
},
{
xtype: 'selectfield',
name : 'defaultCollection',
label: 'Default Collection',
labelWidth: '35%',
labelWrap:true,
options: [
{text: 'First Option', value: 'first'},
{text: 'Second Option', value: 'second'},
{text: 'Third Option', value: 'third'}
]
},
{
xtype: 'selectfield',
name : 'relationshipStatus',
label: 'Relationship Status',
labelWidth: '35%',
labelWrap:true,
options: [
{text: 'Single', value: 'single'},
{text: 'In a Relationship', value: 'inARelationship'},
{text: 'Married', value: 'married'}
]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Gender',
style: settings_sz,
hidden: false,
margin: '0',
id: 'male_female_gender',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'male_female_gender',
label: 'Male',
value: 0,
}, {
name: 'male_female_gender',
label: 'Female',
value: 1,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Sexual Orientation',
style: settings_sz,
hidden: false,
margin: '0',
id: 'sexual_orientation',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'sexual_orientation',
label: 'Straight',
value: 0,
}, {
name: 'sexual_orientation',
label: 'Gay',
value: 1,
},{
name: 'sexual_orientation',
label: 'Bi',
value: 2,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Email Subscription',
style: settings_sz,
hidden: false,
margin: '0',
id: 'enable_disable_email_subscription',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'enable_disable_email_subscription',
label: 'Enabled',
value: 0,
}, {
name: 'enable_disable_email_subscription',
label: 'Disabled',
value: 1,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Default Access',
style: settings_sz,
hidden: false,
margin: '0',
id: 'enable_disable_default_access',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'enable_disable_default_access',
label: 'Public',
value: 0,
}, {
name: 'enable_disable_default_access',
label: 'Private',
value: 1,
}, {
name: 'enable_disable_default_access',
label: 'Adult',
value: 2,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Safe Browsing',
style: settings_sz,
hidden: false,
margin: '0',
id: 'enable_disable_safe_browsing',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'enable_disable_safe_browsing',
label: 'On',
value: 0,
}, {
name: 'enable_disable_safe_browsing',
label: 'Off',
value: 1,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Visibility',
style: settings_sz,
hidden: false,
margin: '0',
id: 'everyone_loggedin_visibility',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'everyone_loggedin_visibility',
label: 'Everyone',
value: 0,
}, {
name: 'everyone_loggedin_visibility',
label: 'Logged In',
value: 1,
}]
},
{
xtype: 'fieldset',
pack: 'center',
title: 'Email Notification',
style: settings_sz,
hidden: false,
margin: '0',
id: 'new_share_emailnotification',
defaults: {
xtype: 'radiofield',
labelWidth: '35%'
},
items: [{
name: 'new_share_emailnotification',
label: 'New Connection',
value: 0,
}, {
name: 'new_share_emailnotification',
label: 'Video Sharing',
value: 1,
}]
},
{
xtype: 'button',
ui: 'plain',
style: 'background-color: green; width: 90%; color: white; margin-left: 5%; margin-bottom: 15px; margin-top: 15px',
id: 'save',
text: 'Save Changes'
},
{
xtype: 'button',
style: 'width: 90%; margin-left: 5%; margin-bottom: 15px;',
id: 'cancel',
text: 'Cancel',
},
],
listeners: {
itemtap: {
fn: function(view, index, target, record, event) {
var user_id = record.get('user_id');
setTimeout(function() {
Ext.getCmp('userprofile_recommendations_var').deselectAll();
}, 500);
}
}
}
};
Ext.define('myVidster.view.UserProfile', {
extend: 'Ext.Panel',
id: 'UserProfile',
fields: [
'email',
{name: 'disp_name', type: 'string', value: 'account.get("disp_name")'},
],
alias: 'widget.UserProfile',
config: {
scrollable: {
direction: 'vertical',
directionLock: true,
},
fullscreen: true,
layout: {
type: 'vbox',
align: 'stretch'
},
items: [userProfileToolbar, profileForm,]
},
listeners: {
load: function(users) {
var profileForm = Ext.getCmp('UserProfile');
profileForm.loadRecord(this.data.first());
}
}
});
Data.js:
//User Profile Data
Ext.define('userprofile_model', {
extend: 'Ext.data.Model',
config: {
fields: [{
name: 'id',
type: 'int'
}, {
name: 'user_id',
type: 'string'
}, {
name: 'disp_name',
type: 'string'
}, {
name: 'email',
type: 'string'
}, {
name: 'phone_number',
type: 'string'
}, {
name: 'pw',
type: 'string'
}, {
name: 'family_filter',
type: 'string'
}, {
name: 'v_orientation_chk',
type: 'string'
}, {
name: 'anc1',
type: 'int'
}, {
name: 'current_video',
type: 'int'
}, {
name: 'current_video_type',
type: 'string'
}, {
name: 'video_history',
type: 'auto'
}, {
name: 'video_history_chk',
type: 'string'
}, {
name: 'HTML5_only',
type: 'string'
}, {
name: 'filter_by',
type: 'string'
}, {
name: 'unlock',
type: 'int'
}],
proxy: {
type: 'localstorage',
id: 'UserProfile'
}
}
});
var userprofile_obj = Ext.create("Ext.data.Store", {
model: 'userprofile_model',
pageSize: 9,
proxy: {
type: 'jsonp',
url: "http://api.example.com/mobile_json2.php",
reader: {
type: 'json',
rootProperty: 'items',
totalProperty: 'total'
},
extraParams: {
last_id: '0'
},
},
autoLoad: false,
listeners: {
load: function(store) {
var tmp = store.first();
var tmp2 = store.getData();
Ext.getCmp('userprofile_recommendations_var').setItemTpl(discover_recommendations_listTpl)
}
}
});
The issue comes when I try to pre populate the field with data.
For instance:
{
xtype: 'textfield',
name : 'disp_name',
label: 'Display Name',
labelWidth: '35%',
value: account.get('disp_name'),
listeners: {
check: {
fn: function() {
account.get('disp_name');
account.set("disp_name", disp_name);
account.setDirty();
store.sync();
}
}
}
},
Does not return the display name.
Hello I've problem to selected by value. And the data is from viewmodel. I also search the answer on google but I not found. I am very confusing about it. Please help me.
This is my form:
Ext.define('Sipen.view.items.ItemsForm', {
extend: 'Ext.window.Window',
xtype: 'items-form',
height: 250,
width: 500,
layout: { type: 'fit' },
bind: {title: '{title}'},
modal: true,
items: [
{
xtype: 'form',
reference: 'form',
bodyPadding: 20,
flex: 1,
modelValidation: true,
layout: {
type: 'hbox',
align: 'stretch'
},
items: [
{
xtype: 'fieldcontainer',
flex: 1,
title: 'Item Information',
layout: 'anchor',
defaults: {
anchor: '100%',
xtype: 'textfield',
msgTarget: 'under',
labelWidht: 100,
allowBlank: false
},
items: [
{
xtype: 'hiddenfield',
name: '_id',
bind: '{currentTipe._id}'
},
{
fieldLabel: 'Code',
name: 'item_code',
bind: '{currentItem.item_code}'
},
{
fieldLabel: 'Name',
name: 'item_name',
bind: '{currentItem.item_name}'
},
{
xtype: 'numberfield',
minValue: 1,
fieldLabel: 'Price',
name: 'item_price',
bind: '{currentItem.item_price}'
},
{
xtype: 'combo',
name: 'type',
fieldLabel: 'Type',
valueField: 'type_name',
displayField: 'type_name',
queryMode: 'local',
forceSelection: true,
submitValue: true,
bind: {
value: '{typeItems.type_name}',
store: '{typeItems}',
selection: '{currentItem.type_name}'
}
}
]
}
],
dockedItems: [
{
xtype: 'toolbar',
dock: 'bottom',
ui: 'footer',
layout: {
pack: 'end',
type: 'hbox'
},
items: [
{
xtype: 'button',
text: 'Save',
formBind: true,
listeners: {
click: 'onSave'
}
},
{
xtype: 'button',
text: 'Cancel',
listeners: {
click: 'onCancel'
}
}
]
}
]
}
]
});
Look at xtype 'combo' and I selection data by {currentItem.type_name} and the data is right, but I get error
this Uncaught TypeError: item.getId is not a function.
And this is my view model:
Ext.define('Sipen.view.items.ItemsModel', {
extend: 'Ext.app.ViewModel',
alias: 'viewmodel.items-items',
requires: [ 'Sipen.model.Items' ],
stores: {
items: {
model: 'Items',
autoLoad: true
},
typeItems: {
model: 'TypeItems',
autoLoad: true
}
}
});
Sorry for my bad english, but please help me...
============[Fixed]======================
I've found the result in here https://www.sencha.com/forum/showthread.php?302067
So the script should be like this:
{
xtype: 'combo',
name: 'type',
fieldLabel: 'Type',
valueField: 'type_name',
displayField: 'type_name',
queryMode: 'local',
forceSelection: true,
submitValue: true,
bind: {
value: '{typeItems.type_name}',
store: '{typeItems}',
selection: '{currentItem.type_name}'
}
}
I have a grid panel and when the user selects the row and clicks the edit button or dbl clicks the row, I want to send the selected row to the new window. But I am having trouble in sending the data.
Here is my grid panel. (List.js)
Ext.define('MyApp.view.main.List', {
extend: 'Ext.grid.Panel',
xtype: 'mainlist',
require: [ 'MyApp.view.student.StudentForm' ],
title: 'Student Records',
scrollable: true,
margin: 20,
layout: {
type: 'vbox',
align: 'stretch'
},
reference: 'studentGrid',
frame: true,
collapsible: true,
store: 'StudentStore',
collapsible: true,
columns: [
{
text: 'Name',
dataIndex: 'name',
flex: 1
},
{
text: 'Address',
dataIndex: 'address',
flex: 1
},
{
text: 'Phone',
dataIndex: 'phone',
flex: 1
},
{
text: 'Email',
dataIndex: 'email',
flex: 1
},
{
text: 'Faculty',
dataIndex:'faculty',
flex: 1
}
],
dockedItems: [
{
xtype: 'toolbar',
dock: 'top',
items: [
{
xtype: 'button',
text: 'Add',
iconCls: 'fa fa-plus',
listeners: {
click: 'onAdd'
}
},
{
xtype: 'button',
text: 'Edit',
iconCls: 'fa fa-edit',
id: 'editButton',
listeners: {
click: 'onEdit'
}
},
{
xtype: 'button',
text: 'Delete',
iconCls: 'fa fa-trash-o',
bind: {
disabled: '{ !mainlist.selection }'
},
listeners: {
click: 'onDelete'
}
}]
}
],
// toolbar for our store filter field
tbar: [{
xtype: 'textfield',
fieldLabel: 'Search Student',
emptyText: '...type to filter',
width: 300,
listeners: {
change: 'onSearch'
},
triggers: {
clear: {
cls: 'x-form-clear-trigger',
handler: function(){
this.reset();
}
}
}
}]
});
And this my Controller (MainController.js)
createDialog: function(record)
{
if (record)
{
var form = Ext.create('MyApp.view.student.StudentForm');
form.loadRecord(record);
form.show();
}
Ext.create('MyApp.view.student.StudentForm').show();
},
onEdit: function(button, e, options){
var row = button.up('mainlist').getSelection();
debugger;
this.createDialog(row[0]);
},
And here is the pop up window where the data has to be loaded(StudentForm.js)
Ext.define('MyApp.view.student.StudentForm', {
extend: 'Ext.window.Window',
xtype: 'student-form',
height: 400,
width: 500,
layout: {
type: 'fit'
},
reference: 'form',
title: 'Add Student',
closable: true,
modal: true,
items: [{
xtype: 'form',
id : 'formId',
bodyPadding: 5,
modelValidation : true,
layout: {
type: 'vbox',
align: 'stretch'
},
items: [{
xtype: 'fieldset',
flex: 1,
title: 'Student Information',
layout: 'anchor',
defaultType: 'textfield',
defaults: {
anchor: '100%',
msgTarget: 'side'
},
items: [
{
xtype: 'hiddenfield',
name: 'id',
fieldLabel: 'Label'
},
{
fieldLabel: 'Name',
name: 'name'
},
{
fieldLabel: 'Address',
name: 'address'
},
{
fieldLabel: 'Phone',
name: 'phone'
},
{
fieldLabel: 'Email',
name: 'email'
},
{
xtype: 'combo',
fieldLabel: 'Faculty',
name: 'facultyName',
queryMode: 'local',
displayField: 'facultyName',
valueField: 'facultyName',
store: {
fields: ['facultyName'],
data: [{
facultyName: 'computing'
}, {
facultyName: 'multimedia'
}, {
facultyName: 'networking'
}]
}
}
]
}],
dockedItems: [
{
xtype: 'toolbar',
dock: 'bottom',
layout: {
pack: 'end',
type: 'hbox'
},
items: [
{
xtype: 'button',
text: 'Save',
iconCls: 'fa fa-check',
listeners: {
click: 'onSave'
}
},
{
xtype: 'button',
text: 'Cancel',
iconCls: 'fa fa-times',
listeners: {
click: 'onCancel'
}
}
]
}]
}]
});
What am I missing here?Any suggestions?
It says loadRecord() is not a function
Your MyApp.view.student.StudentForm is not actually a form. It is a window, hence there is no loadRecord method.
Instead of form.loadRecord(record); call form.down('form').loadRecord(record).
Remember, it is worth naming things what they are.
I have an issue with showing a settings view on the main view when clicking a proper tab. Here is the code for the main view:
Ext.define('App.view.Main', {
extend:'Ext.tab.Panel',
requires: [
'App.view.SettingsView'
],
config: {
fullscreen: true,
tabBarPosition: 'bottom',
items: [
{
title: 'About',
iconCls: 'info',
items: {
docked: 'top',
xtype: 'titlebar',
title: 'Home Screen'
},
html: 'Home Screen'
},
{
title: 'Maps',
iconCls: 'maps',
items:
{
docked: 'top',
xtype: 'titlebar',
title: 'Maps Screen'
},
html: 'Maps Screen'
},
{
title: 'Setiings',
iconCls: 'settings',
items: [
{
docked: 'top',
xtype: 'titlebar',
title: 'Settings'
},
{
xtype: 'settingsview',
id: 'settingsview'
}
]
}
]
}
});
And this is the code for the settings view:
Ext.define('App.view.SettingsView', {
extend: 'Ext.form.Panel',
xtype: 'settingsview',
requires: [
'Ext.form.FieldSet',
'Ext.field.Toggle',
'Ext.field.Select',
'Ext.field.Text',
'Ext.Button'
],
config: {
xtype: 'fieldset',
title: 'SettingsView',
instructions: 'In case you do not want the app to detect your location you can enter the city and country.',
items: [
{
name: 'geo',
xtype: 'togglefield',
label: 'Auto detect?',
labelWidth: '55%',
value: '1',
},
{
name: 'units',
xtype: 'selectfield',
label: 'Units',
options: [
{
text: 'Fahrenheit',
value: 'f'
},
{
text: 'Celsius',
value: 'c'
}
]
},
{
name: 'city',
xtype: 'textfield',
label: 'City',
disabled: true
},
{
name: 'country',
xtype: 'textfield',
label: 'Country',
disabled: true
},
{
xtype: 'button',
text: 'Refresh',
action: 'refresh',
margin: '10 5',
ui: 'confirm'
}
]
}
});
When the settings tab is enabled it shows only the title bar and the tab bar. No error messages. What am I doing wrong?
Try to add layout:'fit' in config inside settingsview
OR
Modify your main view
{
title: 'Setiings',
iconCls: 'settings',
layout: 'vbox',
items: [
{
docked: 'top',
xtype: 'titlebar',
title: 'Settings'
},
{
xtype: 'settingsview',
id: 'settingsview',
flex: 1
}
]
}
I have a sample login form. In that there is a controller, view and a model.I would like to validate the form. my Form panel id is 'formPanelLogin' and have to update the form record in the controller. but this code "formPanelLogin.updateRecord (teamModel);" can't work and error message like "updateRecord is not define".
Please give me an answer for this problem. my code will following..
//Controller
Ext.define('MyApp.controller.mvcController', {
extend: 'Ext.app.Controller',
config: {
refs: {
BtnSubmit: "#btnSubmit",
BtnCancel:"#btnCancel",
BtnPromoHome:"#PromotionsBtnHome",
BtnThirdBack:"#thirdBtnBack",
BtnSecondBack:"#btnUnderHoodService",
},
control: {
BtnSubmit:
{
tap: "onBtnSubmitTap"
},
BtnCancel:
{
tap: "onBtnCancelTap"
},
BtnPromoHome:
{
tap: "onBtnPromoHomeTap"
},
BtnSecondBack:
{
tap: "onBtnSecondBackTap"
},
BtnThirdBack:
{
tap: "onBtnThirdBackTap"
}
}
},
onBtnCancelTap: function (options)
{
//formPanelLogin.reset();
var teamModel = Ext.create('MyApp.model.MyModel'),
errors, errorMessage = '';
formPanelLogin.updateRecord (teamModel);
errors = teamModel.validate();
if (!errors.isValid()) {
errors.each(function (err) {
errorMessage += err.getMessage() + '<br/>';
}); // each()
Ext.Msg.alert('Form is invalid!', errorMessage);
} else {
Ext.Msg.alert('Form is valid!', '');
} // if
console.log("Cancel");
},
});
//view
Ext.define('MyApp.view.MyContainer', {
extend: 'Ext.Container',
config: {
layout:
{
type: 'card'
},
items: [
{
xtype: 'panel',
id: 'panelOuter',
layout:
{
type: 'card',
animation:
{
type: 'slide'
}
},
items: [
{
xtype: 'panel',
items: [
{
xtype: 'toolbar',
docked: 'top',
title: 'MVC',
items: [
{
xtype: 'button',
docked: 'left',
id: 'btnBack'
},
{
xtype: 'button',
docked: 'right',
id: 'btnHome'
}
]
},
{
xtype: 'formpanel',
docked: 'top',
height: 117,
id: 'formPanelLogin',
scrollable: true,
items: [
{
xtype: 'fieldset',
id: 'loginform',
items: [
{
xtype: 'textfield',
label: 'UserName',
name: 'userName',
labelWidth: '40%',
name: 'usernameField',
placeHolder: '...... Type here .......',
required: true
},
{
xtype: 'passwordfield',
label: 'Password',
labelWidth: '40%',
required: true
}
]
}
]
},
{
xtype: 'panel',
height: 45,
id: 'btnPanel',
items: [
{
xtype: 'button',
docked: 'right',
id: 'btnSubmit',
ui: 'action-small',
width: 85,
text: 'Submit'
},
{
xtype: 'button',
docked: 'right',
id: 'btnCancel',
ui: 'decline-small',
width: 85,
text: 'Cancel'
}
]
}
]}
]
},
});
//model
Ext.define('MyApp.model.MyModel', {
extend: 'Ext.data.Model',
config: {
fields : [
{
name: 'userName',
type: 'string'
},
{
name: 'password',
type: 'string'
}
],
validations: [
{
field: 'userName',
type: 'presence',
message: 'User Name is required.'
}
]
}
});