my goal is to build playing drums using vanilla Javascript, whole code worked perfectly when I was using only the keydown event, unfortunately, my drums have to play also on mouse 'click'.
When I added "|| event.button == aKey == 0" this part to my condition, it still plays, but only one sound on each key. So I assumed that there is something wrong with my condition.
And also if it would be possible to somehow make my code less repeatable, I would appreciate it.
const aKey = document.getElementById("A-key");
const sKey = document.getElementById("S-key");
const dKey = document.getElementById("D-key");
const fKey = document.getElementById("F-key");
const gKey = document.getElementById("G-key");
const hKey = document.getElementById("H-key");
const jKey = document.getElementById("J-key");
const kKey = document.getElementById("K-key");
const lKey = document.getElementById("L-key");
const playFunction = (event) => {
if (event.code == "KeyA" || event.button == aKey == 0) {
//
let audioA = document.createElement("AUDIO");
if (audioA.canPlayType("audio/wav")) {
audioA.setAttribute("src","sounds/boom.wav");
}
audioA.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioA);
} else if (event.code == "KeyS" || event.button == sKey == 0 ) {
let audioS= document.createElement("AUDIO");
if (audioS.canPlayType("audio/wav")) {
audioS.setAttribute("src","sounds/clap.wav");
}
audioS.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioS);
} else if (event.code == "KeyD" || event.button == dKey == 0) {
let audioD = document.createElement("AUDIO");
if (audioD.canPlayType("audio/wav")) {
audioD.setAttribute("src","sounds/hihat.wav");
}
audioD.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioD);
} else if (event.code == "KeyF" || event.button == fKey == 0) {
let audioF = document.createElement("AUDIO");
if (audioF.canPlayType("audio/wav")) {
audioF.setAttribute("src","sounds/kick.wav");
}
audioF.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioF);
} else if (event.code == "KeyG" || event.button == gKey == 0) {
let audioG = document.createElement("AUDIO");
if (audioG.canPlayType("audio/wav")) {
audioG.setAttribute("src","sounds/openhat.wav");
}
audioG.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioG);
} else if (event.code == "KeyH" || event.button == hKey == 0) {
let audioH = document.createElement("AUDIO");
if (audioH.canPlayType("audio/wav")) {
audioH.setAttribute("src","sounds/ride.wav");
}
audioH.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioH);
} else if (event.code == "KeyJ" || event.button == jKey == 0) {
let audioJ = document.createElement("AUDIO");
if (audioJ.canPlayType("audio/wav")) {
audioJ.setAttribute("src","sounds/snare.wav");
}
audioJ.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioJ);
} else if (event.code == "KeyK" || event.button == kKey == 0) {
let audioK = document.createElement("AUDIO");
if (audioK.canPlayType("audio/wav")) {
audioK.setAttribute("src","sounds/tink.wav");
}
audioK.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioK);
} else if (event.code == "KeyL" || event.button == lKey == 0) {
let audioL = document.createElement("AUDIO");
if (audioL.canPlayType("audio/wav")) {
audioL.setAttribute("src","sounds/tom.wav");
}
audioL.setAttribute("autoplay", "autoplay");
document.body.appendChild(audioL);
} else {
console.log("Try to use specified keys.")
}
};
window.addEventListener('keydown', playFunction, false);
window.addEventListener('click', playFunction, false);
event.button == kKey == 0 doesn't make much sense. This evaluates like (foo == bar) == baz, that is, the first condition is tested, then the result of that (true or false) is checked against the other condition. If you want to test multiple conditions, use || or && between every condition. Also, always use === to avoid surprising conversion behavior.
As for the refactor request, whenever you have a bunch of branches that only differ based on parameterizable values, like the button text or the sound, use a data structure such as an array or object and index/key into it.
Specifically, all you need here are key -> audio or audio URL pairs, so an object seems suitable.
Once you have such a structure, then you can access the power of loops to DRY out your code.
I don't have your audio files or markup, so you can try to adapt this proof of concept to your project:
const baseURL = `https://upload.wikimedia.org/wikipedia/commons/`;
const sounds = {
a: `7/7c/Bombo_Leg%C3%BCero_Grave.ogg`,
s: `7/7f/Bombo_Ac%C3%BAstico.ogg`,
d: `3/35/Bongo_Agudo.ogg`,
f: `4/44/Bongo_Grave.ogg`,
g: `b/b4/Sting.ogg`,
// ... add more key-sound URL pairs ...
};
Object.keys(sounds).forEach(key => {
const btn = document.createElement("button");
document.querySelector("#drum-pad").appendChild(btn);
const sound = new Audio(baseURL + sounds[key]);
sounds[key] = sound;
btn.textContent = key;
btn.addEventListener("click", e => {
sound.currentTime = 0;
sound.play();
});
});
document.addEventListener("keydown", e => {
if (sounds[e.key]) {
sounds[e.key].currentTime = 0;
sounds[e.key].play();
}
});
<div id="drum-pad"></div>
Here is my jQuery for dynamic attached elements. The jq-select-ring button can be multiple on the DOM. Basically, it was attached through an Ajax call.
let cKeyTabShift = false;
$("body").on("keydown", ".jq-select-ring", function (e) {
if (!isMobileSite) {
var keyCode = (e.keyCode ? e.keyCode : e.which);
if (keyCode == 9) {
if (e.shiftKey) {
cKeyTabShift = true;
} else {
cKeyTabShift = false;
}
}
}
});
$("body").on("focusout", ".jq-select-ring", function () {
if (!isMobileSite) {
const parentIndex = $(this).closest('.flex-item').index();
const $elmSliders = $(this).closest('.container').find("div[id^='touchCarousel-'][role='tabpanel']");
const $nextArrow = $(this).closest('.touch-carousel').find('.touchcarousel-next');
const $prevArrow = $(this).closest('.touch-carousel').find('.touchcarousel-prev');
if (typeof ($elmSliders) != "undefined" && $elmSliders.length > 0) {
if ($elmSliders.length > 1) {
if (parentIndex == 1 && cKeyTabShift == false) {
if (!$nextArrow.hasClass('endArrows')) {
$nextArrow.trigger('click');
}
}
if (parentIndex == 0 && cKeyTabShift == true) {
if (!$prevArrow.hasClass('endArrows')) {
$prevArrow.trigger('click');
cKeyTabShift = false;
}
}
}
}
}
});
The issue is the trigger click is called when I add breakpoint only.
$nextArrow.trigger('click');
$prevArrow.trigger('click');
I have a Homepage Takover running on our website. and I have already written code for displaying the image as background image and it is clickable.
But I need certain part of image needs to clickable to another URL.
<!DOCTYPE html>
<html>
<head>
<title>asdfasdf</title>
</head>
<body>
<div>
<script>
if (top == self) {
var interWindow = window;
var interDoc = window.document;
} else {
try {
var interWindow = window.parent;
var interDoc = window.parent.document;
} catch (e) {
/* The creative cannot escape the iframe. Show an appropriate alternative. The alternative will remain inside of the iframe. */
}
}
var timeDelay = 0;
var backgroundColor = '#ffffff';
function initBackground() {
high = window.screen.height;
size = window.screen.width;
if (size <= 1280) {
interDoc.body.style.backgroundImage = none;
} else if (size > 1280 && size < 1440) {
interDoc.body.style.backgroundImage = "url(https://i.ibb.co/L9hnZJ1/hpto.gif)";
} else {
interDoc.body.style.backgroundImage = "url(https://i.ibb.co/L9hnZJ1/hpto.gif)";
}
if (backgroundColor != '') {
interDoc.body.style.backgroundColor = backgroundColor;
}
interDoc.body.style.backgroundRepeat = 'no-repeat';
interDoc.body.style.backgroundPosition = 'top center';
interDoc.body.style.backgroundAttachment = 'fixed';
interDoc.onclick = backGroundClick;
}
var backGroundClick = function (e) {
if (document.all) {
if (event.button == 2 || event.button == 3) {
return false;
}
} else {
if (e.button == 2 || e.button == 3) {
e.preventDefault();
e.stopPropagation();
return false;
}
}
var link = 'google.com';
EE = e ? e : event;
if (!EE) {
return;
}
var t = EE.target ? EE.target : EE.srcElement;
if (t.tagName == "BODY" || t.tagName == "HTML" || t.tagName == "HEADER" || t.tagName == "SECTION" || t.tagName == "FOOTER") {
var ad = window.open("" + link);
} else {
console.log('link click event: ' + t.tagName);
}
}
interDoc.onmouseover = function (e) {
EE = e ? e : event;
if (!EE)
return;
var t = EE.target ? EE.target : EE.srcElement;
if (t.tagName == "BODY" || t.tagName == "HTML" || t.tagName == "HEADER" || t.tagName == "SECTION" || t.tagName == "FOOTER") {
interDoc.body.parentNode.style.cursor = 'pointer';
} else {
interDoc.body.parentNode.style.cursor = 'auto';
}
}
window.setTimeout("initBackground();", timeDelay);
</script>
</div>
</body>
</html>
The Red highlited part in the background image needs to redirect to another URL when onclick.
This JavaScript function is working fine when I execute it through the debugger, but when I am not using the debugger, it's not executing:
function setColumnDisabled(){
var activeGrid = null;
var activeTab = tabbar1.getActiveTab();
if (activeTab == "a1") {
activeGrid = genInfo.mygrid;
}else if (activeTab == "a2") {
activeGrid = genInfo.mygrid2;
} else if (activeTab == "a21") {
activeGrid = genInfo.mygrid3;
} else if (activeTab == "a22") {
activeGrid = genInfo.mygrid3;
}else if(activeTab == "PartialTunnels"){
activeGrid = genInfo.partialObjectsGrid;
}
if(activeGrid != null){
activeGrid.forEachRow(function(row_id){
activeGrid.cellById(row_id,activeGrid.getColIndexById("Shared")).setDisabled(true);
});
}
}
so i bought a site witch is connected to a gestional programm in office..
the site is a little old, it's fully compatible with all the versions of internet explorer but not with other browsers(opera,safari,chrome,firefox...)
the only piece not working is a menu not opening correctly, when you click on it it doesn't happen anything or in chrome it changes the image but it doesn't upload the links. it seems that it doens't upload things in the hiddenframe...
in chrome it gives error in loadchildren function.
in firefox it gives error in function Toc_click ()
TypeError: window.event is undefined
[Break On This Error]
var eSrc = window.event.srcElement;
we searched for the problem and we think that the problem should be in this file
the problem should be a syntax problem, it's compatible in old browsers but not on the new ones. i cannot change completely the code as it is connected with other files(a lot) and sql server...
we already tried to change
document.frames["hiddenframe"].location.replace(strLoc);
by
document.getElementsByName("hiddenframe").location.replace(strLoc);
it doens't work and it doesn't work on IE either...
/* TOC.JS */
var framesTop = parent.parent;
//var L_LoadingMsg_HTMLText = "Loading, click to cancel...";
var LoadDiv = '<DIV ONCLICK="loadFrame(true);" CLASS="clsLoadMsg">';
L_LoadingMsg_HTMLText = LoadDiv + L_LoadingMsg_HTMLText + "</LI>";
function caps(){
var UA = navigator.userAgent;
if(UA.indexOf("MSIE") != -1)
{
this.ie = true;
this.v = UA.charAt(UA.indexOf("MSIE") + 5);
if( this.v == 2 ) this.ie2 = true;
else if( this.v == 3 ) this.ie3 = true;
else if( this.v == 4 ) this.ie4 = true;
else if( this.v == 5 ) this.ie5 = true;
else if( this.v == 6 ) this.ie6 = true;
else this.ie6 = true;
}
else if(UA.indexOf("Mozilla") != -1 && UA.indexOf("compatible") == -1)
{
this.nav = true;
var v = UA.charAt(UA.indexOf("Mozilla") + 8);
if(v == 2 ) this.nav2 = true;
else if(v == 3 ) this.nav3 = true;
else if(v == 4 ) this.nav4 = true;
}
if(UA.indexOf("Windows 95") != -1 || UA.indexOf("Win95") != -1 || UA.indexOf("Win98") != -1 || UA.indexOf("Windows 98") != -1 || UA.indexOf("Windows NT") != -1 || UA.indexOf("Windows XP") != -1) this.win32 = true;
else if(UA.indexOf("Windows 3.1") != -1 || UA.indexOf("Win16") != -1) this.win16 = true;
else if(UA.indexOf("Mac") != -1) this.anymac = true;
else if(UA.indexOf("SunOS") != -1 || UA.indexOf("HP-UX") != -1 || UA.indexOf("X11") != -1) this.unix = true;
else if(UA.indexOf("Windows CE") != -1) this.wince = true;
}
var bc = new caps();
////////////////////////////////////////////
// Not sure why this is here, it puts a scrollbar up when none is needed
// if("object" == typeof(parent.document.all.fraPaneToc)) parent.document.all.fraPaneToc.scrolling = "yes";
////////////////////////////////////////////
var eSynchedNode = null;
var eCurrentUL = null;
var eCurrentLI = null;
var bLoading = false;
function loadFrame( bStopLoad )
{
if( "object" == typeof( eCurrentUL ) && eCurrentUL && !bStopLoad )
{
eCurrentUL.innerHTML = hiddenframe.chunk.innerHTML;
eCurrentUL = null;
bLoading = false;
}
else if( "object" == typeof( eCurrentUL ) && eCurrentUL )
{
eCurrentUL.parentElement.children[1].className = "";
eCurrentUL.parentElement.children[0].src = "bs.gif";
eCurrentUL.parentElement.className = "kid";
eCurrentUL.className = "clsHidden";
eCurrentUL.innerHTML="";
eCurrentUL = null;
bLoading = false;
}
else
{
bLoading = false;
}
return;
}
function GetNextUL(eSrc)
{
var eRef = eSrc;
for(var i = eRef.sourceIndex + 1; i < document.all.length; i++)
{
if( "UL" == document.all[ i ].tagName )
{
return document.all[ i ];
}
else if( "LI" == document.all[ i ].tagName )
{
break;
}
}
return false;
}
function MarkSync(eSrc)
{
if("object" == typeof(aNodeTree)) aNodeTree = null;
if("LI" == eSrc.tagName.toUpperCase() && eSrc.children[1] && eSynchedNode != eSrc )
{
UnmarkSync();
eSrc.children[1].style.fontWeight = "bold";
eSynchedNode = eSrc;
}
}
function UnmarkSync()
{
if("object" == typeof(eSynchedNode) && eSynchedNode )
{
eSynchedNode.children[1].style.fontWeight = "normal";
eSynchedNode = null;
}
}
function MarkActive(eLI)
{
if( "object" == typeof( eLI ) && eLI && "LI" == eLI.tagName.toUpperCase() && eLI.children[1] && eLI != eCurrentLI )
{
MarkInActive();
window.eCurrentLI = eLI;
window.eCurrentLI.children[1].className = "clsCurrentLI";
}
}
function MarkInActive()
{
if( "object" == typeof( eCurrentLI ) && eCurrentLI )
{
window.eCurrentLI.children[1].className = "";
window.eCurrentLI = null;
}
}
function LoadChildren( eLink )
{
var strLoc = "loadtree.asp" + eLink.href.substring( eLink.href.indexOf( "?" ) );
document.frames["hiddenframe"].location.replace(strLoc);
}
function Navigate_URL( eSrc )
{
var eLink = eSrc.parentElement.children[1];
urlIdx = eLink.href.indexOf( "URL=" );
if("object" == typeof(framesTop.fraTopic) && eLink && "A" == eLink.tagName && urlIdx != -1 )
{
if(eLink.target=="fraTopic"||eLink.target=="_top"){
framesTop.fraTopic.location.href = eSrc.parentElement.children[1].href.substring( urlIdx + 4 );
}else{
window.open(eSrc.parentElement.children[1].href,eLink.target);
}
MarkSync(eSrc.parentElement);
}
else if("object" == typeof(framesTop.fraTopic) && eLink && "A" == eLink.tagName && eLink.href.indexOf( "tocPath=" ) == -1 && eLink.href.indexOf( "javascript:" ) == -1 )
{
if(eLink.target=="fraTopic")
{
framesTop.fraTopic.location.href = eSrc.parentElement.children[1].href;
}
else if( eLink.target=="_top" )
{
top.location = eLink.href;
return;
}
else
{
window.open(eSrc.parentElement.children[1].href,eLink.target);
}
MarkSync(eSrc.parentElement);
}
else if( eSynchedNode != eSrc.parentElement && ( urlIdx != -1 || ( eLink.href.indexOf( "javascript:" ) == -1 && eLink.href.indexOf( "tocPath=" ) == -1 ) ) )
{
// START D.S.
if(eLink.target=="fraTopic")
{
if (navigator.userAgent.indexOf("Windows") == -1) {
var MyHref = eSrc.parentElement.children[1].href;
do
{
if (MyHref.indexOf("%2E") != -1) MyHref = MyHref.replace("%2E", ".");
else if (MyHref.indexOf("%2F") != -1) MyHref = MyHref.replace("%2F", "/");
else if (MyHref.indexOf("%3F") != -1) MyHref = MyHref.replace("%3F", "?");
else if (MyHref.indexOf("%3D") != -1) MyHref = MyHref.replace("%3D", "=");
else if (MyHref.indexOf("%26") != -1) MyHref = MyHref.replace("%26", "&");
else break;
}
while (true);
parent.fraTopic.location.href = MyHref;
} else {
parent.fraTopic.location.href = eSrc.parentElement.children[1].href;
}
}
// END D.S.
MarkSync( eSrc.parentElement );
}
}
function Image_Click( eSrc , bLeaveOpen )
{
var eLink = eSrc.parentElement.children[1];
if("noHand" != eSrc.className)
{
eLI = eSrc.parentElement;
MarkActive(eLI);
var eUL = GetNextUL(eLI);
if(eUL && "kidShown" == eLI.className)
{
// hide on-page kids
if( !bLeaveOpen )
{
eLI.className = "kid";
eUL.className = "clsHidden";
eSrc.src = "bs.gif";
}
}
else if(eUL && eUL.all.length)
{
// show on-page kids
eLI.className = "kidShown";
eUL.className = "clsShown";
eSrc.src = "bo.gif";
}
else if("kid" == eLI.className)
{
// load off-page kids
if( !bLoading )
{
bLoading = true;
eLI.className = "kidShown";
eUL.className = "clsShown";
window.eCurrentUL = eUL;
eSrc.src = "bo.gif";
eUL.innerHTML = L_LoadingMsg_HTMLText;
LoadChildren( eLink );
}
}
}
}
function Toc_click ()
{
var eSrc = window.event.srcElement;
event.returnValue = false;
if("A" == eSrc.tagName.toUpperCase() && "LI" == eSrc.parentElement.tagName)
{
var eImg = eSrc.parentElement.children[0];
if(eImg) eImg_click(eImg);
}
else if("SPAN" == eSrc.tagName && "LI" == eSrc.parentElement.tagName)
{
var eImg = eSrc.parentElement.children[0];
if(eImg) eImg_click(eImg);
}
else if("IMG" == eSrc.tagName)
{
}
return event.returnValue;
}
function eImg_click(eImg)
{
if("IMG" == eImg.tagName)
{
Image_Click( eImg , false );
Navigate_URL( eImg );
}
}
function Toc_dblclick()
{
return;
}
function window_load()
{
if( self == top ) location.replace( "default.asp" );
var objStyle = null;
if( bc.win32 && ( bc.ie4 || bc.ie5 || bc.ie6 ) && "object" == typeof ( ulRoot ) && "object" == typeof( objStyle = document.styleSheets[0] ) && "object" == typeof( objStyle.addRule ) )
{
window.eSynchedNode = document.all["eSynchedNode"];
objStyle.addRule( "UL.clsHidden" , "display:none" , 0 );
objStyle.addRule( "UL.hdn" , "display:none" , 0 );
//--ulRoot.onclick=Toc_click;
ulRoot.ondblclick=Toc_dblclick;
if( window.eSynchedNode )
{
MarkActive(window.eSynchedNode);
window.eSynchedNode.all.tags( "B" )[0].outerHTML = eSynchedNode.all.tags("B")[0].innerHTML;
window.scrollTo(0,window.eSynchedNode.offsetTop-(document.body.clientHeight/2));
}
else
{
MarkActive(document.all.tags( "LI" )[0]);
}
}
}
window.onload = window_load;
suggestions?