Bootstrap 3 - carousel with page numbers - twitter-bootstrap-3

I am wondering how to show page numbers with Bootstrap Carousel. Bootstrap has carousel indicators (dot points):
Is it possible to change the indicator to something like "Page 1/3"?
I have tried adding the number to bootstrap caption and moving it to the left side:
However, whenever I clicked next, the number didn't stay at its place. Any ideas how to make this better?
Thanks!

Found a working solution:
var total = $('.item').length;
var currentIndex = $('div.active').index() + 1;
$('#slidetext').html(currentIndex + '/' + total);
// This triggers after each slide change
$('.carousel').on('slid.bs.carousel', function () {
currentIndex = $('div.active').index() + 1;
// Now display this wherever you want
var text = currentIndex + '/' + total;
$('#slidetext').html(text);
});
http://jsfiddle.net/Lf9krnsm/

carousel.on('slide.bs.carousel', function (event) {
var active = $(event.target).find('.carousel-inner > .item.active');
var from = active.index();
var next = $(event.relatedTarget);
var to = next.index();
var direction = event.direction;
});

HTML5:
<!-- Indicators -->
<ol class="carousel-indicators">
<li data-target="#client" data-slide-to="0" class="active">1</li>
<li data-target="#client" data-slide-to="1">2</li>
<li data-target="#client" data-slide-to="2">3</li>
</ol>
SASS:
.carousel-indicators{
bottom: -15px;
left: 80%;
li{
width: 17px;
height: 17px;
margin: 3px;
text-indent: 0;
background-color: $wcolor;
border: 1px solid $bcolor;
border-radius: 0;
line-height: 13px;
}
.active {
width: 17px;
height: 17px;
background-color: #ddd;
}
}

Related

html, css, js slider images collapse on window resize

Everything perfectly works great until I resize the window as I'm trying to build a responsive website. The images inside the slider collapses. I have to reload the page first so they will be in perfect position. What should I do so i don't need to reload the page when resizing the window?
html
<div class="container">
<!-- --- images ---- -->
<div class="slides">
<div class="slide">
<img src="/images/img1.jpg" alt="">
</div>
<div class="slide">
<img src="/images/img2.jpg" alt="">
</div>
<div class="slide">
<img src="/images/img3.jpg" alt="">
</div>
<div class="slide">
<img src="/images/img4.jpg" alt="">
</div>
</div><!-- ---- end of images ---- -->
<!-- ------ controls -------- -->
<div class="slide-controls">
<button id="prev-btn">
<i class="fas fa-chevron-left"></i>
</button>
<button id="next-btn">
<i class="fas fa-chevron-right"></i>
</button>
</div>
<!-- ------ controls -------- -->
</div> <!-- ----- end of container ------- -->
css
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.container {
margin: 20px auto 0 auto;
width: 60%;
height: 600px;
position: relative;
border: 2px solid red;
overflow: hidden;
}
.slides {
display: flex;
height: 100%;
}
.slide {
min-width: 100%;
}
.slide img {
width: 100%;
height: 100%;
object-fit: cover;
vertical-align: middle;
}
.slide-controls {
position: absolute;
top: 50%;
left: 0;
transform: translateY(-50%);
width: 100%;
display: flex;
justify-content: space-between;
align-items: center;
/* display: none; */
}
#next-btn,
#prev-btn {
cursor: pointer;
background: transparent;
font-size: 40px;
border: none;
padding: 10px;
color: white;
}
#next-btn:focus,
#prev-btn:focus {
outline: none;
}
js
const slideContainer = document.querySelector('.container');
const slide = document.querySelector('.slides');
const prevBtn = document.getElementById('prev-btn');
const nextBtn = document.getElementById('next-btn');
const interval = 3000;
let slides = document.querySelectorAll('.slide');
let index = 1;
let slideId;
const firstClone = slides[0].cloneNode(true);
const lastClone = slides[slides.length - 1].cloneNode(true);
firstClone.id = 'first-clone';
lastClone.id = 'last-clone';
slide.append(firstClone);
slide.prepend(lastClone);
const slideWidth = slides[index].clientWidth;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
const startSlide = () => {
slideId = setInterval( () => {
moveToNextSlide();
}, interval);
}
const getSlides = () => slides = document.querySelectorAll('.slide');
slide.addEventListener('transitionend', () => {
slides = getSlides();
if ( slides[index].id === firstClone.id ) {
slide.style.transition = 'none';
index = 1;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
}
if ( slides[index].id === lastClone.id ) {
slide.style.transition = 'none';
index = slides.length - 2;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
}
});
slideContainer.addEventListener('mouseenter', () => {
clearInterval(slideId);
});
slideContainer.addEventListener('mouseleave', startSlide );
const moveToNextSlide = () => {
slides = getSlides();
if ( index >= slides.length -1 ) return;
index++;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
slide.style.transition = '.7s';
}
const moveToPreviousSlide = () => {
if ( index <= 0 ) return;
index--;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
slide.style.transition = '.7s';
};
nextBtn.addEventListener('click', moveToNextSlide);
prevBtn.addEventListener('click', moveToPreviousSlide );
startSlide();
Here's my code snippet. https://codepen.io/rebeccafm/pen/YzWyrvm
i found the answer to this. I use jquery resize method.
$(window).resize(() => {
slideWidth = slides[index].clientWidth;
slide.style.transform = `translateX(${-slideWidth * index}px)`;
});

