I have a site built using wordpress as the cms and the index has a long accordian style list of post titles and once you click on this heading the content for that post is loaded via ajax into the index page.
I have the problem that when the heading is clicked again, it loads the post content again and if you click a different heading it won't close and remove the previous one that has been clicked.
I am new to working with ajax and unsure how to go about fixing this. Is there a way to make the content be removed once the heading is clicked a second time to close the accordion or another heading is clicked to expand and open. Live site is here: http://www.minervasydney.com/
Below is the code for my ajax and the part in my index file that lists the headings. If anyone has ideas it would be greatly appreciated. Thank you!
AJAX
$("a.exhibitionInformation").on("click", function(event) {
var exhibitionContainer = $(this).parent(".exhibition");
var url = $(this).attr("href");
var doc = $(this).next(".exhibitionDocuments");
var title = convertToSlug($(this).text().split("\n")[1]);
var slug = $(this).attr("data-slug");
$(this).toggleClass("selected");
if($(doc).is(':not(:hidden)')) {
$(doc).slideToggle();
} else {
$.ajax({
url: url,
type: "GET",
success: function(data) {
var content = $(data).find(".single-document");
$(doc).append(content).slideToggle(300);
$("html, body").animate({ scrollTop: exhibitionContainer.offset().top - 26 });
window.location.hash = slug;
}
});
}
event.preventDefault();
});
//ajaxstarStop Loading
$( document ).ajaxStart(function() {
$( "#loading" ).fadeIn(100);
});
$( document ).ajaxStop(function() {
$( "#loading" ).fadeOut();
});
function convertToSlug(Text)
{
return Text
.toLowerCase()
.replace(/ /g,'-')
.replace(/[^\w-]+/g,'')
;
}
INDEX
<section class="exhibition">
<a class="exhibitionInformation" href="<?php the_permalink(); ?>" data-slug="<?php echo $post->post_name; ?>">
<span class="dates"><?php echo types_render_field("dates", array("argument1"=>"value1")); ?></span>
<span class="opening"><?php echo types_render_field("opening", array("argument1"=>"value1")); ?></span>
<span class="title">“<?php the_title(); ?>”</span>
<span class="artist"><?php echo types_render_field("artist", array("argument1"=>"value1")); ?></span>
<span class="extra"><?php echo types_render_field("extra", array("argument1"=>"value1")); ?></span>
</a>
<article class="exhibitionDocuments">
</article>
</section>
Within your ajax request:
$.ajax({
url: url,
type: "GET",
success: function(data) {
var content = $(data).find(".single-document");
$(doc).append(content).slideToggle(300);
$("html, body").animate({ scrollTop: exhibitionContainer.offset().top - 26 });
window.location.hash = slug;
}
});
On the second line under success, change .append to .html.
The line should now be:
$(doc).html(content).slideToggle(300);
It will load the content AND remove previous if there was.
EDIT
To close a previously opened .exhibitionDocuments:
$(document).find(".exhibitionDocuments").hide();
Place it on top of your success callback.
(right before var content = $(data).find(".single-document");)
Related
<div id="success_hold">
<?php
if($row['mandate_end']!=date('Y-m-d') && $row['job_position']=='unhold')
{
echo '<span class="badge badge-success">Open</span>';
}
else
{
echo '<span class="badge badge-warning">Hold</span>';
}
?>
</div>
<script>
$(document).ready(function(){
var flag = 1;
$(".hold").click(function(){
job_id = this.id;
if(flag == 1)
{
$.ajax({
type:"POST",
data:{"job_id":job_id},
url:"<?php echo base_url(); ?>pausehold",
success:function(data){
$("#success_hold").load("#success_hold");
}
});
flag = 0;
}
else
{
$.ajax({
type:"POST",
data:{"job_id":job_id},
url:"<?php echo base_url(); ?>resumehold",
success:function(data){
$("#success_hold").load("#success_hold");
}
});
flag = 1;
}
});
});
</script>
I have div where id="success_hold". Now, what happens when I click on class="hold" I am updating my data. Now, I want to refresh my <div id="success_hold"> without reload whole page where I am using .load() function But the problem is that when I use .load() the function shows the whole page in success_hold. So, How can I fix this issue? I want to refresh only success_hold.
Thank You
The problem is because load() is used to make another AJAX request and place the a portion of the HTML retrieved from that request in the target element.
As you're already making an AJAX request to get the data, which is presumably HTML, you simply need to append() data to the container.
Also note that the only difference between the two sides of your condition is the URL the request is sent to, so you can easily DRY this code up:
$(document).ready(function() {
var flag = true;
$(".hold").click(function() {
var url = '<?php echo base_url(); ?>' + (flag ? 'pausehold' : 'resumehold');
flag = !flag;
$.ajax({
type: "POST",
data: { job_id: this.id },
url: url,
success: function(data) {
$("#success_hold").append(data);
}
});
});
});
If data contains the entire page, then you should change that PHP file to return only the relevant HTML as it will help to speed up the request. If, for whatever reason, you can't do that then you can extract the required element from the response like this:
$("#success_hold").append($(data).find('#success_hold'));
success:function(data){
$("#success_hold").load("#success_hold");
}
This is your success method in ajax. You want to pur the content of data into your div #success_hold ?
If you want that, just do this :
success:function(data){
$("#success_hold").html(data);
}
I have divided my content in two tabs and switching between two tabs with javascript.
<div class='tab-container'>
<div class='tab-1'>
<?php
$sql="SELECT * FROM posts WHERE status='tab1'";
echo "<div class='db'
<h2>post</h2></div>";
?>
</div>
<div class='tab-2'>
<?php
$sql="SELECT * FROM posts WHERE status='tab2'";
echo "<div class='db'
<h2>post</h2></div>";
?>
</div>
</div>
Php code divides content between tabs through WHERE clause select * from posts where status='tab1'; so to remove post from one tab ajax request given below triggers php code which updates status of content from tab1 to tab2.
<script type="text/javascript">
$(function() {
$(".restore").click(function(){
var element = $(this);
var del_id = element.attr("id");
var info = 'id=' + del_id;
if(confirm("Restore?"))
{
$.ajax({
type: "GET",
url: "restore.php",
data: info,
success: function(){
}
});
$(this).parents(".db").animate({ backgroundColor: "#fbc7c7" }, "fast")
.animate({ opacity: "hide" }, "slow");
}
return false;
});
});
</script>
So that post is removed from tab1. Idea here is to move post from one tab to another through ajax. javascript works good on removing post from one tab however for making that post appear in another tab I have to reload page as I haven't used ajax for that. So problem is I don't get how to add that post dynamically to another tab through ajax without refreshing page.
To get content from ajax call, you have to echo it in server side.
May be something like this
echo "hi, this is new content";
Now in ajax success
success: function(data){
alert(data); this will alert what was echoed in php(hi, this is new content)
}
If you want to add the content to some div in view,
$("class or id for the div").html(data);
In restore.php, you should get the selected post and then then update the status of that post to tab2. And append that result in main php page. You can append the same via restore.php.
Try this
HTML
<div class="tabs" id="d-tab1"></div>
<div class="tabs" id="d-tab2"></div>
<a href="#" class="restore" id="tab1">
<a href="#" class="restore" id="tab2">
JS
$('.restore').click(function(e){
e.preventDefault();
var $tab = $(this);
$.post('restore.php',{id: $tab.attr('id')},function(html){
$('.tabs').hide();
$('#d-'+$tab.attr('id')).html(html).show();
})
})
Or use Jquery tabs https://jqueryui.com/tabs/
Agree with #Niranjan N Raju. But want to add some addition.
Use console.log(data) instead alert(data) as last don't shows object info.
So, I have been struggling with making ajax work.
Here is my previous question: AJAX (admin_url('admin-ajax.php');?action=) Not Found
Anyway, I decided to narrow down and only have necessary files.
Here is the set up.
test.php
<div class="test">
Items
</div>
<div id="test_demo"> </div>
<script>
jQuery(document).ready(function() {
jQuery('.test a').click(function(e) {
e.preventDefault();
var tab_id = jQuery('this').attr('id');
jQuery.ajax({
type: "GET",
url: "<?php echo admin_url('admin-ajax.php'); ?>",
dataType: 'html',
data: ({ action: 'test_tab', id: tab_id}),
success: function(data){
jQuery('#test_' + tab_id).html(data);
},
error: function(data)
{
alert("Error!");
return false;
}
});
});
});
</script>
function.php
function test_tab_callback() {
$template_part_path = 'page-parts/test_' . $_GET['id'];
get_template_part($template_part_path);
exit;
}
add_action('wp_ajax_test_tab', 'test_tab_callback');
add_action('wp_ajax_nopriv_test_tab', 'test_tab_callback');
test_demo.php
<div id="test_demo_content">Demo Content</div>
Here is the my idea on how it should work.
test.php: When user clicks Items button, then the tab_idvariable in the jQuery saves the anchor id (in this case, it will be id="demo").
Then admin-ajax.php is called.
The saved id ("demo") is then passed onto the function.php and it is used in the variable $template_part_path = 'page-parts/test_' . $_GET['id']; which gives page-parts/test_demo for test_demo.php
Then the template part is called and calledback to the jQuery.
Then the data is "insert" into the jQuery('#test_' + tab_id).html(data); which is id="test_demo.
The test_demo.php content should be displayed in the #test_demo div.
But it is not working. I used console.log(data) but showed no result.
What am I doing wrong?
When your getting the jquery object of "this" you can't use the quotes. This was making tab_id as undefined and ruining the rest.
Here is what I mean:
http://jsfiddle.net/7r1dg7L4/2/
jQuery(document).ready(function() {
jQuery('.test a').click(function(e) {
e.preventDefault();
var tab_id = jQuery(this).attr('id');
alert(tab_id);
});
});
I know My question Title is not perfectly describe my question extremely sorry about that. I don't know how to tell this as a summery. anyway this is my question.
I am making a admin panel to change some of the content in my web page. this scenario is for change slideshow images.
ok then after someone logged into my page I am loading three pages. like this.
$this->load->view('admin/header');
$this->load->view('admin/menu');
$this->load->view('admin/table_and_editor_holder');
all the page contents I have mentioned below. so basic path is like this. once someone logged he can click the button [slide manage] to load the images and details of already inserted slides. these are getting from a database. so once he clicked the menu button. this jquery function is executing.
$('.menu-item > a').on('click', function() {...})
this function simply getting a html page. filled with previous slide details. this is the controller function handle the menu request.
function slider_edit_delete() {
$sdata['slide_imgs'] = $this->admin_basic_curd->get_all_items('sider_images');
$slide_manager = $this->load->view('admin/slider_manager', $sdata, TRUE);
echo $slide_manager;
}
so previous jquery function is then appending this page content to a div like this.
$('#table_container').html(data);
so inside this page content I have a buttons call edit for each slide already inserted. so by clicking on of this button I can edit that slide image or some test content of it. that button is like this.
<a class="onclick_post_by_a" href="<?php echo base_url() . 'adm_edit_this_slide/' . $sl->id; ?>">
<button class="btn btn-info"> Edit </button>
</a>
so by clicking this button must execute this function in the header section and this function must add a html form (in a separate page) to the #editor-form-container div as previously
$('.onclick_post_by_a').on('click', function() {...})
but the problem is once I click the edit button it couldn't find this function. so it is opening the content as a separate page
How can I make this to work? Thank you
the header page contains all the css and js file links. and some jquery functions. like this.
<script>
$(document).ready(function() {
$('.menu-item > a').on('click', function() {
var url = $(this).attr('href');
var pdata = "";
var rdata = posting_url(url, pdata);
rdata.success(function(data) {
$('#table_container').html(data);
});
return false;
});
$('#editor-form-container').css({
display: "none"
});
function posting_url(url, pdata) {
return $.ajax({
url: url,
data: pdata
});
}
$('.onclick_post_by_a').on('click', function() {
var url = $(this).attr('href');
var pdata = "";
var rdata = posting_url(url, pdata);
rdata.success(function(data) {
$('#editor-form-container').css({
display: "block"
});
$('#editor-form-container').html(data);
});
return false;
});
$('.post_with_image').on('submit', (function(e) {
e.preventDefault();
var formData = new FormData(this);
$.ajax({
type: 'POST',
url: $(this).attr('action'),
data: formData,
cache: false,
contentType: false,
processData: false,
success: function(data) {
console.log("success");
console.log(data);
},
error: function(data) {
console.log("error");
console.log(data);
}
});
}));
});
</script>
</head>
then I have load menu page. it is like this.
<div class="admin-navi">
<div class="menu-item">
Home
</div>
<div class="menu-item">
Side Manage
</div>
</div>
<div class="clearfix"></div>
table_and_editor_holder.php page. it is like this.
<div class="col-lg-12">
<div class="col-lg-2"></div>
<div id="table_container" class="col-lg-8">
</div>
</div>
<div id="editor-form-container" class="col-lg-6">
</div>
Dynamically created element does not respond to direct call to events like below -
$('.onclick_post_by_a').on('click', function() {...})
So you have to write like this
$(document).on('click', '.onclick_post_by_a', function() {...})
Just try it out.
EDIT: for clarity purposes, I've edited this question.
EDIT 2: I was able to solve half of my issue.
Below is a simple script for users to delete the pictures they uploaded.
Depending on whether or not there is an image saved in the database. A toggle OR an upload icon should show.
The issue is that when the delete button is clicked, the picture and the toggle buttons get removed BUT the upload icon won't show (unless page is refreshed).
if (image exists in database) {
<div class="toggle" id="toggle<?php echo $image_id ?>"></div>
}
else {
<div class="upload_icon" id="upload<?php echo $image_id ?>"></div>
}
`SQL query to select image in database`
//this DIV expands when the toggle button is clicked
<div class="content" id="image<?php echo $image_id ?>"><img src="<?php echo
$path ?>" />
<div class="remove content"><a href="#" id="<?php echo $image_id ?>"
class="delete_icon">Remove!</a></div>
</div>
Javascript part:
$(function(){
$('.delete_icon').on("click",function()
{
var ID = $(this).attr("id");
var dataString = 'image_id='+ ID;
$this = $(this);
if(confirm("Are you sure you want to delete this image ?"))
{
$.ajax({
type: "POST",
url: "delete.php",
data: dataString,
cache: false,
success: function(html){
$('#image'+ID).remove()
$('#toggle'+ID).remove()
$('#upload'+ID).show();
});
}
return false;
});
});
What am I missing here ?
this is no longer the link once you're inside the context of the success function. I saved off this and used it inside, that should do the trick.
Also I'm not sure that the find is actually going to work. Based on your example I'm not sure that #toggle elements are actualy nested within .delete_icon.
If they aren't you might want to do $('#toggle'+ID) rather than using find. It's an ID selector anyway so it wouldn't be affecting performance.
$(function(){
$('.delete_icon').on("click",function() {
var ID = $(this).attr("id"),
dataString = 'image_id='+ ID,
$this = $(this);
if( confirm("Are you sure you want to remove this image ?") ) {
$.ajax({
type: "POST",
url: "delete.php",
data: dataString,
cache: false,
success: function(html) {
$this.closest(".content").hide();
$('#toggle'+ID).hide()
$('#upload'+ID).show();
}
});
}
return false;
});
});