How to add metadata for jstree on select_node event - javascript

How to add metadata for jstree on select_node event. This is how I am trying to add:
$.ajax({
type : 'GET',
url : '/assessment/getassess',
dataType : 'json',
success : function(jsonData) {
$("#treeViewDiv").jstree({
"themes" : {
"theme" : "classic",
"dots" : true,
"icons" : true,
"url" : "/css/themes/classic/style.css"
},
"json_data" : jsonData,
"plugins" : ["themes", "json_data", "ui", "contextmenu"],
"contextmenu" : {
items : createMenu
}
}).bind("select_node.jstree", function(e, data) {
$(data.rslt.obj).data("jstree").description = "Size: 45units";
});
}
});

I believe you are using the $.data() function incorrectly.
You don't assign values to the results of the $.data() function, and have it be automagically saved.
What you want to do is change this line,
$(data.rslt.obj).data("jstree").description = "Size: 45units";
to this,
// On the next line, we use "|| {}" because if the data attribute is unassigned, we want to start with a default empty object.
var jstreeData = $(data.rslt.obj).data("jstree") || {};
// assign the property(ies)/value(s) you want.
jstreeData.description = "Size: 45units";
// finally, reassign your modified object back to the data attribute.
$(data.rslt.obj).data("jstree", jstreeData);
If the data attribute consist of an object, you want to:
Cache the object;
Modify the cached object;
Save/assign the modified cached object back to the data attribute.
Lastly, to modify a data attribute, you want to use the $.data( key, value ) function overload.

Related

ExtJS - How do I pass ID when syncing store?

On ExtJS 6.2, I'm getting data from database like this: myStore.load({id: myId);.
How do I pass the ID while syncing?
This doesn't work: myStore.sync({id: myId);
I'm using a REST proxy and my URL is in this format: mydomain/users/1
You can simply use myStore.sync(), you don't need to specify id. The sync function will examine the store contents, and add/delete/update records as needed.
When using REST, you can set writeRecordId of Ext.data.write.Writer (see here) to false, since with REST id is usually appended to the URL, as in your case.
I solved by extending Ext.data.proxy.Rest and overriding the buildUrl method to be able to extract the ID from the request parameters. Then I used this overridden proxy in my model:
Ext.define('MYPROJ.proxy.Settings', {
extend : 'Ext.data.proxy.Rest',
alias : 'proxy.settings',
buildUrl(request) {
const url = this.callParent([request]);
const id = request.getParams().id;
if (id) {
delete request.getParams().id;
const proxyUrl = request.getProxy().getUrl();
return url.replace(proxyUrl, `${proxyUrl}/${id}`);
}
return url;
}
});
Ext.define('MYPROJ.model.Setting', {
extend : 'Ext.data.Model',
alias : 'model.setting',
clientIdProperty: 'clientId',
fields: [{
name : 'id',
type : 'int',
persist : false
}, {
name : 'name',
type : 'string',
unique : true
}],
proxy: {
type : 'settings', // <- Use overridden proxy here
url : `/something/settings`
}
});
Then in my code I can use sync() like this:
const myID = 10;
this.settingsStore.load({id: myID});
//...
this.settingsStore.sync({params: {id: myID}});
When sync() is called myID will be extracted from params on MYPROJ.proxy.Settings and added to the URL (/something/settings/10).

Send additional data to KendoUI DataSource and use it in dataBound event