Adding scroll down button to Shopify custom theme

I am customizing shopify motion theme. I added a scroll down svg on bottom of the slider. But having problem with scrolling down to the next section
I have added the scroll down button with that code;
div.hero__image-wrapper:after {
content: url({{ "icon-scroll-down.svg" | asset_url }}) ;
position: absolute;
display: block;
z-index: 34560;
bottom: 20px;
left: 48%;
font-size: 2em;
border-radius: 1em;
font-weight: bold;
border: 3px solid gray;
padding: 0.1em 0.1em 0;
animation-name: color_change;
animation-duration: 3s;
animation-iteration-count: infinite;
animation-direction: alternate;
}
#keyframes color_change {
0% { color: gray; bottom:20px;}
10% { color: black; bottom:10px;}
20% { color: gray; bottom:20px;}
100%{ color: gray; bottom:20px;}
}
But currently it's only an icon. I need to make it scroll to down
I would do it with JS instead. Let's assume your button is an actual element instead of pseudo ::after:
<div class="scroll-down-button"></div>
.scroll-down-button {
// whatever style you prefer
}
Then the JS code would look like this:
(function() {
// Get the button element
var button = document.querySelector('.scroll-down-button');
// Get current section
var currentSection = button.closest('.shopify-section');
// Get next section (the very next element after current section container)
var nextSection = currentSection.nextSibling();
// Get the coordinates of the next section
var nextSectionCoordinates = nextSection.getBoundingClientRect();
// Get the top Y axis coordinates of next section
var nextSectionTop = nextSectionCoordinates.top;
// Scroll to the top of next section (0 means no scroll on X axis)
window.scrollTo(0, nextSectionTop);
})();
The above is not tested, so let me know if it doesn't work or you can console.log any values. You should get the idea though!

vue-pagination-2 not working

