Js Script not working in NextJs Class Problem - javascript

I have an FAQ page on the website I am building right now. I got the faq section from a template. I tried to use Javascript within my NextJs Projekt but it is not working.
var faq = document.getElementsByClassName("faqpage");
var i;
for (i = 0; i < faq.length; i++) {
faq[i].addEventListener("click", function () {
/* Toggle between adding and removing the "active" class,
to highlight the button that controls the panel */
this.classList.toggle("active");
/* Toggle between hiding and showing the active panel */
var body = this.nextElementSibling;
if (body.style.display === "block") {
body.style.display = "none";
} else {
body.style.display = "block";
}
});
}
var cpt = document.getElementsByClassName("faqbody");
var i;
for (i = 0; i < faq.length; i++) {
cpt[i].addEventListener("click", function () {
/* Toggle between adding and removing the "active" class,
to highlight the button that controls the panel */
this.classList.toggle("active");
/* Toggle between hiding and showing the active panel */
var body = this.nextElementSibling;
if (body.style.display === "block") {
body.style.display = "none";
} else {
body.style.display = "block";
}
});
}
.Faq {
background-color: rgba(46,40,35,255);
padding-top: 50px;
padding-bottom: 150px;
}
.Faq h2 {
color: white;
text-align: center;
font-size: 4vh;
margin-bottom: 20px;
}
.faqcontainer{
display: flex;
justify-content: center;
flex-direction: column;
}
.hrline{
width: 62%;
margin: auto;
margin-top: 20px;
}
.faqpage {
cursor: pointer;
padding: 30px 20px;
width: 60%;
border: none;
font-size: 25px;
font-weight: 600;
outline: none;
transition: 0.4s;
margin: auto;
color: #EC2628;
}
.faqbody{
margin: auto;
/* text-align: center; */
width: 50%;
line-height: 30px;
font-size: 20px;
padding: 0 18px;
display: none;
overflow: hidden;
padding-bottom: 20px;
}
.faqpage:after {
content: '\002B';
/* Unicode character for "plus" sign (+) */
font-size: 35px;
font-weight: 100;
color: white;
float: right;
transition-duration: 0.5s;
}
.active:after {
transform: rotate(45deg);
/* Unicode character for "minus" sign (-) */
font-weight: 100;
}
<div className={styles.Faq}>
<h2>FAQ</h2>
<div className={styles.faqone}>
<h1 className={styles.faqpage}>How can I join the community?</h1>
<div className={styles.faqbody}>
<p>We have a very active community and we welcome new members with open arms! Come and chat with us on Discord.</p>
</div>
</div>
<hr className={styles.hrline}/>
<div className={styles.faqtwo}>
<h1 className={styles.faqpage}>How can I join the community?</h1>
<div className={styles.faqbody}>
<p>We have a very active community and we welcome new members with open arms! Come and chat with us on Discord.</p>
</div>
</div>
<hr className={styles.hrline}/>
<div className={styles.faqthree}>
<h1 className={styles.faqpage}>How can I join the community?</h1>
<div className={styles.faqbody}>
<p>We have a very active community and we welcome new members with open arms! Come and chat with us on Discord.</p>
</div>
</div>
<hr className={styles.hrline}/>
<div className={styles.faqfour}>
<h1 className={styles.faqpage}>How can I join the community?</h1>
<div className={styles.faqbody}>
<p>We have a very active community and we welcome new members with open arms! Come and chat with us on Discord.</p>
</div>
</div>
<hr className={styles.hrline}/>
<Script src="../components/FAQLOC.js"></Script>
</div>
I thought it has something to do with the classes and that javascript cannot grab the classes from nextjs but I also don't know how to solve this problem.
The Snippet is so that you can see all of my CODE!
Can someone help me?

Components on Nextjs are all server-side by default so you don't have access to the document object. Have you tried importing your component dynamically and setting SSR to false? https://nextjs.org/docs/advanced-features/dynamic-import

Related

Css animation doesn't move object

