Reputation: 17392
I'm appending a <div>
via Ajax. There are jQuery functions and CSS to be applied to that <div>
after getting appended dynamically via Ajax. The <div>
gets appended correctly but the jQuery functions and CSS does not get loads for that <div>
. How do I do it?
AJAX CODE
$.ajax({
type: "POST",
url: "/dashboard/",
data : { 'widgets_list' : widgets_list },
success: function(result){
console.log(widgets_list);
$("#column1").append(result); // div gets appended.
}
});
view.py
HTMLstr += "<div class='portlet'><div class='portlet-header'>Live Graph</div>" + \
"<div class='portlet-content' id='live_graph' style='height: 270px margin: 0 auto'>" + \
"</div></div>"
return HttpResponse(HTMLstr)
The jQuery functions
which needed to applies are:-
$(function() {
$( ".column" ).sortable({
connectWith: ".column",
handle: ".portlet-header"
});
$( ".portlet" ).addClass( "ui-widget ui-widget-content ui-helper-clearfix ui-corner-all" )
.find( ".portlet-header" )
.addClass( "ui-widget-header ui-corner-all" )
.prepend( "<span class='ui-icon ui-icon-minusthick'></span>")
.end()
.find( ".portlet-content" );
$( ".portlet-header .ui-icon" ).click(function() {
$( this ).toggleClass( "ui-icon-minusthick" ).toggleClass( "ui-icon-plusthick" );
$( this ).parents( ".portlet:first" ).find( ".portlet-content" ).toggle();
});
});
and 1 more jQuery function.
CSS
<style>
body { min-width: 520px; }
.column { width: 170px; float: left; padding-bottom: 100px;}
.portlet { margin: 0 1em 1em 0; }
.portlet-header { margin: 0.3em; padding-bottom: 4px; padding-left: 0.2em; }
.portlet-header .ui-icon { float: right; }
.portlet-content { padding: 0.4em; max-height: 270px;}
.ui-sortable-placeholder { border: 1px dotted black; visibility: visible !important; height: 50px !important; }
.ui-sortable-placeholder * { visibility: hidden; }
</style>
UPDATED QUESTION
HTML
<div class="column span4" id="column1">
<div class="portlet">
<div class="portlet-header">Line Chart</div>
<div class="portlet-content" id="basic_line" style="height: 270px"></div>
</div>
</div>
jQuery Function
$(function () { // I replaced this line with $("#portlet").on('click', '#live_graph',function() {.... But it didnt work!!
$(document).ready(function() {
Highcharts.setOptions({
global: {
useUTC: false
}
});
var chart;
$('#live_graph').highcharts({
chart: {
type: 'spline',
animation: Highcharts.svg, // don't animate in old IE
marginRight: 10,
events: {
load: function() {
// set up the updating of the chart each second
var series = this.series[0];
setInterval(function() {
var x = (new Date()).getTime(), // current time
y = Math.random();
series.addPoint([x, y], true, true);
}, 1000);
}
}
},
title: {
text: 'Live random data'
},
xAxis: {
type: 'datetime',
tickPixelInterval: 150
},
yAxis: {
title: {
text: 'Value'
},
plotLines: [{
value: 0,
width: 1,
color: '#808080'
}]
},
tooltip: {
formatter: function() {
return '<b>'+ this.series.name +'</b><br/>'+
Highcharts.dateFormat('%Y-%m-%d %H:%M:%S', this.x) +'<br/>'+
Highcharts.numberFormat(this.y, 2);
}
},
legend: {
enabled: false
},
exporting: {
enabled: false
},
series: [{
name: 'Random data',
data: (function() {
// generate an array of random data
var data = [],
time = (new Date()).getTime(),
i;
for (i = -19; i <= 0; i++) {
data.push({
x: time + i * 1000,
y: Math.random()
});
}
return data;
})()
}]
});
});
});
I want this highchart to be in the portlet-content, but I'm unable to. Where am I going wrong?
.on( events [, selector ] [, data ], handler(eventObject) )
Can ready
be an event?
Upvotes: 0
Views: 572
Reputation: 2469
I'm going to break it down by the functions you listed.
$( ".column" ).sortable({
connectWith: ".column",
handle: ".portlet-header"
});
This is very specific to jQueryUI, but in order for Function 1 to work, you need to use http://api.jqueryui.com/sortable/#method-refresh . Since some of the items in your sortable are loaded later you need to referesh the sortable to recognize these items.
So you will have code like
success: function(result){
// div gets appended.
$("#column1").append(result);
// refresh sortable items now that markup is appended to columns
$( ".column ).sortable( "refresh" );
}
$( ".portlet" ).addClass( "ui-widget ui-widget-content ui-helper-clearfix ui-corner-all" )
.find( ".portlet-header" )
.addClass( "ui-widget-header ui-corner-all" )
.prepend( "<span class='ui-icon ui-icon-minusthick'></span>")
.end()
.find( ".portlet-content" );
Is there a reason why this markup is not generated in view.py , since view.py is already generating dynamic markup. If you prefer to do this in jQuery, make you sure you invoke the function after appending the result.
$( ".portlet-header .ui-icon" ).click(function() {
$( this ).toggleClass( "ui-icon-minusthick" ).toggleClass( "ui-icon-plusthick" );
$( this ).parents( ".portlet:first" ).find( ".portlet-content" ).toggle();
});
Instead of needing to call this function each time the element is created, there is a concept known as event delegation. The premise of event delegation is that Delegated events have the advantage that they can process events from descendant elements that are added to the document at a later time. But in order to apply event delegation, Event handlers are bound only to the currently selected elements; they must exist on the page at the time your code makes the call to*
From your ajax call it looks like the function is "#column_1"
already exists by the time the result is appended.
An example of event delegation is :
// This tells #column_1 that if a descendant element matches the selector
// '.portlet-header .ui-icon' then invoke the function
$('#column_1').on('click', '.portlet-header .ui-icon' ).,function() {
$( this ).toggleClass( "ui-icon-minusthick" ).toggleClass( "ui-icon-plusthick" );
$( this ).parents( ".portlet:first" ).find( ".portlet-content" ).toggle();
});
Upvotes: 4