I am brand new to VueJS and almost everything is working, except for pagination. As a matter of fact, I have zero warnings. The only thing appearing in the console is "[HMR] Waiting for update signal from WDS... log.js?4244:23" followed by a ">" on the next line.
With that said, the pagination is showing the correct number of pages - given the data coming from the JSON, but I do not know how to connect the pagination to the UL or the app.
At least when there is an error, I can figure something out. Any help is appreciated and thanks in advance.
<template>
<div class="container" id="app">
<span>VueJS-Example</span>
<ul class="list-group list-inline mHeaders">
<li class="list-group-item">Title</li>
<li class="list-group-item">Band</li>
<li class="list-group-item">Date Posted</li>
<li class="list-group-item">Downloads</li>
<li class="list-group-item">YouTube</li>
<li class="list-group-item">MP3</li>
</ul>
<ul :key="item.id" class="list-group list-inline" v-for="item in items">
<li class="list-group-item">
{{item.title}}
</li>
<li class="list-group-item">
{{item.original_band}}
</li>
<li class="list-group-item">
{{item.date_posted}}
</li>
<li class="list-group-item mZip">
<a v-bind:href="''+item.download_midi_tabs+''" target="_blank"></a>
</li>
<li class="list-group-item mYt">
<a v-bind:href="''+item.youtube_link+''" target="_blank"></a>
</li>
<li class="list-group-item mAudio">
<a v-bind:href="''+item.download_guitar_m4v+''" target="_blank"></a>
</li>
</ul>
<pagination :records="288" :per-page="30" #paginate="getPostsViaREST"></pagination>
</div>
</template>
<script>
import axios from 'axios'
import {Pagination} from 'vue-pagination-2'
export default {
name: 'App',
data: function () {
return {
items: [{
title: '',
original_band: '',
date_posted: '',
download_midi_tabs: '',
youtube_link: '',
download_guitar_m4v: ''
}]
}
},
created: function () {
this.getPostsViaREST()
},
methods: {
getPostsViaREST: function () {
axios.get('http://local.sites/getSongs.php')
.then(response => { this.items = response.data })
}
},
components: {
Pagination
}
}
</script>
<style>
#app {
font-family: 'Avenir', Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
}
a {
color: #999;
}
.current {
color: red;
}
ul {
padding: 0;
list-style-type: none;
}
li {
display: inline;
margin: 5px 5px;
}
ul.list-group:after {
clear: both;
display: block;
content: "";
}
.list-group-item {
float: left;
}
.list-group li{
max-width: 30%;
min-width: 50px;
min-height: 48px;
max-height: 48px;
}
.list-group li:first-child{
width: 200px;
cursor: pointer;
}
.list-group li:nth-child(2){
width: 200px;
}
.list-group li:nth-child(3){
width: 110px;
}
.list-group li:nth-child(4){
width: 48px;
}
.list-group li:nth-child(5){
width: 48px;
}
.list-group li:last-child{
width: 48px;
}
.mZip{
background: url("http://www.kronusproductions.com/songs_angular/assets/images/mZip.png");
display: block !important;
max-width: 48px;
height: 48px;
cursor: pointer;
}
.mYt{
background: url("http://www.kronusproductions.com/songs_angular/assets/images/youtube-icon_48x48.png");
display: block !important;
width: 48px;
height: 48px;
cursor: pointer;
}
.mAudio{
background: url("http://www.kronusproductions.com/songs_angular/assets/images/volume.png");
display: block !important;
width: 48px;
height: 48px;
cursor: pointer;
}
.mZip a{
display: block !important;
width: 48px;
height: 48px;
}
.mYt a{
display: block !important;
width: 48px;
height: 48px;
}
.mAudio a{
display: block !important;
width: 48px;
height: 48px;
}
.mHeaders li{
background-color: cornflowerblue;
font-size: 0.85rem;
color: white;
}
OK - this is somewhat of a hack, but it works.
The following URL is a working example:
Needed help from some old fashion native JavaScript on the index.html file. First, I needed to be able to read a hidden field that contained the number of entries coming from the JSON., followed by setting all the ULs to display none - the setTimeout is to make sure that the JSON file was loaded
<script type="text/javascript">
var mTO = setTimeout(function () {
for (var x = 31; x <= $(".numRows").val() - 1; x++) {
if (typeof (document.getElementById('sp_' + x)) === 'undefined') {
} else {
document.getElementById('sp_' + x).style.display = 'none'
}
}
}, 1000);
mTO;
</script>
This is followed by calling a computed user created method to set this.mVar to the number of elements/entries/properties - whatever name you want to use for it - for Vue to know how many elements, so that we could divide by the number of pages to paginate
computed: {
mFunc: function () {
this.mVar = Object.keys(this.items).length
return Object.keys(this.items).length
}
}
This is another portion of the aforementioned hack - depending on page clicked in the pagination section, this determines what to hide and what to show
setPage: function (page) {
this.page = page
// console.log(page)
for (var y = 0; y <= this.mVar - 1; y++) {
if (typeof (document.getElementById('sp_' + y)) === 'undefined') {
} else {
document.getElementById('sp_' + y).style.display = 'none'
}
}
for (var x = (30 * (this.page - 1)); x <= 30 * (this.page); x++) {
if (typeof (document.getElementById('sp_' + x)) === 'undefined' || (document.getElementById('sp_' + x)) == null) {
break
} else {
document.getElementById('sp_' + x).style.display = 'block'
}
}
}
In case you were wondering what the "30" is for, that is the number of ULs that I wanted to show per page.
The last portion of the hack is within the template section
<pagination :records="mFunc" :per-page="30" #paginate="setPage"></pagination>
<span style="display: none;"><input type="hidden" class="numRows" :value="this.mVar" /></span>
If you would like to use the entire, then you can find it on my github:
Github repo for vuejs-example