I have a problem with a css animation im trying to add to each child inside a nav tag
I'm trying to create a moving stock panel
The weird thing about it is that if I add another css attribute like color it does work
Does anyone knows how to solve this
function DoAnimation(animation, a) {
var parent = a.parentElement
if (animation != null) {
parent.removeChild(a);
parent.appendChild(a);
console.log(1);
a.style.animationName = animation;
a.style.animationDuration = "2s";
}
}
#keyframes MoveStockTORIght {
from {
left: 0;
}
to {
transform: translateX(100px);
}
}
.SiteNav {
overflow: hidden;
text-align: center;
margin: auto;
text-align: center;
}
.SiteNav a {
gap: 10%;
padding: 1%;
}
<nav class="SiteNav" id="siteNavigantion">
MSFT 294.23
CLOV 8.06
LCID 22.87
SAVA 51.08
AAL 20.13
AMZN 3246.3
NFLX 627.04
GOOG 2776.95
AAPL 142.81
NVDA 206.95
</nav>
Why not just use Marquee?
.SiteNav {
overflow: hidden;
text-align: center;
margin: auto;
text-align: center;
}
.SiteNav a {
gap: 10%;
padding: 1%;
}
marquee a { text-decoration: none; color:green; }
<marquee class="SiteNav" id="siteNavigantion">
MSFT 294.23
CLOV 8.06
LCID 22.87
SAVA 51.08
AAL 20.13
AMZN 3246.3
NFLX 627.04
GOOG 2776.95
AAPL 142.81
NVDA 206.95
</marquee>

Make the Modal Box Appear only Once in Tab Session

I am facing a problem with the modal box that I created.
Let me first put all of the code first.
var modal = document.getElementById("modal");
var close = document.getElementsByClassName("modal-close")[0];
if (modal.style.display == "block") {
sessionStorage.setItem("ModalSeen", "Seen")
}
if (window.performance) {
console.log("Window Performance works fine.")
}
if (performance.getEntriesByType('navigation')[0].type != 'navigate') { // Reload Happened
modal.style.display = "none";
sessionStorage.setItem("ModalSeen", "Seen");
} else {
modal.style.display = "block";
sessionStorage.setItem("ModalSeen", "Not Seen");
}
close.onclick = function() {
modal.style.display = "none";
sessionStorage.setItem("ModalSeen", "Seen");
}
window.onclick = function(event) {
if (event.target == modal) {
modal.style.display = "none";
sessionStorage.setItem("ModalSeen", "Seen");
}
}
if (sessionStorage.getItem("ModalSeen") == "Seen") {
modal.style.display = "none";
} else if (sessionStorage.getItem("ModalSeen") == "Not Seen") {
modal.style.display = "block";
}
.modal {
display: none;
position: fixed;
z-index: 1;
padding-top: 100px;
left: 0;
top: 0;
width: 100%;
height: 100%;
overflow: auto;
background-color: rgb(0, 0, 0);
background-color: rgba(0, 0, 0, 0.4);
}
.modal-content {
background-color: #fefefe;
margin-left: auto;
margin-right: auto;
margin-top: 2%;
padding: 20px;
border: 1px solid #888;
border-radius: 13px;
width: 33%;
}
.modal-close {
color: #aaaaaa;
float: right;
font-size: 30px;
font-weight: bold;
}
.modal-close:hover,
.modal-close:focus {
color: #000;
text-decoration: none;
cursor: pointer;
}
.modal-img {
width: 20%;
display: block;
margin-left: 41%;
}
.modal-heading {
font-family: Noto Sans KR, sans-serif;
font-size: xx-large;
font-weight: bold;
color: #363636;
margin-left: 36.3%;
}
.modal-txt {
font-family: Noto Sans KR, sans-serif;
font-size: 17px;
color: #363636;
text-align: center;
width: 85%;
margin-left: 7.5%;
}
<div id="modal" class="modal">
<div class="modal-content">
<span class="modal-close">×</span>
<img class="modal-img" src="icons/Country - Error.png">
<p class="modal-heading">Warning</p>
<p class="modal-txt">Hey! This doesn't work outside of India.</p>
<p class="modal-txt">If you are outside India, you can continue to use the website, but you can't install the app.</p>
</div>
</div>
I want to display a modal box to the user when the user first opens the website. I don't want it to appear ever again, even if he refreshes the page or manipulates it. I only want it to appear when the user opens a new tab and goes to my website.
In the HTML and CSS code, I don't believe there is anything wrong with it.
In JavaScript, I have used SessionStorage (because that is more relevant than local storage in this case) and I put a key as "ModalSeen" and there are 2 values for it: "Seen" & "Not Seen". In the end, I have placed an if condition: If the value is Seen, the modal box should not appear again. If the value is Not Seen, the modal can appear again.
I tried a lot of things, but this was the best I could do.
Can you please help me to achieve this by making the modal open only once in the whole tab session? Thanks in Advance!
I think that you might need to use cookies for that

