My jquery slider refresh rate won't update live - javascript

I am trying to develop a simple jquery slider, the slier switches between images and text each three seconds by default (var segundos = 3;), the slider has a button which acts as a play/pause action and a menu option which lets you increase or decrease the ammoun of seconds it will switch between images each time. This is done via the classes .resta and .suma(decrease and decrease).
Now, the slider works good but there is a problem, when the segundos variable (segundos means seconds) changes the effect don't take action unless the slider is paused, it won't automatically refresh while theslider is running. It has to go like this: pause slider > change default seconds > play slider > see results
My objective is to make it so it changes the refresh rate while the slider is up and running.
Here is the code:
<script>
$(document).ready(function(){
var segundos = 3000;
var stop = true;
var slideInterval;
$('.play').click(function(){
if (stop == false) {
stop = true;
$('#playpause').text('Play it');
clearInterval(slideInterval);
}
else {
stop = false;
$('#playpause').text('Pause it');
slideInterval = setInterval(swapSlides, segundos);
}
});
function swapSlides(){
//var cs = $('div.currentslide:first');
var cs = $('#polaroid1').children('.currentslide:first');
var ns = cs.next();
if(ns.hasClass('mySlides1')){
cs.removeClass('currentslide');
ns.addClass('currentslide');
}
else{
ns = $('#polaroid1').children('div.mySlides1:first');
cs.removeClass('currentslide');
ns.addClass('currentslide');
}
}
$('.resta').click(function(){
if(segundos > 1000){
segundos = segundos - 1000;
segundoss = (segundos/1000);
$('.segundos').text(" " + segundoss + "s ");
}
});
$('.suma').click(function(){
if(segundos >= 1000 && segundos < 15000){
segundos = segundos + 1000;
segundoss = (segundos/1000);
$('.segundos').text(" " + segundoss + "s ");
}
});
});
</script>
.menu{
list-style:none;
bottom:8px;
position:absolute;
font-family: 'Covered By Your Grace', cursive;
font-weight:300;
width:200px;
}
.menu > li{
}
.play{
width:59px;
height:52px;
position:absolute;
left:5px;
bottom:5px;
cursor:pointer;
z-index:10000;
}
.polaroid1{
box-shadow: 10px 10px 7px -7px rgba(0, 0, 0, 0.5);
-webkit-backface-visibility: hidden;
transform: rotate(-8deg);
margin-bottom:30px;
width:380px;
height:320px;
background-color:rgba(255, 255, 255, 1.0);
text-align:right;
padding-top:10px;
padding-right:10px;
padding-left:10px;
padding-bottom:15px;
top:15px;
left:25px;
position:relative;
}
.photo1{
width:100%;
height:85%;
position:relative;
padding:5px;
}
.date1{
margin:0;
padding-right:10px;
font-family: 'Covered By Your Grace', cursive;
transform: rotate(-5deg);
font-size:28px;
}
.mySlides1{
display:none;
width:380px;
height:320px;
position:absolute;
top:0px;
left:0px;
}
.currentslide{display:block;}
<ul class="menu hide">
<li style="font-size:22px; margin-top:8px;">Diapositivas: <span class="resta" style="cursor:pointer;">< </span><span class="segundos">3s</span><span class="suma" style="cursor:pointer;"> ></span></li>
</ul>
</div>
<div id="polaroid1" class="polaroid1">
<div class="tooltip2 play" style="background-image: url('images/heart2.png');"><span id="playpause" class="tooltiptext2">Play it</span></div>
<div class="mySlides1 fade currentslide">
<img class="photo1" src="images/IMG-20170610-WA0028.jpg">
<h3 class="date1">22-05-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170812_181516.jpg">
<h3 class="date1">12-08-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170522_112958.jpg">
<h3 class="date1">22-05-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/IMG-20170610-WA0017.jpg">
<h3 class="date1">10-06-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170819_194526.jpg">
<h3 class="date1">19-08-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170811_182103.jpg">
<h3 class="date1">11-08-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170522_124602.jpg">
<h3 class="date1">22-05-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170419_020725.jpg">
<h3 class="date1">19-04-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170520_115819.jpg">
<h3 class="date1">20-05-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170822_011703.jpg">
<h3 class="date1">22-08-2017</h3>
</div>
<div class="mySlides1 fade">
<img class="photo1" src="images/20170705_184344.jpg">
<h3 class="date1">05-07-2017</h3>
</div>
</div>