How can I change a brand image on scroll in bootstrap?

I have managed to make the image change when I scroll it but it positioning is all wrong and out of the nav bar. I'd like the image to change color when the user scrolls down, but putting the image in the CSS like this positions it wrong. Is there a good way to do it?
CSS:
#fh5co-header .navbar-brand {
float: left;
display: block;
font-size: 30px;
font-weight: 700;
padding-left: 0;
color: #fff;
background: url(../images/loc2.png);
}
#fh5co-header.navbar-fixed-top {
position: fixed !important;
background: #fff;
-webkit-box-shadow: 0 0 9px 0 rgba(0, 0, 0, 0.1);
-moz-box-shadow: 0 0 9px 0 rgba(0, 0, 0, 0.1);
-ms-box-shadow: 0 0 9px 0 rgba(0, 0, 0, 0.1);
box-shadow: 0 0 9px 0 rgba(0, 0, 0, 0.1);
margin-top: 0px;
top: 0;
#fh5co-header.navbar-fixed-top .navbar-brand {
background: url(../images/loc.png);
color: #96281B;
HTML:
#fh5co-header.navbar-fixed-top .navbar-brand {
background: url(../images/loc.png);
color: #96281B;
<nav class="navbar navbar-default">
<div class="navbar-header">
<!-- Mobile Toggle Menu Button -->
<i></i>
<a class="navbar-brand" href="index.html"></a>
</div>
<div id="navbar" class="navbar-collapse collapse">
<ul class="nav navbar-nav navbar-right">
<li class="active"><span>Home</span></li>
<li><span>Menus</span></li>
<li><span>Testimonials</span></li>
<li><span>Services</span></li>
<li><span>About</span></li>
<li><span>Contact</span></li>
<li><i class="icon-facebook"></i></li>
<li><i class="icon-twitter"></i></li>
</ul>
<ul class="social social-circle">
</ul>
</div>
</nav>
JS
var windowScroll = function() {
var lastScrollTop = 0;
$(window).scroll(function(event){
var header = $('#fh5co-header'),
scrlTop = $(this).scrollTop();
if ( scrlTop > 500 && scrlTop <= 2000 ) {
header.addClass('navbar-fixed-top fh5co-animated slideInDown');
} else if ( scrlTop <= 500) {
if ( header.hasClass('navbar-fixed-top') ) {
header.addClass('navbar-fixed-top fh5co-animated slideOutUp');
setTimeout(function(){
header.removeClass('navbar-fixed-top fh5co-animated slideInDown slideOutUp');
}, 100 );
}
}
});
};
Try somthing like this.
Create classes to switch between, where you can set a background-image.
$(window).scroll(function() {
var scroll = $(window).scrollTop();
if (scroll >= 80) {
$(".navy").addClass("scrolling");
$(".navbar-brand").addClass("navscroll");
} else {
$(".navy").removeClass("scrolling");
$(".navbar-brand").removeClass("navscroll");
}
});
CSS:
.drop.menuscroll {
margin-top: 0px;
transition: 0.8s
}
.menu.linesscroll {
margin-top: 8px;
transition: 0.8s;
}
.navy.scrolling {
transition: 0.8s;
height: 50px;
margin-top: 0px;
}
.navbar-brand img.navscroll {
margin-top: -10px;
width: 63px;
transition: 0.8s;
}
Place tha class on the navbar etc. This worked for me.
All you need to do is amend the class specifics to fit your project.