Little problem with accordion-menu (hide/show)

Good time. There is an accordion menu at this link: https://www.w3schools.com/code/tryit.asp?filename=G3Z0U159KFM3
(to see it, you need to click on the green "Run" button)
This is a simple show / hide menu. How to make the default content was expanded and by clicking could hide it? (i.e. the opposite of the current one)
Dears, please help with this problem.
Well, although the way you described your issue wasn't clear, I think you are trying to do the opposite of the code you provided, so you would like the "contents" menu to be shown by default and when you click on it the menu would collapse back.
First you want to set the .active class by default to the .ContentsAccordion button like so :
<button class="ContentsAccordion active">Contents</button>
And then you want to get the height of your menu and put it into the style element of your .ContentsPanel div with this code :
var pan = document.getElementsByClassName("ContentsPanel");
pan[0].setAttribute('style', 'max-height: ' + pan[0].scrollHeight + 'px;');
and the rest of your code doesn't need any change.
Working example below :
<style>
.ContentsAccordion {
background-color: #eee;
color: #444;
cursor: pointer;
padding: 18px;
width: 100%;
border: none;
text-align: left;
outline: none;
font-size: 18px;
transition: 0.4s;
}
button.ContentsAccordion:after {
content: '\002B';
color: #777;
font-weight: bold;
float: right;
margin-left: 5px;
}
button.ContentsAccordion.active:after {
content: '\2212';
}
.active, .ContentsAccordion:hover {
background-color: #ccc;
}
.ContentsPanel {
padding: 0 18px;
background-color: white;
max-height: 0;
overflow: hidden;
transition: max-height 0.2s ease-out;
border: 1px #ccc solid;
}
.ContentsAccordionP {
font-size: 16px;
}
</style>
<button class="ContentsAccordion active">Contents</button>
<div class="ContentsPanel">
<p class="ContentsAccordionP">Some text 1</p>
<p class="ContentsAccordionP">Some text 2</p>
<p class="ContentsAccordionP">Some text 3</p>
</div>
<script>
var acc = document.getElementsByClassName("ContentsAccordion");
var i;
var pan = document.getElementsByClassName("ContentsPanel");
pan[0].setAttribute('style', 'max-height: ' + pan[0].scrollHeight + 'px;');
for (i = 0; i < acc.length; i++) {
acc[i].addEventListener("click", function() {
this.classList.toggle("active");
var panel = this.nextElementSibling;
if (panel.style.maxHeight){
panel.style.maxHeight = null;
} else {
panel.style.maxHeight = panel.scrollHeight + "px";
}
});
}
</script>

Show/hide div only one at a time