It has to go like this: pause slider > change default seconds > play
slider > see results
My objective is to make it so it changes the refresh rate while the
slider is up and running.
That's because you never do anything to your slideInterval when you increase/decrease the slide interval time (segundos).
Solution:
Add function to restart your slideInterval like so:
function _restartSlide() {
clearInterval(slideInterval);
slideInterval = setInterval(swapSlides, segundos);
}
jsfiddle link https://jsfiddle.net/sudarpochong/2za1ccra/1/

Related

Programatically setting images widths based on container width

I have a series of images i'd liike to output per row. I ned these image to take up the ful width of each row in question. The only way I can think to to do this is by calculating the combined widths of the images vs container width. Then use the pecenateg difference to reduce the image widths.
I have this working nearly 100% as expected, but the images do not quite fill the space in some cases. There must be a flaw in my logic as this should always fit the space based on the calculations.
As you can see from the example below, the images do not quite line up in the righthand side. I think the flaw in my logic is on this line return imageWidths + (60 * imgs.length);
Demo: http://jsfiddle.net/rev3tsuf/5/
JS:
function processImageRows(className, containerWidth) {
let imgWidths = getImageWidthCombines(className);
// initiate image width setting if too large for container
if (imgWidths > containerWidth) {
let percent = Math.ceil((containerWidth / imgWidths) * 100);
getImageWidthCombines(className, percent);
}
}
function getImageWidthCombines(className, percent = false) {
// loop through images for given row and return combined width
let imgs = document.querySelectorAll(`#image-wrapper .${ className } img.set-img`);
let imageWidths = 0;
imgs.forEach(function(el, index) {
if (percent) {
// if percentage is set that means we now set the widths as opposed to return their value
el.style.width = `${Math.floor(el.width * (percent / 100))}px`;
} else {
el.style.width = null;
imageWidths += el.offsetWidth;
}
});
// ??? needs 60 added otherwsie doesn't get right percentage.
return imageWidths + (60 * imgs.length);
}
HTML:
<div class="container">
<div class="row row-1">
<div class="col-auto">
<img src="https://via.placeholder.com/400x473.png" />
</div>
... more images
</div>
<div class="row row-2">
<div class="col-auto">
<img src="https://via.placeholder.com/473x473.png" />
</div>
... more images
</div>
<div class="row row-3">
<div class="col-auto">
<img src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
... more images
</div>
</div>
I also have a window resize event that triggers the above process, but i've left that out of the example in order to keep it simple.
Any help would be greatly appreciated. It's taken me two days to get this far, and half a day stuck on this one issue, now i'm completely stuck with nothing more to try.
EDIT
To adjust your work just customize CSS class as below:
.row {
margin-right: -4px;
margin-left: -4px;
}
.row .col-auto:first-child{
margin-left: 0!important; /* ADDED */
}
.row .col-auto:last-child{
margin-right: 0 !important; /* ADDED */
}
.row .col-auto{
margin-left: auto; /* ADDED */
margin-right:auto; /* ADDED */
}
.col-auto {
padding-right: 4px !important; /* ADDED !important */
padding-left: 4px !important; /* ADDED !important */
padding-bottom: 8px;
position: relative;
overflow: hidden;
cursor: pointer;
}
DEMO with JS CODE your code:
function processImageRows(className, containerWidth) {
let imgWidths = getImageWidthCombines(className);
// initiate image width setting if too large for container
if (imgWidths > containerWidth) {
let percent = Math.ceil((containerWidth / imgWidths) * 100);
getImageWidthCombines(className, percent);
}
}
function getImageWidthCombines(className, percent = false) {
// loop through images for given row and return combined width
let imgs = document.querySelectorAll(`#image-wrapper .${ className } img.set-img`);
let imageWidths = 0;
imgs.forEach(function(el, index) {
if (percent) {
// if percentage is set that means we now set the widths as opposed to return their value
el.style.width = `${Math.floor(el.width * (percent / 100))}px`;
} else {
el.style.width = null;
imageWidths += el.offsetWidth;
}
});
// ??? needs 60 added otherwsie doesn't get right percentage.
return imageWidths + (60 * imgs.length);
}
// this is called after each image load
function checkLoadingProgress() {
let containerWidth = document.getElementById('image-wrapper').clientWidth;
let imgsTotal = 0;
let imgsLoaded = 0;
// loop through rows
['row-1', 'row-2', 'row-3'].forEach(function(el, index) {
imgsTotal = document.querySelectorAll(`#image-wrapper .${el} img.set-img`).length;
imgsLoaded = document.querySelectorAll(`#image-wrapper .${el} img.set-img.image-loaded`).length;
// only process is all images have loaded for the given row
if (imgsLoaded > 0 && imgsLoaded == imgsTotal) {
processImageRows(el, containerWidth);
}
});
// finally all images have loaded. Updated loading class on container
let allImgsTotal = document.querySelectorAll(`#image-wrapper img.set-img`).length;
let allImgsLoaded = document.querySelectorAll(`#image-wrapper img.set-img.image-loaded`).length;
if (allImgsTotal == allImgsLoaded) {
document.getElementById('image-wrapper').classList.add('image-loaded');
document.getElementById('image-wrapper').classList.remove('image-loading');
}
}
// bind onload event to images
let imgs = document.querySelectorAll('img.set-img');
imgs.forEach(function(el, index) {
el.addEventListener('load', function() {
this.classList.add('image-loaded');
checkLoadingProgress();
}, false);
});
body {
margin: 10px;
}
.row {
margin-right: -4px;
margin-left: -4px;
}
.row .col-auto:first-child{
margin-left: 0!important; /* ADDED */
}
.row .col-auto:last-child{
margin-right: 0 !important; /* ADDED */
}
.row .col-auto{
margin-left: auto; /* ADDED */
margin-right:auto; /* ADDED */
}
.col-auto {
padding-right: 4px !important; /* ADDED !important */
padding-left: 4px !important; /* ADDED !important */
padding-bottom: 8px;
position: relative;
overflow: hidden;
cursor: pointer;
}
.image-wrapper.images-loading .col-auto {
position: absolute;
top: 0;
left: 0;
}
.image-wrapper.images-loaded .col-auto img {
max-width: 100%;
}
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap#4.5.3/dist/css/bootstrap.min.css" integrity="sha384-TX8t27EcRE3e/ihU7zmQxVncDAy5uIKz4rEkgIXeMed4M0jlfIDPvg6uqKI2xXr2" crossorigin="anonymous">
<script src="https://code.jquery.com/jquery-3.5.1.slim.min.js" integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj" crossorigin="anonymous"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap#4.5.3/dist/js/bootstrap.bundle.min.js" integrity="sha384-ho+j7jyWK8fNQe+A12Hb8AhRq26LrZ/JpcUGGOn+Y7RsweNrtN/tE3MoK7ZeZDyx" crossorigin="anonymous"></script>
<div class="container">
<div id="image-wrapper" class="images-loading">
<div class="row row-1">
<div class="col-auto">
<img src="https://via.placeholder.com/400x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/400x473.png" class="set-img" />
</div>
</div>
<div class="row row-2">
<div class="col-auto">
<img src="https://via.placeholder.com/473x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/1042x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/473x473.png" class="set-img" />
</div>
</div>
<div class="row row-3">
<div class="col-auto">
<img src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/474x473.png" class="set-img" />
</div>
<div class="col-auto">
<img src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
</div>
</div>
</div>
BEFORE EDIT:
From the point you know the container size or use flex box, no need to have js, you can simply use CSS by fixing a container as below:
.flexible-container{
max-height: 100%;
overflow:hidden;
position: relative;
}
And then set img with class w-100 and the below CSS:
.flexible-container img{
position: absolute;
left:50%;
top:50%;
transform: translate(-50%, -50%);
}
Images size will be respected and won't be stretch as the extra height will be hidden by container overflow: hidden;.
With class col so automatic width as you seems to have you are grid, pretty much either use grid directly or customize flex class as below:
.flex-15{
flex:1 1 15% !important;
}
.flex-30{
flex:1 1 30% !important;
}
DEMO:
.row-1, .row-2, .row-3{
height: 20vh;
margin-bottom: 10px;
}
.flexible-container{
max-height: 100%;
overflow:hidden;
position: relative;
}
.flexible-container img{
position: absolute;
left:50%;
top:50%;
transform: translate(-50%, -50%);
margin: 1px;
}
.flex-15{
flex:1 1 15% !important;
}
.flex-30{
flex:1 1 30% !important;
}
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap#4.5.3/dist/css/bootstrap.min.css" integrity="sha384-TX8t27EcRE3e/ihU7zmQxVncDAy5uIKz4rEkgIXeMed4M0jlfIDPvg6uqKI2xXr2" crossorigin="anonymous">
<div class="container">
<div class="row row-1">
<div class="col flexible-container">
<img class="w-100" src="https://via.placeholder.com/400x473.png" />
</div>
<div class="col flex-15 flexible-container">
<img class="w-100" src="https://via.placeholder.com/578x473.png" />
</div>
<div class="col flex-15 flexible-container">
<img class="w-100" src="https://via.placeholder.com/578x473.png" />
</div>
<div class="col flexible-container">
<img class="w-100" src="https://via.placeholder.com/400x473.png" />
</div>
</div>
<div class="row row-2">
<div class="col flexible-container">
<img class="w-100" src="https://via.placeholder.com/473x473.png" class="set-img" />
</div>
<div class="col flexible-container flex-30">
<img class="w-100" src="https://via.placeholder.com/1042x473.png" class="set-img" />
</div>
<div class="col flexible-container">
<img class="w-100" src="https://via.placeholder.com/473x473.png" class="set-img" />
</div>
</div>
<div class="row row-3">
<div class="col flexible-container flex-15">
<img class="w-100" src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
<div class="col flexible-container">
<img class="w-100" src="https://via.placeholder.com/473x473.png" class="set-img" />
</div>
<div class="col flexible-container flex-15">
<img class="w-100" src="https://via.placeholder.com/578x473.png" class="set-img" />
</div>
</div>
</div>

