Write new data into javascript variable and parse JSON - javascript

I have this code which help me to show Verite Timeline on my page so:
<div id="timeline-embed"></div>
<script type="text/javascript">
var timeline_config = {
width: "100%",
height: "100%",
debug: true,
rows: 2,
source: {
"timeline":
{
"headline":"Sh*t People Say",
"type":"default",
"text":"People say stuff",
"startDate":"10/4/2011 15:02:00",
"date": [
{
"startDate":"10/4/2011 15:10:00",
"endDate":"10/4/2011 15:55:00",
"headline":"FIRST",
"text":"<p>FIRSTTEXT</p>",
"asset":
{
"caption":"yessss"
}
},
{
"startDate":"10/4/2011 17:02:00",
"endDate":"10/4/2011 18:02:00",
"headline":"SECOND",
"text":"<p>In true political fashion, his character rattles off common jargon heard from people running for office.</p>",
"asset":
{
"media":"http://youtu.be/u4XpeU9erbg",
"credit":"",
"caption":""
}
}
]
}
}
}
</script>
so Now on source: into date I want to add new element:
{
"startDate":"CurrentDate + zajson",
"endDate":"10/4/2011 18:02:00",
"headline":"place.name",
"asset":
{
"media":"http://youtu.be/u4XpeU9erbg",
"credit":"",
"caption":""
}
}
so offcource I have a variable:
var place.name;
var zajson;
and When I click on <button>Add to timeline</button> I want to add new element (as i show above) into source: in date, as new block of values ...
Is it posible to do this?
And how I can update source: and run it again when I add new block of data???
sorry for my english

function addContent() {
var content = {
"startDate":"CurrentDate + zajson", // <-- these two probably shouldn't be in quotes, but concated
"endDate":"10/4/2011 18:02:00",
"headline":"place.name", // <-- this one, too
"asset":
{
"media":"http://youtu.be/u4XpeU9erbg",
"credit":"",
"caption":""
}
};
timeline_config.source.timeline.date.push(content);
}
Something like this should do it.
Then, for the button:
<button onclick="addContent()">Add to timeline</button>

Related

Get a list from javascript object