This code is the untouched version of a FAQ consisting of three answers that can be shown or hidden when click on it. My task is to modify to show only one answer at a time (the other two must close).
I got a hint to use a for loop to go through the h2 elements in the array and remove the class attribute for all h2 elements that aren’t the one that has been clicked.
Thank you,
"use strict";
var $ = function(id) { return document.getElementById(id); };
// the event handler for the click event of each h2 element
var toggle = function() {
var h2 = this; // clicked h2 tag
var div = h2.nextElementSibling; // h2 tag's sibling div tag
// toggle plus and minus image in h2 elements by adding or removing a class
if (h2.hasAttribute("class")) {
h2.removeAttribute("class");
} else {
h2.setAttribute("class", "minus");
}
// toggle div visibility by adding or removing a class
if (div.hasAttribute("class")) {
div.removeAttribute("class");
} else {
div.setAttribute("class", "open");
}
};
window.onload = function() {
// get the h2 tags
var faqs = $("faqs");
var h2Elements = faqs.getElementsByTagName("h2");
// attach event handler for each h2 tag
for (var i = 0; i < h2Elements.length; i++ ) {
h2Elements[i].onclick = toggle;
}
// set focus on first h2 tag's <a> tag
h2Elements[0].firstChild.focus();
};
HTML for the script:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>FAQs</title>
<link rel="stylesheet" href="main.css">
<script src="faqs.js"></script>
</head>
<body>
<main id="faqs">
<h1>JavaScript FAQs</h1>
<h2><a href="#" >What is JavaScript?</a></h2>
<div>
<p>JavaScript is a programming language that's built into the major web browsers.
It makes web pages more responsive and saves round trips to the server.
</p>
</div>
<h2>What is jQuery?</h2>
<div>
<p>jQuery is a library of the JavaScript functions that you're most likely
to need as you develop web sites.
</p>
</div>
<h2>Why is jQuery becoming so popular?</h2>
<div>
<p>Three reasons:</p>
<ul>
<li>It's free.</li>
<li>It lets you get more done in less time.</li>
<li>All of its functions are cross-browser compatible.</li>
</ul>
</div>
</main>
</body>
</html>
And CSS for the script:
* {
margin: 0;
padding: 0;
}
body {
font-family: Verdana, Arial, Helvetica, sans-serif;
font-size: 87.5%;
width: 650px;
margin: 0 auto;
border: 3px solid blue;
padding: 15px 25px;
}
h1 {
font-size: 150%;
}
h2 {
font-size: 120%;
padding: .25em 0 .25em 25px;
cursor: pointer;
background: url(images/plus.png) no-repeat left center;
}
h2.minus {
background: url(images/minus.png) no-repeat left center;
}
a {
color: black;
text-decoration: none;
}
a:focus, a:hover {
color: blue;
}
div {
display: none;
}
div.open {
display: block;
}
ul {
padding-left: 45px;
}
li {
padding-bottom: .25em;
}
p {
padding-bottom: .25em;
padding-left: 25px;
}
Something like the following might do the trick assuming your existing script/markup is currently working. I can't test my answer without the HTML/CSS.
Essentially it just iterates over the faq items when ones clicked and hides them if they aren't the element that was clicked or shows if it is the element clicked - it won't toggle if the same element is clicked twice - one will always remain open.
"use strict";
var $ = function(id) { return document.getElementById(id); };
// the event handler for the click event of each h2 element
window.onload = function() {
// get the h2 tags
var faqs = $("faqs");
var h2Elements = faqs.getElementsByTagName("h2");
function accordionClick(){
var h2;
for(var i=0; i < h2Elements.length; i++){
h2 = h2Elements[i];
if(h2 == this){ // The item we clicked
if(!h2.hasAttribute("class")){ // If it's open
closeItem(h2);
} else{ // If not
openItem(h2);
}
} else{ // Not the item we clicked so it should be closed
closeItem(h2);
}
}
}
function openItem(h2){
var div = h2.nextElementSibling;
h2.removeAttribute("class")
div.setAttribute("class", "open");
}
function closeItem(h2){
var div = h2.nextElementSibling;
h2.setAttribute("class", "minus")
div.removeAttribute("class");
}
// attach event handler for each h2 tag and init classes
for (var i = 0; i < h2Elements.length; i++ ) {
h2Elements[i].onclick = accordionClick;
closeItem(h2Elements[i]);
}
// set focus on first h2 tag's <a> tag
h2Elements[0].firstChild.focus();
};
* {
margin: 0;
padding: 0;
}
body {
font-family: Verdana, Arial, Helvetica, sans-serif;
font-size: 87.5%;
width: 650px;
margin: 0 auto;
border: 3px solid blue;
padding: 15px 25px;
}
h1 {
font-size: 150%;
}
h2 {
font-size: 120%;
padding: .25em 0 .25em 25px;
cursor: pointer;
background: url(images/plus.png) no-repeat left center;
}
h2.minus {
background: url(images/minus.png) no-repeat left center;
}
a {
color: black;
text-decoration: none;
}
a:focus, a:hover {
color: blue;
}
div {
display: none;
}
div.open {
display: block;
}
ul {
padding-left: 45px;
}
li {
padding-bottom: .25em;
}
p {
padding-bottom: .25em;
padding-left: 25px;
}
<main id="faqs">
<h1>JavaScript FAQs</h1>
<h2><a href="#" >What is JavaScript?</a></h2>
<div>
<p>JavaScript is a programming language that's built into the major web browsers.
It makes web pages more responsive and saves round trips to the server.
</p>
</div>
<h2>What is jQuery?</h2>
<div>
<p>jQuery is a library of the JavaScript functions that you're most likely
to need as you develop web sites.
</p>
</div>
<h2>Why is jQuery becoming so popular?</h2>
<div>
<p>Three reasons:</p>
<ul>
<li>It's free.</li>
<li>It lets you get more done in less time.</li>
<li>All of its functions are cross-browser compatible.</li>
</ul>
</div>
</main>