Simple Gallery Slider

I'm trying to create a simple slider using divs and javascript. I set up a div with six images and an arrow that movies the containder holding the images 528px (the width of each image) every time it's clicked. When I reach the begining or end of the gallery, I want the respective arrow button to fade out so that the user won't keep pressing next/prev.
Any help is appreciated.
JAVASCRIPT
$("#btn-gallery-next").click(function(){
$("div#gallery li").not(this).removeClass('clicked');
$("div#gallery-slide").animate({left:"-=528px"});
if($("div#gallery-slide").position().left < -3168)
{
$("#btn-gallery-next").fadeOut();
}
else {
$("#btn-gallery-next").fadeIn();
}
});
$("#btn-gallery-prev").click(function(){
$("div#gallery li").not(this).removeClass('clicked');
$("div#gallery-slide").animate({left:"+=528px"});
if($("div#gallery-slide").position().left > 0)
{
$("#btn-gallery-prev").fadeOut();
}
else {
$("#btn-gallery-prev").fadeIn();
}
});
HTML
<div id="gallery-slide">
<img class="gallery-img" src="_/img/gallery/img1.jpg" alt="" />
<img class="gallery-img" src="_/img/gallery/img2.jpg" alt="" />
<img class="gallery-img" src="_/img/gallery/img3.jpg" alt="" />
<img class="gallery-img" src="_/img/gallery/img4.jpg" alt="" />
<img class="gallery-img" src="_/img/gallery/img5.jpg" alt="" />
<img class="gallery-img" src="_/img/gallery/img6.jpg" alt="" />
</div>
Try flex slider from woothemes, it have all ur needs.
Why not use a slider library like Owl Slider? It comes with lots of options and configurations. It is super simple to integrate into any project.
Example #1 www.midwestgathering.com/#galleries
Example #2 www.owlgraphic.com/owlcarousel/demos/images.html
Another option is jcarousel. The basic slider is shown with an example that makes the left next button inactive until the user slides to the right, then once the user gets to the end of the gallery the right next button becomes inactive:
JS
(function($) {
$(function() {
$('.jcarousel').jcarousel();
$('.jcarousel-control-prev')
.on('jcarouselcontrol:active', function() {
$(this).removeClass('inactive');
})
.on('jcarouselcontrol:inactive', function() {
$(this).addClass('inactive');
})
.jcarouselControl({
target: '-=1'
});
$('.jcarousel-control-next')
.on('jcarouselcontrol:active', function() {
$(this).removeClass('inactive');
})
.on('jcarouselcontrol:inactive', function() {
$(this).addClass('inactive');
})
.jcarouselControl({
target: '+=1'
});
$('.jcarousel-pagination')
.on('jcarouselpagination:active', 'a', function() {
$(this).addClass('active');
})
.on('jcarouselpagination:inactive', 'a', function() {
$(this).removeClass('active');
})
.jcarouselPagination();
});
})(jQuery);
CSS
.jcarousel-wrapper {
margin: 20px auto;
position: relative;
border: 10px solid #fff;
-webkit-border-radius: 5px;
-moz-border-radius: 5px;
border-radius: 5px;
-webkit-box-shadow: 0 0 2px #999;
-moz-box-shadow: 0 0 2px #999;
box-shadow: 0 0 2px #999;
}
.jcarousel-wrapper .photo-credits {
position: absolute;
right: 15px;
bottom: 0;
font-size: 13px;
color: #fff;
text-shadow: 0 0 1px rgba(0, 0, 0, 0.85);
opacity: .66;
}
.jcarousel-wrapper .photo-credits a {
color: #fff;
}
/** Carousel **/
.jcarousel {
position: relative;
overflow: hidden;
width: 600px;
height: 400px;
}
.jcarousel ul {
width: 20000em;
position: relative;
list-style: none;
margin: 0;
padding: 0;
}
.jcarousel li {
float: left;
}
/** Carousel Controls **/
.jcarousel-control-prev,
.jcarousel-control-next {
position: absolute;
top: 200px;
width: 30px;
height: 30px;
text-align: center;
background: #4E443C;
color: #fff;
text-decoration: none;
text-shadow: 0 0 1px #000;
font: 24px/27px Arial, sans-serif;
-webkit-border-radius: 30px;
-moz-border-radius: 30px;
border-radius: 30px;
-webkit-box-shadow: 0 0 2px #999;
-moz-box-shadow: 0 0 2px #999;
box-shadow: 0 0 2px #999;
}
.jcarousel-control-prev {
left: -50px;
}
.jcarousel-control-next {
right: -50px;
}
.jcarousel-control-prev:hover span,
.jcarousel-control-next:hover span {
display: block;
}
.jcarousel-control-prev.inactive,
.jcarousel-control-next.inactive {
opacity: .5;
cursor: default;
}
/** Carousel Pagination **/
.jcarousel-pagination {
position: absolute;
bottom: 0;
left: 15px;
}
.jcarousel-pagination a {
text-decoration: none;
display: inline-block;
font-size: 11px;
line-height: 14px;
min-width: 14px;
background: #fff;
color: #4E443C;
border-radius: 14px;
padding: 3px;
text-align: center;
margin-right: 2px;
opacity: .75;
}
.jcarousel-pagination a.active {
background: #4E443C;
color: #fff;
opacity: 1;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.75);
}
You can find documentation for jcarousel at www.sorgalla.com/jcarousel/docs/.
see demo - http://codepen.io/vsync/pen/waKju?editors=011
javascript
/**
* Slider - loops over images
* SEP 2014
* By - Yair Even-Or
*/
var Slider = function(elm, prev, next){
var that = this;
this.locked = false;
this.slider = elm;
this.children = this.slider.children;
this.itemWidth = this.children[0].clientWidth;
this.preloadImages();
next && next.addEventListener('click', function(){ that.move('next') });
prev && prev.addEventListener('click', function(){ that.move('prev') });
}
Slider.prototype = {
move : function(dir){
var that = this,
itemToMove;
if( this.locked ){
this.locked.removeAttribute('style');
this.slider.appendChild(this.locked);
clearTimeout(this.timer);
moveToEnd();
}
// do nothing if there are no items
if( this.children.length < 2 )
return false;
itemToMove = this.children[0];
this.locked = itemToMove;
if( dir == 'next' )
itemToMove.style.marginLeft = -this.itemWidth + 'px';
else{
itemToMove = this.children[this.children.length-1];
itemToMove.style.marginLeft = -this.itemWidth + 'px';
this.slider.insertBefore(itemToMove, this.children[0]);
setTimeout(function(){
itemToMove.removeAttribute('style');
},50);
this.preloadImages();
this.locked = false;
}
// move the child to the end of the items' list
if( dir == 'next' )
this.timer = setTimeout(moveToEnd, 420);
function moveToEnd(el){
itemToMove = el || itemToMove;
if( !itemToMove ) return;
itemToMove.removeAttribute('style');
that.slider.appendChild(itemToMove);
that.locked = false;
that.preloadImages();
}
},
preloadImages : function(){
this.lazyload(this.children[1].getElementsByTagName('img')[0] );
this.lazyload(this.children[this.children.length-1].getElementsByTagName('img')[0] );
},
// lazy load image
lazyload : function(img){
var lazy = img.getAttribute('data-src');
if( lazy ){
img.src = lazy;
img.removeAttribute('data-src');
}
}
}
// HOW TO USE /////////////////
var sliderElm = document.querySelector('.content'),
next = document.querySelector('.next'),
prev = document.querySelector('.prev'),
slider = new Slider(sliderElm, prev, next);
HTML (JADE syntax)
.slider
a.arrow.next
a.arrow.prev
ul.content
li
img(src='image1.jpg')
li
img(src='image2.jpg')
li
img(src='image3.jpg')
li
img(src='image4.jpg')