I want to get some additional data in the dataSource to use it in the dataBound event.
Here is transport I use in the grid:
"transport" : {
"read" : {
"url" : "f?p=120:0:701647109622339:PLUGIN=BC",
"dataType" : "json",
},
},
"pageSize" : 20,
"schema" : {
data : "row",
total : "total",
rowsdata : "rowsdata",
model : {
"id" : "doc_id",
}
},
I want to access rowsdata via $('#grid').data("kendoGrid").dataSource.data().rowsdata. Is it possible?
Here is a jsfiddle: http://jsfiddle.net/M8jvz/10/
In this particular case, I want to pass a list of permanently hidden columns into HideGrouped function
Here is the fiddle with the solution http://jsfiddle.net/Casufi/4ya83/2/
$('#grid').data("kendoGrid").dataSource.data()
Returns array. And what is that rowsdata inside your schema? Such configuration is not supported.
How to send addtional arguments to the server is covered here.
You can use dataSource.schema.data as an function to achieve what you want:
var dataSource = new kendo.data.DataSource({
"autoSync" : true,
"data" : l_json,
"pageSize" : 20,
"schema" : {
data : function(data){
data.rowsdata[0] = { hidden: 0, name: "name" }
return data.row;
},
...
Documentation here:
http://docs.kendoui.com/api/framework/datasource#configuration-schema.data

using $.getJSON to populate jstree gets stuck at loading

I am having troubles populating a div using jstree with data from a separate json file.
In order to do that I tried to get the json with $.getJSON (i am not sure that this is the right function to use) and I assigned the result to a variable which I use next to populate the tree, this is how i get the json file:
var tree;
tree=$.getJSON("tree_data.json",function(data){
tree=data;
});
console.log(tree);
And here is the code which i use to populate the jstree div:
$("#treeViewDiv").jstree({
"json_data" : tree,
"themes" : {
"theme" : "apple",
"dots" : true,
"icons" : false
},
"plugins" : [
"themes", "json_data", "ui"
]
}).bind("select_node.jstree", function(e, data)
{
if(jQuery.data(data.rslt.obj[0], "href"))
{
window.location=jQuery.data(data.rslt.obj[0], "href");
}
else
{
alert("No href defined for this element");
}
});
here is my tree_data.json file, which contains the data i am trying to populate the tree with:
{
"data":[
{
"data" : "Search engines",
"children" :[
{"data":{"title":"Yahoo", "icon":"./themes/file.png"}, "metadata":{"href":"http://www.yahoo.com"}},
{"data":"Bing", "metadata":{"href":"http://www.bing.com"}},
{"data":"Google", "children":[{"data":"Youtube", "metadata":{"href":"http://youtube.com"}},{"data":"Gmail", "metadata":{"href":"http://www.gmail.com"}},{"data":"Orkut","metadata":{"href":"http://www.orkut.com"}}], "metadata" : {"href":"http://youtube.com"}}
],
"state" : "open"
},
{
"data" : "Networking sites",
"children" :[
{"data":"Facebook", "metadata":{"href":"http://www.fb.com"}},
{"data":"Twitter", "metadata":{"href":"http://twitter.com"}}
]
}
]
}
As a result of my code i have a beginning of the jstree and only one span with "loading" text within it, so i am guessing that data has troubles to load.
here is how it looks like:
what am i doing wrong? any ideas?
thank you for your time.
Put the entire $("#treeViewDiv").jstree({... bloc inside the $.getJSON callback
$.getJSON does not return the data; the data is in the callback:
var tree;
$.getJSON("tree_data.json", function(data){
tree = data;
console.log(tree);
});
Try calling your plugin in place of the above console.log.
The problem is that
console.log(tree);
is executed before the callback. Place console.log(tree); in the callback function.
As such:
var tree;
tree=$.getJSON("tree_data.json",function(data){
tree=data;
console.log(tree);
});

backbone-relational .set() method not updating related models

I've got backbone-relational working fairly well so far. I have relationships and reverse relationships well established (see below). When I initially call .fetch() on my Country model instance, the nominees array is parsed out into nominee models perfectly.
When I call .fetch() again later, however, these related models do not update, even though the nominee data has changed (e.g. the vote count has incremented). Essentially it seems that Backbone's .set() method understands relationships initially but not subsequently.
Country Model
var Country = Backbone.RelationalModel.extend({
baseUrl : config.service.url + '/country',
url : function () {
return this.baseUrl;
},
relations : [
{
type : Backbone.HasMany,
key : 'nominees',
relatedModel : Nominee,
collectionType : Nominee_Collection,
reverseRelation : {
key : 'country',
includeInJSON : false
}
}
]
});
JSON Response on country.fetch()
{
"entrant_count" : 1234,
"vote_count" : 1234,
"nominees" : [
{
"id" : 3,
"name" : "John Doe",
"vote_count" : 1,
"user_can_vote" : true
},
{
"id" : 4,
"name" : "Marty McFly",
"vote_count" : 2,
"user_can_vote" : true
}
]
}
Any help would be greatly appreciated, as always.
So it appears that backbone-relational specifically forgoes updating relations automatically (see the updateRelations method), and simply emits a relational:change:nominees event which your models can target. If, however, you wish to programmatically update your related models, simply modify the updateRelations method as follows:
Backbone.RelationalModel.prototype.updateRelations = function( options ) {
if ( this._isInitialized && !this.isLocked() ) {
_.each( this._relations || [], function( rel ) {
// Update from data in `rel.keySource` if set, or `rel.key` otherwise
var val = this.attributes[ rel.keySource ] || this.attributes[ rel.key ];
if ( rel.related !== val ) {
this.trigger( 'relational:change:' + rel.key, this, val, options || {} );
// automatically update related models
_.each(val, function (data) {
var model = rel.related.get(data.id);
if (model) {
model.set(data);
} else {
rel.related.add(data);
}
});
}
}, this );
}
};
(Note that this does not handle deletion of models from a collection, only updates to existing models, and the addition of new models to a collection)

ExtJS: return total rows/records in json store

I have a json store that returns values in json format. Now I need to get the number of rows/records in the json string but when I use store.getCount() function it returns 0, but the combobox is populated with rows, and when I use store.length I get undefined, probably because its not an array anymore, its returning from store, which is calling php script. Anyways, whats the best approach for this problem?
Try this out:
var myStore = Ext.extend(Ext.data.JsonStore, {
... config...,
count : 0,
listeners : {
load : function(){
this.count = this.getCount();
}
}
Ext.reg('myStore', myStore);
and then use inside panels:
items : [{
xtype : 'myStore',
id : 'myStoreId'
}]
Whenever you need to get the count then you can simply do this:
Ext.getCmp('myStoreId').count
Your Json response from server, can be something like this...
{
"total": 9999,
"success": true,
"users": [
{
"id": 1,
"name": "Foo",
"email": "foo#bar.com"
}
]
}
Then you can use reader: {
type : 'json',
root : 'users',
totalProperty : 'total',
successProperty: 'success'
} in your store object.
As from docs if your data source provided you can call getTotalCount to get dataset size.
If you use ajax proxy for the store, smth like
proxy : {
type : 'ajax',
url : 'YOUR URL',
reader : {
type : 'json',
root : 'NAME OF YOUR ROOT ELEMENT',
totalProperty : 'NAME OF YOUR TOTAL PROPERTY' // requiered for paging
}
}
and then load your store like
store.load();
There will be sent Ajax asynchronous request, so you should check count in callback like this
store.load({
callback : function(records, operation, success) {
console.log(this.getCount()); // count considering paging
console.log(this.getTotalCount()); // total size
// or even
console.log(records.length); // number of returned records = getCount()
}
});

Categories