I have a tabpanel, that initially has 1 tab and a button. But the user should be able to add more tabs by clicking on the button. Here is the code so far:
var tabPan = Ext.create('Ext.TabPanel', {
listeners: {
beforetabchange: function(tabs, newTab, oldTab, eOpts) {
if (newTab.title=='Add') { // Or some other condition
return false;
}
}
},
items:[
{
title: 'Default Tab',
html: innerHtml
},
{
xtype: 'button',
title : 'Add',
},
]
})
Your approach is right, All you need is to create a panel and add it to the TabPanel.
var i = 1;
var onAddTab = function(tabPanel) {
var newTab = {
xtype: 'panel',
title: 'Untitled Tab ' + (i++)
};
var index = tabPanel.items.length - 1;
var newTabItem = tabPanel.insert(index, newTab);
tabPanel.setActiveTab(newTabItem);
};
var tabPanel = Ext.create('Ext.TabPanel', {
listeners: {
beforetabchange: function(tabs, newTab, oldTab, eOpts) {
if (newTab.title == 'Add') {
onAddTab(tabPanel);
return false;
}
}
},
items: [{
title: 'Default Tab',
html: 'Hello World'
}, {
xtype: 'button',
title: 'Add',
}],
renderTo: Ext.getBody()
});
Related
I am not a Web developer, I have to do just a small task once, but I hate copy & paste.
Look at the code below, I'd like to avoid copy and paste (question1, question2 ,..., question[i]). I'd like to create a for statement but I should handle properties with a dynamic name. In c# I would use reflection or dynamic.
Is it possible in Javascript? Is it the correct approach? Should I dynamically generate the code and use Eval()?
tinymce.PluginManager.add('test_containers', function(editor, url) {
editor.addButton('test_containers2', {
title: 'Container 2',
text: 'Container 2',
onclick: function() {
editor.windowManager.open({
title: 'Test Container',
body: [{
type: 'container',
layout: 'stack',
columns: 2,
minWidth: 500,
minHeight: 500,
items: [{
type: 'textbox',
name: 'question1'
}, {
type: 'textbox',
name: 'question2'
}, ]
}],
onsubmit: function(e) {
ed.insertContent(e.data.question1 + e.data.question2);
}
});
}
});
});
tinymce.init({
selector: '#mytextarea',
plugins: 'colorpicker test_containers',
toolbar: 'test_containers2'
});
// Taken from core plugins
var editor = tinymce.activeEditor;
function createColorPickAction() {
var colorPickerCallback = editor.settings.color_picker_callback;
if (colorPickerCallback) {
return function() {
var self = this;
colorPickerCallback.call(
editor,
function(value) {
self.value(value).fire('change');
},
self.value()
);
};
}
}
<script src="https://cdn.tinymce.com/4/tinymce.min.js"></script>
<textarea id="mytextarea">Hello, World!</textarea>
See: https://jsfiddle.net/Revious/gm2phuva/3/
From my understanding, you need to add the items dynamically.
I have added two function on your code.
createArr -> will create the array of list of the specified number (n)
handleQuesData -> will concat the data of all the questions and pass it to onsubmit function
tinymce.PluginManager.add('test_containers', function(editor, url) {
// item creation dynamically
let createArr = (n) => {
let arr = []
for (let i = 0; i < n; i++) {
arr.push({
type: 'textbox',
name: `question{i+1}`
})
}
return arr;
}
// onsubmit handled dynamically
let handleQuesData = (data, n) => {
let quesdata = ''
for (let i = 0; i < n; i++) {
quesdata += data[`question{i+1}`]
}
return quesdata
}
let numItem = 2;
editor.addButton('test_containers2', {
title: 'Container 2',
text: 'Container 2',
onclick: function() {
editor.windowManager.open({
title: 'Test Container',
body: [{
type: 'container',
layout: 'stack',
columns: 2,
minWidth: 500,
minHeight: 500,
items: createArr(numItem)
}],
onsubmit: function(e) {
ed.insertContent(handleQuesData(e.data, numItem));
}
});
}
});
});
tinymce.init({
selector: '#mytextarea',
plugins: 'colorpicker test_containers',
toolbar: 'test_containers2'
});
// Taken from core plugins
var editor = tinymce.activeEditor;
function createColorPickAction() {
var colorPickerCallback = editor.settings.color_picker_callback;
if (colorPickerCallback) {
return function() {
var self = this;
colorPickerCallback.call(
editor,
function(value) {
self.value(value).fire('change');
},
self.value()
);
};
}
}
Here is the demo code : JSFiddle
Hope it helps :)
Yes, you can dynamically generate the list of items.
tinymce.PluginManager.add('test_containers', function(editor, url) {
const totalQuestions = 10;
let questions = [];
for (let i = 1; i < totalQuestions; i++) {
questions.push({
type: 'textbox',
name: 'question' + i
});
}
editor.addButton('test_containers2', {
title: 'Container 2',
text: 'Container 2',
onclick: function() {
editor.windowManager.open({
title: 'Test Container',
body: [{
type: 'container',
layout: 'stack',
columns: 2,
minWidth: 500,
minHeight: 500,
items: questions
}],
onsubmit: function(e) {
ed.insertContent(e.data.question1 + e.data.question2);
}
});
}});
});
//......
I have a main.js
**Ext.define('EDevlet.view.Main', {
viewport: {
autoMaximize: true
},
extend: 'Ext.Container',
xtype: 'mainview',
defaultColumnCount: 2,
config: {
scrollable:"vertical",
cls: "page-content-style page-with-main-buttons",
fullscreen: true,
title: i18n["edevlet_title"],
flex:1,
height:800,
layout: {
type: 'vbox',
align: 'stretch'
},
defaults: {
flex:1
},
items: [{
xtype: "panel",
id: "greeting-message",
cls: "greeting",
docked: "top"
}
]
},**
loadMenu: function () {
Logger.log("#Main::loadMenu");
this.removeAll(true, false);
var services = SegmentUtil.getServiceContent(), // boş olma ihtimali yok, BE den gelmez ise yereldeki DEFAULT segment içeriğini kullanıyor
maxServiceSize = SegmentUtil.getHomePageMaxServiceSize(),
columnCount = this.defaultColumnCount,
rowCount = Math.ceil((maxServiceSize + 1) / columnCount), // +1 diğer servisler düğmesi için !
index,
service,
title,
itemId,
button,
menuRow,
rowIndex,
isLeftSide,
verticalPosition = -1;
Logger.log('services: ' + services);
Logger.log('rowCount: ' + rowCount + ', columnCount: ' + columnCount + ', maxServiceSize: ' + maxServiceSize);
// satırları oluştur
var newCount=rowCount+1;
for (index = 0; index < newCount; index++) {
if(index==0){
**this.add({
id: 'mainRow-' + index,
xtype: 'carousel', flex:3,
layout: 'hbox',
defaults: {
flex:1
}, items: [
{ id: 'Image1',
html: ''
},
{ id: 'Image2',
html: ''
},
{ id: 'Image3',
html: ''
},
{ id: 'Image4',
html: ''
}
]
});
this.requestBackEndForNewsUrl();
}
else{
this.add({
id: 'mainMenuRow-' + index,
xtype: 'container',
flex:2,
layout: 'hbox',
defaults: {
flex:1
}
});
}**
}
}
}
And I have a load function.Load function add items(this items is image).But my scrool seem but not working.I hold scroll but if a release scroll is going up.
I have a vbox.After two hbox is added.But scroll is not working.
Try this. Write this override code in app.js file & then check.
// Fix for scroll
Ext.override(Ext.util.SizeMonitor, {
constructor: function (config) {
var namespace = Ext.util.sizemonitor;
return new namespace.Scroll(config);
}
});
Ext.override(Ext.util.PaintMonitor, {
constructor: function (config) {
return new Ext.util.paintmonitor.CssAnimation(config);
}
});
Change your view's config to this:
scrollable: {
direction: 'vertical',
directionLock: true
},
flex:1,
height: '100%',
This will serve your purpose. Let me know if it helps or not.
. when i run and click on Icon button then it is not able to call function func_1(); nothing is appear. on the screen
Ext.onReady(function () {
function func_1() {
//some functionality
}
new_win = new Ext.Panel({
renderTo: Ext.getBody(),
activeItem: 0,
tbar: {
items: [{
text: 'List',
ref: '../prevButton',
disabled: true,
handler: function () {
new_win.getLayout().setActiveItem(0);
new_win.prevButton.disable();
new_win.nextButton.enable();
}
}, '-', {
text: 'Icon',
ref: '../nextButton',
handler: function () {
new_win.getLayout().setActiveItem(1);
new_win.prevButton.enable();
new_win.nextButton.disable();
}
}]
},
items: [{
html: 'hello'
}, {
handler: function () {
func_1();
}
}]
});
});
can you please tell me how to call func_1(); or handler in panel items ?
There is no need to call the function from within anonymous function you can refer to it directly from the handler.
for example:
tbar: {
items: {
xtype: 'toolbar',
style: 'border:0;',
items: [{
xtype: 'buttongroup',
items: [{
id: 'btnAddItem',
text: 'Add Item',
icon: 'images/icons/add-icon.png',
handler: add_item
}]
}]
}
},
...
function add_item(){
}
You should create a global variable and then you can see the scope within the handler like this:
Ext.onReady(function () {
var me = this;
function func_1() {
//some functionality
}
new_win = new Ext.Panel({
renderTo: Ext.getBody(),
activeItem: 0,
tbar: {
items: [{
text: 'List',
ref: '../prevButton',
disabled: true,
handler: function () {
new_win.getLayout().setActiveItem(0);
new_win.prevButton.disable();
new_win.nextButton.enable();
}
}, '-', {
text: 'Icon',
ref: '../nextButton',
handler: function () {
me.func_1();
new_win.getLayout().setActiveItem(1);
new_win.prevButton.enable();
new_win.nextButton.disable();
}
}]
},
items: [{
html: 'hello'
}, {
handler: function () {
func_1();
}
}]
});
I have created a picker in Sencha touch 2.1. My Data is displaying properly. I want to disable a particular value not all so that if I select that value and click "doneButton" then it shouldn't be taken.
Example:
function loadPicker(paramName, valueSet) {
Ext.Viewport.remove(Ext.getCmp(paramName + 'Pickerfield'), true);
if (!paramName.picker) {
paramName.picker = Ext.Viewport.add({
xtype: 'picker',
id: paramName + 'Pickerfield',
useTitles: true,
slots: [{
name: paramName,
title: paramName,
data: valueSet
}],
doneButton: {
listeners: {
tap: function(button, event, eOpts) {
var selectedPacingModeValue =
Ext.getCmp(paramName + 'Pickerfield').getValue()[paramName];
sendSetPendingRequest(paramName, selectedPacingModeValue);
}
}
}
});
}
}
lets take these are the values in my picker field. What I am doing on select of an value and click of "doneButton", I am showing the value in a textfield. What I want is if I will select "option 2" and click "doneButton" then option 2 shouldn't be displayed in textfield but for all other values this selecting and showing in textfield operation should work.
You can just get the selected record and check that flag upon click of the done button, then move to textbox (or not).
Ext.create('Ext.form.Panel', {
fullscreen: true,
items: [
{
xtype: 'fieldset',
title: 'Select',
items: [
{
xtype: 'selectfield',
itemId: 'mySelectField',
label: 'Choose one',
options: [
{
text: 'apple',
value: 50
}, {
text: 'orange',
value: 100,
disabled: true
}, {
text: 'banana',
value: 200
}, {
text: 'papaya',
value: 300
}
]
},
{
xtype: 'button',
text: 'done',
handler: function(button){
var panel = button.up(),
sf = panel.down('#mySelectField'),
tf = panel.down('#answerfield');
/* you can only access the raw value unless you use
* an actual store and an actual model with the
* disabled field. In that case you can do
* sf.getRecord().get('disabled')
*/
if(sf.getRecord().raw.disabled === true){
tf.setValue(''); //noting to see :)
} else {
tf.setValue(sf.getRecord().get('text')); //display value
}
}
},
{
xtype: 'textfield',
itemId: 'answerfield',
title: 'answer'
}
]
}
]
});
Working fiddle: http://www.senchafiddle.com/#d46XZ
UPDATE
Like you asked: with the picker
Ext.Loader.setConfig({
enabled: true
});
Ext.application({
name: 'SenchaFiddle',
launch: function() {
var picker = Ext.create('Ext.Picker', {
slots: [
{
name : 'stuff',
title: 'Stuff',
data : [
{
text: 'apple',
value: 50
}, {
text: 'orange',
value: 100,
disabled: true
}, {
text: 'banana',
value: 200
}, {
text: 'papaya',
value: 300
}
]
}
],
listeners: {
change: function(p, value){
var tf = panel.down('#answerfield'),
firstSlot = p.getItems().get(1), //index 0 is the toolbar 1 first slot and so on..
selectedRecord = firstSlot.getData()[firstSlot.selectedIndex];
if(selectedRecord.disabled === true){
tf.setValue(''); //noting to see :)
} else {
console.log(selectedRecord);
tf.setValue(selectedRecord.text); //display value
}
}
}
});
var panel = Ext.create('Ext.form.Panel', {
fullscreen: true,
items: [
{
xtype: 'fieldset',
title: 'Select',
items: [
{
xtype: 'button',
text: 'show picker',
handler: function(button){
Ext.Viewport.add(picker);
picker.show();
}
},
{
xtype: 'textfield',
itemId: 'answerfield',
title: 'answer'
}
]
}
]
});
}
});
working fiddle: http://www.senchafiddle.com/#SFgpV
I've already done a toolbar with buttons that have a dropdown menu but I need more submenu levels. It's possible to do that? Example:
toolbarbutton ->
menu 1 lv 1
menu 2 lv 1
menu 3 lv 1->
submenu 1 lv 2
submenu 2 lv 2
menu 4 lv 1
and so on...
Have a look at this example! You can achieve using the Ext.menu.Menu class.
Here is an Example:
{
text: 'Main Menu',
menu: {
xtype: 'menu',
items: [{
text: 'Menu One',
iconCls: 'edit'
}, {
text: 'Menu Two',
menu: {
xtype: 'menu',
items: [{
text: 'Next Level'
},{
text: 'Next Level'
},{
text: 'Next Level'
}]
}
}, {
text: 'Menu Three',
scale: 'small'
}, {
text: 'Menu Four',
scale: 'small'
}]
}
}
Yes it is possible.
This menu is created dynamically with ExtJs, the data is loaded from Json.
See my demo with the code.
Demo Online:
https://fiddle.sencha.com/#view/editor&fiddle/2vcq
Json loaded:
https://api.myjson.com/bins/1d9tdd
Code ExtJs:
//Description: ExtJs - Create a dynamical menu from JSON
//Autor: Ronny Morán <ronney41#gmail.com>
Ext.application({
name : 'Fiddle',
launch : function() {
var formPanelFMBtn = Ext.create('Ext.form.Panel', {
bodyPadding: 2,
waitMsgTarget: true,
fieldDefaults: {
labelAlign: 'left',
labelWidth: 85,
msgTarget: 'side'
},
items: [
{
xtype: 'container',
layout: 'hbox',
items: [
]
}
]
});
var win = Ext.create('Ext.window.Window', {
title: 'EXTJS DYNAMICAL MENU FROM JSON',
modal: true,
width: 680,
closable: true,
layout: 'fit',
items: [formPanelFMBtn]
}).show();
//Consuming JSON from URL using method GET
Ext.Ajax.request({
url: 'https://api.myjson.com/bins/1d9tdd',
method: 'get',
timeout: 400000,
headers: { 'Content-Type': 'application/json' },
//params : Ext.JSON.encode(dataJsonRequest),
success: function(conn, response, options, eOpts) {
var result = Ext.JSON.decode(conn.responseText);
//passing JSON data in 'result'
viewMenuDinamical(formPanelFMBtn,result);
},
failure: function(conn, response, options, eOpts) {
//Ext.Msg.alert(titleAlerta,msgErrorGetFin);
}
});
}
});
//Generate dynamical menu with data from JSON
//Params: formPanelFMBtn - > Panel
// result - > Json data
function viewMenuDinamical(formPanelFMBtn,result){
var resultFinTarea = result;
var arrayCategoriaTareas = resultFinTarea.categoriaTareas;
var containerFinTarea = Ext.create('Ext.form.FieldSet', {
xtype: 'fieldset',
title: 'Menu:',
margins:'0 0 5 0',
flex:1,
layout: 'anchor',
//autoHeight: true,
autoScroll: true,
height: 200,
align: 'stretch',
items: [
]
});
var arrayMenu1 = [];
//LEVEL 1
for(var i = 0; i < arrayCategoriaTareas.length; i++)
{
var categoriaPadre = arrayCategoriaTareas[i];
var nombrePadre = categoriaPadre.nombreCategoria;
var hijosPadre = categoriaPadre.hijosCategoria;
var arrayMenu2 = [];
//LEVEL 2
for(var j = 0; j<hijosPadre.length; j++)
{
var categoriaHijo = hijosPadre[j];
var nombreHijo = categoriaHijo.nombreHijo;
var listaTareas = categoriaHijo.listaTareas;
var arrayMenu3 = [];
//LEVEL 3
for(var k = 0; k < listaTareas.length; k++)
{
var tarea = listaTareas[k];
var nombreTarea = tarea.nombreTarea;
var objFinLTres =
{
text: nombreTarea,
handler: function () {
alert("CLICK XD");
}
};
arrayMenu3.push(objFinLTres);
}
var menuLevel3 = Ext.create('Ext.menu.Menu', {
items: arrayMenu3
});
var objFinLDos;
if(arrayMenu3.length > 0)
{
objFinLDos = {
text: nombreHijo,
menu:menuLevel3
};
}
else
{
//without menu parameter If don't have children
objFinLDos = {
text: nombreHijo
};
}
arrayMenu2.push(objFinLDos);
}
var menuLevel2 = Ext.create('Ext.menu.Menu', {
items: arrayMenu2
});
var objFinLUno;
if(arrayMenu2.length > 0)
{
objFinLUno = {
text: nombrePadre,
menu:menuLevel2
};
}
else
{
//without menu parameter If don't have children
objFinLUno = {
text: nombrePadre
};
}
arrayMenu1.push(objFinLUno);
}
var mymenu = new Ext.menu.Menu({
items: arrayMenu1
});
containerFinTarea.add({
xtype: 'splitbutton',
text: 'Example xD',
menu: mymenu
});
formPanelFMBtn.add(containerFinTarea);
}