How to use document.getElementsByClassName

I have 2 questions
Please help me understand some JavaScript to create an accordion menu I got from W3Schools
css
<style>
button.accordion_f {
background-color: #eee;
color: #444;
cursor: pointer;
padding: 14px;
width: 100%;
border: none;
text-align: left;
outline: none;
font-size: 15px;
transition: 0.4s;
}
button.accordion_f.active, button.accordion_f:hover {
background-color: #ddd;
color: blue;
}
button.accordion_f:after {
content: '\02795';
font-size: 13px;
color: #777;
float: right;
margin-left: 5px;
}
button.accordion_f.active:after {
color: blue;
content: "\2796";
}
div.panel {
padding: 0 14px;
background-color: white;
max-height: 0;
overflow: hidden;
transition: 0.3s ease-in-out;
opacity: 0;
}
div.panel.show {
opacity: 1;
max-height: 6000px;
}
</style>
JavaScript
<script>
var acc = document.getElementsByClassName("accordion_f");
var i;
for (i = 0; i < acc.length; i++) {
acc[i].onclick = function(){
this.classList.toggle("active");
this.nextElementSibling.classList.toggle("show");
}
}
</script>
Example use
<button class="accordion_f">3rd party compatibility</button>
<div class="panel">
<p>Offers an easy way to connect your Polar training device with 3<sup>rd</sup> party services.</p>
</div>
This works correctly
If I encapsulate this in another class for example in a pill menu it will not expand the menu, the css seems to work, the background shading etc, when I inspect the element I do not see the script, is the parent class affecting document.getElementsByClassName some how?
<ul class="tabs">
<button class="accordion_f">3rd party compatibility</button>
<div class="panel">
<p>Offers an easy way to connect your Polar training device with 3<sup>rd</sup> party services.</p>
</div>
</ul>
How do I put my script into a function and call it with onclick or onmouseover?
I tried:
<button class="accordion_f" onmouseover="accordion_menu()">Activity</button>
<div class="panel">
<p>Tracks your daily activity at five intensity levels for 24 hours a day, seven days a week, and provides a complete picture of all of your activity. It counts your active time, daily burnt calories, steps, distance from steps and sleep.</p>
</div>
function accordion_menu(){
var acc = document.getElementsByClassName("accordion_f");
var i;
for (i = 0; i < acc.length; i++) {
acc[i].onclick.classList.toggle("active");
acc[i].onclick.nextElementSibling.classList.toggle("show");
}
}
This just opened all panels with a class of accordion_f, not just the active one as I would like.
It is working, I.E was in compatibility mode and ie8 had poor support for document.getElementsByClassName

Categories