I have an issue at the moment regarding PHP, Jquery and Ajax.
I have a a div at the bottom of my page that has data in it from a database, now for every iteration of the data a new div is formed, the div has an id of 'pagestatus' and has an auto increment next to it so the id changes for each div like so: 'pagestatus0', 'pagestatus1' etc.
Now I'm not completely new to Jquery as I have used it to make pages more interactive and I've used Ajax to update a MySQL database.
I'm having trouble with the code though, I would like it go something like this:
Button is clicked in div
Button fades in (or div, which ever is easier)
A hidden div with a loading gif appears underneath
Ajax calls to the php file to make changes to the database
jquery then fades the loading gif back out and fades the button back in
I have wrote some code for it but I think I am going wrong somewhere, could someone see what I am doing wrong and let me know how to fix it.
Here is my Jquery:
$(document).ready(function(){
for(i=0;i<$('#changestatusoff').val();i++){
(function(x){
$('#changestatusoff'+x).click(function(){
$('#changestatusoff'+x).fadeOut('slow',function(){
$('#loadingstatus').fadeIn('slow',function(){
$.ajax
({
type: "POST",
url: '.php',
data: {'changestatusoff': changestatusoff},
success: function(data) {
return data;
},
error: function() {
alert('Error occured');
}
$('#loadingstatus').fadeOut('slow',function(){
$('#changestatusoff'+x).fadeIn('slow',function();
});
});
});
});
});
});
}
})(i);
});
And here is the button in the div:
<input type='button' value='Offline' id='changestatusoff".$count."' style='background: none repeat scroll 0% 0% rgb(0, 118, 188); color: rgb(255, 255, 255); border: 1px solid rgb(0, 0, 0); font-weight: bold; cursor: pointer; margin:5px;'/>
Any help is appreciated
As the others mentioned, we have no idea what you are submitting ;-)
Use a class, which means it dosent have to make a new bind for each item, it can do it all at once.
You could do something like:
$(function() {
//set loading
var $loading = $('#loadingstatus');
//on changeStatus click
$('.changeStatus').click( function(e) {
//since we dont have a form, disable default behaviour
e.preventDefault();
//set $this as the item clicked
var $this = $(this);
//fadeIn loading, fadeout the item
$this.fadeOut();
$loading.fadeIn();
//make ajax request
$.ajax
({
type: "POST",
url: 'yourPhpFile.php',
data: {'changestatusoff': $(this).val()},
success: function(data) {
//Do something with data?
$loading.fadeOut();
$this.fadeIn();
},
error: function() {
//Do nothing, and tell an error happened
alert('An error occured');
$loading.fadeOut();
$this.fadeIn();
}
});
});
});
I think you need to check data: {'changestatusoff': changestatusoff} and try changing it to data: {changestatusoff: 'changestatusoff'}
If you want to change loading gif back, then you should put the last two lines:
$('#loadingstatus').fadeOut('slow',function(){
$('#changestatusoff'+x).fadeIn('slow',function();
in completed callback, not after ajax call.
$.ajax
({
type: "POST",
url: '.php',
data: {'changestatusoff': changestatusoff},
success: function(data) {
return data;
},
error: function() {
alert('Error occured');
},
completed: function() {
$('#loadingstatus').fadeOut('slow',function(){
$.('#changestatusoff'+x).fadeIn('slow',function();
}
Try the following
$(function(){
$('#Your_Event_Source').click(function(){
$(this).fadeOut(600);
$('#loadingstatus').fadeIn(600);
$.post('you_file.php',{changestatusoff: 'yourValue'},function(data){
if(data.success == 'yes'){
alert(data.message);
$('#Your_Event_Source').fadeIn(600);
$('#loadingstatus').fadeOut(600);
}else{
alert('failed'+ data.message);
$('#Your_Event_Source').fadeIn(600);
$('#loadingstatus').fadeOut(600);
}
},'json');
});
});
I recommend to use 'success' in php:
$data = array('success'=>'yes','message' => 'your meaasage',...);
echo json_encode($data);
Related
I done ajax pagination (by watching tutorial) but now i need to add fadein effect and i cant figure how. I tried to add .fadeIn() probably everywhere but it wont work and i dont know where to put it. What i want to do is smooth page change.
Here is my script i think i dont need to add php.
And i have only back and next options. Not numbers of sites.
<script>
$(document).ready(function(){
//showing the data without refresh but on going to next pagination
setTimeout(function(){
load_fn_data();
}, 1000);
function load_fn_data(page){
$.ajax({
url:"data.php",
method:"POST",
data: {
page:page
},
success: function(data){
$('#load_data').html(data);
}
});
}
$(document).on('click','.pagination_link',function(){
var page = $(this).attr("id");
load_fn_data(page);
});
});
</script>
Hide before, than .html and afterwards .fadeIn() on success like:
function load_fn_data(page){
$('#load_data').hide()
$.ajax({
url:"data.php",
method:"POST",
data: {
page:page
},
success: function(data){
$('#load_data').html(data).fadeIn(800);
}
});
}
I am trying to display a loading animation and hide the search input box before the ajax request has been sent, the ".se-pre-con" element is the loader.
As you can see below I am tring to show this in the beforeSend of the ajax request. However, when the user is typing in the search box then stops for the delay specified (1000ms) the input box still displays throughout the ajax request but it is unresponsive.
Then the results are returned, and the loading animation does the fadeOut so it the show() must be triggering but the page remains unchanged until the results are returned. I want to prevent the unresponsive page effect and show a loading animation during the request. Any help is much appreciated.
$(document).ready(function() {
var delay = (function() {
var timer = 0;
return function(callback, ms) {
clearTimeout(timer);
timer = setTimeout(callback, ms);
};
})();
$('#search_field').keyup(function() {
var target = $(this);
delay(function() {
getSearchResults(target.val());
}, 1000);
});
function getSearchResults(str) {
$.ajax({
beforeSend: function(){
$(".se-pre-con").show();
$("#search_field").hide();
},
url: "http://example.com/Search_Results.php",
dataType:"html",
data: {"search_term": str},
method: "post",
async: false,
success: function(data){
if(data !== null) {
$("#search_default").hide();
$("#search_results_wrapper").html(data);
}
$(".se-pre-con").fadeOut("slow");
$("#search_field").show();
$("#search_field").focus();
},
error: function(){
$(".se-pre-con").fadeOut("slow");
$("#search_field").show();
$("#search_field").focus();
}
});
}
});
I found the solution.
Solution
It started working when I removed the option:
async: false
I have a PHP populated table from Mysql and I am using JQuery to listen if a button is clicked and if clicked it will grab notes on the associated name that they clicked. It all works wonderful, there is just one problem. Sometimes when you click it and the dialog(JQuery UI) window opens, there in the text area there is nothing. If you are to click it again it will pop back up. So it seems sometimes, maybe the value is getting thrown out? I am not to sure and could use a hand.
Code:
$(document).ready(function () {
$(".NotesAccessor").click(function () {
notes_name = $(this).parent().parent().find(".user_table");
run();
});
});
function run(){
var url = '/pcg/popups/grabnotes.php';
showUrlInDialog(url);
sendUserfNotes();
}
function showUrlInDialog(url)
{
var tag = $("#dialog-container");
$.ajax({
url: url,
success: function(data) {
tag.html(data).dialog
({
width: '100%',
modal: true
}).dialog('open');
}
});
}
function sendUserfNotes()
{
$.ajax({
type: "POST",
dataType: "json",
url: '/pcg/popups/getNotes.php',
data:
{
'nameNotes': notes_name.text()
},
success: function(response) {
$('#notes_msg').text(response.the_notes)
}
});
}
function getNewnotes(){
new_notes = $('#notes_msg').val();
update(new_notes);
}
// if user updates notes
function update(new_notes)
{
$.ajax({
type: "POST",
//dataType: "json",
url: '/pcg/popups/updateNotes.php',
data:
{
'nameNotes': notes_name.text(),
'newNotes': new_notes
},
success: function(response) {
alert("Notes Updated.");
var i;
$("#dialog-container").effect( 'fade', 500 );
i = setInterval(function(){
$("#dialog-container").dialog( 'close' );
clearInterval(i);
}, 500);
}
});
}
/******is user closes notes ******/
function closeNotes()
{
var i;
$("#dialog-container").effect( 'fade', 500 );
i = setInterval(function(){
$("#dialog-container").dialog( 'close' );
clearInterval(i);
}, 500);
}
Let me know if you need anything else!
UPDATE:
The basic layout is
<div>
<div>
other stuff...
the table
</div>
</div>
Assuming that #notes_msg is located in #dialog-container, you would have to make sure that the actions happen in the correct order.
The best way to do that, is to wait for both ajax calls to finish and continue then. You can do that using the promises / jqXHR objects that the ajax calls return, see this section of the manual.
You code would look something like (you'd have to test it...):
function run(){
var url = '/pcg/popups/grabnotes.php';
var tag = $("#dialog-container");
var promise1 = showUrlInDialog(url);
var promise2 = sendUserfNotes();
$.when(promise1, promise2).done(function(data1, data2) {
// do something with the data returned from both functions:
// check to see what data1 and data2 contain, possibly the content is found
// in data1[2].responseText and data2[2].responseText
// stuff from first ajax call
tag.html(data1).dialog({
width: '100%',
modal: true
}).dialog('open');
// stuff from second ajax call, will not fail because we just added the correct html
$('#notes_msg').text(data2.the_notes)
});
}
The functions you are calling, should just return the result of the ajax call and do not do anything else:
function showUrlInDialog(url)
{
return $.ajax({
url: url
});
}
function sendUserfNotes()
{
return $.ajax({
type: "POST",
dataType: "json",
url: '/pcg/popups/getNotes.php',
data: {
'nameNotes': notes_name.text()
}
});
}
It's hard to tell from this, especially without the mark up, but both showUrlInDialog and sendUserfNotes are asynchronous actions. If showUrlInDialog finished after sendUserfNotes, then showUrlInDialog overwrites the contents of the dialog container with the data returned. This may or may not overwrite what sendUserfNotes put inside #notes_msg - depending on how the markup is laid out. If that is the case, then it would explains why the notes sometimes do not appear, seemingly randomly. It's a race condition.
There are several ways you can chain your ajax calls to keep sendUserOfNotes() from completing before ShowUrlInDialog(). Try using .ajaxComplete()
jQuery.ajaxComplete
Another ajax chaining technique you can use is to put the next call in the return of the first. The following snippet should get you on track:
function ShowUrlInDialog(url){
$.get(url,function(data){
tag.html(data).dialog({width: '100%',modal: true}).dialog('open');
sendUserOfNotes();
});
}
function sendUserOfNotes(){
$.post('/pcg/popups/getNotes.php',{'nameNotes': notes_name.text()},function(response){
$('#notes_msg').text(response.the_notes)
},"json");
}
James has it right. ShowUrlInDialog() sets the dialog's html and sendUserOfNotes() changes an element's content within the dialog. Everytime sendUserOfNotes() comes back first ShowUrlInDialog() wipes out the notes. The promise example by jeroen should work too.
PROBLEM SOLVED
updated the jscrollpane to the latest version which support jquery 1.8 !
https://github.com/vitch/jScrollPane/blob/master/script/jquery.jscrollpane.min.js
I'm trying to refresh a div with content for a certain period. It will fire an Ajax GET call to a php script which render the content. For the first time ajax GET called, the ScrollPane is there, but for the second time Ajax GET(refresh) JScrollPane disappeared. Any how to reinitialize the jscrollpane?
function getActivity(callback)
{
$.ajax({
url: '../../views/main/activity.php',
type: 'GET',
complete: function(){
$('#activityLineHolder').jScrollPane({
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12
//autoReinitialize = true
});
},
success: function(data) {
var api = $('#activityLineHolder').jScrollPane(
{
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12
}
).data('jsp');
api.getContentPane().html(data);
api.reinitialise();
}
});
setTimeout(callback,10000);
}
$(document).ready(function(){
(function getActivitysTimeoutFunction(){
getActivity(getActivitysTimeoutFunction);
})();
});
Right now, my scrollpane is there after every Ajax call, but it shows buggy, the jscrollpane will keep moving left after every Ajax Call and slowly, it will hide the content. How is this happened?
foreach ($list as $notification) {
echo "<div class='feeds' id='$notification->notification_id'>";
$userObj = $user->show($notification->added_by);
echo $userObj->first_name.":<span class='text'>".$notification->activity."</span>";
echo " <span class='time'>".$notification_obj->nicetime($notification->created_at)."</span>";
echo "</div>";
}
something like this , that is my activity.php
here is my screenshot , anyone pls do help me #_#
http://img31.imageshack.us/img31/6871/jscrollpane.png
change the order of your commands. make a global variable that caches the ID like this:
var $activity, $activity_pane; // outside the dom ready
function getActivity(callback){
$.ajax({
url: '../../views/main/activity.php',
type: 'GET',
success: function(data) {
$activity_pane.html(data);
}
});
setTimeout(callback,10000);
}
$(function(){
$activity = $('#activityLineHolder');
$activity.jScrollPane({
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12
autoReinitialise: true
});
$activity_pane = $activity.data('jsp').getContentPane();
(function getActivitysTimeoutFunction(){
getActivity(getActivitysTimeoutFunction);
})();
});
My understanding is that a callback should be executed when the code within your method completes. If you are then wanting to run the getActivity() method again, shouldn't that be used in setTimeout(). Something like this:
function getActivity(callback)
{
$.ajax({
url: '../../views/main/activity.php',
type: 'GET',
complete: function(){
$('#activityLineHolder').jScrollPane({
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12
//autoReinitialize = true
});
},
success: function(data) {
$('#activityLineHolder').html(data);
}
});
setTimeout(function(){getActivity(callback);},10000);
if($.isFunction(callback)) {
callback();
}
}
I just take a look at http://jscrollpane.kelvinluck.com/ajax.html
I had tried and works. i change setTimeout into setInterval (function from scrollpane).
you can try this (i had tested)
$(document).ready(function(){
var api = $('#activityLineHolder').jScrollPane(
{
showArrows:true,
maintainPosition: false,
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12,
autoReinitialise: true
}
).data('jsp');
setInterval(
function()
{
$.ajax({
url: '../../views/main/activity.php',
success: function(data) {
api.getContentPane().html(data);
}
});
},
10000
);
});
I've faced this problem before, here is a snippet so you can get the idea. Good luck!
attachScroll = function(){
return $('.scroll-pane').jScrollPane({
verticalDragMinHeight: 17,
verticalDragMaxHeight: 17,
showArrows: true,
maintainPosition: false
});
}; // in this var I store all settings related to jScrollPane
var api = attachScroll().data('jsp');
$ajaxObj = $.ajax({
type: "GET", //set get or post
url: YOUR_URL,
data: null,
cache: false, //make sure you get fresh data
async: false, //very important!
beforeSend: function(){
},
success: function(){
},
complete: function(){
}
}).responseText; //$ajaxObj get the data from Ajax and store it
api.getContentPane().html($ajaxObj); //insert $ajaxObj data into "api" pane previously defined.
api.reinitialise(); //redraw jScrollPane
You can define the ajax call as a function and put it into a setInterval.
An example from official docs can be found here
Hope it helps!
Well I suppose that your HTML content coming from AJAX is long and you have problem with decreasing area size because it takes some time to render content by .html():
api.getContentPane().html(data);
And when it goes to the next line api.reinitialise() - HTML rendering isn't complete yet, but jScrollPane already catches current DIV width / height, initializes by those width / height, and then remaining html content is being inserted - and it appears outside of jScrollPane boundaries.
Read similar question: Wait for jquery .html method to finish rendering
So my adice:
1) Add a DIV at the end of your PHP code which will mark end of HTML coming from Ajax:
foreach ($list as $notification) {
...
}
echo '<div id="end-of-ajax"></div>';
2) Add periodical (200ms) check for "end-of-ajax" in your JS code - when it finds the end is reached, it calls for api.reinitialise():
var timer = setInterval(function(){
if ($("#activityLineHolder").find('#end-of-ajax').length) {
api.reinitialise();
clearInterval(timer);
}
}, 200);
EDIT
This is full JavaScript code:
function getActivity()
{
$.ajax({
url: '../../views/main/activity.php',
type: 'GET',
complete: function(){
$('#activityLineHolder').jScrollPane({
verticalDragMinHeight: 12,
verticalDragMaxHeight: 12
//autoReinitialize = true
});
},
success: function(data) {
var api = $('#activityLineHolder').jScrollPane(
{verticalDragMinHeight: 12,verticalDragMaxHeight: 12}
).data('jsp');
api.getContentPane().html(data);
var timer = setInterval(function(){
if ($("#activityLineHolder").find('#end-of-ajax').length) {
api.reinitialise();
clearInterval(timer);
}
}, 200);
}
});
}
$(document).ready(function(){
setInterval(getActivity,10000);
});
Im not sure about what your content is but just make sure that you reset the widths and heights accordingly before reinitlizing. as i had the same issue, and that was the problem
var origHeight =$('#GnattChartContainerClip').height();
var GanttChart = $('#EntireGnattWrapper').get(0).GanttChart;
$('#GnattChartContainerClip').find('#PaddingGnatt').remove();
$('#HeadersCol').find('#PaddingHeaders').remove();
var pane = $('#GnattChartContainerClip');
$('#GnattChartContainerClip').height(origHeight+height);
$('#GnattChartContainerClip').append('<div id="PaddingGnatt" style="width:'+GanttChart.TotalWidth+'px;height:25px"></div>');
$('#HeadersCol').append('<div id="PaddingHeaders" class="header" style="height:25px"></div>');
var paned = pane.data('jsp');
paned.reinitialise();
I am trying to fetch data form a callback page (php) and load it into a html div with jQuery mobile. This should happen if a user clicks on another div.
What I actually got is
$.('#home-button').bind('vclick', function( e ) {
$.get('homeCallback.php',function(data){
$('#displayContent').append(data).trigger('create');
},'html');
});
Where #home-button is the div that should trigger the event and #displayContent the div where the content should be put in.
The request should be able to pass some parameters, too. Like homeCallback.php?param=1 but it could also use the post method.
The callback does not have to be html only, it could also be possible that the callback php script provides JSON data or anything.
I am not a JS crack so I have problems solving this issue. Thanks for your help!
Edit:
So I found a solution on my own:
$(document).ready(function() {
$.ajaxSetup ({
cache: false
});
var ajaxLoader = '<img src="images/ajax-loader.gif" alt="loading.." />';
var loadUrl = "homeCallback.php";
$('#home-button1').click(function(){
$('#displayContent').toggle('fast', function() {
$(this).html(ajaxLoader);
$(this).toggle('fast', function() {
$.get(loadUrl + '?option1',function(data){
$('#displayContent').html(data);
},'html');
});
});
});
$('#home-button2').click(function(){
$('#displayContent').toggle('fast', function() {
$(this).html(ajaxLoader);
$(this).toggle('fast', function() {
$.get(loadUrl + '?option2',function(data){
$('#displayContent').html(data);
},'html');
});
});
});
});
And this is what homeCallback.php simply does..
<?php
if( isset($_GET["option1"] ))
echo "option1";
if( isset($_GET["option2"] ))
echo "option2";
So far.
$.('#home-button').bind('click', function() {
$.ajax({
url: "homeCallback.php",
type: "POST",
data: ({param: 1, param2: 2}),
success: function(html){
$("#displayContent").html(html);
}
});
});