I'm submitting a form to a php file, which returns some products from the database. I now need to add a knockout template with the returned data. Here is the code:
$("#search-filter-form").submit(function(event) {
// stop form from submitting normally
event.preventDefault();
// get some values from elements on the page:
var $form = $( this ),
url = $form.attr( 'action' );
// Send the data using post
var posting = $.post(url,
{ place: searchFilterViewModel.searchFilterAutoComplete.placeObject,
categories: searchFilterViewModel.categorySelect.selectedCategories
}).done(function(data) {
searchResultsViewModel.allProducts(JSON.parse(data));
for(var x = 0; x < searchResultsViewModel.allProducts().length; x++) {
$("search-results").append();// NEED TO APPEND THE KNOCKOUT TEMPLATE HERE
}
});
});
I want to have a seperate file with the html template. I have created this example file:
product_template.html:
<script type="text/html" id="product-template">
<h3 data-bind="text: allProducts.name"></h3>
<p>Credits: <span data-bind="text: credits"></span></p>
</script>
How do I get that template file to print out, from within the javascript function above?
Store the data in an observable/object, and pass that to the template itself, so it can read it.
You only linked the template file, you need another line to apply data to it, e.g.
<div data-bind="template: { name: 'product-template', data: buyer }"></div>
Related
so i'm currently working on a project and i want to add a calendar to one view, i'm using FullCalendar, the calendar is shown in the view but i'm currently trying to add events to that calendar, those events are going to be "pulled" from my database into the calendar to be displayed, now the problem is that when i pass the array with the events to the blade.php view that contains the calendar a error comes up saying that the variable "events" is undefined and i don't know if i'm doing something wrong, here's the code:
RegisteredUserController.php
$events = array();
$citas = Cita::all();
foreach($citas as $cita){
$events[] = [
'title' => $cita->paciente_id,
'start' => $cita->hora_de_inicio,
'end' => $cita->hora_de_finalizacion
];
}
return redirect(RouteServiceProvider::HOME)->with(['events' => $events]);
RouteServiceProvider.php
public const HOME = '/home';
homeView.blade.php (This is where i get the error, in the line where i assign it to citas)
<div id="calendar">
</div>
<script>
$(document).ready(function(){
var citas = #json($events);
$('#calendar').fullCalendar({
header: {
left: 'month, agendaWeek, agendaDay',
},
events: citas
})
});
</script>
routes / web.php
Route::get('/home', function (){
return view('homeView');
})->name('homeView');
Not sure if it's helpful but i'm using Laravel's Breeze to handle the authentication of users, so when an user is aunthenticated they're redirected to the page where the calendar is.
i've tried the following
RegisteredUserController.php
return redirect(RouteServiceProvider::HOME, compact('events));
This one makes the whole calendar disappear:
homeView.blade.php
var citas = {{ Session::get('events') }};
Thank you in advance.
the return should be like this
return view('path_of_the_blade', compact('events'));
So then in View, you can use
<script>
var citas = #json($events);
</script>
On you controller, why don't you just simply use:
return view('homeView')->with(['events' => $events]);
or simplier:
return view('homeView', compact('events'));
This would surely pass the variable events on the blade file.
Then on your blade file, you will just reference it as:
var citas = {{ $events }};
I am doing a ajax request to pass some data from Views.py to the HTML file and render it using DataTables() javascript library.
The problem I am facing is that the displayed datatable is not following the column order that I would like to.
I don´t know if the solution is to reorder the json data that the datatable receives or to use some functionallity of DataTables().
What should be the best solution to reorder the table´s column? And how can I apply it to the code bellow?
Views.py
...
def test_table(request):
data_pers = {
'Product':request.GET.get('Product'),
'Length':request.GET.get('Length'),
'Cod':request.GET.get('cod'),
'partnumbetr':'42367325'
}
return JsonResponse({'data_prod':data_prod})
...
HTML
...
$.get('{% url "test_table" %}',
{Product:Product,Length:Length,Cod:Cod},
function (data_prod) {
var data_json_prod=data_prod['data_prod'];
var data_array_prod = [];
var arr_prod = $.map(data_json_prod, function(el) { return el });
data_array_prod.push(arr_prod);
$('#id_prod').DataTable({
destroy: true,
data:data_array_prod,
});
...
I am using Blueimp jQuery File Upload Plugin to upload single and multiple images.
Here I want to pass some additional data along with images to server like caption,share option etc. I searched site and found how to sent multiple files in a single ajax request and also passed additional data to server. But the problem is, when I added a textarea in template for capturing caption of images in template the data is getting like [object Object] in server. But when I pass only caption I am getting it as array.
Here is the code:
$('#fileupload').fileupload({
disableImageResize: false,
autoUpload: false,
singleFileUploads:false,
url: jQuery('#site').val()+'UserPhotos/upload?Token='+jQuery('#token').val()
}).bind('fileuploadsubmit', function(e, data) {
//binding
var photo_share = jQuery('#photo_share').val();
var public = 1;
//serializing the captions for photos to be send to server
var inputs = data.context.find(':input');
if (inputs.filter('[value=""]').first().focus().length) {
data.context.find('button').prop('disabled', false);
return false;
}
data.formData = {
'caption': inputs.serializeArray(),
'photo_share':photo_share,
'public':public
};
});
HTML:
<script id="template-upload" type="text/x-tmpl">
{% for (var i=0, file; file=o.files[i]; i++) { %}
<tr class="template-upload fade">
<td>
<textarea name="caption[]" placeholder="Enter caption" class="form-control" rows="3"></textarea>
</td>
// ...
Any help to get this passed to server properly and parse the same?
SOLUTION: simply use serializeArray() of form id in "fileuploadsubmit" bind of fileupload function.Data will be passed to server correctly.
var inputs = data.context.find(':input');
if (inputs.filter('[value=""]').first().focus().length) {
data.context.find('button').prop('disabled', false);
return false;
}
data.formData = jQuery('#fileupload').serializeArray();
my jquery looks like this:
$('#id_start_date_list').change(
function get_time()
{
var value = $(this).attr('value');
alert(value);
var request = $.ajax({
url: "/getTime/",
type: "GET",
data: {start_date : value},
dataType: "json",
success: function(data) {
//Popluate combo here by unpacking the json
}
});
});
my view.py looks like this:
def getTime(request):
if request.method == "GET":
date_val = request.GET.get('start_date')
format = '%Y-%m-%d'
sd = datetime.datetime.strptime(date_val, format)
sql_qw = MeasurementTest.objects.filter(start_date = sd)
results = [{'start_time': str(date.start_time), 'id_start_time':date.start_time} for date in sql_qw]
print results
*****json_serializer = serializers.get_serializer("json")()
response_var= json_serializer.serialize(results, ensure_ascii=False, indent=2, use_natural_keys=True)*****
return HttpResponse(response_var, mimetype="application/json")
my html page looks like this:
html>
<head>
<title>date Comparison</title>
<script src="http://code.jquery.com/jquery-latest.js"></script>
</head>
<body>
{% if form.errors %}
<p style="color: red;">
Please correct the error{{ form.errors|pluralize }} below.
</p>
{% endif %}
<form action="/example/" method="post" align= "center">{% csrf_token %}
<table align = "center">
<tr>
<th><label for="start_date_list">Date 1:</label></th>
<th> {{ form.start_date_list }} </th>
</tr>
<tr>
<th><label for="start_time_list">time:</label></th>
<th><select name="start_time_list" id="start_time_list"></th>
<option></option>
</select>
<th></th>
<div id = "log"></div>
</tr>
<tr align = "center"><th><input type="submit" value="Submit"></th></tr>
</table>
</form>
</body>
</html>
As you can see i am getting the value from the select box and i am performing operations on the database and retreiving values and storing it in the json object.
There are two parts that i am totally blind.
First is the json object, where i am not sure whether the results are getting stored in the response_var object.
The second is that, i am not sure how to get values from a json object onto the new list of "start_time_list"
In detail: have i have done anything wrong in the json object initialisation. I have tried to print the respose_var, but it seems not to be printed on the console. Am i using the right syntax? and can someone tell me how to view the values stored in the json object in the view.py
In the similar way, how do i perform operations on the jquery side, to extract values from a json object and how to assign the values of a json object onto a list box by means of sample code and possible solutions.
To convert the results to json, use simplejson:
from django.utils import simplejson
def getTime(request):
if request.method == "GET":
date_val = request.GET.get('start_date')
format = '%Y-%m-%d'
sd = datetime.datetime.strptime(date_val, format)
sql_qw = MeasurementTest.objects.filter(start_date = sd)
results = [{'start_time': str(date.start_time), 'id_start_time':date.start_time} for date in sql_qw]
print results
response_var = simplejson.dumps(results)
return HttpResponse(response_var, mimetype="application/json")
To access the json object in your javascript, take a look at your ajax request. The success callback is being passed a parameter, data in this case. That is the variable containing the server response. So, to access the first element of the resultant array (for instance), you could:
var request = $.ajax({
url: "/getTime/",
type: "GET",
data: {start_date : value},
dataType: "json",
success: function(data) {
//Popluate combo here by unpacking the json
data[0]; // This is the first element of the array sent by the server
}
});
Lastly, to modify the html, jQuery provides plenty of methods, such as html or append. It's worth taking a look at the doc. So if you want to build a collection of options for a select tag, you should iterate over the result set using the javascript for loop, jQuery each method or similar, construct the options (this can be accomplished either concatenating strings or creating DOM elements, which I think is the best solution, as it performs better) and insert them in the html with one of the methods previously mentioned.
I have a list of attachments on a page which is generated using a jQuery $.ajax call and Knockout JS.
My HTML looks like (this is stripped back):
<tbody data-bind="foreach: attachments">
<tr>
<td data-bind="text: Filename" />
</tr>
</tbody>
I have a function that gets the list of attachments which is returned as a JSON response:
$(function () {
getFormAttachments();
});
function getAttachments() {
var request = $.ajax({
type: "GET",
datatype: "json",
url: "/Attachment/GetAttachments"
});
request.done(function (response) {
ko.applyBindings(new vm(response));
});
}
My view model looks like:
function vm(response) {
this.attachments = ko.observableArray(response);
};
There is a refresh button that the use can click to refresh this list because over time attachments may have been added/removed:
$(function () {
$("#refresh").on("click", getAttachments);
});
The initial rendering of the list of attachments is fine, however when I call getAttachments again via the refresh button click the list is added to (in fact each item is duplicated several times).
I've created a jsFiddle to demonstrate this problem here:
http://jsfiddle.net/CpdbJ/137
What am I doing wrong?
Here is a fiddle that fixes your sample. Your biggest issue was that you were calling 'applyBindings' multiple times. In general you will call applyBindings on page load and then the page will interact with the View Model to cause Knockout to refresh portions of your page.
http://jsfiddle.net/CpdbJ/136
html
<table>
<thead>
<tr><th>File Name</th></tr>
</thead>
<tbody data-bind="foreach: attachments">
<tr><td data-bind="text: Filename" /></tr>
</tbody>
</table>
<button data-bind="click: refresh">Refresh</button>
javascript
$(function () {
var ViewModel = function() {
var self = this;
self.count = 0;
self.getAttachments = function() {
var data = [{ Filename: "f"+(self.count*2+1)+".doc" },
{ Filename: "f"+(self.count*2+2)+".doc"}];
self.count = self.count + 1;
return data;
}
self.attachments = ko.observableArray(self.getAttachments());
self.refresh = function() {
self.attachments(self.getAttachments());
}
};
ko.applyBindings(new ViewModel());
});
--
You may also want to look at the mapping plugin - http://knockoutjs.com/documentation/plugins-mapping.html. It can help you transform JSON into View Models. Additionally it is able to assign a property to be the "key" for an object... this will be used to determine old vs new objects on subsequent mappings.
Here is a fiddle I wrote a while back to demonstrate a similar idea:
http://jsfiddle.net/wgZ59/276
NOTE: I use 'update' as part of my mapping rules, but ONLY so I can log to the console. You would only need to add this if you wanted to customize how the mapping plugin updated objects.