Toggle Visibility Not Working (HTML/CSS/Javascript) [duplicate] - javascript

This question already has answers here:
What do querySelectorAll and getElementsBy* methods return?
(12 answers)
Closed 4 years ago.
I am following this tutorial from W3Schools on how to build a slideshow using HTML, CSS, and Javascript. On the website I am developing, I would like the thumbnails at the bottom and the arrows on the sides to be initially hidden, until the user presses a button.
To do so, in the CSS file, I have set the visibility: hidden;. The CSS code for the class dot, which is the bottom thumbnail, is as follows:
.dot {
cursor: pointer;
height: 15px;
width: 15px;
margin: 0 2px;
background-color: #bbb;
border-radius: 50%;
display: inline-block;
visibility: hidden;
transition: background-color 0.6s ease;
}
In the Javascript action for the button, I have set the visibility of the document's elements under the class "dot" to visible, like so:
document.getElementsByClassName("dot").style.visibility="visible";
I have verified that this action is being triggered when the button is pressed through an alert() view. Every line of code seems to run as intended up until this command. Also, the thumbnails at the bottom (the "dot" elements) do not appear, so their visibility does not become visible as intended.
Any ideas on why this may be, or how I can fix it? Thanks a lot for your help!

This document.getElementsByClassName("dot") returns an array and you cannot apply a style attribute to the array.
I'll give you a couple ideas about how you might approach or reconsider this problem.
1) loop through the array and apply a style to each element
var elements = document.getElementsByClassName("dot")
for(var i = 0; i < elements.length; i++) {
elements[i].style.visibility = "visible";
}
2) give an ID to each class and call document.getElementById("someID")
<div id="one">one</div>
<div id="two">two</div>
<div id="three">three</div>
document.getElementyById("one").style.visibility = "visible";
document.getElementyById("two").style.visibility = "hidden";
document.getElementyById("three").style.visibility = "hidden";

document.getElementsByClassName() will return an array.
If you have only one element you could use the first index in the array:
document.getElementsByClassName("dot")[0].style.visibility="visible";
Else if you have more that one:
var dot = document.getElementsByClassName("dot")
for(var i = 0; i < dot.length; i++) {
dot[i].style.visibility = "visible";
}

Related

CSS change body background-color on button hover? [duplicate]

