I successfully implemented a Masonry-Gallery for a WordPress website by using Bootstrap 5 in combination with 'Masonry-Layout'.
It works all fine except in Safari, where the layout usually breaks, a known problem and the solution is supposed to be 'imagesLoaded'.
I tried a lot, but I just don't manage to add the needed classes at the right place(s).
The code as far as I got, see below. Anybody who can help?
<div class="row grid" id="gallery-masonry" data-masonry='{"percentPosition": true }'>
<?php
$images = get_field('gallery');
$size = 'large';
if( $images ): ?>
<?php foreach( $images as $image_id ): ?>
<div class="col-md-6 mb-3">
<div id="post-<?php the_ID(); ?>" class="card rounded-0" >
<?php echo wp_get_attachment_image( $image_id, $size, "", ["class" => "card-img-top rounded-0","alt"=>""]); ?>
</div>
</div>
<?php endforeach; ?>
<?php endif; ?>
</div>
<!--Masonry-Layout-->
<script src="https://cdn.jsdelivr.net/npm/masonry-layout#4.2.2/dist/masonry.pkgd.min.js" integrity="sha384-GNFwBvfVxBkLMJpYMOABq3c+d3KnQxudP/mGPkzpZSTYykLBNsZEnG2D9G/X/+7D" crossorigin="anonymous" async></script>
<!--ImagesLoaded-->
<script src="https://unpkg.com/imagesloaded#5/imagesloaded.pkgd.min.js"></script>
<!--Script ImagesLoaded-->
<script>
var $grid = $('.grid').imagesLoaded( function() {
// init Masonry after all images have loaded
$grid.masonry({
// options...
});
});
</script>
Please check my post regarding adding a Masonry to a Wordpress Site.
https://www.customfitwebdesign.com/how-to-add-masonry-layout-in-wordpress/
Note: Masonry is actually built into the core of WordPress ( wp-includes/js/masonry.min.js ). This WordPress version of Masonry also includes ImagesLoaded (imagesloaded.min.js).
Related
I am trying to position a div vertically in the middle of a window in Wordpress.
I have a function.js file with the following code:
function setToCenter()
{
var a = document.getElementById("R_center");
var h = window.innerHeight;
var p = (h/2)-(650/2);
if( p < 80 ){ p = 80; }//limit to header height
//a.style.transform = "transform(0,"+p+"px)";
//a.style.margin-top= p+"px";
a.style.paddingTop = p+"px";
}
and a php file to get the post content:
<?php
/*
Template Name: Page R Center
*/
?>
<?php global $optimizer;?>
<?php get_header(); ?>
<div id="R_center" class="R">
<script type="text/javascript"> setToCenter(); </script>
<?php if(have_posts()): ?><?php while(have_posts()): ?><?php the_post(); ?>
<div <?php post_class(); ?> id="post-<?php the_ID(); ?>">
<div class="thn_post_wrap">
<?php the_content(); ?>
</div>
</div>
<?php endwhile ?>
</div><!--R_center class END-->
<?php endif ?>
<?php get_footer(); ?>
and in my header.php:
<script type="text/javascript" src="http://localhost/wp/wp-content/themes/r-child/assets/js/functions.js"></script>
evrything is working well. The Div is positioned in the vertical middle of my screen. BUT because the Div is rendered after the java script it works only after refreshing the page.
My question is where do I have to place my javascript to avoid refreshing? Can I execute everything from my functions.js without calling function in my php?
thx
In your case you need to launch setToCenter function after DOM is loaded by browser. You should wrap it into DOMContentLoaded event, example:
document.addEventListener("DOMContentLoaded", function(event) {
setToCenter();
});
or if you use jQuery:
$(function(){
setToCenter();
});
The easiest way is to place your function call near the footer even you can place it after the footer as well. this will solve you problem.
You have asked "can you place the code in function.js?" yes you can do this as well. just place function call inside window.load function and put this code in function.js file.
Below are the example for both cases .
$(window).load(function() { setToCenter(); });
OR
<?php
/*
Template Name: Page R Center
*/
?>
<?php global $optimizer;?>
<?php get_header(); ?>
<div id="R_center" class="R">
<?php if(have_posts()): ?><?php while(have_posts()): ?><?php the_post(); ?>
<div <?php post_class(); ?> id="post-<?php the_ID(); ?>">
<div class="thn_post_wrap">
<?php the_content(); ?>
</div>
</div>
<?php endwhile ?>
</div><!--R_center class END-->
<?php endif ?>
<?php get_footer(); ?>
<script type="text/javascript"> setToCenter(); </script>
Here is my code
jQuery:
jQuery(document).ready(function(){
jQuery('#admin-page-wrapper ul').sortable({cursor: 'move'});
});
Here is my order of jquery which are enqued
wp_enqueue_script('jquery');
wp_enqueue_script('jquery-ui-core');
And here is my plugin code
<div id="admin-page-wrapper">
<h2>Published Pages</h2>
<?php
$pages = new WP_Query(array('post_type'=>'page','post_status'=>'publish','posts_per_page'=>'-1','order'=>'ASC'));
?>
<ul id="dashboard-page">
<?php if($pages -> have_posts()){
while($pages -> have_posts()){
$pages->the_post(); ?>
<li class="dashboard-item"><?php echo the_title(); ?></li>
<?php }
} ?>
</ul>
</div>
Add 3rd script & add it as last one:
wp_enqueue_script( 'jquery-ui-sortable');
You can find a list of all WordPress built in scripts at this page:
https://codex.wordpress.org/Function_Reference/wp_enqueue_script
I wonder if anyone could help me with a problem I am having with bxslider. I am creating a Wordpress site and using the jQuery bxslider instead of the plugin version. Everything with the slider is fine when you load the website, but when you leave the homepage to go to another page, and then come back the slider is broken.
When I say broken, both slides are showing and the JavaScript has stopped. Im using Bootstrap 3 as the framework of the theme.
I'm not used to posting on here, so sorry if I have made a mistake please feel free to correct it.
Any help would be appreciated.
Many Thanks
<div class="container">
<section class="row" id="slidercontainer">
<div class="col-lg-12 col-md-12 col-sm-12 col-xs-12" id="sliderholder">
<ul class="bxslider">
<?php
global $post;
$args = array('numberposts' => 4, 'category' => 2, 'post_status'=>"publish");
$myposts = get_posts($args);
foreach($myposts as $post) : setup_postdata($post);
?>
<li id="post-<?php the_ID(); ?>" class="slider-item">
<h1><?php echo get_the_title();?></h1>
<?php
$imageArray = get_field('slider_image'); // Array returned by Advanced Custom Fields
$imageAlt = $imageArray['alt']; // Grab, from the array, the 'alt'
$imageThumbURL = $imageArray['sizes']['postslider']; //grab from the array, the 'sizes', and from it, the 'thumbnail'
?>
<img class="pull-right" src="<?php echo $imageThumbURL;?>" alt="<?php echo $imageAlt; ?>">
<?php
$content = apply_filters( 'the_excerpt', get_the_excerpt() );
$content = str_replace( ']]>', ']]>', $content );
?>
<div class="slider-content"><?php echo $content;?></div>
</li>
<?php
endforeach;
wp_reset_postdata();
?>
</ul>
</div>
</section>
</div>
<!-- JavaScript -->
$(document).ready(function(){
$('.bxslider').bxSlider({
maxSlides: 4,
pager: false,
auto: true,
autoHidePager: true,
pause: 10500,
controls: true,
speed: 1800,
mode: 'horizontal'
});
});
I have a php script that loops over the results of a database query and prints them out. I am trying to load them into an Admin Interface Panel with AJAX, but to no avail. My job requires me to write mostly backend code, so I haven't gotten around to learning much JS/Jquery. Anyways, I have a page "insert.php" that has a button I want to click and have it call the results from the "posts.php" page. Here are my files
insert.php
Load Posts
</div>
</div>
<div class="row main">
<div class="small-8 columns" id="posts">
</div>
</div>
</div>
posts.php
<?php
require_once 'connect.php';
$user = 'admin';
$sql = "SELECT * FROM posts WHERE author = ?";
$stmt = $db->prepare($sql);
$stmt->bindParam(1, $user);
$stmt->execute();
$data = $stmt->fetchAll();
foreach ($data as $row)
{
$id = $row['id'];
$title = $row['title'];
$author = $row['author'];
$date = $row['date'];
$smalltext = $row['smalltext'];
$bodytext = $row['bodytext'];
$images = $row['images'];
$imagelist = split(' ', $images);
$shorttext = str_replace(
array("\r\n", "\n"),
array("</p><p>", "</p><p>"),
$smalltext);
echo
"
<div class='row main'>
<h1 class='padding-top-12 bottom-rule-green'>$title</h1>
<div class='small-2 columns'>
<p class='text-justify small-text'>
Post MetaData goes here
</p>
</div>
<div class='small-10 columns bottom-rule-red text-justify'>
<p>
$shorttext
";
foreach ($imagelist as $key => $value)
{
echo "<img src='users/$author/img/$value'>";
}
echo
"
</p>
</div>
</div>
<div class='row main small-text padding-top-1'>
<div class='small-2 small-oofset-2 columns'>
<a href='posts/$author/$id'>Edit Post</a>
</div>
<div class='small-4 columns'>
Timestamp: $date
</div>
<div class='small-4 columns'>
Author: <a href='users/$user'>$user</a>
</div>
</div>
";
}
?>
postAjax.js
$.ajaxSetup ({
cache: false
});
var loadUrl = "../../includes/posts.php";
$(function(){
$('#ajaxbtn').on('click', function(e){
e.preventDefault();
$('#ajaxbtn').fadeOut(300);
$.post(loadUrl, {language: "php", version: 5},
function(res){
$("posts").html(res)
}, "html");
});
});
This is the file that loads my scripts into the page
<!--Foundation Framework Necessities-->
<script type="text/javascript" src="../../assets/js/vendor/jquery.js"></script>
<script type="text/javascript" src="../../assets/js/foundation/foundation.min.js"></script>
<script type="text/javascript" src="../../assets/js/postAjax.js"></script>
<script type="text/javascript">
$(document).foundation();
</script>
When I click the #ajaxbtn button, it fades out so I know the JS is being called to that element onclick, but it doesn't post the results of posts.php. I think this may just be my misunderstanding of how Ajax works; if you would please tell me what I did wrong.
Try changing,
$("posts").html(res)
to
$("#posts").html(res)
Also I see some mistakes in your code in posts.php
You are not embedding php variables in strings properly.
I believe you need to use a delegated event. Change your code from:
$('#ajaxbtn').on('click', function(e)
to:
$('#ajaxbtn').on('click', 'a', function(e)
This way event handlers will fire as expected even if the contents of that parent element change. I had the same issue and this solved it. Good luck.
I'm new to jQuery and am having trouble figuring out the right way to loop a set of code for a basic carousel/banner rotator. I've tried a few versions of "for" statements and .each(), but I can't get it to work on my own so I'm reaching out for help.
Here's my code so far:
$('.next-1').click(function () {
$('.featured-1').fadeOut(500,function(){
$('.featured-2').fadeIn(500,function(){
$('.featured-2').toggleClass("hide");
});
});
});
$('.next-2').click(function () {
$('.featured-2').fadeOut(500,function(){
$('.featured-3').fadeIn(500,function(){
$('.featured-3').toggleClass("hide");
});
});
});
And then a similar code block for going back within the slider:
$('.prev-2').click(function () {
$('.featured-2').fadeOut(500,function(){
$('.featured-1').fadeIn(500,function(){
$('.featured-2').toggleClass("hide");
});
});
});
$('.prev-3').click(function () {
$('.featured-3').fadeOut(500,function(){
$('.featured-2').fadeIn(500,function(){
$('.featured-3').toggleClass("hide");
});
});
});
This code does work right now, I just don't want to have to output so many unnecessary lines of code when I know I could loop it. I'd like to be able to loop until there are no more "featured-n" divs to cycle through (being able to cycle around to the beginning would be great too!)
Here's the PHP/HTML I'm using to generate each "featured-n" div block:
function home_slider_loop() {
$count = 0;
query_posts ('tag=slider');
if (have_posts()) : while (have_posts()) : the_post();
$count++;
?>
<div class="featured-post featured-<?php echo $count; if ($count>1) { echo ' hide';}?>">
<div class="featured-header">
<h1 class="featured-title"><?php the_title(); ?></h1>
<p class="author">Written by Evan Luzi</p>
</div>
<div class="image-wrap">
<?php the_post_thumbnail('full', array('class' => 'slider-image')); ?>
<div class="slider-nav">
<div class="featured-prev prev-<?php echo $count; ?>"></div>
<div class="featured-next next-<?php echo $count; ?>"></div>
</div><!--End Navigation-->
</div><!--End Image <?php echo $count; ?>-->
<div class="featured-footer">
<?php the_excerpt(); ?>
<a class="more-link" href="<?php the_permalink(); ?>" alt="<?php the_title(); ?>" >Read more</a>
</div>
</div><!--End Featured <?php echo $count; ?>-->
<?php
endwhile;
endif;
}
Here's a sample of one of the static HTML outputs (just imagine this iterated several times with the "featured-n" classes incrementing:
<div class="featured-1">
<div class="featured-header">
<h1 class="featured-title">5 Useful Cinematography Apps for iOS You Should Download Today</h1>
<p class="author">Written by Evan Luzi</p>
</div>
<div class="image-wrap">
<img width="1018" height="416" src="http://www.tbabdev.com/wp-content/uploads/2013/07/cinematography-apps-8-hero.jpg" class="slider-image wp-post-image" alt="cinematography-apps-8-hero" />
<div class="slider-nav">
<div class="featured-prev prev-1"></div>
<div class="featured-next next-1"></div>
</div><!--End Navigation-->
</div><!--End Image 1-->
<div class="featured-footer">
<p>The devices we have in our pockets, the ones that can run these apps, these are the new leathermans. They have everything we need. They eliminate the need to carry paper manuals and enable us to do complex timelapse calculations in a fraction of the time as a paper and pen.</p>
<a class="more-link" href="http://www.tbabdev.com/?p=27" alt="5 Useful Cinematography Apps for iOS You Should Download Today" >Read more</a>
</div>
</div><!--End Featured 1-->
You can see the code in action at http://www.tbabdev.com/
Thank you in advance for your help and please be kind to a n00b :)
Use something like this :
$('.nav .prev').click(function(){
activeBlock = $('.featured.active');
prevBlock = activeBlock.prev('.featured');
activeBlock.fadeOut('slow',function(){
prevBlock.fadeIn().addClass('active');
}).removeClass('active');
});
$('.nav .next').click(function(){
activeBlock = $('.featured.active');
nextBlock = activeBlock.next('.featured');
activeBlock.fadeOut('slow',function(){
nextBlock.fadeIn().addClass('active');
}).removeClass('active');
});
Html
<div class="nav">
<div class="prev"> </div>
<div class="next"> </div>
</div>
<div class="featured-post featured <?php if($count>1) echo 'hide' ?>">
<div class="featured-header">
<h1 class="featured-title"><?php the_title(); ?></h1>
<p class="author">Written by Evan Luzi</p>
</div>
<div class="image-wrap">
<?php the_post_thumbnail('full', array('class' => 'slider-image')); ?>
</div>
<!--End Image <?php echo $count; ?>-->
<div class="featured-footer">
<?php the_excerpt(); ?>
<a class="more-link" href="<?php the_permalink(); ?>" alt="<?php the_title(); ?>" >Read more</a>
</div>
</div>
You could do it this way :
$('.featured-next, .featured-prev').click(function () {
//find out if the clicked element is a prev or next element, extract the last part, will be useful later
var direction = $(this).hasClass("featured-next") ? "next" : "prev";
//select the ".featured-n" block which is the super-parent of clicked element
var $fullBlock = $(this).closest('div[class^="featured-"]'); //or add a class here to make your life easier
//fade out full block
$fullBlock.fadeOut(500, function () {
//search for the next element and show it
//note that $fullBlock.next() => $fullBlock["next"]() => $fullBlock[direction]()
$fullBlock[direction]().fadeIn(500, function () {
//toggle the class "hide" of the element next to fullBlock
$(this).toggleClass("hide");
});
});
});
Explanation:
You can join up both prev and next events together.
Then, you have to check if its a next or a prev element. Set that to a variable called direction. We'll be using this to find out if we have to use prev() or next() when we're trying to fadeIn featured-n divs.
Find the parent with the class set to featured-n (in your case its the superparent). It might be better if you give a common class to all these elements so that we can stop using 'div[class^="featured-"]' selector, which is slightly inefficient.
Fade out the superparent.
In the callback, based on the direction variable, we'll have to decide if the carousel is gonna go to prev block or next block, something like this :
if(direction === "prev")
{
$fullBlock.prev().fadeIn(//your code)
}
else
{
$fullBlock.next().fadeIn(//your code)
}
You must also know that, in an object like this :
var data = {"name" : "Blah Blah"}
To get the "Blah Blah" out, we can say
data.name
or we could say :
data["name"]
So based on this, in our situation, instead of
$fullBlock.prev()
Or we could say
$fullBlock["prev"]()
Which is what direction variable contains. So finally, we could do this to select the next/prev element based on what was clicked :
$fullBlockdirection
Show the prev/next element.
Add/remove "hide" class.
Hope this helped!