I hope someone can help me with this, It's a strange question maybe as I didn't find an answer online.
I call the database and retrieve a list (in json) of items.
Then in angularjs,I render this list by extracting relevant pieces of data(name,age,etc) and show it properly in a table as a list of rows.
I have then an edit button that takes me to another page where I want to put a dropdown list.
What I want to know if is possible to add to that dropdown list the rendered list I previously created in my previous page.
is it possible to save the previously rendered list in a variable and then use that variable in the dropdown?
thank you
You could store the list within a controller and make this data availablte to this dropdown, I think.
Instead of trying to query for the list, add the list to the template, get the list from the template and render somewhere else, I'd suggest query for the list, save the list in a service , and then when you want to use that list again, get it from the service. Something like:
service:
var services = angular.module('services');
services.factory('getListService',['$http',function($http){
var getListOfStuff = function(){
//call to database
return //your json
};
var extractNameAgeEtc = function(){
var myListOfStuff = //get list of stuff from $http or database
var myListOfNameAgeEtc = //make a list of tuples or {name,age,etc} objects
return myListOfNameAgeEtc;
};
return {
extractNameAgeEtc : extractNameAgeEtc
};
}]);
controllers:
angular.module('controllers',['services']);
var controllersModule = angular.module('controllers');
controllersModule.controller('tableRenderController',['getListService','$scope',function(getListService,$scope){
//use this with your table rendering template, probably with ng-repeat
$scope.MyTableValue = getListService.extractNameAgeEtc();
}]);
controllersModule.controller('dropdownRenderController',['getListService','$scope',function(getListService,$scope){
//use this with your dropdown rendering template, probably with ng-repeat
$scope.MyDropDownValue = getListService.extractNameAgeEtc();
}]);
Related
I have problems binding this JSON to my list view.
http://pubapi.cryptsy.com/api.php?method=marketdatav2
No data is displayed.
Data.js
(function () {
"use strict";
var _list;
WinJS.xhr({ url: 'http://pubapi.cryptsy.com/api.php?method=marketdatav2' }).then(
function (response) {
var json = JSON.parse(response.responseText);
_list = new WinJS.Binding.List(json.return.markets);
},
function (error) {
//handle error
}
);
var publicMembers =
{
itemList: _list
};
WinJS.Namespace.define("DataExample", publicMembers);
})();
HTML:
<section aria-label="Main content" role="main">
<div id="listItemTemplate" data-win-control="WinJS.Binding.Template">
<div class="listItem">
<div class="listItemTemplate-Detail">
<h4 data-win-bind="innerText: label"></h4>
</div>
</div>
</div>
<div id="listView" data-win-control="WinJS.UI.ListView" data-win-options="{itemDataSource : DataExample.itemList, itemTemplate: select('#listItemTemplate'), layout: {type: WinJS.UI.GridLayout}}"></div>
</section>
I feel that the API is not that well formed.
Isnt this part a bit odd?
"markets":{"ADT/XPM":{...}...}
There are three things going on in your code here.
First, a ListView must be bound to a WinJS.Binding.List's dataSource property, not the List directly. So in your HTML you can use itemDataSource: DataExample.itemList.dataSource, or you can make your DataExample.itemList dereference the dataSource at that level.
Second, you're also running into the issue that the declarative binding of itemDataSource in data-win-options is happening well before DataExample.itemList is even populated. At the point that the ListView gets instantiated, _list and therefore itemList will be undefined. This causes a problem with trying to dereference .dataSource.
The way around this is to make sure that DataExample.itemList is initialized with at least an empty instance of WinJS.Binding.List on startup. So putting this and the first bit together, we have this:
var _list = new WinJS.Binding.List();
var publicMembers =
{
itemList: _list.dataSource
};
With this, you can later replace _list with a different List instance, and the ListView will refresh itself.
This brings us to the third issue, populating the List with your HTTP response data. The WinJS.Binding.List takes an array in its constructor, not an object. You're passing the parsed JSON object straight from the HTTP request, which won't work.
Now if you have a WinJS.Binding.List instance already in _list as before, then you can just walk the object and add items directly to the List as follows:
var jm = json.return.markets;
for (var i in jm) {
_list.push(jm[i]);
}
Alternately, you could populate a separate array and then create a new List from that. In this case, however, you'll need to assign that new List.dataSource to the ListView in code:
var jm = json.return.markets;
var markets = [];
for (var i in jm) {
markets.push(jm[i]);
}
_list = new WinJS.Binding.List(markets);
var listview = document.getElementById("listView").winControl;
listview.itemDataSource = _list.dataSource;
Both ways will work (I tested them). Although the first solution is simpler and shorter, you'll need to make sure to clear out the List if you make another HTTP request and repopulate from that. With the second solution you just create a new List with each request and hand that to the ListView, which might work better depending on your particular needs.
Note also that in the second solution you can remove the itemDataSource option from the HTML altogether, and also eliminate the DataExample namespace and its variables because you'll assign the data source in code each time. Then you can also keep _list entirely local to the HTTP request.
Hope that helps. If you want to know more about ListView intricacies, see Chapter 7 of my free ebook from MSPress, Programming Windows Store Apps with HTML, CSS, and JavaScript, Second Edition.
I'm trying to drag Ember objects from one list to another. If I drag an item to a new list, the item should be removed from its current list and moved to the new one.
Thanks to Drag&Drop with Ember.js and Ember.js - drag and drop list, I figured out how to copy an item to a different list. However, I am unable to determine from which list a dragged object originated. I have dozens of lists on the page, so I'd rather not do a O(n*k) search for the original object.
Currently, I'm using Ember views and the HTML 5 API. It seems like the Handelbars action helper should achieve my goal more easily. Ember's action supports the drop event, but I can't get it to fire: {{ action foo on="drop" }}. It probably has something to do with the nuanced event propagation defaults of the HTML 5 drag-and-drop implementation.
If you know how to solve this problem using actions instead of views, I'd much prefer that solution.
Here's how I'm currently transferring objects:
// this is heavily inspired by http://jsfiddle.net/ud3323/5uX9H/
// Draggable items
App.ItemView = Ember.View.extend({
templateName: 'item',
attributeBindings: 'draggable',
draggable: 'true',
dragStart: function(event) {
var dataTransfer = event.originalEvent.dataTransfer;
// The view's context is the item to transfer
var item = this.get('context');
// Use HTML 5 API to transfer object as JSON.
// There must be a more elegant way to do this.
dataTransfer.setData('application/json', JSON.stringify(item));
}
});
// Item list drop zone
App.ItemListView = Ember.View.extend({
templateName: 'itemList',
dragEnter: function(event) {
event.preventDefault();
return false;
},
dragOver: function(event) {
event.preventDefault();
return false;
},
drop: function(event) {
event.preventDefault();
// Extract the transferred data
var rawData = event.dataTransfer.getData('application/json');
// Create a new Ember object from the data
var item = App.Todo.create(JSON.parse(rawData));
this.get('controller').send('add', item);
return false;
}
});
Check out JS Bin for the complete code.
Thanks in advance for your help. Very much appreciated.
This is maybe not the full solution to your problem, but it satisfies the need to use the action helper instead of the itemView. Here is your modified jsbin http://jsbin.com/ibufeh/15/edit?html,javascript,live, the drop event fires and is catched at the ApplicationRoute level, from where you can then redirect your function call to the appropriate controller, have a look! it's not working correctly but it solves part of your problem - using an action helper. You need still to figure out from which list the item originated, but this will be easy I guess.
hope it helps
Apologies if this has already been mentioned or answered but I have looked for a few days and cannot work this out. I am new to both Knockout and StackOverflow so bear with me please.
I am working with CakePHP and have some JSON returned from my controller which is in the following format
{"countries":[{"Country":{"id":"1","country":"England"}},{"Country":{"id":"2","country":"Wales\/Cymru"}},{"Country":{"id":"3","country":"Scotland"}},{"Country":{"id":"4","country":"Republic of Ireland"}},{"Country":{"id":"5","country":"Northern Ireland"}}]};
I am hoping to have the above counties appear as an item in a select statement with the value being set to 1 and the text displayed as the country. However I cannot seem to get knockout to do this for me. I am sure this is a simple question to those familiar with knockout but I cannot understand what to do all I see is the list of objects but do not know how to access the object properties on the data-bind
HTML
<select data-bind="options:countries, optionsText:'Country'"></select>
Javascript
var viewModel = {};
var data = {"countries":[{"Country":{"id":"1","country":"England"}},{"Country":{"id":"2","country":"Wales\/Cymru"}},{"Country":{"id":"3","country":"Scotland"}},{"Country":{"id":"4","country":"Republic of Ireland"}},{"Country":{"id":"5","country":"Northern Ireland"}}]};
var jsData = ko.mapping.fromJS(data);
ko.applyBindings(jsData);
I have created a simple JSFiddle http://jsfiddle.net/jbrr5/14/ to show what is happening any help would be appreciated with this small challenge
Your data has an odd structure. It's like this:
- countries
- Country
- id
- country
The actual id and country is another level deep in the array of countries. You'd have to do some hacking around just to get those to appear in the select element as-is. It would be better if you just mapped to the inner Country objects.
var mappingOptions = {
'countries': {
'create': function (options) {
// map to the inner `Country`
return ko.mapping.fromJS(options.data.Country);
}
}
};
var viewModel = ko.mapping.fromJS(data, mappingOptions);
ko.applyBindings(viewModel);
Updated fiddle
You have very complex structure of array. For your case you have to write 'Country.country' in options binding but it doesn't work because binding cannot parse such complex expression. Instead of using options and optionsText bindings you can use foreach:
Here is working fiddle: http://jsfiddle.net/vyshniakov/jbrr5/18/
But I would recommend you change structure of your data to
{"countries":[{"id":"1","country":"England"}]};
or map data accordingly. In this case you could use options binding:
<select data-bind="options:countries, optionsText:'country', optionsValue:'id'"></select>
I have recently started working with backbone.js and i am finally started to get my head around after many tutorials.
One thing i am stuck on is how to use the routing to allow a list to pull different rest request.
Say i have the following in my collection
var NewsCollection = Backbone.Collection.extend({
model : News,
url: 'http://api.example.com/index.php/news/all/format/json',
});
From my understanding correct me if i am wrong backbone stores all the data pulled from the above feed into my model that extends this collection, this will all work i will pull in the feed and then display it in the view
This is where i get confused within my routing i have the following.
var NewsRouter = Backbone.Router.extend({
routes: {
"": "defaultRoute",
"news/:country_code":"updatedRoute"
},
defaultRoute: function () {
console.log("defaultRoute");
var movies = new NewsCollection()
new NewsView({ collection: movies });
movies.fetch();
//setInterval(function(){movies.fetch({success: function(){}});}, 60000);
},
updatedRoute:function (country_code) {
//confused
this.movie = this.movies.get(country_code);
}
})
I need to run the updatedRoute function when that will display a list of news based on cat of country code see below.
http://api.example.com/index.php/news/country/gb/format/json
How do i update the whole feed when a list item is click so the browser url would be.
http://localhost:8888/backbonetut/#news/gb
my list item is.
<li><a href='#news/gb'>GB</a></li>
I can get that in the updateRoute function with
this.movie = this.movies.get(country_code);
Can someone please help
You can either override the fetch function on your collection or temporarily change the url of the collection in your router action.
I have a form where I select the number of items. Upon clicking submit, it should take me to a new page where it would display the item selected and depending on the number of items selected, it would create those many jqPlots, one for each item.
Any suggestions on how do I go about doing this?
Thanks,
S.
It's hard to give any specifics without more detail about the items, but basically you would pass a JSON structure to your view with the items to be plotted. Then you would loop through the JSON structure, creating DIV tag for each item to be plotted and appending the DIV tags to the body.
The Javascript part would look something like this:
$.each(items, function(index, value) {
$myPlot = $("<div>");
$myPlot.attr("id", "item"+index);
$.jqplot($myPlot.attr("id"), ...);
$("body").append($myPlot);
});
This question is very general, but answering (specifically and only) the question of loading multiple charts:
You need a unique HTML div id for each chart; consider using an RFC 4122 UUID (generate as needed) for each chart/div rather than a sequential index for each. Use something that looks like this as a placeholder div for each:
<div class="chartdiv" id="chartdiv-${UID}">
<a rel="api" type="application/json" href="${JSON_URL}" style="display:none">Data</a>
</div>
This embeds the JSON URL for each div inside it, in a hidden hyperlink that can be discovered by JavaScript iterating over your multi-chart HTML page.
The matter of the UUID is inconsequential -- it just seems the most robust way to guarantee a unique HTML id addressable by JavaScript for each chart.
Subsequently, you should have JavaScript that looks something like:
jq('document').ready(function(){
jq('.chartdiv').each(function(index) {
var div = jq(this);
var json_url = jq('a[type="application/json"]', div).attr('href');
var divid = div.attr('id');
jq.ajax({
url: json_url,
success: function(responseText) { /*callback*/
// TODO: responseText is JSON, use it, normalize it, whatever!
var chartdata = responseText;
jq.jqplot(divid, chartdata.seriesdata, chartdata.options);
}
});
});
});