So i have been trying to build this accordion component for a review section for a couple of days...I'm really new to javascript and have figured it out mostly except the review section that collapses out is being shown in the initial state so on a page reload you see the section expanded right away, and only is hidden when you click the expand arrow. I would rather it be hidden on the initial state so it only is shown after the user clicks the expand arrow.
I have a div with the class="reviewsHide" as a wrapper and another div with the class="reviewsActive" as a wrapper. Its written in sass and any solution i try to come up with in targeting the wrapper with javascript doesn't apply its children class styles so it ends up not looking right. Inside the main container wrappers i have 3 more container sections each is its own container. with a couple of classes inside each of those containers.
<div class="reviewsHide">
<div class="reviewsActive">
<div class="reviewsActive__top">
<button href="#" class="reviewsActive__top-smallTxt">Write A Review →</button>
<span class="reviewsActive__top-largeTxt">Reviews(10)</span>
<button href="#" class="reviewsActive__top-smallTxt">More Reviews →</button>
</div>
<div class="reviewsActive__bottomL">
<div class="reviewsActive__bottomL-title">
<img class="starSmall"src="img/main/StarRating.svg" alt="Star Rating"> Title
</div>
<p class="reviewsActive__bottomL-reviewP">
  Lorem ipsum dolor sit amet consectetur adipisicing elit. Perferendis, dolorem quae! Quidem officiis rerum nam, veritatis ullam, placeat est doloremque exercitationem, a quis sequi tempora blanditiis eligendi consequuntur. Ipsam a hic eligendi? Facilis vero fugit omnis ducimus inventore ipsam libero ad expedita numquam, ullam delectus ratione modi, atque esse veritatis.
</p>
</div>
<div class="reviewsActive__bottomR">
<div class="reviewsActive__bottomR-title">
<img class="starSmall"src="img/main/StarRating.svg" alt="Star Rating"> Title
</div>
<p class="reviewsActive__bottomR-reviewP">
  Lorem ipsum dolor sit amet consectetur adipisicing elit. Perferendis, dolorem quae! Quidem officiis rerum nam, veritatis ullam, placeat est doloremque exercitationem, a quis sequi tempora blanditiis eligendi consequuntur.