Why does my slider go blank after reaching the end?

I'm having a two issues/problems with the following slide.
It is a "double slider", so, two simultaneous slider in body section.
First is that when i reach the last image (9-nth, cos that much both sliders contain), the second slider continues to work properly (sliding images infinitely) but the first one just get blank.
Or if i click on previous button on begining then second doesn't work and images disapear, while the first one work nicely. Can't figure it out why. I've tried changing the "id" in the HTML and styling it but nothing change.
Second is, that i finally need to make it more dynamic, so, to avoid hardcoding images in the HTML and to putt them in JS and somehow append them in the DOM, but don't know what exactlly to do; creating an array, or using the "createElement"?
And which logic could be usable to actually include them in the DOM and have the following slider(s), considering the provided code?
Since it's my just second slider which i'm making, i found it pretty much hard, so any help/hint/advice is welcomed.
P.S Must be in jQuery and plugins excluded, so please don't provide any plugins links.
Thank you in advance.
var slides = $('.slide');
slides.first().before(slides.last());
$('button').on('click', function() {
// Selecting the slides
slides = $('.slide');
// Selecting button
var button = $(this);
// Register active slide
var activeSlide = $('.active');
// Next function
if (button.attr('id') == 'next') {
slides.last().after(slides.first());
activeSlide.removeClass('active').next('.slide').addClass('active');
}
// Previous function
if (button.attr('id') == 'previous') {
slides.first().before(slides.last());
activeSlide.removeClass('active').prev('.slide').addClass('active');
}
});
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
.slider {
position: relative;
width: 100%;
height: 300px;
overflow: hidden;
}
.slide {
width: 100%;
height: 300px;
position: absolute;
transition: 0.6s ease;
transform: translate(-100%, 0);
}
.slide img {
width: 100%;
height: 300px;
}
.slide.active {
transform: translate(0, 0);
}
.slide.active~.slide {
transform: translate(100%, 0);
}
body {
text-align: center;
}
button {
margin-top: 20px;
border: none;
border-radius: 0;
background: aqua;
color: #333;
padding: 10px;
cursor: pointer;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="slider">
<div class="slide active">
<img src="Assets/slider-image-1.jpg" alt="">
</div>
<div class="slide">
<img src="Assets/slider-image-2.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-3.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-4.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-5.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-6.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-7.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-8.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-9.jpg">
</div>
</div>
<div class="slider">
<div class="slide active">
<img src="Assets/slider-image-1.jpg" alt="">
</div>
<div class="slide">
<img src="Assets/slider-image-2.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-3.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-4.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-5.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-6.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-7.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-8.jpg">
</div>
<div class="slide">
<img src="Assets/slider-image-9.jpg">
</div>
</div>
<button id="previous"><img src="Assets/arrow-blue-left.png" alt=""></button>
<button id="next"><img src="Assets/arrow-blue-right.png" alt=""></button>
Your code doesn't work properly because the slides = $('.slide') variable contains all slides from both sliders. You have to manipulate the slides in the to sliders independently. The second failure is that in your example the first slide is the initial active slide. Only slides in range second -> penultimate are allowed. Working example here
function handleSlide(slider, direction) {
var slides = $(slider).find('.slide');
if(slides.length < 1) return;
// Register active slide
var activeSlide = $(slider).find('.active');
// Next function
if (direction == 'next') {
slides.last().after(slides.first());
activeSlide.removeClass('active').next('.slide').addClass('active');
}
// Previous function
if (direction == 'previous') {
slides.first().before(slides.last());
activeSlide.removeClass('active').prev('.slide').addClass('active');
}
}
$('button').on('click', function() {
var button = $(this);
handleSlide($("#slider1"), $(button).attr('id'));
handleSlide($("#slider2"), $(button).attr('id'));
});
Loading images dinamically: You can do that by defining an array which contains the images and you can append the images into the slider using the jQuery 'append' method. Working example on jsFiddle.
function fillSliders(slider, images) {
$(slider).empty();
for(var i = 0; i < images.length; i++) {
if(typeof images[i] == "string" && images[i] !== "") {
var active = (i == 1) ? " active" : "";
$(slider).append('<div class="slide'+active+'"><img src="'+images[i]+'"
alt="image-'+i+'" /></div>');
}
}
}
var images = ["image1.jpg", "image2.jpg","image3.jpg","image4.jpg"];
fillSliders($("#slider"), images);

Hi, I'm trying to replicate an event listener with different elements on my page, pairing different elements with different keys

const input = document.querySelector('input');
document.addEventListener('keydown', logKey);
function logKey(e) {
if(e.code == 'KeyB') {
var tag = document.querySelector('.batman');
tag.classList.toggle('active');
}
}
body {display:flex; flex-flow:row wrap; align-items:center; justify-content:center; background:#333 url(https://images.unsplash.com/photo-1475862013929-0af29a1197f4?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=2534&q=80) fixed 50% 50%/ cover; }
.holo {margin:0 10px 20px 10px; xwidth:300px; xheight:200px; border:5px solid rgba(0,100,200,0.5); border-radius:20px; text-align:center; color:rgba(0,100,200,0.9); background:rgba(0,0,0,0.7); transform:scale(1.0);}
.holo:hover, .holo.active {background:rgba(30,30,30,0.8); transition-duration:0.5s; transform:scale(1.1);}
.holo h1 {font:bold 30px Arial; text-transform:uppercase;}
.holo img {width:100%; width:300px; margin:10px; border-radius:20px;}
<div class="holo batman active">
<h1>Batman</h1>
<img src="https://images.unsplash.com/photo-1509347528160-9a9e33742cdb?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Spiderman</h1>
<img src="https://images.unsplash.com/photo-1521714161819-15534968fc5f?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Iron Man</h1>
<img src="https://images.unsplash.com/photo-1509817445409-e2057fd6feac?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Thor</h1>
<img src="https://images.unsplash.com/photo-1495044245703-b07f266e47b4?ixlib=rb-1.2.1&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Spiderman 2</h1>
<img src="https://images.unsplash.com/photo-1505925456693-124134d66749?ixlib=rb-1.2.1&auto=format&fit=crop&w=2550&q=80">
</div>
<div class="holo">
<h1>The Dark Knight</h1>
<img src="https://images.unsplash.com/photo-1519740296995-10d3d8267019?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Avengers</h1>
<img src="https://images.unsplash.com/photo-1471877325906-aee7c2240b5f?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>WonderWoman</h1>
<img src="https://images.unsplash.com/photo-1517242296655-0a451dd85b30?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo">
<h1>Spiderman 3</h1>
<img src="https://images.unsplash.com/photo-1534375971785-5c1826f739d8?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
I want to use an event listener to get every element on the page to respond to a keypush - however, I'm having problems replicating the Javascript code for each element, it just won't work.
const input = document.querySelector('input');
document.addEventListener('keydown', logKey);
function logKey(e) {
if(e.code == 'KeyB') {
var tag = document.querySelector('.batman');
tag.classList.toggle('active');
}
}
I want to use a different key - say 'KeyA' for a different element - say '.spiderman'. I've tried replicating the code above with these replacements, but this hasn't worked.
What's the best way to achieve this?
Your forgot to assign each separate div a classname. I added the names for all of them, but only tied in batman and spiderman (b and s keys). Try it out, and you can easily add the rest of them.
const input = document.querySelector('input');
document.addEventListener('keydown', logKey);
function logKey(e) {
if(e.code == 'KeyB') {
var tag = document.querySelector('.batman');
tag.classList.toggle('active');
console.log('B clicked')
}
if (e.code == 'KeyS') {
var tag = document.querySelector('.spiderman');
tag.classList.toggle('active');
console.log('S clicked')
}
}
body {display:flex; flex-flow:row wrap; align-items:center; justify-content:center; background:#333 url(https://images.unsplash.com/photo-1475862013929-0af29a1197f4?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=2534&q=80) fixed 50% 50%/ cover; }
.holo {margin:0 10px 20px 10px; xwidth:300px; xheight:200px; border:5px solid rgba(0,100,200,0.5); border-radius:20px; text-align:center; color:rgba(0,100,200,0.9); background:rgba(0,0,0,0.7); transform:scale(1.0);}
.holo:hover, .holo.active {background:rgba(30,30,30,0.8); transition-duration:0.5s; transform:scale(1.1);}
.holo h1 {font:bold 30px Arial; text-transform:uppercase;}
.holo img {width:100%; width:300px; margin:10px; border-radius:20px;}
<div class="holo batman">
<h1>Batman</h1>
<img src="https://images.unsplash.com/photo-1509347528160-9a9e33742cdb?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo spiderman">
<h1>Spiderman</h1>
<img src="https://images.unsplash.com/photo-1521714161819-15534968fc5f?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo ironman">
<h1>Iron Man</h1>
<img src="https://images.unsplash.com/photo-1509817445409-e2057fd6feac?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo thor">
<h1>Thor</h1>
<img src="https://images.unsplash.com/photo-1495044245703-b07f266e47b4?ixlib=rb-1.2.1&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo spiderman2">
<h1>Spiderman 2</h1>
<img src="https://images.unsplash.com/photo-1505925456693-124134d66749?ixlib=rb-1.2.1&auto=format&fit=crop&w=2550&q=80">
</div>
<div class="holo darkknight">
<h1>The Dark Knight</h1>
<img src="https://images.unsplash.com/photo-1519740296995-10d3d8267019?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo avengers">
<h1>Avengers</h1>
<img src="https://images.unsplash.com/photo-1471877325906-aee7c2240b5f?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo wonderwoman">
<h1>WonderWoman</h1>
<img src="https://images.unsplash.com/photo-1517242296655-0a451dd85b30?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>
<div class="holo spiderman3">
<h1>Spiderman 3</h1>
<img src="https://images.unsplash.com/photo-1534375971785-5c1826f739d8?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=1050&q=80">
</div>

Dynamically cover 2 divs with CSS

I have 2 divs that I need a shade over after a user action. The divs are just two divs next to each other:
<div class="bought">content</div>
<div class="class2">content</div>
Here is the CSS which is made visible via jQuery:
#view-hint .body > .img .bought {
display:none;
cursor:pointer;
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
z-index:2;
background: rgba(0,0,0,0.75);
}
When the event fires this is what it looks like:
That bottom white area needs to be covered dynamically as well.
The approach I thought to take was to wrap both div's in another div but it breaks the look of everything. So I tried to make the top div longer based off size but it's still not perfect...
var originalHeight = $('.bought').height();
var windowWidth = $(window).width();
if (windowWidth < 710) {
$('.bought').css('height', originalHeight * 0.6);
} else if (windowWidth > 710 && windowWidth < 1000) {
$('.bought').css('height', originalHeight * 0.698);
} else if (windowWidth > 1000 && windowWidth < 1300) {
$('.bought').css('height', originalHeight * 0.699);
} else if (windowWidth > 1300 && windowWidth < 1600) {
$('.bought').css('height', originalHeight * 0.865);
} else if (windowWidth > 1600 && windowWidth < 2000) {
$('.bought').css('height', originalHeight * 1.035);
} else {
$('.bought').css('height', "662px");
}
This mostly works for all size screens, but if you change the zoom it still causes issues.
How can I make it where both of these divs are covered by the CSS dynamically?
Edit:
Here is the full HTML with an added wrapper and an image that results:
<div id="test123">
<div class="bought">
<div class="row">
<div class="col">
<div class="body">
<?php if(Request::is('user/*')) { ?>
<div id="boughtquestion">Did you buy this for <?php echo $user->firstName ?>?</div>
<div class="options">
<!-- <a id="boughtyes" class="cbutton whiteonpurple" onclick="markPurchased(event)">Yes</a> -->
<a id="boughtyes" class="cbutton whiteonpurple">Yes</a>
<a id="boughtno" class="cbutton whiteonpurple">No</a>
</div>
<?php } else { ?>
<div>Bought?</div>
<p>Click here to send hinters a message to let them know.<br />And yes, it can still be a surprise!</p>
<?php } ?>
</div>
</div>
</div>
</div>
<div class="markedaspurchased">
<div class="row">
<div class="col">
<div class="body">
<div id="markedpurchased">Marked as Purchased</div>
<p id="markedmessage">Marking as purchased prevents duplicate gift giving. Dont worry <?php echo $user->firstName ?> doesn't get notified but you can let <?php echo ($user->gender == 'female' ? 'him' : 'her') ?> know by sending a message!</p>
<p><a id="sendmessagebutton" class="cbutton whiteonpurple purchasebutton">Send message to let them know</a></p>
<p><a id="anonymousbutton" class="cbutton whiteonpurple purchasebutton">Send anonymous message</a></p>
<p><a id="secretbutton" class="cbutton whiteonpurple purchasebutton">Keep it a secret</a></p>
</div>
</div>
</div>
</div>
</div>
<p class="description"></info-coverp>
<div class="options">
<a class="buy cbutton whiteonpurple" target="_blank">Buy</a>
<a class="hint cbutton whiteonblack" target="_blank">Hint</a>
</div>
<div class="info">
<div class="bar"></div>
<div class="rehints">10 REHINTS</div>
<div class="hinter">
<div class="picture monophoto">
<div class="text">BO</div>
<div class="img" style="background-image: url();" onclick=""></div>
</div>
<div class="content">
<div class="one">Hinted by:</div>
<div class="two"></div>
</div>
</div>
<div class="partnertext">Partnered Hint</div>
<div style="clear:both;"></div>
</div>
</div>
Since you're using Jquery, why not give the divs a separate class and then use .wrapAll to create a wrapper...then position the overlay on top of that.
$(".wrapped").wrapAll('<div class="overlay" />');
.overlay {
display: inline-block;
position: relative;
}
.overlay::after {
content: '';
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.5);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="wrapped bought">content 1</div>
<div class="wrapped class2">content 2</div>

Cannot update Offset using JQuery in Internet Explorer 10

I'm trying to set an the offset of an element.
The code works ok in Chrome but i can't get the offset to change in IE;
this.moveH = function (e) {
if (this.target != null){
console.log(this.target.offset())
this.target.offset({
left: e.pageX - this.target.outerWidth(true) / 2,
top: e.pageY - this.target.outerHeight(true) / 2
});
}
console.log(this.target.offset())
e.preventDefault();
}
If i run in chrome the first console.log is different from the second. If i run in IE it never changes.
Thank you
Update 1
The offset function is the one from JQuery
Update 2 Added HTML and CSS
*{
margin:0px;
left:0px;
right:0px;
}
#applet {
position: absolute;
width: 700px;
height: 520px;
direction:ltr;
text-align: center;
}
#puzzle{
top:80px;
left:20px;
position:absolute;
}
.left-column{
position:absolute;
width:388px;
}
.left-puzzle{
margin-top:10px;
width:388px;
background-image:url("../images/left_puzzle.png");
height:83px;
}
.left-puzzle p{
margin-right:194px;
}
.right-column{
float:right;
left:500px;
width:182px;
margin-right:10px;
}
.targets{
left:206px;
top:1px;
width:194px;
position:absolute;
}
.target{
margin-top:10px;
width:194px;
height:83px;
}
.right-puzzle{
margin-top:10px;
width:182px;
height:82px;
background-image:url("../images/right_puzzle.png")
}
#bg{
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
HTML
<div id='applet'>
<img id='bg' src='images/background.jpg' />
<div id="puzzle">
<div class="left-column">
<div class="left-puzzle">
<p>يبدأ خلف الشرج ولدى بعض الحبليات ذيل يوجد في مرحلة الجنين فقط.</p>
</div>
<div class="left-puzzle">
<p>يمتد بطول الظهر وهو مليء بالسائل عند الفقاريات ويطلق عليه اسم الحبل الشوكي .</p>
</div>
<div class="left-puzzle">
<p>تتطور إلى خياشيم أو إلى أجزاء أخرى من الجسم أثناء تطور الجنين .</p>
</div>
<div class="left-puzzle">
<p>قضيب صلب لكنه مرن يدعم الجسم وفي الفقاريات يحل محله عمود فقري .</p>
</div>
</div>
<div class="targets">
<div class="target drop" id="t1"></div>
<div class="target drop" id="t2"></div>
<div class="target drop" id="t3"></div>
<div class="target drop" id="t4"></div>
</div>
<div class="right-column">
<div id="d1" class="right-puzzle drag" data-target-id="t2">
<p>الحبل العصبي المجوف</p>
</div>
<div id="d2" class="right-puzzle drag" data-target-id="t1">
<p>الذيل</p>
</div>
<div id="d3" class="right-puzzle drag" data-target-id="t3">
<p>الجيوب البلعومية </p>
</div>
<div id="d4" class="right-puzzle drag" data-target-id="t4">
<p>الحبل الظهري</p>
</div>
</div>
</div>
</div>
Try using native javascript instead.
Use obj.offsetLeft and obj.offsetTop. It should work in IE as well. Looks like a cross browser issue to me.

Categories

Resources