This question already has answers here:
Javascript addEventListener - using to create a mouseover effect?
(2 answers)
Set CSS property in JavaScript?
(11 answers)
How do I toggle an element's class in pure JavaScript?
(13 answers)
Closed 4 years ago.
For my Website, I have a set background-color of the body, for example
body {
background-color: #FFFFFF;
}
I also have a button defined in the .html-File (Let's say it has the ID "button1"), and I want the Background-Color of the body to change (to for example #000000;) when the button is beeing hovered over with a mouse and change back when the mouse isnt on the button anymore. Is there a way to do this?
I am a new webdeveloper and am still looking at/learning JavaScript.
It's not possbile in CSS. In JavaScript it's quite easy, you're looking for onmouseover/out events.
var button = document.getElementById('hover');
var body = document.body;
button.onmouseover = function() {
body.className = 'hovered';
}
button.onmouseout = function() {
body.className = '';
}
body {background: #000;}
body.hovered {background: #ff0;}
<button id="hover">button</button>
Using pure css, you can add a background div:
#button:hover ~ #background {
background-color: red;
}
#background {
position:absolute;
background-color: blue;
top: 0px;
right: 0px;
bottom: 0px;
left: 0px;
z-index: -1;
}
<button id="button">Button</button>
<div id="background"></div>

Slide one div over two div [closed]

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 5 years ago.
Improve this question
I have two div . div-1 and div-2 .it need to stay all the time but i want some menu items using another div name div-3 which is visible when button clicks. i want div-3 over div-1 and div-2 at the same time .how can i do that ?
JavaScript Notes
An IIFE is a very common design pattern in JavaScript commonly used to hide your code so that it doesn't get changed by other scripts.
You can add event listeners to elements using the addEventListner function.
You can get an HTMLElement using the querySelector function which accepts a selector. So to get the first div you could use document.querySelector("div"). To get the element with id "item" you can use document.querySelector("#item"). To get the first element element with class "active" you can use document.querySelector(".active"). You can also use document.querySelector("div#item.active") to get the item the fills all the previous requirements or document.querySelector("div, #item, .active") to get the item that fills any of the requirements. As you can see this works the same as CSS selectors.
To check if a variable is an instance of a Class you can use instanceof.
There are several ways to change how an Element looks using JavaScript.
One is to change the class name element.className = "active", another is to directly change the styling element.style = "opacity: 1;".
Styling Notes
To position an element on top of other elements you need to set its position to absolute and the container's element to relative. When you absolutely position an element then its positioned relatively to the last container that is positioned relatively (default is <html> element).
There are 2 main ways to position elements next to each other: float: left; and display: inline-block;. This works like writing on a notepad, it fits as many elements on next to each other and the repeats the same process below them.
There are 3 common ways to hide an element. 1: opacity: 0; which just makes the item invisible but it it's still there so you should probably also use pointer-events: none; so that it doesn't stop you from clicking what's behind it. 2: height: 0; This just shrinks the element so that it has no height which essentially makes it invisible. 3: display: block; this essentially completely removes the element.
Example
// IIFE Design Pattern
(function() {
// Run onLoad function if page is fully loaded
if (document.readystate === "complete") onLoad();
// Else add an event listener to call onLoad function when page gets fully loaded
else document.addEventListener("DOMContentLoaded", onLoad);
var divIsActive = false;
/**
* Function to be called when page is fully rendered
* #returns {void}
*/
function onLoad() {
// Find button
var button = document.querySelector("#toggle");
// Check if the button was found
if (button instanceof HTMLElement) {
// Add an click event listener
button.addEventListener("click", toggle);
}
}
/**
* Toggles the div to open/close
* #returns {void}
*/
function toggle() {
// Find Div
var div = document.querySelector("#div-3");
// Check if the div was found
if (div instanceof HTMLElement) {
// swap the boolean value
divIsActive = !divIsActive;
// change the classname based on the boolean value
div.className = divIsActive ? "active" : "";
}
}
})();
html,
body {
height: 100%;
width: 100%;
margin: 0;
}
#container {
position: relative;
height: 100%;
width: 100%;
}
#div-1, #div-2 {
height: 100%;
float: left;
width: 50%;
}
#div-1 {
background-color: brown;
}
#div-2 {
background-color: pink;
}
#div-3 {
background-color: green;
pointer-events: none;
transition: all 0.4s;
position: absolute;
height: 40%;
opacity: 0;
right: 0;
left: 0;
top: 0;
}
#div-3.active {
pointer-events: all;
opacity: 1;
}
#toggle {
position: absolute;
cursor: pointer;
z-index: 99999;
right: 10px;
top: 10px;
}
<div id="container">
<button id="toggle">Toggle</button>
<div id="div-1"></div>
<div id="div-2"></div>
<div id="div-3"></div>
</div>

onClick action to show more information html, css, javascript

I have created html and css that looks something like this:
https://jsfiddle.net/jw7pfb1w/
As you can see, I made those boxes 300px in height, but I have more information, that is hidden with overflow: hidden;. Now I created a button
//html
<a id="show-more" class="show">Show More</a>
/css
.show {
display: block;
background-color: #75868E;
width: 100px;
font-size: 12px;
text-transform: uppercase;
display: inline-block;
margin: 20px auto;
cursor: pointer;
height: 15px;
padding: 10px 0;
}
And now I want to see all the information in those three boxes when I click the button. I tried something like this
I added this to css:
#model1.open {
max-height: 1000px;
//transitions
-webkit-transition: max-heigth 0.7s;
-moz-transition: max-heigth 0.7s;
transition: max-heigth 0.7s;
}
and this to javascript
var content = document.getElementByClassName(".model1");
var button = document.getElementById("show-more")
button.onclick = function(){
if(content.className == "open"){
content.className = "";
button.innerHTML = "Show More";
} else {
content.className = "open";
button.innerHTML = "Show Less";
}
};
But it does'not work. I am stuck. Can someone help me to make this work, please?
There's a handful of bugs with your code.
In your CSS, you refer to model1 as an id, but in your JavaScript you
refer to it as a class.
getElementByClassName should be getElementsByClassName with an s after Element. You will have seen this issue if you looked in your browser console. (ctrl + shift + i).
You don't include the . symbol in getElementsByClassName, so you should use the value modal1 instead of .modal1.
If you do use getElementsByClassName, you need to specify which element of that class to affect, otherwise all elements with that class will be effected, meaning clicking that button will show more and less of all the modals. I use jQuery, so I'm not sure what the pure JS alternative is, but you probably want to detect which .modal1 has a shared parent with the button that was clicked, or alternately put an attribute of which number button that is, and put the same attribute on the modal, and use that to tie the two elements behavior together.
This may not be a complete list of bugs, but these are the most obvious ones I see.
If i have only one element, then it works. See > https://jsfiddle.net/075tcezL/
But how do i make it show or hide all three elements at the same time when i
click the button?