</p>
</div>
</div>
</div>
.reviewsHide.show {
height: 15rem;
display: none;
}
.reviewsActive {
display: flex;
flex-direction: row;
flex-wrap: wrap;
background-color: white;
height: 22.5rem;
font-family: 'Montserrat Alternates', sans-serif;
&__top {
display: flex;
flex-direction: row;
justify-content: space-evenly;
align-items: center;
height: 3rem;
width: 100%;
&-smallTxt {
cursor: pointer;
font-size: 1.05rem;
}
&-largeTxt {
font-size: 2rem;
}
}
&__bottomL {
#include reviewsBottom;
margin: auto 1rem .75rem 1rem;
&-title {
#include reviewsTitle;
}
&-reviewP {
#include reviewsParagraph;
}
}
&__bottomR {
#include reviewsBottom;
margin: 1rem 1rem .75rem auto;
&-title {
#include reviewsTitle;
}
&-reviewP {
#include reviewsParagraph;
}
}
}
// Get the button, and when the user clicks on it, execute myFunction
document.querySelector(".span").onclick = function() {myFunction()};
/* myFunction toggles between adding and removing the show class, which is used to hide and show the dropdown content */
function myFunction() {
document.querySelector(".reviewsHide").classList.toggle("show");
/* This selector below is for the arrow animation to rotate on click */
document.querySelector(".span").classList.toggle("spanshow");
}
Re-wrote my javascript to this and its working as intended
const reviewsOpen = () => {
var expandArrow = document.querySelector(".span");
var hide = document.querySelector(".reviewsHide");
expandArrow.addEventListener('click', () => {
hide.classList.toggle("reviewsHide");
expandArrow.classList.toggle("spanshow")
});
}
reviewsOpen();
Related
I am trying to create a parallax effect on the background image when I move the slider. I decided to just change the position of the background on the image, but I'm not entirely sure that's a good solution. Please tell me how to improve such an effect so that the picture on the background moves more smoothly, so that it is really called parallax.
const p = document.getElementById("price");
const bg = document.getElementById("bg");
p.addEventListener("input", function() {
bg.style.backgroundPosition = `${p.value}% 50%`;
}, false);
.parent {
display: flex;
width: 500px;
height: 300px;
justify-content: center;
align-items: center;
background-image: url('https://wallpaperaccess.com/full/99840.jpg');
background-size: cover;
background-repeat: no-repeat;
}
.child {
width: 50%;
background-color: #fff;
padding: 5%;
}
<input id="price" type="range" value="" />
<div class="parent" id="bg">
<div class="child">
Lorem ipsum dolor sit amet, consectetur adipisicing elit. Nam officia voluptatem, sint voluptatibus. Cumque vel voluptatem voluptatibus quisquam corporis nam, fugit maxime, architecto similique natus, ipsam enim eveniet recusandae odio.
</div>
</div>
So this div doesn't respond when I click on the h3 inside it or on the span
I used flex box in the "question-title" div, I guess that what causes the problem, is there a way I can make this div showing more/less when I click on it, not specifically outside h3 and the span, because it only works when I click in the space between h3 and the span.
let downBtn = document.querySelectorAll(".main-question .question-title");
downBtn.forEach(dbtn => {
dbtn.addEventListener("click", (e)=> {
let paragraphElement = e.target.parentNode.querySelector("p");
paragraphElement.classList.toggle("showHide");
let spanSign = dbtn.querySelector("span");
if (paragraphElement.classList.contains("showHide")) {
spanSign.innerHTML = "--";
} else {
spanSign.innerHTML = "+";
}
});
});
.question {
width: 60%;
margin: 0 auto;
}
.part-one h3 {
color: var(--main-color);
font-size: 30px;
margin: 0 0 20px;
}
.main-question {
margin: 20px auto;
padding: 20px;
text-align: center;
border: 1px solid rgb(207, 207, 207);
border-radius: 6px;
position: relative;
overflow: hidden;
}
.main-question h4 {
margin: 0;
color: #607d8b;
}
.main-question h4::selection {
background-color: transparent;
}
.main-question p {
margin: 34px 0 0;
text-align: justify;
color: var(--main-color2);
display: none;
}
.main-question p.showHide {
display: block;
}
.question-title {
display: flex;
justify-content: space-between;
align-items: center;
cursor: pointer;
position: absolute;
top: 0;
left: 0;
height: 20%;
width: 100%;
background-color: #EEE;
padding: 20px;
}
.question-title span {
font-size: 20px;
font-weight: bold;
color: #607d8b;
letter-spacing: -3px;
}
.question-title span::selection {
background-color: transparent;
}
<!-- Start questions -->
<div class="container">
<div class="question">
<div class="part-one">
<h3>Some Frequent Questions</h3>
<div class="main-question">
<div class="question-title">
<h4>Lorem ipsum dolor sit amet consectetur adipisicing elit</h4>
<span>+</span>
</div>
<p>Lorem ipsum dolor sit amet consectetur, adipisicing elit. Dolorum fugiat ullam molestias dignissimos deleniti inventore aspernatur nam excepturi vitae nihil, temporibus accusantium tempore deserunt error libero, itaque earum sapiente sequi.</p>
</div>
<div class="main-question">
<div class="question-title">
<h4>Lorem ipsum dolor sit amet consectetur adipisicing elit</h4>
<span>+</span>
</div>
<p>Lorem ipsum dolor sit amet consectetur, adipisicing elit. Dolorum fugiat ullam molestias dignissimos deleniti inventore aspernatur nam excepturi vitae nihil, temporibus accusantium tempore deserunt error libero, itaque earum sapiente sequi.</p>
</div>
<div class="main-question">
<div class="question-title">
<h4>Lorem ipsum dolor sit amet consectetur adipisicing elit</h4>
<span>+</span>
</div>
<p>Lorem ipsum dolor sit amet consectetur, adipisicing elit. Dolorum fugiat ullam molestias dignissimos deleniti inventore aspernatur nam excepturi vitae nihil, temporibus accusantium tempore deserunt error libero, itaque earum sapiente sequi.</p>
</div>
</div>
</div>
</div>
<!-- End questions -->
Your issue here is this line of code:
let paragraphElement = e.target.parentNode.querySelector("p");
Since you didn't set the indentations on your HTML properly, I didn't notice this issue in the first place.
You need to use this instead:
let paragraphElement = e.target.closest(".main-question").querySelector("p")
The answer of your question in the comment is NO, but when you click h4, you also click div because they are occupying the same area, unless you added stopPropagation to your function. But "e.target" is the item you clicked directly. If it's h4, its parentNode is "question-title" and it has no "p" child.
When you work with JS, always use console.log(). You can see the problem most of the time.
//This part is not necessary because the class "showHide" will be toggled below
document.querySelectorAll(".main-question").forEach(el ...
Also change your CSS for ".question-title" => "justify-content: space-around;" to show the icon
let downBtn = document.querySelectorAll(".main-question .question-title");
downBtn.forEach(dbtn => {
dbtn.addEventListener("click", (e) => {
let paragraphElement = e.target.parentNode.parentNode.querySelector("p");
paragraphElement.classList.toggle("showHide");
let spanSign = dbtn.querySelector("span");
if (paragraphElement.classList.contains("showHide")) {
spanSign.innerHTML = "--";
} else {
spanSign.innerHTML = "+";
}
});
});
I'd like for users to be able scroll horizontally across text in a React component, but I'd like to still have some bounded width that's larger than the component's bounding rectangle. This way, I could just have regular paragraphs without worrying about any line breaking on-the-fly. I know I would need to set the overflow-x property to auto, but I'm not sure what to do past that. Thanks for the help!
Here would be my solution.
body {
width: 100%;
max-width: 800px;
margin: 30px auto;
}
.wrapper {
border: 1px solid #afafaf;
width: 100%;
overflow-x: scroll;
box-sizing: border-box;
}
.inner {
padding: 10px;
width: 130%;
}
<div class="wrapper">
<div class="inner">Lorem ipsum dolor sit amet consectetur adipisicing elit. Ex labore, provident dolorum repellendus earum aliquid voluptatem nobis odit. Deserunt corrupti repellendus voluptate harum quaerat adipisci aut sequi consequuntur voluptas cum?</div>
</div>
I am basically transferring existing slider from existing site to a new one, and I didn't want to waste additional time by figuring out how to create a text slider from scratch, since the client wants the same thing on his new site.
I found the code and modified it a bit to work on the new site. Except it doesn't really works as it should. The slider looks like this:
var counter = 1;
var total_width = 0;
function slider_total_width() {
$('.items a').each(function() {
total_width += parseInt($(this).width(), 10);
});
$('.items').width(total_width);
}
slider_total_width();
function job_slider(wrapper) {
var first_link = $('#active');
var width = first_link.width();
$(wrapper + ' a').each(function() {
total_width += $(this).width() + 50;
});
first_link.removeAttr('id');
$(wrapper).animate({
left: '-=' + width
}, 1000, function() {
$(first_link).clone().appendTo(wrapper);
$(first_link).css('color', 'transparent');
var links = $(wrapper + ' a');
var new_first_link = links[counter];
counter++;
$(new_first_link).attr('id', 'active');
$(wrapper).width(total_width);
total_width = 0;
});
}
var activate = function() {
job_slider('.items');
};
var interval = setInterval(activate, 5000);
$('.items').hover(function() {
clearInterval(interval);
}, function() {
interval = setInterval(activate, 5000);
});
.container {
margin: 0 auto;
width: 700px;
}
a {
text-decoration: none;
}
#ads_scroller .container {
font-size: 0;
position: relative;
}
#ads_scroller .icon_holder {
display: inline-block;
width: 3%;
margin-top: 8px;
}
#ads_scroller .icon_holder i {
font-size: 22px;
color: #fe9700;
}
#ads_scroller .scroller_container {
display: inline-block;
overflow: hidden;
vertical-align: top;
width: 97%;
height: 31px;
position: relative;
}
#ads_scroller .scroller_container .items {
position: relative;
display: block;
}
#ads_scroller .scrollable_title {
position: relative;
color: #727272;
font-size: 14px;
font-weight: 400;
line-height: 41px;
display: inline;
white-space: nowrap;
padding: 0 0 0 2px;
box-sizing: border-box;
}
#ads_scroller .scrollable_title:last-of-type {
margin-right: 0;
}
#ads_scroller #active.scrollable_title {
color: #1a171b;
}
#ads_scroller .scrollable_title:hover {
color: #555;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
<div id="ads_scroller">
<div class="container">
<div class="icon_holder"><i class="fa fa-bell-o"></i>
</div>
<div class="scroller_container">
<div class="items" style="width: 2642px;">
Lorem ipsum dolor sit amet –
Consectetur adipisicing elit –
Incidunt tempore explicabo ea autem, eligendi excepturi –
Sapiente sint officiis non minima ex –
Tenetur provident, ipsum dignissimos autem earum nobis dolor –
Obcaecati iste animi cumque culpa –
Vero asperiores illum rerum –
Test to see how announcements look –
</div>
</div>
</div>
</div>
Now I think I know what the issue is, but I don't know how to fix it. For some reason, my .items wrapper, if it doesn't have set width, won't have all the links in one line, so after a while I won't have any links inside to scroll.
Strangely this isn't set on the client side and I couldn't figure out what css rule they used that will allow this (move to left infinitely without width being set). So to circumvent this I'm calculating total width, and then setting it each time the slider clones the element that passed.
But what this does (at least that's my guess) is that after a while the gap between the .items wrapper start on the left (where the icon is), and the link that slides in, becomes progressively bigger. After a minute or so the gap becomes really big.
So is there a way to prevent this? What am I doing wrong here? :\
Hi try this sample i hope it help you
<html>
<head>
<title>Demo Slider</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.0.1/js/bootstrap.min.js"></script>
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css"/>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.0.1/css/bootstrap.min.css" />
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body>
<div class="container">
<div class="carousel slide carousel-fade" data-ride="carousel">
<div class="carousel-inner">
<div class="item active" >
<div class="caption">
Lorem ipsum dolor sit amet –
Consectetur adipisicing elit –
Incidunt tempore explicabo ea autem, eligendi excepturi –
Sapiente sint officiis non minima ex –
Tenetur provident, ipsum dignissimos autem earum nobis dolor –
Obcaecati iste animi cumque culpa –
Vero asperiores illum rerum –
Test to see how announcements look –
</div>
</div>
<div class="item " >
<div class="caption">
Lorem ipsum dolor sit amet –
Consectetur adipisicing elit –
Incidunt tempore explicabo ea autem, eligendi excepturi –
Sapiente sint officiis non minima ex –
Tenetur provident, ipsum dignissimos autem earum nobis dolor –
Obcaecati iste animi cumque culpa –
Vero asperiores illum rerum –
Test to see how announcements look –
</div>
</div>
<div class="item" >
<div class="caption">
Lorem ipsum dolor sit amet –
Consectetur adipisicing elit –
Incidunt tempore explicabo ea autem, eligendi excepturi –
Sapiente sint officiis non minima ex –
Tenetur provident, ipsum dignissimos autem earum nobis dolor –
Obcaecati iste animi cumque culpa –
Vero asperiores illum rerum –
Test to see how announcements look –
</div>
</div>
</div>
</div>
</div>
</body>
</html>
You can try outerwidth() instead of width() as I think the solution is to add +2px to the width which is actually the padding-left of each anchor item.
var counter = 1;
var total_width = 0;
function slider_total_width() {
$('.items a').each(function() {
total_width += parseInt($(this).outerWidth(), 10);
});
$('.items').width(total_width);
}
slider_total_width();
function job_slider(wrapper) {
var first_link = $('#active');
var width = first_link.outerWidth();
$(wrapper + ' a').each(function() {
total_width += $(this).width() + 50;
});
first_link.removeAttr('id');
$(wrapper).animate({
left: '-=' + width
}, 1000, function() {
$(first_link).clone().appendTo(wrapper);
$(first_link).css('color', 'transparent');
var links = $(wrapper + ' a');
var new_first_link = links[counter];
counter++;
$(new_first_link).attr('id', 'active');
$(wrapper).width(total_width);
total_width = 0;
});
}
var activate = function() {
job_slider('.items');
};
var interval = setInterval(activate, 5000);
$('.items').hover(function() {
clearInterval(interval);
}, function() {
interval = setInterval(activate, 5000);
});
.container {
margin: 0 auto;
width: 700px;
}
a {
text-decoration: none;
}
#ads_scroller .container {
font-size: 0;
position: relative;
}
#ads_scroller .icon_holder {
display: inline-block;
width: 3%;
margin-top: 8px;
}
#ads_scroller .icon_holder i {
font-size: 22px;
color: #fe9700;
}
#ads_scroller .scroller_container {
display: inline-block;
overflow: hidden;
vertical-align: top;
width: 97%;
height: 31px;
position: relative;
}
#ads_scroller .scroller_container .items {
position: relative;
display: block;
}
#ads_scroller .scrollable_title {
position: relative;
color: #727272;
font-size: 14px;
font-weight: 400;
line-height: 41px;
display: inline;
white-space: nowrap;
padding: 0 0 0 2px;
box-sizing: border-box;
}
#ads_scroller .scrollable_title:last-of-type {
margin-right: 0;
}
#ads_scroller #active.scrollable_title {
color: #1a171b;
}
#ads_scroller .scrollable_title:hover {
color: #555;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
<div id="ads_scroller">
<div class="container">
<div class="icon_holder"><i class="fa fa-bell-o"></i>
</div>
<div class="scroller_container">
<div class="items" style="width: 2642px;">
Lorem ipsum dolor sit amet –
Consectetur adipisicing elit –
Incidunt tempore explicabo ea autem, eligendi excepturi –
Sapiente sint officiis non minima ex –
Tenetur provident, ipsum dignissimos autem earum nobis dolor –
Obcaecati iste animi cumque culpa –
Vero asperiores illum rerum –
Test to see how announcements look –
</div>
</div>
</div>
</div>
I've got a responsive site I'm building Where I have two elements that overlap each other. THe size of the elements will change depending on the browser width as will the overlap and consequently I need to set left-padding on the right element dynamically.
I'm unsure of how to proceed with this. Have set up a Fiddle here.
html:
<div class="container">
<div class="row copy intro">
<section class="red">
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Dolor illum nobis ullam neque, harum, magni. Reprehenderit veritatis in deleniti incidunt dolore dolores ex id expedita.</p>
<p>Corporis soluta ducimus ut quasi libero nesciunt, eligendi autem, consequatur error sapiente labore, officia tempora in voluptas non deleniti veniam officiis, quis vero consequuntur quia!</p>
</section>
<section class="white">
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Dolor illum nobis ullam neque, harum, magni. Reprehenderit veritatis in deleniti incidunt dolore dolores ex id expedita.</p>
<p>Corporis soluta ducimus ut quasi libero nesciunt, eligendi autem, consequatur error sapiente labore, officia tempora in voluptas non deleniti veniam officiis, quis vero consequuntur quia!</p>
</section>
</div>
</div><!--container-->
css:
/* line 3, ../build/sass/_intro.scss */
.intro {
background: #0079c2;
position: relative;
padding: 15px;
padding-bottom: 150px;
}
/* line 9, ../build/sass/_intro.scss */
.intro section {
position: relative;
padding: 100px;
width: 60%;
-moz-border-radius: 500px;
-webkit-border-radius: 500px;
border-radius: 500px;
}
/* line 26, ../build/sass/_intro.scss */
.intro section.red {
background: rgba(238, 45, 36, 0.85);
color: #fff;
z-index: 200;
}
/* line 31, ../build/sass/_intro.scss */
.intro section.red h1 {
font-size: 24px;
}
/* line 45, ../build/sass/_intro.scss */
.intro section.white {
background: #fff;
color: #0079c2;
position: absolute;
top: 150px;
right: 15px;
}
js:
// set intro sections width = height
$(document).ready(function() {
var circleWidth= $('.intro section.red').outerWidth();
$('.intro section').css('min-height', circleWidth + 'px');
$('.intro section.white').css('width', circleWidth + 'px');
});
Thank you for your time.
Use % for padding and adjust accordingly. See this revised Fiddle for an example.
The revised Fiddle comments out:
$('.intro section.white').css('width', circleWidth + 'px');
Fixing the width of the white circle means that it is not responsive any more. If you need to do that for some reason, you would have to make adjustments.
Here's a JSFiddle doing what I think you want: http://jsfiddle.net/6yro5vhx/2/
Basically I user offset() & outerWidth() on the two elements to work out the overlap, and then call calculatePadding() function on documentready & resize events.
function calculatePadding() {
var white = $('.intro section.white');
var red = $('.intro section.red');
var extraPadding = 20;
var distanceLeft = white.offset().left;
var redDistanceRight = red.offset().left + red.outerWidth();
var paddingLeft = (redDistanceRight - distanceLeft) + extraPadding;
$('.intro section.white').css('padding-left', paddingLeft + 'px');
}
Update the answer below mine is a far better way to achieve what you're looking for. CSS is a much better responsive approach than excess JQuery.