I made an analog clock using html, css, and JS for a website I'm working on. I want this clock to show time in a specific timezone which I want, but using the codes below it only shows time based on client's time.
actually my final goal is to have 5 of these analog clocks and each would show a different time like Sydney, Tokyo, Frankfurt, London and New York.
any ideas how to do that?
this is my clock.css:
body {
display: flex;
justify-content: center;
align-items: center;
height: 100vh;
background-color: #091921;
}
.clock {
width: 120px;
height: 120px;
border-radius: 50%;
background-image: url("https://i.postimg.cc/hjVspvcJ/clock.png");
background-size: cover;
display: flex;
background-color: #D3D3D3;
justify-content: center;
align-items: center;
box-shadow: 0 -5px 5px rgba(255, 255, 255, 0.05),
inset 0 -5px 5px rgba(255, 255, 255, 0.05), 0 5px 5px rgba(0, 0, 0, 0.3),
inset 0 5px 5px rgba(0, 0, 0, 0.3);
}
.clock::before {
content: "";
width: 5px;
height: 5px;
position: absolute;
background-color: #000000;
border-radius: 50%;
z-index: 1000;
}
.hour,
.min,
.sec {
position: absolute;
}
.hr {
width: 64px;
height: 64px;
}
.mn {
width: 76x;
height: 76px;
}
.sc {
width: 92px;
height: 92px;
}
.hr,
.mn,
.sc {
display: flex;
justify-content: center;
}
.hr::before {
content: "";
width: 3px;
height: 32px;
background-color: #000000;
z-index: 100;
border-radius: 2px;
}
.mn::before {
content: "";
width: 2px;
height: 36px;
background-color: #000000;
z-index: 11;
border-radius: 2px;
}
.sc::before {
content: "";
width: 1px;
height: 56px;
background-color: #000000;
z-index: 10;
border-radius: 2px;
}
this is clock.html:
<html>
<head>
<link rel="stylesheet" href="clock.css">
</head>
<body>
<div class="clock">
<div class="hour">
<div class="hr" id="hr"></div>
</div>
<!-- <button class= id="nine">9</button>
<button class= -bg" id="divide">/</button>
<button class=" ary" id="four">4</button>-->
<div class="min">
<div class="mn" id="mn"></div>
</div>
<div class="sec">
<div class="sc" id="sc"></div>
</div>
</div>
<script src="clock.js"></script>
</body>
</html>
and this is clock.js:
const deg = 6;
const hr = document.querySelector("#hr");
const mn = document.querySelector("#mn");
const sc = document.querySelector("#sc");
/*height: 3px;
background-color: #fb7454;
opacity: 0.8;*/
setInterval(() => {
let day = new Date();
let hh = day.getHours() * 30; //360deg / 12 hour => 30
let mm = day.getMinutes() * deg;
let ss = day.getSeconds() * deg;
/*height: 3px;
background-color: #fb7454;
opacity: 0.8;*/
hr.style.transform = `rotateZ(${hh + mm / 12}deg)`;
mn.style.transform = `rotateZ(${mm}deg)`;
sc.style.transform = `rotateZ(${ss}deg)`;
});
Btw guys I found the answer.
I used this function to convert the current time to annother time zone:
function convertTZ(date, tzString) {
return new Date((typeof date === "string" ? new Date(date) : date).toLocaleString("en-US", {timeZone: tzString}));
I hope this helps others with similar problem.
Related
For this Slider to work I have set pointer-events: none; . But I want to have a clickable Button within the slide. Thats not possible right now, since pointer-events: none;. Since I only know a bare minimum about JS I need help.
const sliderContainer = document.querySelector(".slider-container");
const slider = document.querySelector(".slider");
const onButton = document.querySelector(".btn");
let clicked = false;
let xAxis;
let x;
sliderContainer.addEventListener("mouseup", () => {
sliderContainer.style.cursor = `grab`;
});
sliderContainer.addEventListener("mousedown", (e) => {
clicked = true;
xAxis = e.offsetX - slider.offsetLeft;
// tells the current position
sliderContainer.style.cursor = `grabbing`;
});
window.addEventListener("mouseup", () => {
clicked = false;
});
sliderContainer.addEventListener("mousemove", (e) => {
if (!clicked) return;
e.preventDefault();
x = e.offsetX;
slider.style.left = `${x - xAxis}px`;
// but we dont want it to scroll forever
checkSize();
});
function checkSize() {
let sliderContainerOut = sliderContainer.getBoundingClientRect();
let sliderIn = slider.getBoundingClientRect();
if (parseInt(slider.style.left) > 0) {
slider.style.left = `0px`;
} else if (sliderIn.right < sliderContainerOut.right) {
slider.style.left = `-${sliderIn.width - sliderContainerOut.width}px`;
}
}
#import url("//fonts.googleapis.com/css?family=Raleway");
:root {
--item-height: 80vh;
--item-witdh: 80vw;
--item-spacing: 300px;
--item-count: 4;
--starting-slide-distance-left: 40vw;
--blur: 3.5px;
--spread: -2.5px;
--horiz: 1.3616px;
--vert: 2.09668px;
}
.wrapper {
height: 100vh;
width: 100vw;
}
/*----------------------------Slider Start-----------------------------*/
.slider-container {
position: absolute;
width: 100vw;
min-height: var(--item-height);
overflow: hidden;
cursor: grab;
padding: 50px;
}
.slider {
position: absolute;
width: auto;
height: auto;
display: grid;
grid-template-columns: repeat(var(--item-count), 1fr);
column-gap: var(--item-spacing);
pointer-events: none;
transform: translatex(var(--starting-slide-distance-left));
}
.slider-item {
width: var(--item-witdh);
height: var(--item-height);
border: 2px solid green;
border-radius: 20px;
overflow: hidden;
align-content: center;
}
.item-shadow {
box-shadow: calc(clamp(0px, var(--horiz), 2px)) calc(clamp(0px, var(--vert), 2px)) 2px calc(var(--spread)) rgba(0, 0, 0, 0.233), calc(2 * var(--horiz)) calc(2 * var(--vert)) calc(var(--blur)) calc(var(--spread)) rgba(0, 0, 0, 0.2), calc(3 * var(--horiz)) calc(3 * var(--vert)) calc(var(--blur)) calc(var(--spread)) rgba(0, 0, 0, 0.123), calc(5 * var(--horiz)) calc(5 * var(--vert)) calc(var(--blur)) calc(var(--spread)) rgba(0, 0, 0, 0.076), calc(8 * var(--horiz)) calc(8 * var(--vert)) calc(var(--blur)) calc(var(--spread)) rgba(0, 0, 0, 0.047), calc(13 * var(--horiz)) calc(13 * var(--vert)) calc(var(--blur)) calc(var(--spread)) rgba(0, 0, 0, 0.028);
border: 1px solid rgba(0, 0, 0, 0.068);
}
/*----------------------------Slider end-----------------------------*/
/*------------------------Item Content Start-------------------------*/
h2 {
color: #fff;
font-family: Raleway;
text-align: center;
font-size: 35px;
padding: 30px;
}
.slide1 {
background-image: url(https://www.memorabilien.org/wp-content/uploads/pexels-pixabay-220201.webp);
background-size: cover;
display: grid;
grid-template-columns: auto auto auto auto;
grid-template-rows: auto auto;
justify-content: space-around;
}
.images:hover {}
img {
max-height: var(--item-height);
width: auto;
}
.img:hover {
cursor: pointer!important;
}
.colnum-wrapper {
border: 2px solid yellow;
align-content: center;
display: flex;
flex-wrap: wrap;
align-content: center;
}
.colnum-wrapper2 {
border: 2px solid purple;
}
/*----------------Button Start------------------*/
.btn-wrapper {
border: 2px solid cyan;
text-align: center;
padding: 30px;
}
.btn {
border-radius: 20px;
padding: 15px;
border: 5px solid #aa80ff;
background: transparent;
font: Raleway, bold;
font-size: 30px;
color: #fff;
position: relative;
}
.btn:hover {
background: #aa80ff;
color: black;
}
<div class="wrapper" style="border: 2px dotted green;">
<div class="slider-container" style="border: 2px dotted green;">
<div class="slider" style="border: 2px dotted green;">
<div class="slider-item item-shadow slide1" style="border: 2px dotted red;">
<div class="colnum-wrapper">
<div class="colnum-wrapper2">
<div class="headline" style="border: 3px solid red;">
<h2>The Space and Universe Poster Collection</h2>
</div>
<div class="btn-wrapper"><button class="btn item-shadow" id="btn">Explore</button></div>
</div>
</div>
<div class="images" style="border: 2px solid green">
<img src="https://www.memorabilien.org/wp-content/uploads/Untitled-2-1.webp"></img>
</div>
</div>
<div class="slider-item item-shadow">item</div>
<div class="slider-item item-shadow">item</div>
<div class="slider-item item-shadow">item</div>
</div>
</div>
</div>
Here is a Codepen-Link: https://codepen.io/memorabilien/pen/MWVKmaB
I have a product card that I would like to be able to change the main image src of when the user hovers over a 'colour swatch' however, I'm finding this difficult using the answer from here: Change Image Source from Div with onmouseover.
My current code is as follows:
(function() {
var img1 = "https://picsum.photos/300";
var img2 = "https://picsum.photos/300";
var myimg = document.getElementById('img');
myimg.src = img1;
var hoverables = document.getElementsByClassName('hoverme');
for (var i = hoverables.length; i--;) {
hoverables[i].addEventListener("mouseover", hoverMe, false);
hoverables[i].addEventListener("mouseout", unhoverMe, false);
}
function hoverMe() {
myimg.src = img2;
}
function unhoverMe() {
myimg.src = img1;
}
})();
.product-card{
height: auto;
width: auto;
border-radius: 25px;
box-shadow: 0px 0px 15px 5px rgba(0,0,0,0.1);
-webkit-box-shadow: 0px 0px 15px 5px rgba(0,0,0,0.1);}
.card-body{
height: auto;
width: 100%;
text-align: left;
position: relative;}
.card-image{
max-width:350px;
max-height:350px;
padding: 10px;}
.card-sidebar{
height: 100%;
width: 50px;
display: flex;
align-items: center;
position: absolute;
right: 0;
top: 0;
border-radius: 0 25px 0 0;
background-color: rgba(255, 255, 255, .15);
backdrop-filter: blur(2.5px);}
.swatch-contain{
height: auto;
width: 100%;
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-evenly;}
.swatch{
height: 25px;
width: 25px;
background-color: aqua;
border: 1px solid whitesmoke;
border-radius: 100%;
margin: 5px;}
.swatch.black{
background-color: black;}
.card-foot{
height: 100px;
width: 100%;
border-top: 1px solid whitesmoke;
}
<div class="product-card">
<div class="card-body">
<img src="https://picsum.photos300" alt="Aqua Evo22 Backpack" class="card-image" id="img">
<div class="card-sidebar">
<div class="swatch-contain">
<div class="swatch black hoverme" id=""></div>
<div class="swatch" id=""></div>
<div class="swatch" id=""></div>
</div>
</div>
</div>
<div class="card-foot">
<p></p>
</div>
</div>
I'm going to have this function for multiple 'swatches' on over around 100 products so I need a solution that is a minimal and easily replicable as possible. what I currently have doesn't function as expected and is very long to keep copying to replace for each product I'll list.
I m making a Toast Notification.
I hope that When I click the 'Toast Notification' button, notification message come to on the bottom side and after a while, the messages disappear.
So I set the disappearing time to 5s , then after clicking the button and later 5 second , the messages are disappeared in sequence.
But the disappearing time was not the 5second except the first disappearing .
Time is getting faster and faster that is disappeared . It's not 5 second what I set before
My english is bad so I hope you understand by running code below
let toast = document.querySelector('.toast');
let notification = document.querySelector(".notification")
let sec = 5000;
toast.addEventListener('click', () => {
let newDiv = document.createElement("span");
let newText = document.createTextNode("No Way!");
newDiv.classList.add("notification_word");
newDiv.appendChild(newText);
notification.appendChild(newDiv);
if (document.querySelector(".notification_word")) {
setInterval(function() {
removeNotification()
}, sec);
}
})
function removeNotification() {
document.querySelectorAll(".notification_word")[0].remove()
}
body {
text-align: center;
justify-content: center;
align-items: center;
}
button.toast {
position: absolute;
top: 50%;
left: 50%;
width: 200px;
height: 100px;
font-size: 20px;
background: rgb(215, 188, 240);
margin: -100px 0 0 -100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 20px;
cursor: pointer;
}
button.toast:hover {
background: rgb(178, 157, 201);
}
.notification {
display: flex;
flex-direction: column-reverse;
position: absolute;
right: 2%;
bottom: 2%;
}
span.notification_word {
background-color: rgb(196, 77, 243);
padding: 10px 0;
margin: 3px;
width: 100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 5px;
}
<button class="toast">Toast Notification</button>
<div class="notification">
</div>
Try this code I have written some comment on code it may help you
let toast = document.querySelector('.toast');
let notification = document.querySelector(".notification")
let sec = 5000;
let timeoutHandler;
toast.addEventListener('click', () => {
// clear previous timeout function
clearTimeout(timeoutHandler);
//remove previous notification if exist
//if you don't want to remove previous notification than remove below calling function.
removeNotification();
let newDiv = document.createElement("span");
let newText = document.createTextNode("No Way!");
newDiv.classList.add("notification_word");
newDiv.appendChild(newText);
notification.appendChild(newDiv);
if (document.querySelector(".notification_word")) {
// use timeout function instead of setinterval and assign on a variable
timeoutHandler = setTimeout(function() {
removeNotification()
}, sec);
}
})
function removeNotification() {
let notificationWord = document.querySelector(".notification_word");
if(notificationWord) notificationWord.remove();
}
body {
text-align: center;
justify-content: center;
align-items: center;
}
button.toast {
position: absolute;
top: 50%;
left: 50%;
width: 200px;
height: 100px;
font-size: 20px;
background: rgb(215, 188, 240);
margin: -100px 0 0 -100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 20px;
cursor: pointer;
}
button.toast:hover {
background: rgb(178, 157, 201);
}
.notification {
display: flex;
flex-direction: column-reverse;
position: absolute;
right: 2%;
bottom: 2%;
}
span.notification_word {
background-color: rgb(196, 77, 243);
padding: 10px 0;
margin: 3px;
width: 100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 5px;
}
<button class="toast">Toast Notification</button>
<div class="notification">
</div>
Happens in your code -> 5 seconds after you click the button, the notification that appears after you click the button disappears.
In the code I wrote, after a delay of 5 seconds it will remove the oldest notification: it will loop
I think you can understand.
Try this code ...
let toast = document.querySelector('.toast');
let notification = document.querySelector(".notification");
let sec = 5000;
let Divarray = [];
let arraynum = 0;
toast.addEventListener('click', () => {
let newDiv = document.createElement("span");
let newText = document.createTextNode("No Way!"+arraynum);
newDiv.classList.add("notification_word");
newDiv.appendChild(newText);
notification.appendChild(newDiv);
Divarray[arraynum] = newDiv;
arraynum += 1;
})
function array(){
setInterval(function(){
Divarray.splice(arraynum, 1);
removeNotification();
},sec);
}
array();
function removeNotification() {
document.querySelectorAll(".notification_word")[0].remove();
}
body {
text-align: center;
justify-content: center;
align-items: center;
}
button.toast {
position: absolute;
top: 50%;
left: 50%;
width: 200px;
height: 100px;
font-size: 20px;
background: rgb(215, 188, 240);
margin: -100px 0 0 -100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 20px;
cursor: pointer;
}
button.toast:hover {
background: rgb(178, 157, 201);
}
.notification {
display: flex;
flex-direction: column-reverse;
position: absolute;
right: 2%;
bottom: 2%;
}
span.notification_word {
background-color: rgb(196, 77, 243);
padding: 10px 0;
margin: 3px;
width: 100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 5px;
}
<button class="toast">Toast Notification</button>
<div class="notification">
</div>
Replacing setInterval with setTimeout should fix your problem.
setTimeout(() => { removeNotification(); }, sec);
you can learn more from here: setTimeout or setInterval?
setInterval would execute every specified interval unless its cleared using clearInterval. You could check if there exists any other .notification_word classes, if not clearInterval.
Or a simple no brainer would be to replace setInterval with setTimeout. The latter will execute only once after 5 secs, which seems the ideal solution to what you seem to achieve.
At first, when you use the queryselectorAll javascript delete every single toast that match with the classname. I assume that is not the intention of a toast notification. So i created a new piece of code that handle removing the specific element. second, the javascript interval fires every preset seconds, but your intention is one time! so instead of using interval i recommend to use the setTimeout function.
To avoid double ids i created an object where ids are being 'parked'.
let toast = document.querySelector('.toast');
let notification = document.querySelector(".notification")
let sec = 5000;
let UID = {};
toast.addEventListener('click', () => {
let newDiv = document.createElement("span");
let newText = document.createTextNode("No Way!");
let id = Math.floor(Math.random() * 100);
let check = false
while(check == false) {
if(id in UID == false) {
UID[ id ] = {};
check = true;
} else {
id = Math.floor(Math.random() * 100);
}
}
newDiv.id = id;
newDiv.classList.add("notification_word");
newDiv.appendChild(newText);
notification.appendChild(newDiv);
if (document.getElementById(id)) {
setTimeout(function() {
document.getElementById(id).remove()
delete UID[ id ];
}, sec);
}
})
body {
text-align: center;
justify-content: center;
align-items: center;
}
button.toast {
position: absolute;
top: 50%;
left: 50%;
width: 200px;
height: 100px;
font-size: 20px;
background: rgb(215, 188, 240);
margin: -100px 0 0 -100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 20px;
cursor: pointer;
}
button.toast:hover {
background: rgb(178, 157, 201);
}
.notification {
display: flex;
flex-direction: column-reverse;
position: absolute;
right: 2%;
bottom: 2%;
}
span.notification_word {
background-color: rgb(196, 77, 243);
padding: 10px 0;
margin: 3px;
width: 100px;
border: 1px solid rgb(28, 3, 51);
border-radius: 5px;
}
<body>
<button class="toast">Toast Notification</button>
<div class="notification">
</div>
I programmed an HTML editor, but it isn’t working. It was working a little time ago, but probably my sister edited the code (she practically knows nothing of HTML)
Now the problem is that whenever I press the enter key, instead of simply moving to the next line, a rectangle is created. Why?
Here is the code:
const first = document.querySelector(".first");
const iframe = document.querySelector("iframe");
const btn = document.querySelector("button");
btn.addEventListener("click", () => {
var html = first.textContent;
iframe.src = "data:text/html;charset=utf-8," + encodeURI(html);
});
first.addEventListener('keyup',()=>{
var html = first.textContent;
iframe.src = "data:text/html;charset=utf-8," + encodeURI(html);
})
first.addEventListener("paste", function(e) {
e.preventDefault();
var text = e.clipboardData.getData("text/plain");
document.execCommand("insertText", false, text);
});
* {
box-shadow: 0 2px 3px black;
position: fixed;
height: 100vh;
justify-content: center;
align-items: center;
border: 7px solid #36383f;
}
.first {
background-color: #ffffff;
width: 50%;
overflow-x: hidden;
overflow-y: auto;
white-space: pre;
box-shadow: 0 1px 1px rgb(22, 22, 22);
outline: none;
padding: 0.4rem;
height: 90vh;
}
.second {
background-color: rgb(255, 255, 255);
width: 50%;
overflow-y: auto;
white-space: pre;
right: 0;
box-shadow: 0 1px 1px rgb(22, 22, 22);
padding: 0.4rem;
height: 90vh;
}
<div class="main-editor">
<button class="btn">Run</button>
<div class="first" contenteditable>writecode</div>
<iframe class="second" > </iframe>
</div>
It is because you added box-shadow and border to all elements.
Remove them from *.
I changed * to .first, .second
const first = document.querySelector(".first");
const iframe = document.querySelector("iframe");
const btn = document.querySelector("button");
btn.addEventListener("click", () => {
var html = first.textContent;
iframe.src = "data:text/html;charset=utf-8," + encodeURI(html);
});
first.addEventListener('keyup',()=>{
var html = first.textContent;
iframe.src = "data:text/html;charset=utf-8," + encodeURI(html);
})
first.addEventListener("paste", function(e) {
e.preventDefault();
var text = e.clipboardData.getData("text/plain");
document.execCommand("insertText", false, text);
});
.first, .second {
box-shadow: 0 2px 3px black;
position: fixed;
justify-content: center;
align-items: center;
border: 7px solid #36383f;
}
.first {
background-color: #ffffff;
width: 50%;
overflow-x: hidden;
overflow-y: auto;
white-space: pre;
box-shadow: 0 1px 1px rgb(22, 22, 22);
outline: none;
padding: 0.4rem;
height: 90vh;
}
.second {
background-color: rgb(255, 255, 255);
width: 50%;
overflow-y: auto;
white-space: pre;
right: 0;
box-shadow: 0 1px 1px rgb(22, 22, 22);
padding: 0.4rem;
height: 90vh;
}
<div class="main-editor">
<button class="btn">Run</button>
<div class="first" contenteditable>writecode</div>
<iframe class="second" > </iframe>
</div>
https://codepen.io/matthewbert86/pen/pogdEvB
http://beer-food.surge.sh/
I am working on a little search app. It pulls up the beer pairing results based on what food you type in. My problem is that after I get results once, it wont clear out, and the same results stay up for anything I try to enter after that. Ive been messing with it for a long time and no luck. Any suggestions?
// Step 1 - assign elements from HTML and assign it to javascript variables
const btnSearch = document.getElementById('btnSearch');
const txtSearch = document.getElementById('food');
const resultArea = document.getElementById('result');
// This is where we will store out output as its process
let out = "";
// an onclick function runs when the button is clicked
btnSearch.onclick = function() {
// this returns the user input from the searchbar
var searchTerm = txtSearch.value;
const url = `https://api.punkapi.com/v2/beers?food=${searchTerm}`
console.log(url);
// fetch will go to the url
fetch(url)
.then(function(data) {
// return jsonObject from the url
return data.json();
})
.then(function(jsonObject) {
console.log(jsonObject);
for (beer in jsonObject) {
const beerInfo = new Array(jsonObject[beer].name, jsonObject[beer].tagline, jsonObject[beer].description, jsonObject[beer].image_url)
beerOut(beerInfo);
}
resultArea.innerHTML = out;
})
.catch(function(e) {
console.log("Error: " + e);
});
}
// This function we will use logic to take the array from beerOut and display it in HTML using template literals
function beerOut(beer) {
console.log(beer);
out += `<div class="beer">
<div class="beerImage"><img src="${beer[3]}"/></div>
<div class="beerText">
<h2>${beer[0]}</h2>
<h3>${beer[1]}</h3>
<p><em>${beer[2]}</em></p>
</div><!--beerText-->
</div><!--beer-->
`
//This will go back to the resultArea.innerHTML = out; to display on the main page
}
#food {
width: 50%;
margin: 0 25%;
border: 3px solid black;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
text-align: center;
}
.text-input,
.text-input--underbar {
font: inherit;
vertical-align: top;
-moz-osx-font-smoothing: grayscale;
letter-spacing: 0;
box-shadow: none;
padding: 20px;
width: auto;
height: 31px;
border: none;
margin: 0;
outline: 0;
}
#container {
margin: 5px;
}
#btnSearch {
display: flex;
align-items: center;
justify-content: center;
width: 200px;
font-size: 30px;
padding: 10px 10px;
text-align: center;
margin: 0 auto;
}
.beer {
border: 1px solid black;
margin: 5px;
margin-bottom: 15px;
padding: 10px;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
justify-content: space-between;
}
.beerImage {
padding: 30px;
width: 50px;
/*order: 1;*/
}
.beerImage img {
width: 60px;
}
.beerText {
width: 85%;
padding: 20px;
}
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsenui.css">
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsen-css-components.min.css">
<script src="https://unpkg.com/onsenui/js/onsenui.min.js"></script>
<link rel="stylesheet" href="style.css">
</head>
<body>
<ons-page>
<ons-toolbar>
<div class="center">Beer & Food Pairings</div>
</ons-toolbar>
<section id="container">
<p>
<ons-input id="food" modifier="underbar" placeholder="enter a food to pair">
</ons-input>
</p>
<p>
<ons-button modifier="medium" id="btnSearch">Search</ons-button>
</p>
<div id="result"></div>
</section>
</ons-page>
You saved the out
Here I clear the potential containers and add a random to the url to make sure it is not cached
btnSearch.onclick = function() {
out = "";
I search for "ale" and get result and "lager" and get none
// Step 1 - assign elements from HTML and assign it to javascript variables
const btnSearch = document.getElementById('btnSearch');
const txtSearch = document.getElementById('food');
const resultArea = document.getElementById('result');
// This is where we will store out output as its process
let out = "";
// an onclick function runs when the button is clicked
btnSearch.onclick = function() {
out = "";
resultArea.innerHTML = "Please wait...";
jsonObject = ""
// this returns the user input from the searchbar
var searchTerm = txtSearch.value;
const url = `https://api.punkapi.com/v2/beers?food=${searchTerm}&rdn=${new Date().getTime()}`
console.log(url);
// fetch will go to the url
fetch(url)
.then(function(data) {
// return jsonObject from the url
return data.json();
})
.then(function(jsonObject) {
console.log(jsonObject);
for (beer in jsonObject) {
const beerInfo = new Array(jsonObject[beer].name, jsonObject[beer].tagline, jsonObject[beer].description, jsonObject[beer].image_url)
beerOut(beerInfo);
}
resultArea.innerHTML = out;
})
.catch(function(e) {
console.log("Error: " + e);
});
}
// This function we will use logic to take the array from beerOut and display it in HTML using template literals
function beerOut(beer) {
console.log(beer);
out += `<div class="beer">
<div class="beerImage"><img src="${beer[3]}"/></div>
<div class="beerText">
<h2>${beer[0]}</h2>
<h3>${beer[1]}</h3>
<p><em>${beer[2]}</em></p>
</div><!--beerText-->
</div><!--beer-->
`
//This will go back to the resultArea.innerHTML = out; to display on the main page
}
#food {
width: 50%;
margin: 0 25%;
border: 3px solid black;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
text-align: center;
}
.text-input,
.text-input--underbar {
font: inherit;
vertical-align: top;
-moz-osx-font-smoothing: grayscale;
letter-spacing: 0;
box-shadow: none;
padding: 20px;
width: auto;
height: 31px;
border: none;
margin: 0;
outline: 0;
}
#container {
margin: 5px;
}
#btnSearch {
display: flex;
align-items: center;
justify-content: center;
width: 200px;
font-size: 30px;
padding: 10px 10px;
text-align: center;
margin: 0 auto;
}
.beer {
border: 1px solid black;
margin: 5px;
margin-bottom: 15px;
padding: 10px;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
justify-content: space-between;
}
.beerImage {
padding: 30px;
width: 50px;
/*order: 1;*/
}
.beerImage img {
width: 60px;
}
.beerText {
width: 85%;
padding: 20px;
}
<!doctype html>
<html>
<head>
<title>Search</title>
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsenui.css">
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsen-css-components.min.css">
<script src="https://unpkg.com/onsenui/js/onsenui.min.js"></script>
</head>
<body>
<ons-page>
<ons-toolbar>
<div class="center">Beer & Food Pairings</div>
</ons-toolbar>
<section id="container">
<p>
<ons-input id="food" modifier="underbar" placeholder="enter a food to pair">
</ons-input>
</p>
<p>
<ons-button modifier="medium" id="btnSearch">Search</ons-button>
</p>
<div id="result"></div>
</section>
</ons-page>
Simpler version - I fixed your missing image
function beerOut(jsonObject) {
return jsonObject.map(item => {
const {name, tagline, description, image_url} = item;
return `<div class="beer">
<div class="beerImage"><img src="${image_url || 'https://i.ya-webdesign.com/images/wine-bottle-silhouette-png-14.png'}"/></div>
<div class="beerText">
<h2>${name}</h2>
<h3>${tagline}</h3>
<p><em>${description}</em></p>
</div><!--beerText-->
</div><!--beer-->
`;
})
}
// Step 1 - assign elements from HTML and assign it to javascript variables
const btnSearch = document.getElementById('btnSearch');
const txtSearch = document.getElementById('food');
const resultArea = document.getElementById('result');
// This is where we will store out output as its process
// an onclick function runs when the button is clicked
btnSearch.addEventListener("click",function() {
resultArea.innerHTML = "Please wait...";
// this returns the user input from the searchbar
var searchTerm = txtSearch.value;
const url = `https://api.punkapi.com/v2/beers?food=${searchTerm}&rdn=${new Date().getTime()}`;
console.log(url);
// fetch will go to the url
fetch(url)
.then(function(data) {
return data.json();
})
.then(function(jsonObject) {
resultArea.innerHTML = beerOut(jsonObject);
})
.catch(function(e) {
console.log("Error: " + e);
});
})
// This function we will use logic to take the array from beerOut and display it in HTML using template literals
function beerOut(jsonObject) {
return jsonObject.map(item => {
const {name, tagline, description, image_url} = item;
return `<div class="beer">
<div class="beerImage"><img src="${image_url || 'https://i.ya-webdesign.com/images/wine-bottle-silhouette-png-14.png'}"/></div>
<div class="beerText">
<h2>${name}</h2>
<h3>${tagline}</h3>
<p><em>${description}</em></p>
</div><!--beerText-->
</div><!--beer-->
`;
})
}
#food {
width: 50%;
margin: 0 25%;
border: 3px solid black;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
text-align: center;
}
.text-input,
.text-input--underbar {
font: inherit;
vertical-align: top;
-moz-osx-font-smoothing: grayscale;
letter-spacing: 0;
box-shadow: none;
padding: 20px;
width: auto;
height: 31px;
border: none;
margin: 0;
outline: 0;
}
#container {
margin: 5px;
}
#btnSearch {
display: flex;
align-items: center;
justify-content: center;
width: 200px;
font-size: 30px;
padding: 10px 10px;
text-align: center;
margin: 0 auto;
}
.beer {
border: 1px solid black;
margin: 5px;
margin-bottom: 15px;
padding: 10px;
border-radius: 5px;
background-color: white;
-webkit-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
box-shadow: 10px 13px 30px -19px rgba(0, 0, 0, 0.5);
display: flex;
justify-content: space-between;
}
.beerImage {
padding: 30px;
width: 50px;
/*order: 1;*/
}
.beerImage img {
width: 60px;
}
.beerText {
width: 85%;
padding: 20px;
}
<!doctype html>
<html>
<head>
<title>Search</title>
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsenui.css">
<link rel="stylesheet" href="https://unpkg.com/onsenui/css/onsen-css-components.min.css">
<script src="https://unpkg.com/onsenui/js/onsenui.min.js"></script>
</head>
<body>
<ons-page>
<ons-toolbar>
<div class="center">Beer & Food Pairings</div>
</ons-toolbar>
<section id="container">
<p>
<ons-input id="food" modifier="underbar" placeholder="enter a food to pair">
</ons-input>
</p>
<p>
<ons-button modifier="medium" id="btnSearch">Search</ons-button>
</p>
<div id="result"></div>
</section>
</ons-page>