CSS transitions in Edge and IE11 not working

I don't often find myself with CSS issues, but this has me scratching my head.
In this plunk http://plnkr.co/i2Fxol, everything works exactly as expected in all browsers, with the exception of IE10 and 11 and Edge completely failing to apply css transitions to some elements, not all. And no matter how much I look at it, I cannot see why it's failing in those particular places. (CSS added here but it needs to be seen in context as this is a really simplistic view)
#navigation ul {
display: block;
list-style: none;
overflow: hidden;
transition: all .2s ease;
}
Essentially, they burp when the accordion is open and the menus are available to expand and contract in the 0.2 seconds stated. All the other transitions work.
Oh, and there is now way that I am ever going to add closures to svg paths within HTML5 just to remove those utterly pointless warnings in IE and Edge.
edit
The initial heights for the accordions are gathered on load with this:
...
var initialHeights = document.getElementsByClassName("level-1");
var values = [];
for(var i = 0; initialHeights.length > i; i++){
values.push(initialHeights[i].offsetHeight);
}
...
They are then zeroed inline with the values stored safely in an array using:
function toZero(){
for(i = 0; mainSubMenus.length > i; i++){
mainSubMenus[i].setAttribute("style", "height:0;");
}
}
toZero();
This allows the use of css to transition between a zero height and a known value.
brainfart
I thought that maybe the following would cure the ill:
mainSubMenus[i].style.height = 0;
I was wrong.
I believe the issue here is with the lack of an initial height. If you cycle over the elements, and set their heights equal to that of their computed height style, you could then use your collapse style to override the height to 0px, triggering a transition between two explicit numbers.
var box = document.querySelector( ".box" );
// Set the box's initial height to its computed height
box.style.height = window.getComputedStyle( box ).height;
// Hide the box
box.classList.add( "collapsed" );
// Click will toggle a "collapsed" class on the box
document.addEventListener( "click", e => box.classList.toggle( "collapsed" ) )
.box {
width: 100px;
overflow: hidden;
border: 1px solid #000;
transition: all .2s ease;
}
.collapsed {
height: 0!important;
}
<ul class="box">
<li>Hello</li>
<li>World</li>
</ul>

Why is my animation "replayed" when an element is added via innerHTML?

I have a little script that adds a div named "doge" using innerHTML when clicking on a button on my page, and on this page there's a div with a CSS keyframes animation.
However, when I click on the button to add the div named "doge" on my page, the CSS animation is "replayed". Why? How can I fix that?
function addHtml() {
document.getElementById("wow").innerHTML += '<div class="doge">such wow</div>';
}
#keyframes color {
10% {
background: #4CAF50;
}
50% {
background: #3F51B5;
}
100% {
background: #009688;
}
}
.myDiv {
background: #000;
color: #fff;
animation: color 1s;
}
.doge {
background: #F57F17;
}
<div id="wow">
<div class="myDiv">Hi!</div>
<br>
<button onclick="addHtml()">Add HTML!</button>
</div>
JSFiddle
It's because you're modifying all of the element's HTML when you modify the .innerHTML property.
According to MDN:
.innerHTML - Removes all of element's children, parses the content string and assigns the resulting nodes as children of the element.
In doing so, the DOM assumes that the .myDiv element has just been added which means that the animation is going to be replayed. To work around that, use the .appendChild() method instead:
Updated Example
var div = document.createElement('div');
div.textContent = 'such wow';
div.className += 'doge';
document.getElementById("wow").appendChild(div);
Alternatively, as Teemu points out, you can also use the .insertAdjacentHTML() method:
Updated Example
document.getElementById("wow").insertAdjacentHTML('afterend', '<div class="doge">such wow</div>');

Categories