I am a new beginner in javascript and I am trying to figure out how to get a list from this object components.
I only need to select js keys from mndatory
var components = {
mandatory: {
alert: {
js: ['./bootstrap/js/alert.js'],
css: ['./bootstrap/css/alert.css', './bootstrap/css/alert2.css'],
},
button: {
js: ['./bootstrap/js/button.js'],
css: ['./bootstrap/css/button.css'],
},
dropdown: {
js: ['./bootstrap/js/dropdown.js'],
css: ['./bootstrap/css/dropdown.css'],
},
},
optional: {
carousel: {
js: ['./bootstrap/js/carousel.js'],
css: ['./bootstrap/css/carousel.css'],
},
modal: {
js: ['./bootstrap/js/modal.js'],
css: ['./bootstrap/css/modal.css'],
},
},
};
So the result will be the selection of only the js keys:
[
'./bootstrap/js/alert.js',
'./bootstrap/js/button.js',
'./bootstrap/js/dropdown.js'
]
I really appreciate your help.
You can use a for-in loop:
for (const property in components.mandatory) {
console.log(property.js);
}
You can probably take it from here.
Documentation:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/for...in
Something like the below code should help you. Please try to understand how the below code is working.
var components = {
mandatory: {
alert: {
js: ['./bootstrap/js/alert.js'],
css: [
'./bootstrap/css/alert.css',
'./bootstrap/css/alert2.css'
]
},
button: {
js: ['./bootstrap/js/button.js'],
css: ['./bootstrap/css/button.css']
},
dropdown: {
js: ['./bootstrap/js/dropdown.js'],
css: ['./bootstrap/css/dropdown.css']
}
},
optional: {
carousel: {
js: ['./bootstrap/js/carousel.js'],
css: ['./bootstrap/css/carousel.css']
},
modal: {
js: ['./bootstrap/js/modal.js'],
css: ['./bootstrap/css/modal.css']
}
}
}
var array = [components.mandatory.alert.js, components.mandatory.button.js, components.mandatory.dropdown.js].flat();
console.log(array)
You can iterate over the attributes and then add the js elements to a global list as follows:
$(document).ready(function() {
var components = {
mandatory: {
alert: {
js: ['./bootstrap/js/alert.js'],
css: [
'./bootstrap/css/alert.css',
'./bootstrap/css/alert2.css'
]
},
button: {
js: ['./bootstrap/js/button.js'],
css: ['./bootstrap/css/button.css']
},
dropdown: {
js: ['./bootstrap/js/dropdown.js'],
css: ['./bootstrap/css/dropdown.css']
}
},
optional: {
carousel: {
js: ['./bootstrap/js/carousel.js'],
css: ['./bootstrap/css/carousel.css']
},
modal: {
js: ['./bootstrap/js/modal.js'],
css: ['./bootstrap/css/modal.css']
}
}
};
let mandatory = components.mandatory;
let list = [];
for (var key in mandatory) {
if (mandatory.hasOwnProperty(key)) {
let current = mandatory[key]['js'];
if(current){
for(var i = 0; i < current.length; i++)
list.push(current[i]);
}
}
}
console.log(list)
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
Well, as others have answered without waiting for effort from the OP, let me throw my suggestion out there:
const extractJs = components =>
Object .values (components .mandatory) .flatMap (x => x .js)
const components = {mandatory: {alert: {js: ["./bootstrap/js/alert.js"], css: ["./bootstrap/css/alert.css", "./bootstrap/css/alert2.css"]}, button: {js: ["./bootstrap/js/button.js"], css: ["./bootstrap/css/button.css"]}, dropdown: {js: ["./bootstrap/js/dropdown.js"], css: ["./bootstrap/css/dropdown.css"]}}, optional: {carousel: {js: ["./bootstrap/js/carousel.js"], css: ["./bootstrap/css/carousel.css"]}, modal: {js: ["./bootstrap/js/modal.js"], css: ["./bootstrap/css/modal.css"]}}};
console .log (extractJs (components))
We first take the mandatory property, then use Object .values to extract the values of each of its properties. We flatMap over the resulting objects, combining their .js properties. The flatMap call will flatten the resulting arrays into one as it goes.
You might want to add some checking along the way. Is components actually an object?, Does it have an object mandatory property?, etc. I leave that to you.
var result = []
Object.keys(components.mandatory).forEach(x => {
components.mandatory[x].js.forEach(y => result.push(y));
})

How to display two C3 charts in the same row in two different divs

I've some problems with c3 plugins.
I'm trying to put 2 charts in a structure like this:
<div class="row">
<div class="col-6">
<div id="chart1"></div>
</div>
<div class="col-6">
<div id="chart2"></div>
</div>
</div>
My output is the attached one, and i couldn't find the reason why the charts go out of the div.
I've already tried to use chart.resize() but it doesn't work (maybe i put it in the wrong place).
Can you help me ?
You can find my code here:
js1, js2, html
Thank you !
The problem is that you are loading the charts (I think!) within a div that is not displayed when the page loads, the C3 doesn't know how to size the charts correctly.
Instead of loading every chart in the Document Ready, wrap your posts in a function like this:
function loadStatArticoliCharts() {
$.post(
'{{ url('myGetter') }}/{{ data.listId }}',
{},
function(data) {
grafico_fatturato = c3.generate({
bindto: "#fatturato-mensile-barre",
data: {
columns: [
[new Date().getFullYear() - 1, 0,0,0,0,0,0,0,0,0,0,0,0],
[new Date().getFullYear(), 0,0,0,0,0,0,0,0,0,0,0,0],
],
type : 'bar',
colors: data.colors
},
bar: {
width: 30
},
axis: {
x: {
type: 'category',
categories: months
},
y: {
tick: {
format: function(value) { return value.formatMoney(2, ',', '.') }
}
}
},
tooltip: {
format: {
value: function(value) { return "€ " + value.formatMoney(2, ",", "."); }
}
},
transition: {
duration: 1000
}
});
setTimeout(function() {
grafico_fatturato.load({
columns: [
data.columns.current,
data.columns.past
],
});
grafico_fatturato.resize();
}, 500);
}
);
}
Create a global boolean variable to store if you've already loaded the charts (so you won't trigger the load multiple times) with
let loadedChart1 = false;
let loadedChart2 = false;
Finally create a controller that will trigger the load function when you click the tab:
$('a[data-toggle="tab"]').on('shown.bs.tab', function (ev) {
let tabId = $(ev.target).attr("aria-controls");
switch (tabId) {
case "chart1":
if (!loadedChart1) {
loadChart1();
loadedChart1 = true;
}
break;
case "chart2":
if (!loadedChart2) {
loadChart2();
loadedChart2 = true;
}
break;
}
let oldTabId = $(ev.relatedTarget).attr("aria-controls");
$('#' + oldTabId).removeClass("active");
}

Making table elements (from JSON) linkable

I have a JSON file that contains document titles and a URL for each. So far I've been able to render each document into a table created with DataTables. I also rendered each url into the first table row as a test. It was good that they appeared but it's not what I'm going for.
How can I make it so that each document title is linked with its respective URL? I didn't see any info. about it in the DataTables manual or its forum so I thought I'd ask.
If you'd like to see a snippet of the JSON file, please let me know.
JS snippet:
import $ from 'jquery';
import JSONfile from '../../../public/JSONfile.json';
import { basename } from 'path';
import dt from 'datatables.net';
var tableRes = '';
export default class {
constructor() {
this.loadTableData();
}
loadTableData() {
$.noConflict();
let tableRes = JSONfile.d.results.filter(function(val) {
return (val.FileLeafRef.trim().length > 0);
}).map(function(obj) {
return {
// "FileName": obj.FileLeafRef,
// "Path": obj.EncodedAbsUrl, ///// these are the URLs for each document
"Titles": obj.File.Name
}
});
$('#km-table-id').DataTable( {
columns: [
{ "data": " " },
{ "data": "Titles" }, ///// Ideally I want each Title to be linked in the table---i.e. the document names appearing blue
{ "data": " " }
],
data: tableRes,
"pagingType": "full_numbers"
});
} // ------- loadTableData
} // ------- export default class
Update: Thanks to a user on the DataTables forum, I was able to find a solution. Simply put, I had to use columDefs that was detailed under the columns.render section of the docs :
Code snippet:
return {
"Path": obj.EncodedAbsUrl,
"Titles": obj.File.Name
}
});
$('#km-table-id').DataTable( {
columns: [
{ data: "Path" }, // populates rows with each document link
{ data: "Titles" }, // populates rows with docs
{ data: "check" }
],
columnDefs: [ {
targets: 0,
data: "Path",
render: function(data) {
return 'Download';
}
}],
...
Hyperlinking actual document cells:
columnDefs: [
{
data: "Path",
render: function(data, type, row) {
return $('<a>')
.attr({target: "_blank", href: row.Path})
.text(data)
.wrap('<div></div>')
.parent()
.html();
},
targets: [] // Column position
},
...

ZingChart X-axis labels showing as numbers instead of strings

I am using the ZingChart library to graph results from an API call. When I pass in a normal array for the "values" field of the chart data object, everything works fine. However, when I pass in an array made from Object.keys(titleSet) (where titleSet is a normal Javascript object), the graph displays as follows:
Example Chart
As you can see, the x-axis is now labeled with numbers instead of the array of strings. But when I print out the the result of Object.keys(titleSet) vs. passing in a normal array, they both appear to be the same in the console. Can anyone help me figure out what I'm doing wrong?
//List of movies inputted by the user
var movieList = [];
var movieSet = {};
var IMDBData = {
"values": [],
"text": "IMDB",
};
var metascoreData = {
"values": [],
"text": "Metascore"
};
var RTMData = {
"values": [],
"text": "Rotten Tomatoes Meter"
};
var RTUData = {
"values": [],
"text": "Rotten Tomatoes User"
};
var chartData = {
"type":"bar",
"legend":{
"adjust-layout": true
},
"plotarea": {
"adjust-layout":true
},
"plot":{
"stacked": true,
"border-radius": "1px",
"tooltip": {
"text": "Rated %v by %plot-text"
},
"animation":{
"effect":"11",
"method":"3",
"sequence":"ANIMATION_BY_PLOT_AND_NODE",
"speed":10
}
},
"scale-x": {
"label":{ /* Scale Title */
"text":"Movie Title",
},
"values": Object.keys(movieSet) /* Needs to be list of movie titles */
},
"scale-y": {
"label":{ /* Scale Title */
"text":"Total Score",
}
},
"series":[metascoreData, IMDBData, RTUData, RTMData]
};
var callback = function(data)
{
var resp = JSON.parse(data);
movieSet[resp.Title] = true;
//Render
zingchart.render({
id:'chartDiv',
data:chartData,
});
};
Full Disclosure, I'm a member of the ZingChart team.
Thank you for updating your question. The problem is you have defined your variable movieSet before the variablechartData. When parsing the page, top down, it is executing Object.keys({}) on an empty object when creating the variable chartData. You should just directly assign it into your config later on chartData['scale-x']['values'] = Object.keys(moviSet).
var callback = function(data)
{
var resp = JSON.parse(data);
movieSet[resp.Title] = true;
//Render
zingchart.render({
id:'chartDiv',
data:chartData,
});
};
There is a problem with the above code as well. It seems you are calling render on the chart every time you call this API. You should have one initial zingchart.render() and then from there on out use our API. I would suggest setdata method as it replaces a whole new JSON packet or modify method.
I am making some assumptions on how you are handling data. Regardless, check out the following demo
var movieValues = {};
var myConfig = {
type: "bar",
scaleX:{
values:[]
},
series : [
{
values : [35,42,67,89,25,34,67,85]
}
]
};
zingchart.render({
id : 'myChart',
data : myConfig,
height: 300,
width: '100%'
});
var callback = function(data) {
movieValues[data.title] = true;
myConfig.scaleX.values = Object.keys(movieValues);
zingchart.exec('myChart', 'setdata', {
data:myConfig
})
}
var index = 0;
var movieNamesFromDB = ['Sausage Party', 'Animal House', 'Hot Rod', 'Blazing Saddles'];
setInterval(function() {
if (index < 4) {
callback({title:movieNamesFromDB[index++]});
}
},1000)
<!DOCTYPE html>
<html>
<head>
<!--Assets will be injected here on compile. Use the assets button above-->
<script src= "https://cdn.zingchart.com/zingchart.min.js"></script>
<script> zingchart.MODULESDIR = "https://cdn.zingchart.com/modules/";
</script>
<!--Inject End-->
</head>
<body>
<div id='myChart'></div>
</body>
</html>
If you noticed in the demo, the length of scaleX.values determines how many nodes are shown on the graph. If you change values to labels this wont happen.

itemfilereadstore reading from json file

i'm starting out with Dojo and trying to get a thumbnail gallery to display from a json file with no luck so far. I've searched and viewed other examples but none have helped me. Please help me to see what i'm doing wrong.
It's working when specifying the data in the script however(as shown by the commented out code) I can't get it to read data from an external file.
My code so far:
<script>
require(["dojo/ready",
"dijit/registry",
"dojo/dom",
"dojo/on",
"dojo/parser",
"dojo/data/ItemFileReadStore",
"dojox/image/Gallery"
], function (ready, registry, dom, on, parser, ifrs, Gallery) {
ready(function () {
// Define the attribute names used to access the items in the data store
parser.parse();
var itemNameMap = {
imageThumbAttr: "thumb",
imageLargeAttr: "large"
};
// Define the request, with no query, and a count of 20, so 20 items will be
// requested with each request
var request = {
query: {},
count: 20
};
// var store = new ifrs(imgs);
/* imageItemStore.data = {
identifier: 'title',
label: 'Images',
items: [
{
thumb: "http://www.flickr.com/photos/44153025#N00/748348847",
large: "http://www.flickr.com/photos/44153025#N00/748348847",
title: "Photo"
}
]
};*/
imageItemStore = new dojo.data.ItemFileReadStore({ url: "/images.json" });
registry.byId('gallery1').setDataStore(imageItemStore, request, itemNameMap);
});
});
</script>
My json file:
{ items: [
{
"thumb":"images/extraWide.jpg",
"large":"images/extraWide.jpg",
"title":"I'm wide, me",
"link":"http://www.flickr.com/photos/44153025#N00/748348847"
},
{
"thumb":"images/imageHoriz.jpg",
"large":"images/imageHoriz.jpg",
"title":"I'm a horizontal picture",
"link":"http://www.flickr.com/photos/44153025#N00/735656038"
},
{
"thumb":"images/imageHoriz2.jpg",
"large":"images/imageHoriz2.jpg",
"title":"I'm another horizontal picture",
"link":"http://www.flickr.com/photos/44153025#N00/714540483"
},
{
"thumb":"images/imageVert.jpg",
"large":"images/imageVert.jpg",
"title":"I'm a vertical picture",
"link":"http://www.flickr.com/photos/44153025#N00/715392758"
},
{
"large":"images/square.jpg",
"thumb":"images/square.jpg",
"link" :"images/square.jpg",
"title":"1:1 aspect ratio"
}
]}
My markup:
<div class="claro" style="height:400px">
<div data-dojo-type="dojox.image.Gallery" id="gallery1" style="height:400px"></div>
<div data-dojo-id="imageItemStore" data-dojo-type="dojo.data.ItemFileReadStore"></div>
</div>
Any help would be greatly appreciated
Have you looked a the JsonRest store instead of an ItemFileReadStore? http://dojotoolkit.org/reference-guide/1.9/dojo/store/JsonRest.html

Categories

Resources