Put automatic sub-heading on my table of content - javascript

I want automatic sub-headings, can anyone help me?
I just learn DOM property yesterday .I am just familiar with HTML css.
function bttext() {
var btn = document.getElementById("bttext");
if (btn.innerText == "show") {
btn.innerText = "hide";
} else {
btn.innerText = "show";
}
var x = document.getElementById("hide");
if (x.style.display === "none") {
x.style.display = "block";
} else {
x.style.display = "none";
}
}
var hsub = sub = s = htoc = i = hl = gh = 0;
hl = document.getElementById("p-toc").getElementsByTagName("h2").length;
for (i = 0; i < hl; i++) {
gh = document.getElementById("p-toc").getElementsByTagName("h2")[i].innerText;
document.getElementById("p-toc").getElementsByTagName("h2")[i].setAttribute("id", "point" + i);
htoc = "<li><a href='#point" + i + "'>" + gh + "</a></li>";
document.getElementById("htoc").innerHTML += htoc;
}
hsub = document.getElementById("p-toc").getElementsByTagName("h3").length;
for (s = 0; s < hsub; s++) {
sub = document.getElementById("p-toc").getElementsByTagName("h3")[i].innerText;
document.getElementById("p-toc").getElementsByTagName("h3")[i].setAttribute("id", "sub" + i);
stoc = "<li><a href='#sub" + i + "'>" + sub + "</a></li>";
document.getElementById("stoc").innerHTML += stoc;
}
//*************TOC plugin by MyBloggerTricks.com
function mbtTOC() {
var mbtTOC = i = headlength = gethead = 0;
headlength = document.getElementById("post-toc").getElementsByTagName("h2").length;
for (i = 0; i < headlength; i++) {
gethead = document.getElementById("post-toc").getElementsByTagName("h2")[i].textContent;
document.getElementById("post-toc").getElementsByTagName("h2")[i].setAttribute("id", "point" + i);
mbtTOC = "<li><a href='#point" + i + "'>" + gethead + "</a></li>";
document.getElementById("mbtTOC").innerHTML += mbtTOC;
}
}
function mbtToggle() {
var mbt = document.getElementById('mbtTOC');
if (mbt.style.display === 'none') {
mbt.style.display = 'block';
} else {
mbt.style.display = 'none';
}
}
.toc {
border: 3px solid #A2A9B1;
background-color: #F8F9FA;
display: block;
line-height: 1.4em;
width: 70%;
display: block;
padding: 20px 30px 10px;
border-radius: 5px;
}
.toc button {
background-color: inherit;
font-size: 16px;
outline: none;
border: none;
padding: 0px 0px 10px;
color: blue;
}
.toc span {
font-size: 20px;
}
.toc ol>li {
counter-increment: item;
}
.toc ol>li:first-child {
counter-reset: item;
}
.toc ol ol>li {
display: block;
}
.toc ol ol>li:before {
content: counters(item, ".") ". ";
margin-left: -20px;
}
.e {
height: 500px;
margin: 40px;
}
<div id="p-toc">
<div class="toc">
<span>Contents [ <button id="bttext" onclick="bttext();">hide</button> ] </span>
<div id="hide">
<ol id="htoc">
</ol>
</div>
</div>
<div class="e">
new
</div>
<h2>sameer</h2>
<h3>sameer 111</h3>
<h3>sameer 1big11</h3>
<h3>sameer small</h3>
<div class="e">
new
</div>
<h2>sameer lai susu ayo</h2>
<div class="e">
new
</div>
<h2>sameer ko big ass</h2>
<div class="e">
new
</div>
<h2>sameer ko fly jatro brain</h2>
</div>

Please have a look at querySelectorAll
function bttext() {
var btn = document.getElementById("bttext");
btn.innerText = btn.innerText == "show" ? "hide" : "show";
var x = document.getElementById("hide");
x.style.display = x.style.display === "none" ? "block" : "none";
}
let htoc = [...document.querySelectorAll("#p-toc h2")].map((header, i) => {
const gh = header.innerText;
header.setAttribute("id", "point" + i);
return "<li><a href='#point" + i + "'>" + gh + "</a></li>";
})
document.getElementById("htoc").innerHTML = htoc.join("");
/* no stoc in page
let stoc = [...document.querySelectorAll("#p-toc h3")].map((header, i) => {
const gh = header.textContent;
header.setAttribute("id", "sub" + i);
return "<li><a href='#sub" + i + "'>" + gh + "</a></li>";
})
document.getElementById("stoc").innerHTML = stoc.join("");
*/
.toc {
border: 3px solid #A2A9B1;
background-color: #F8F9FA;
display: block;
line-height: 1.4em;
width: 70%;
display: block;
padding: 20px 30px 10px;
border-radius: 5px;
}
.toc button {
background-color: inherit;
font-size: 16px;
outline: none;
border: none;
padding: 0px 0px 10px;
color: blue;
}
.toc span {
font-size: 20px;
}
.toc ol>li {
counter-increment: item;
}
.toc ol>li:first-child {
counter-reset: item;
}
.toc ol ol>li {
display: block;
}
.toc ol ol>li:before {
content: counters(item, ".") ". ";
margin-left: -20px;
}
.e {
height: 500px;
margin: 40px;
}
<div id="p-toc">
<div class="toc">
<span>Contents [ <button id="bttext" onclick="bttext();">hide</button> ] </span>
<div id="hide">
<ol id="htoc">
</ol>
</div>
</div>
<div class="e">
new
</div>
<h2>sameer</h2>
<h3>sameer 111</h3>
<h3>sameer 1big11</h3>
<h3>sameer small</h3>
<div class="e">
new
</div>
<h2>sameer lai susu ayo</h2>
<div class="e">
new
</div>
<h2>sameer ko big ass</h2>
<div class="e">
new
</div>
<h2>sameer ko fly jatro brain</h2>
</div>

Related

how to avoid document.write my below code

This code is working, but google pagespeed detect avoid document.write.
I've tested various alternatives, lining up my HTML elements prior to the JS, then using getElementById, followed by either innerHTML or appendChild, or even lining up the elements inside the JS, by means of createElement, but to no avail, really. maybe my tested was wrong.
Probably a factor as to why they're doing so poorly. I'm sure I couldn't sort the above codes correctly. I'm basically not experienced in JavaScript.
Here is my CSS/HTML/JS inside this snipet code:
.cat-back {
font-size: 18px;
font-weight: 400;
border-bottom: 1px solid #000;
margin-top: 13px;
margin-bottom: 5px;
padding: 5px;
border-left: 3px solid #000
}
.row:after {
content: "";
display: table;
clear: both
}
.catcol {
float: left;
width: 33.33%;
padding: 10px;
box-sizing: border-box
}
.mbtlist {
list-style-type: none;
overflow: hidden
}
.mbtlist li {
margin: 0px auto 20px auto;
clear: both;
color: #666;
font-family: Helvetica;
font-size: 12px;
border-bottom: 1px dotted #ddd;
padding-bottom: 10px;
}
.mbtlist .mbttitle {
font-family: oswald;
font-size: 16px;
color: #0080ff;
font-weight: normal;
text-decoration: none;
}
.mbtlist .mbttitle:hover {
color: #00A5FF;
}
font-family:georgia;
font-size:15px;
font-weight:bold
}
.mbtlist div span {
margin: 0 10px 0 0;
display: inline-block;
}
.mbtlist span {
display: block;
margin: 5px 0px 0px;
padding-right: 5px;
}
.mbtlist .imore {
font-size: 16px;
font-weight: bold;
text-decoration: none;
color: #666;
line-height: 0.7em;
}
.mbtlist img {
float: left;
margin: 0px 10px 10px 0px;
border: 6px solid #fff;
padding: 0px;
width: 80px;
height: 65px;
box-shadow: -1px -1px 4px #777;
}
.mbtlist .icontent {
text-align: justify;
}
<script>
//----------------------------Defaults
var ListBlogLink = window.location.hostname;
var ListCount = 5;
var TitleCount = 70;
var ListLabel = " ";
var ChrCount = 80;
var ImageSize = 100;
//----------------------------Function Start
function mbtlist(json) {
document.write('<ul class="mbtlist">');
for (var i = 0; i < ListCount; i++) {
//-----------------------------Variables Declared
var listing = ListUrl = ListTitle = ListConten = ListContent = ListImage = thumbUrl = sk = "";
//----------------------------- Title URL
for (var j = 0; j < json.feed.entry[i].link.length; j++) {
if (json.feed.entry[i].link[j].rel == 'alternate') {
break;
}
}
ListUrl = "'" + json.feed.entry[i].link[j].href + "'";
//----------------------------------- Title Stirng
if (json.feed.entry[i].title != null) {
ListTitle = json.feed.entry[i].title.$t.substr(0, TitleCount);
}
//----------------------------------- Content Check
ListConten = json.feed.entry[i].content.$t;
ListContent = ListConten.replace(/(<([^>]+)>)/ig, "").substr(0, ChrCount);
//------------------------------------ Thumbnail Check
if (json.feed.entry[i].media$thumbnail) {
thumbUrl = json.feed.entry[i].media$thumbnail.url;
sk = thumbUrl.replace("/s72-c/", "/s" + ImageSize + "/");
ListImage = "'" + sk.replace("?imgmax=800", "") + "'";
}
// Support For 3rd Party Images
else if (json.feed.entry[i].content.$t.match(/src=(.+?[\.jpg|\.gif|\.png]")/) != null) {
ListImage = json.feed.entry[i].content.$t.match(/src=(.+?[\.jpg|\.gif|\.png]")/)[1];
} else {
ListImage = "'http://4.bp.blogspot.com/-HALLtgFeep0/VfryhQ0C5oI/AAAAAAAAPcY/77mSGND4q84/s200/Icon.png'";
}
//----------------------------------- Printing List
var listing = "<li><a href=" +
ListUrl +
"><img src=" +
ListImage +
"/></a><a class='mbttitle' href=" +
ListUrl +
"target='_blank'>" +
ListTitle +
"</a><span class='icontent'>" +
ListContent +
" ... <a href=" +
ListUrl +
" class='imore'>»</a></span></li>";
document.write(listing);
}
document.write("</ul>");
}</script>
<div class='row'>
<div class='catcol'><div class='cat-back'><h3>Seba Top</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "seba-top";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
<div class='catcol'><div class='cat-back'><h3>Lead News</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "lead-news";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
<div class='catcol'><div class='cat-back'><h3>Top News</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "top-news";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
</div>
<div class='row'>
<div class='catcol'><div class='cat-back'><h3>জাতীয়</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "জাতীয়";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
<div class='catcol'><div class='cat-back'><h3>রাজনীতি</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "রাজনীতি";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
<div class='catcol'><div class='cat-back'><h3>বিশ্ব</h3></div></div>
<script>
ListBlogLink = "https://www.sebahotnews.org";
ListCount = 4;
TitleCount = 70;
ListLabel = "বিশ্ব";
ChrCount = 150;
document.write("<script src='" + ListBlogLink + "/feeds/posts/default/-/" + ListLabel + "?alt=json-in-script&callback=mbtlist'></" + "script>");
</script>
</div>
</div>
Would it be possible for anyone to point me to the right direction?
Please solve this problem any one.
So based on new code I suggest this
//----------------------------Defaults
var ListBlogLink = "https://www.sebahotnews.org",
ListCount = 4,
TitleCount = 70,
ChrCount = 150,
ImageSize = 100;
const lists = [{"label":"seba-top" },{"label":"lead-news" },{"label":"top-news" }]
let cnt = 0;
function next() {
if (cnt>=lists.length) return
document.getElementById("container").innerHTML += `<div class='catcol ${lists[cnt].label}'></div>`
const scr = document.createElement("script");
scr.src = ListBlogLink + "/feeds/posts/default/-/" + lists[cnt].label + "?alt=json-in-script&callback=mbtlist";
document.querySelector("head").appendChild(scr);
};
next(); // start
function mbtlist(json) {
let div = document.querySelector("#container ."+lists[cnt].label);
let html = '<ul class="mbtlist">';
for (var i = 0; i < ListCount; i++) {
//-----------------------------Variables Declared
var listing = ListUrl = ListTitle = ListConten = ListContent = ListImage = thumbUrl = sk = "";
//----------------------------- Title URL
for (var j = 0; j < json.feed.entry[i].link.length; j++) {
if (json.feed.entry[i].link[j].rel == 'alternate') {
break;
}
}
ListUrl = "'" + json.feed.entry[i].link[j].href + "'";
//----------------------------------- Title Stirng
if (json.feed.entry[i].title != null) {
ListTitle = json.feed.entry[i].title.$t.substr(0, TitleCount);
}
//----------------------------------- Content Check
ListConten = json.feed.entry[i].content.$t;
ListContent = ListConten.replace(/(<([^>]+)>)/ig, "").substr(0, ChrCount);
//------------------------------------ Thumbnail Check
if (json.feed.entry[i].media$thumbnail) {
thumbUrl = json.feed.entry[i].media$thumbnail.url;
sk = thumbUrl.replace("/s72-c/", "/s" + ImageSize + "/");
ListImage = "'" + sk.replace("?imgmax=800", "") + "'";
}
// Support For 3rd Party Images
else if (json.feed.entry[i].content.$t.match(/src=(.+?[\.jpg|\.gif|\.png]")/) != null) {
ListImage = json.feed.entry[i].content.$t.match(/src=(.+?[\.jpg|\.gif|\.png]")/)[1];
} else {
ListImage = "'http://4.bp.blogspot.com/-HALLtgFeep0/VfryhQ0C5oI/AAAAAAAAPcY/77mSGND4q84/s200/Icon.png'";
}
//----------------------------------- Printing List
var listing = "<li><a href=" +
ListUrl +
"><img src=" +
ListImage +
"/></a><a class='mbttitle' href=" +
ListUrl +
"target='_blank'>" +
ListTitle +
"</a><span class='icontent'>" +
ListContent +
" ... <a href=" +
ListUrl +
" class='imore'>»</a></span></li>";
html += listing;
}
html += "</ul>";
div.innerHTML = html;
cnt++;
next(); // call next
}
.seba-top { background-color:orange;}
.top-news { background-color:tan;}
.lead-news { background-color:yellow;}
.catcol {
float: left;
width: 33.33%;
padding: 10px;
box-sizing: border-box;
border: 1px solid black;
}
.mbtlist {
list-style-type: none;
overflow: hidden
}
.mbtlist li {
margin: 0px auto 20px auto;
clear: both;
color: #666;
font-family: Helvetica;
font-size: 12px;
border-bottom: 1px dotted #ddd;
padding-bottom: 10px;
}
.mbtlist .mbttitle {
font-family: oswald;
font-size: 16px;
color: #0080ff;
font-weight: normal;
text-decoration: none;
}
.mbtlist .mbttitle:hover {
color: #00A5FF;
}
font-family:georgia;
font-size:15px;
font-weight:bold
}
.mbtlist div span {
margin: 0 10px 0 0;
display: inline-block;
}
.mbtlist span {
display: block;
margin: 5px 0px 0px;
padding-right: 5px;
}
.mbtlist .imore {
font-size: 16px;
font-weight: bold;
text-decoration: none;
color: #666;
line-height: 0.7em;
}
.mbtlist img {
float: left;
margin: 0px 10px 10px 0px;
border: 6px solid #fff;
padding: 0px;
width: 80px;
height: 65px;
box-shadow: -1px -1px 4px #777;
}
.mbtlist .icontent {
text-align: justify;
}
<div id="container"></div>

Javascript - NaN.undefined as textholder problem

I have got a problem at the coding project I am doing, as I formatted the numbers to be shown nicer, I ran into a problem. The webpage when it loads shows NaN. undefined in the total income/expenses at the top. I can't figure out what is the problem.
//Budget controller
var budgetController = (function() {
var Expense = function(id, description, value) {
this.id = id;
this.description = description;
this.value = value;
this.percentage = -1;
};
Expense.prototype.calcPercentage = function(totalIncome) {
if (totalIncome > 0) {
this.percentage = Math.round((this.value / totalIncome) * 100);
} else {
this.percentage = -1;
}
};
Expense.prototype.getPercentage = function() {
return this.percentage;
};
var Income = function(id, description, value) {
this.id = id;
this.description = description;
this.value = value;
};
var calculateTotal = function(type) {
var sum = 0;
data.allItems[type].forEach(function(cur) {
sum = sum + cur.value;
});
data.totals[type] = sum;
};
var data = {
allItems: {
exp: [],
inc: []
},
totals: {
exp: 0,
inc: 0
},
budget: 0,
percentage: -1
};
return {
addItem: function(type, des, val) {
var newItem, ID;
//create new iD
if (data.allItems[type].length > 0) {
ID = data.allItems[type][data.allItems[type].length - 1].id + 1;
} else {
ID = 0;
}
//CREATe new item, if it is inc or exp
if (type === 'exp') {
newItem = new Expense(ID, des, val);
} else if (type === 'inc') {
newItem = new Income(ID, des, val);
}
// Push all items into data structure and return the new element
data.allItems[type].push(newItem);
return newItem;
},
deleteItem: function(type, id) {
var ids, index;
ids = data.allItems[type].map(function(current) {
return current.id;
});
index = ids.indexOf(id);
if (index !== -1) {
data.allItems[type].splice(index, 1);
}
},
calculateBudget: function() {
// calculate the total income and expenses
calculateTotal('exp');
calculateTotal('inc');
// calculate the budget: income - expenses
data.budget = data.totals.inc - data.totals.exp;
if (data.totals.inc > 0) {
data.percentage = Math.round((data.totals.exp / data.totals.inc) * 100);
} else {
data.percentage = -1;
}
},
calculatePercentages: function() {
data.allItems.exp.forEach(function(cur) {
cur.calcPercentage(data.totals.inc);
});
},
getPercentages: function() {
var allPerc = data.allItems.exp.map(function(cur) {
return cur.getPercentage();
});
return allPerc;
},
getBudget: function() {
return {
budget: data.budget,
totalInc: data.totals.inc,
totalExp: data.totals.exp,
percentage: data.percentage
};
}
};
})();
// UI Controller
var UIController = (function() {
var DOMstrings = {
inputType: '.add__type',
inputDescription: '.add__description',
inputValue: '.add__value',
inputBtn: '.add__btn',
incomeContainer: '.income__list',
expensesContainer: '.expenses__list',
budgetLabel: '.budget__value',
incomeLabel: '.budget__income--value',
expensesLabel: '.budget__expenses--value',
percentageLabel: '.budget__expenses--percentage',
container: '.container',
expensesPercLabel: '.item__percentage',
dateLabel: '.budget__title--month'
};
var formatNumber = function(num, type) {
var numSplit, int, dec, type;
/* + or - befofe a number
on 2 decimals
comma seperating thousands
*/
num = Math.abs(num);
num = num.toFixed(2);
numSplit = num.split('.');
int = numSplit[0];
if (int.length > 3) {
int = int.substr(0, int.length - 3) + ',' + int.substr(int.length - 3, 3); //input 23510, output 23,510
}
dec = numSplit[1];
return (type === 'exp' ? '-' : '+') + ' ' + int + '.' + dec;
};
var nodeListForEach = function(list, callback) {
for (var i = 0; i < list.length; i++) {
callback(list[i], i);
}
};
return {
getInput: function() {
return {
type: document.querySelector(DOMstrings.inputType).value, //will be either inc or exp
description: document.querySelector(DOMstrings.inputDescription).value,
value: parseFloat(document.querySelector(DOMstrings.inputValue).value)
};
},
addListItem: function(obj, type) {
var html, newHtml, element;
// Create HTML string with placeholder text
if (type === 'inc') {
element = DOMstrings.incomeContainer;
html = '<div class="item clearfix" id="inc-%id%"> <div class="item__description">%description%</div><div class="right clearfix"><div class="item__value">%value%</div><div class="item__delete"><button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button></div></div></div>';
} else if (type === 'exp') {
element = DOMstrings.expensesContainer;
html = '<div class="item clearfix" id="exp-%id%"><div class="item__description">%description%</div><div class="right clearfix"><div class="item__value">%value%</div><div class="item__percentage">21%</div><div class="item__delete"><button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button></div></div></div>';
}
// Replace the placeholder text with some actual data
newHtml = html.replace('%id%', obj.id);
newHtml = newHtml.replace('%description%', obj.description);
newHtml = newHtml.replace('%value%', formatNumber(obj.value, type));
// Insert the HTML into the DOM
document.querySelector(element).insertAdjacentHTML('beforeend', newHtml);
},
deleteListItem: function(selectorID) {
var el = document.getElementById(selectorID);
el.parentNode.removeChild(el);
},
clearFields: function() {
var fields, fieldsArr;
fields = document.querySelectorAll(
DOMstrings.inputDescription + ',' + DOMstrings.inputValue
);
fieldsArr = Array.prototype.slice.call(fields);
fieldsArr.forEach(function(current, index, array) {
current.value = "";
});
fieldsArr[0].focus();
},
displayBudget: function(obj) {
var type;
obj.budget > 0 ? type = 'inc' : type = 'exp';
document.querySelector(DOMstrings.budgetLabel).textContent = formatNumber(obj.budget, type);
document.querySelector(DOMstrings.incomeLabel).textContent = formatNumber(obj.totalInc, 'inc');
document.querySelector(DOMstrings.expensesLabel).textContent = formatNumber(obj.totalExp, 'exp');
if (obj.percentage > 0) {
document.querySelector(DOMstrings.percentageLabel).textContent = obj.percentage + '%';
} else {
document.querySelector(DOMstrings.percentageLabel).textContent = '---';
}
},
displayPercentages: function(percentages) {
var fields = document.querySelectorAll(DOMstrings.expensesPercLabel);
nodeListForEach(fields, function(current, index) {
if (percentages[index] > 0) {
current.textContent = percentages[index] + '%';
} else {
current.textContent = '---';
}
});
},
getDOMstrings: function() {
return DOMstrings;
}
};
})();
// App Controller - global
var controller = (function(budgetCtrl, UICtrl) {
var setupEventListeners = function() {
var DOM = UICtrl.getDOMstrings();
document.querySelector(DOM.inputBtn).addEventListener('click', ctrlAddItem);
document.addEventListener('keypress', function(event) {
if (event.keyCode === 13 || event.which === 13) {
ctrlAddItem();
}
});
document.querySelector(DOM.container).addEventListener('click', ctrlDeleteItem);
};
var updateBudget = function() {
// 1. Calculate the budget
budgetCtrl.calculateBudget();
// 2. Return the budget
var budget = budgetCtrl.getBudget();
// 3. Display the budget on the UI
UICtrl.displayBudget(budget);
};
var updatePercentages = function() {
// 1. Calculate percentages
budgetCtrl.calculatePercentages();
// 2. Read percentages from the budget controller
var percentages = budgetCtrl.getPercentages();
// 3. Update the UI with the new percentages
UICtrl.displayPercentages(percentages);
};
var ctrlAddItem = function() {
var input, newItem;
// 1. Get the field input data
input = UICtrl.getInput();
if (input.description !== "" && !isNaN(input.value) && input.value > 0) {
// 2. Add the item to the budget controller
newItem = budgetCtrl.addItem(input.type, input.description, input.value);
// 3. Add the item to the UI
UICtrl.addListItem(newItem, input.type);
// 4. Clear the fields
UICtrl.clearFields();
// 5. Calculate and update budget
updateBudget();
// 6. Calculate and update percentages
updatePercentages();
}
};
var ctrlDeleteItem = function(event) {
var itemID, splitID, type, ID;
itemID = event.target.parentNode.parentNode.parentNode.parentNode.id;
if (itemID) {
//inc-1
splitID = itemID.split('-');
type = splitID[0];
ID = parseInt(splitID[1]);
// 1. delete the item from the data structure
budgetCtrl.deleteItem(type, ID);
// 2. Delete the item from the UI
UICtrl.deleteListItem(itemID);
// 3. Update and show the new budget
updateBudget();
// 4. Calculate and update percentages
updatePercentages();
}
};
return {
init: function() {
console.log('App has started');
UICtrl.displayBudget({
budget: 0,
totalIncome: 0,
totalExpenses: 0,
percentage: -1
});
setupEventListeners();
}
};
})(budgetController, UIController);
controller.init();
/**********************************************
*** GENERAL
**********************************************/
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.clearfix::after {
content: "";
display: table;
clear: both;
}
body {
color: #555;
font-family: Open Sans;
font-size: 16px;
position: relative;
height: 100vh;
font-weight: 400;
}
.right {
float: right;
}
.red {
color: #FF5049 !important;
}
.red-focus:focus {
border: 1px solid #FF5049 !important;
}
/**********************************************
*** TOP PART
**********************************************/
.top {
height: 40vh;
background-image: linear-gradient(rgba(0, 0, 0, 0.35), rgba(0, 0, 0, 0.35)), url(back.png);
background-size: cover;
background-position: center;
position: relative;
}
.budget {
position: absolute;
width: 350px;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
color: #fff;
}
.budget__title {
font-size: 18px;
text-align: center;
margin-bottom: 10px;
font-weight: 300;
}
.budget__value {
font-weight: 300;
font-size: 46px;
text-align: center;
margin-bottom: 25px;
letter-spacing: 2px;
}
.budget__income,
.budget__expenses {
padding: 12px;
text-transform: uppercase;
}
.budget__income {
margin-bottom: 10px;
background-color: #28B9B5;
}
.budget__expenses {
background-color: #FF5049;
}
.budget__income--text,
.budget__expenses--text {
float: left;
font-size: 13px;
color: #444;
margin-top: 2px;
}
.budget__income--value,
.budget__expenses--value {
letter-spacing: 1px;
float: left;
}
.budget__income--percentage,
.budget__expenses--percentage {
float: left;
width: 34px;
font-size: 11px;
padding: 3px 0;
margin-left: 10px;
}
.budget__expenses--percentage {
background-color: rgba(255, 255, 255, 0.2);
text-align: center;
border-radius: 3px;
}
/**********************************************
*** BOTTOM PART
**********************************************/
/***** FORM *****/
.add {
padding: 14px;
border-bottom: 1px solid #e7e7e7;
background-color: #f7f7f7;
}
.add__container {
margin: 0 auto;
text-align: center;
}
.add__type {
width: 55px;
border: 1px solid #e7e7e7;
height: 44px;
font-size: 18px;
color: inherit;
background-color: #fff;
margin-right: 10px;
font-weight: 300;
transition: border 0.3s;
}
.add__description,
.add__value {
border: 1px solid #e7e7e7;
background-color: #fff;
color: inherit;
font-family: inherit;
font-size: 14px;
padding: 12px 15px;
margin-right: 10px;
border-radius: 5px;
transition: border 0.3s;
}
.add__description {
width: 400px;
}
.add__value {
width: 100px;
}
.add__btn {
font-size: 35px;
background: none;
border: none;
color: #28B9B5;
cursor: pointer;
display: inline-block;
vertical-align: middle;
line-height: 1.1;
margin-left: 10px;
}
.add__btn:active {
transform: translateY(2px);
}
.add__type:focus,
.add__description:focus,
.add__value:focus {
outline: none;
border: 1px solid #28B9B5;
}
.add__btn:focus {
outline: none;
}
/***** LISTS *****/
.container {
width: 1000px;
margin: 60px auto;
}
.income {
float: left;
width: 475px;
margin-right: 50px;
}
.expenses {
float: left;
width: 475px;
}
h2 {
text-transform: uppercase;
font-size: 18px;
font-weight: 400;
margin-bottom: 15px;
}
.icome__title {
color: #28B9B5;
}
.expenses__title {
color: #FF5049;
}
.item {
padding: 13px;
border-bottom: 1px solid #e7e7e7;
}
.item:first-child {
border-top: 1px solid #e7e7e7;
}
.item:nth-child(even) {
background-color: #f7f7f7;
}
.item__description {
float: left;
}
.item__value {
float: left;
transition: transform 0.3s;
}
.item__percentage {
float: left;
margin-left: 20px;
transition: transform 0.3s;
font-size: 11px;
background-color: #FFDAD9;
padding: 3px;
border-radius: 3px;
width: 32px;
text-align: center;
}
.income .item__value,
.income .item__delete--btn {
color: #28B9B5;
}
.expenses .item__value,
.expenses .item__percentage,
.expenses .item__delete--btn {
color: #FF5049;
}
.item__delete {
float: left;
}
.item__delete--btn {
font-size: 22px;
background: none;
border: none;
cursor: pointer;
display: inline-block;
vertical-align: middle;
line-height: 1;
display: none;
}
.item__delete--btn:focus {
outline: none;
}
.item__delete--btn:active {
transform: translateY(2px);
}
.item:hover .item__delete--btn {
display: block;
}
.item:hover .item__value {
transform: translateX(-20px);
}
.item:hover .item__percentage {
transform: translateX(-20px);
}
.unpaid {
background-color: #FFDAD9 !important;
cursor: pointer;
color: #FF5049;
}
.unpaid .item__percentage {
box-shadow: 0 2px 6px 0 rgba(0, 0, 0, 0.1);
}
.unpaid:hover .item__description {
font-weight: 900;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<link href="https://fonts.googleapis.com/css?family=Open+Sans:100,300,400,600" rel="stylesheet" type="text/css">
<link href="http://code.ionicframework.com/ionicons/2.0.1/css/ionicons.min.css" rel="stylesheet" type="text/css">
<link type="text/css" rel="stylesheet" href="style.css">
<title>Budgety</title>
</head>
<body>
<div class="top">
<div class="budget">
<div class="budget__title">
Available Budget in <span class="budget__title--month">%Month%</span>:
</div>
<div class="budget__value">+ 2,345.64</div>
<div class="budget__income clearfix">
<div class="budget__income--text">Income</div>
<div class="right">
<div class="budget__income--value">+ 4,300.00</div>
<div class="budget__income--percentage"> </div>
</div>
</div>
<div class="budget__expenses clearfix">
<div class="budget__expenses--text">Expenses</div>
<div class="right clearfix">
<div class="budget__expenses--value">- 1,954.36</div>
<div class="budget__expenses--percentage">45%</div>
</div>
</div>
</div>
</div>
<div class="bottom">
<div class="add">
<div class="add__container">
<select class="add__type">
<option value="inc" selected>+</option>
<option value="exp">-</option>
</select>
<input type="text" class="add__description" placeholder="Add description">
<input type="number" class="add__value" placeholder="Value">
<button class="add__btn"><i class="ion-ios-checkmark-outline"></i></button>
</div>
</div>
<div class="container clearfix">
<div class="income">
<h2 class="icome__title">Income</h2>
<div class="income__list">
<!--
<div class="item clearfix" id="income-0">
<div class="item__description">Salary</div>
<div class="right clearfix">
<div class="item__value">+ 2,100.00</div>
<div class="item__delete">
<button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button>
</div>
</div>
</div>
<div class="item clearfix" id="income-1">
<div class="item__description">Sold car</div>
<div class="right clearfix">
<div class="item__value">+ 1,500.00</div>
<div class="item__delete">
<button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button>
</div>
</div>
</div>
-->
</div>
</div>
<div class="expenses">
<h2 class="expenses__title">Expenses</h2>
<div class="expenses__list">
<!--
<div class="item clearfix" id="expense-0">
<div class="item__description">Apartment rent</div>
<div class="right clearfix">
<div class="item__value">- 900.00</div>
<div class="item__percentage">21%</div>
<div class="item__delete">
<button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button>
</div>
</div>
</div>
<div class="item clearfix" id="expense-1">
<div class="item__description">Grocery shopping</div>
<div class="right clearfix">
<div class="item__value">- 435.28</div>
<div class="item__percentage">10%</div>
<div class="item__delete">
<button class="item__delete--btn"><i class="ion-ios-close-outline"></i></button>
</div>
</div>
</div>
-->
</div>
</div>
</div>
</div>
<script src="app.js"></script>
</body>
</html>
The problem is that in the function formatNumber, the value num is not initialized at first time. For solving this, you can put a default value when the value of num is empty, like this:
var formatNumber = function(num = 0, type = '') {
var numSplit, int, dec, type;
/* + or - befofe a number
on 2 decimals
comma seperating thousands
*/
num = Math.abs(num);
num = num.toFixed(2);
numSplit = num.split('.');
int = numSplit[0];
if (int.length > 3) {
int = int.substr(0, int.length - 3) + ',' + int.substr(int.length - 3, 3); //input 23510, output 23,510
}
dec = numSplit[1];
return (type === 'exp' ? '-' : '+') + ' ' + int + '.' + dec;
};

jquery popups instance duplication problem

can someone take a look at the code here is the problem screenshot
enter image description here
when clicking on sidebar user a popup appears after clicking on popup header it will go down and then if someone will click on the same user from sidebar a duplicate instance is created and click on the head will make the first one appear and 2nd one to go down.
I want to stop that duplication when someone clicks on sidebar user again then the already generated popup will toggle.
https://jsfiddle.net/hamzasgd/Lqyajokp/4/
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Facebook like chat popup layout</title>
</head>
<body>
<div id="chat-sidebar">
<div id="sidebar-user-box" class="100">
<img src="user.png" />
<span id="slider-username">User 1</span>
</div>
<div id="sidebar-user-box" class="200">
<img src="user.png" />
<span id="slider-username">User 2</span>
</div>
</div>
</body>
</html>
$(document).ready(function(){
var arr = []; // List of users
$(document).on('click', '.msg_head', function() {
var chatbox = $(this).parents().attr("rel") ;
$('[rel="'+chatbox+'"] .msg_wrap').slideToggle('slow');
return false;
});
$(document).on('click', '.close', function() {
var chatbox = $(this).parents().parents().attr("rel") ;
$('[rel="'+chatbox+'"]').hide();
arr.splice($.inArray(chatbox, arr), 1);
displayChatBox();
return false;
});
$(document).on('click', '#sidebar-user-box', function() {
var userID = $(this).attr("class");
var username = $(this).children().text() ;
if ($.inArray(userID, arr) != -1)
{
arr.splice($.inArray(userID, arr), 1);
}
arr.unshift(userID);
chatPopup = '<div class="msg_box" style="right:270px" rel="'+ userID+'">'+
'<div class="msg_head">'+username +
'<div class="close">x</div> </div>'+
'<div class="msg_wrap"> <div class="msg_body"> <div class="msg_push"></div> </div>'+
'<div class="msg_footer"><textarea class="msg_input" rows="4"></textarea></div> </div> </div>' ;
$("body").append( chatPopup );
displayChatBox();
});
$(document).on('keypress', 'textarea' , function(e) {
if (e.keyCode == 13 ) {
var msg = $(this).val();
$(this).val('');
if(msg.trim().length != 0){
var chatbox = $(this).parents().parents().parents().attr("rel") ;
$('<div class="msg-right">'+msg+'</div>').insertBefore('[rel="'+chatbox+'"] .msg_push');
$('.msg_body').scrollTop($('.msg_body')[0].scrollHeight);
}
}
});
function displayChatBox(){
i = 270 ; // start position
j = 260; //next position
$.each( arr, function( index, value ) {
if(index < 4){
$('[rel="'+value+'"]').css("right",i);
$('[rel="'+value+'"]').show();
i = i+j;
}
else{
$('[rel="'+value+'"]').hide();
}
});
}
});
I've added a check that will look if you already have a chatbox with that userID:
var exist = $('.msg_box[rel="' + userID + '"]').length;
if (exist == 0) {
arr.unshift(userID);
chatPopup = '<div class="msg_box" style="right:270px" rel="' + userID + '">' +
'<div class="msg_head">' + username +
'<div class="close">x</div> </div>' +
'<div class="msg_wrap"> <div class="msg_body"> <div class="msg_push"></div> </div>' +
'<div class="msg_footer"><textarea class="msg_input" rows="4"></textarea></div> </div> </div>';
$("body").append(chatPopup);
displayChatBox();
}
Please note that you have some invalid html. You are not allowed, to have the id on multiple element.
Demo
$(document).ready(function() {
var arr = []; // List of users
$(document).on('click', '.msg_head', function() {
var chatbox = $(this).parents().attr("rel");
$('[rel="' + chatbox + '"] .msg_wrap').slideToggle('slow');
return false;
});
$(document).on('click', '.close', function() {
var chatbox = $(this).parents().parents().attr("rel");
$('[rel="' + chatbox + '"]').hide();
arr.splice($.inArray(chatbox, arr), 1);
displayChatBox();
return false;
});
$(document).on('click', '#sidebar-user-box', function() {
var userID = $(this).attr("class");
var username = $(this).children().text();
if ($.inArray(userID, arr) != -1) {
arr.splice($.inArray(userID, arr), 1);
}
var exist = $('.msg_box[rel="' + userID + '"]').length;
if (exist == 0) {
arr.unshift(userID);
chatPopup = '<div class="msg_box" style="right:270px" rel="' + userID + '">' +
'<div class="msg_head">' + username +
'<div class="close">x</div> </div>' +
'<div class="msg_wrap"> <div class="msg_body"> <div class="msg_push"></div> </div>' +
'<div class="msg_footer"><textarea class="msg_input" rows="4"></textarea></div> </div> </div>';
$("body").append(chatPopup);
displayChatBox();
} else {
$('.msg_box[rel="' + userID + '"] .msg_wrap').slideToggle('slow');
}
});
$(document).on('keypress', 'textarea', function(e) {
if (e.keyCode == 13) {
var msg = $(this).val();
$(this).val('');
if (msg.trim().length != 0) {
var chatbox = $(this).parents().parents().parents().attr("rel");
$('<div class="msg-right">' + msg + '</div>').insertBefore('[rel="' + chatbox + '"] .msg_push');
$('.msg_body').scrollTop($('.msg_body')[0].scrollHeight);
}
}
});
function displayChatBox() {
i = 270; // start position
j = 260; //next position
$.each(arr, function(index, value) {
if (index < 4) {
$('[rel="' + value + '"]').css("right", i);
$('[rel="' + value + '"]').show();
i = i + j;
} else {
$('[rel="' + value + '"]').hide();
}
});
}
});
/**** Chat Popup Layout******/
body {
background: #e5e5e5;
font-family: sans-serif;
}
.msg_box {
position: fixed;
bottom: -5px;
width: 250px;
background: white;
border-radius: 5px 5px 0px 0px;
}
.msg_head {
background: black;
color: white;
padding: 8px;
font-weight: bold;
cursor: pointer;
border-radius: 5px 5px 0px 0px;
}
.msg_body {
background: white;
height: 200px;
font-size: 12px;
padding: 15px;
overflow: auto;
overflow-x: hidden;
}
.msg_input {
width: 100%;
height: 55px;
border: 1px solid white;
border-top: 1px solid #DDDDDD;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.close {
float: right;
cursor: pointer;
}
.minimize {
float: right;
cursor: pointer;
padding-right: 5px;
}
.msg-left {
position: relative;
background: #e2e2e2;
padding: 5px;
min-height: 10px;
margin-bottom: 5px;
margin-right: 10px;
border-radius: 5px;
word-break: break-all;
}
.msg-right {
background: #d4e7fa;
padding: 5px;
min-height: 15px;
margin-bottom: 5px;
position: relative;
margin-left: 10px;
border-radius: 5px;
word-break: break-all;
}
/**** Slider Layout Popup *********/
#chat-sidebar {
width: 250px;
position: fixed;
height: 100%;
right: 0px;
top: 0px;
padding-top: 10px;
padding-bottom: 10px;
border: 1px solid #b2b2b2;
}
#sidebar-user-box {
padding: 4px;
margin-bottom: 4px;
font-size: 15px;
font-family: Calibri;
font-weight: bold;
cursor: pointer;
}
#sidebar-user-box:hover {
background-color: #999999;
}
#sidebar-user-box:after {
content: ".";
display: block;
height: 0;
clear: both;
visibility: hidden;
}
img {
width: 35px;
height: 35px;
border-radius: 50%;
float: left;
}
#slider-username {
float: left;
line-height: 30px;
margin-left: 5px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="chat-sidebar">
<div id="sidebar-user-box" class="100">
<img src="user.png" />
<span id="slider-username">User 1</span>
</div>
<div id="sidebar-user-box" class="200">
<img src="user.png" />
<span id="slider-username">User 2</span>
</div>
</div>

Addition table to modal and catching data from array

I get a problem when I try generate table in modal with data from js code.
There is a problem with 249 line in js. I can not understand why my params.progress array is not defined.
rock-paper-scissors app on codepen
I create new object in empty params.progress array after every player move:
var objectResults = {
number: params.numberOfRounds,
playerMove: userChoice,
computerMove: computerChoice,
gameResult: params.userScore+":"+params.computerScore,
}
params.progress[params.numberOfRounds] = objectResults;
Finally I try to generate table with those data:
function makeTableFromProgress() {
var resultsTableBody = document.querySelector('#resultsTableBody');
var rows = params.progress.length;
for (i = 0; i<rows; i++) {
var row = resultsTableBody.insertRow(i);
var cell1 = row.insertCell(0);
var cell2 = row.insertCell(1);
var cell3 = row.insertCell(2);
var cell4 = row.insertCell(3);
cell1.innerHTML = params.progress[i]['number'];
cell2.innerHTML = params.progress[i]['playerMove'];
cell3.innerHTML = params.progress[i]['computerMove'];
cell4.innerHTML = params.progress[i]['gameResult'];
}
}
In modal window, like this:
<table>
<thead>
<tr>
<th>No.</th>
<th>Player move</th>
<th>Computer move</th>
<th>Game result</th>
</tr>
</thead>
<tbody id="resultsTableBody"></tbody>
</table>
And it brings kind of that problem:
Cannot read property 'number' of undefined
Thanks for help
The problem is in function makeTableFromProgress. i must start with 1 instead of 0 and also insertRow(i - 1); instead of insertRow(i);
function makeTableFromProgress() {
var resultsTableBody = document.querySelector('#resultsTableBody');
var rows = params.progress.length;
for (i = 1; i < rows; i++) {
var row = resultsTableBody.insertRow(i - 1);
var cell1 = row.insertCell(0);
var cell2 = row.insertCell(1);
var cell3 = row.insertCell(2);
var cell4 = row.insertCell(3);
cell1.innerHTML = params.progress[i]['number'];
cell2.innerHTML = params.progress[i]['playerMove'];
cell3.innerHTML = params.progress[i]['computerMove'];
cell4.innerHTML = params.progress[i]['gameResult'];
}
};
The final code will be this
var userScore_span = document.getElementById("user-score");
var computerScore_span = document.getElementById("computer-score");
var scoreBoard_div = document.querySelector(".score-board");
var result_p = document.querySelector(".result > p");
var moveButtons = document.querySelectorAll("[data-move]");
var newGame_div = document.querySelector(".newGame");
var choices_div = document.querySelector(".choices");
var message_p = document.getElementById("message");
var trophy_p = document.getElementById("numberOfWins");
var roundsCounter_p = document.getElementById("numberOfRounds");
var modal_h = document.getElementById("endMessage");
var userName_div = document.getElementById("user-label");
var userName;
var numberOfGames;
var params = {
userScore: 0,
computerScore: 0,
numberOfRounds: 0,
progress: []
}
function main() {
moveButtons.forEach(function(button) {
var userChoice = button.dataset.move;
button.addEventListener('click', function() {
game(userChoice);
});
});
}
function game(userChoice) {
var computerChoice = getComputerChoice();
switch (userChoice + computerChoice) {
case "RockRock":
case "PaperPaper":
case "ScissorsScissors":
draw(userChoice, computerChoice);
break;
case "RockScissors":
case "PaperRock":
case "ScissorsPaper":
win(userChoice, computerChoice);
break;
case "RockPaper":
case "PaperScissors":
case "ScissorsRock":
lose(userChoice, computerChoice);
break;
}
}
function getComputerChoice() {
var choices = ['Rock', 'Paper', 'Scissors'];
randomNumber = Math.floor(Math.random() * 3)
return choices[randomNumber];
}
function draw(userChoice, computerChoice) {
params.numberOfRounds++;
roundsCounter_p.innerHTML = "Number of rounds: " + params.numberOfRounds;
computerScore_span.innerHTML = params.computerScore;
userScore_span.innerHTML = params.userScore;
var smallerUserWord = "user ".fontsize(4);
var smallerCompWord = " comp".fontsize(4);
result_p.innerHTML = smallerUserWord + userChoice + " vs " + computerChoice + smallerCompWord + "<br>It is a draw!";
document.getElementById(userChoice).classList.add('gray-glow');
setTimeout(function() {
document.getElementById(userChoice).classList.remove('gray-glow')
}, 400);
var objectResults = {
number: params.numberOfRounds,
playerMove: userChoice,
computerMove: computerChoice,
gameResult: params.userScore + ":" + params.computerScore,
}
params.progress[params.numberOfRounds] = objectResults;
}
function win(userChoice, computerChoice) {
params.numberOfRounds++;
roundsCounter_p.innerHTML = "Number of rounds: " + params.numberOfRounds;
params.userScore++;
userScore_span.innerHTML = params.userScore;
computerScore_span.innerHTML = params.computerScore;
var smallerUserWord = "user ".fontsize(4);
var smallerCompWord = " comp".fontsize(4);
result_p.innerHTML = smallerUserWord + userChoice + " vs " + computerChoice + smallerCompWord + "<br>You won!";
document.getElementById(userChoice).classList.add('green-glow');
setTimeout(function() {
document.getElementById(userChoice).classList.remove('green-glow')
}, 400);
var objectResults = {
number: params.numberOfRounds,
playerMove: userChoice,
computerMove: computerChoice,
gameResult: params.userScore + ":" + params.computerScore,
}
params.progress[params.numberOfRounds] = objectResults;
endGame();
}
function lose(userChoice, computerChoice) {
params.numberOfRounds++;
roundsCounter_p.innerHTML = "Number of rounds: " + params.numberOfRounds;
params.computerScore++;
computerScore_span.innerHTML = params.computerScore;
userScore_span.innerHTML = params.userScore;
var smallerUserWord = "user ".fontsize(4);
var smallerCompWord = " comp".fontsize(4);
result_p.innerHTML = smallerUserWord + userChoice + " vs " + computerChoice + smallerCompWord + "<br>You lost!";
document.getElementById(userChoice).classList.add('red-glow');
setTimeout(function() {
document.getElementById(userChoice).classList.remove('red-glow')
}, 400);
var objectResults = {
number: params.numberOfRounds,
playerMove: userChoice,
computerMove: computerChoice,
gameResult: params.userScore + ":" + params.computerScore,
}
params.progress[params.numberOfRounds] = objectResults;
endGame();
}
function newGame() {
newGame_div.addEventListener('click', function() {
howManyWins();
})
main();
}
function howManyWins() {
var userAnswer = prompt("TILL HOW MANY WINS?");
if (userAnswer === null || userAnswer === "" || isNaN(userAnswer)) {
thereIsAnError();
} else {
giveMeYourName();
resetScore();
games(userAnswer);
}
}
function thereIsAnError() {
message_p.innerHTML = "Please press NEW GAME and choose the number!";
setTimeout(function() {
message_p.innerHTML = ""
}, 3000);
}
function giveMeYourName() {
var name = prompt("WHAT IS YOUR NAME?");
if (name === null || name === "" || isNaN(name) === false) {
thereIsAnError();
document.querySelector('#trophy').classList.add('trophydisabled');
} else if (name.length > 9) {
message_p.innerHTML = "Your name is too long. 9 letters summary!";
} else {
document.querySelector('#trophy').classList.remove('trophydisabled');
choices_div.classList.remove('choices-disabled');
newGame_div.classList.add('newGame-disabled');
userName_div.innerHTML = name;
userName = name;
}
}
function resetScore() {
params.userScore = 0;
params.computerScore = 0;
params.numberOfRounds = 0;
userScore_span.innerHTML = params.userScore;
computerScore_span.innerHTML = params.computerScore;
roundsCounter_p.innerHTML = "";
}
function games(userAnswer) {
trophy_p.innerHTML = "Up to: " + userAnswer;
numberOfGames = userAnswer;
}
function endGame() {
if (numberOfGames == params.userScore) {
choices_div.classList.add('choices-disabled');
newGame_div.classList.remove('newGame-disabled');
result_p.innerHTML = "";
userName_h = userName;
modal_h.innerHTML = userName + "<br>You won the ENTIRE game!";
makeTableFromProgress()
showModal();
} else if (numberOfGames == params.computerScore) {
choices_div.classList.add('choices-disabled');
newGame_div.classList.remove('newGame-disabled');
showModal();
result_p.innerHTML = "";
userName_h = userName;
modal_h.innerHTML = userName + "<br>You lose the ENTIRE game!";
makeTableFromProgress()
showModal();
}
}
newGame();
choices_div.classList.add('choices-disabled');
//MODAL
var modal = document.getElementById("modal-one");
var showModal = function() {
event.preventDefault();
document.querySelector('#modal-overlay').classList.add('show');
modal.classList.add('show');
};
var hideModal = function(event) {
event.preventDefault();
document.querySelector('#modal-overlay').classList.remove('show');
this.parentElement.classList.remove('show');
};
var closeButtons = document.querySelectorAll('.close');
for (var i = 0; i < closeButtons.length; i++) {
closeButtons[i].addEventListener('click', hideModal);
}
document.querySelector('#modal-overlay').addEventListener('click', hideModal);
var modals = document.querySelectorAll('.modal');
for (var i = 0; i < modals.length; i++) {
modals[i].addEventListener('click', function(event) {
event.stopPropagation();
});
}
function makeTableFromProgress() {
var resultsTableBody = document.querySelector('#resultsTableBody');
var rows = params.progress.length;
for (i = 1; i < rows; i++) {
var row = resultsTableBody.insertRow(i - 1);
var cell1 = row.insertCell(0);
var cell2 = row.insertCell(1);
var cell3 = row.insertCell(2);
var cell4 = row.insertCell(3);
cell1.innerHTML = params.progress[i]['number'];
cell2.innerHTML = params.progress[i]['playerMove'];
cell3.innerHTML = params.progress[i]['computerMove'];
cell4.innerHTML = params.progress[i]['gameResult'];
}
};
$black: #000;
$white: #fff;
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
font-family: 'Open Sans', sans-serif;
background-color: #2d3030;
}
header {
background-color: $white;
padding: 20px;
}
header>h1 {
color: #2d3030;
text-align: center;
text-transform: uppercase;
}
#trophy {
margin-top: 20px;
text-align: center;
font-size: 30px;
color: $white;
&.trophydisabled {
display: none;
}
}
#trophy>p {
color: $white;
font-size: 20px;
}
.roundsCounter {
margin-top: 20px;
text-align: center;
}
.roundsCounter>p {
color: $white;
font-size: 20px;
}
.score-board {
margin: 30px auto;
border: 3px solid $white;
border-radius: 5px;
width: 200px;
color: $white;
font-size: 50px;
text-align: center;
padding: 15px 20px;
position: relative;
}
.badge {
width: 100px;
background-color: #af0e0e;
color: $white;
font-size: 15px;
padding: 2px 10px;
text-transform: lowercase;
}
#user-label {
position: absolute;
top: 40px;
left: -110px;
}
#computer-label {
position: absolute;
top: 40px;
right: -110px;
}
.result {
font-size: 40px;
color: $white;
}
.result>p {
text-align: center;
}
.newGame {
margin: 20px auto;
width: 250px;
border: 4px solid $white;
}
.newGame>p {
padding: 10px;
color: $white;
text-align: center;
font-size: 40px;
text-transform: uppercase;
}
.newGame:hover p {
background-color: $white;
color: #d01115;
font-weight: bold;
cursor: pointer;
}
#message {
margin: 20px;
text-align: center;
color: $white;
font-size: 30px;
font-weight: bold;
}
.choices {
margin-top: 30px;
text-align: center;
}
.choices button {
background-color: #2d3030;
display: inline-block;
width: 115px;
border: 4px solid $white;
border-radius: 50%;
font-size: 50px;
color: $white;
padding: 20px;
margin: 10px;
transition: all 0.4s ease;
}
.choices button:hover {
cursor: pointer;
color: #2d3030;
;
background-color: $white;
}
.challenge {
margin-top: 30px;
text-align: center;
color: $white;
font-size: 20px;
font-weight: bold;
}
.gray-glow {
border: 4px solid #787c77;
box-shadow: 0 0 15px 10px #787c77;
}
.green-glow {
border: 4px solid #31b43a;
box-shadow: 0 0 15px 10px #31b43a;
}
.red-glow {
border: 4px solid #d01115;
box-shadow: 0 0 15px 10px #d01115;
}
.choices-disabled {
display: none;
}
.newGame-disabled {
display: none;
}
.overlay {
display: none;
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.7);
&.show {
display: block;
}
}
.modal {
display: none;
background: $white;
width: 800px;
position: absolute;
top: 50%;
left: 50%;
transform: translate3d(-50%, -50%, 0);
padding: 20px;
text-align: center;
&.show {
display: block;
}
.close {
font-size: 20px;
position: absolute;
right: 0;
top: 0;
right: 5px;
padding: 5px;
color: $black;
text-decoration: none;
}
table {
text-align: center;
margin: 0 auto;
}
table th {
padding: 20px;
}
}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Rock Paper Scissors Final</title>
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.3.1/css/all.css" integrity="sha384-mzrmE5qonljUremFsqc01SB46JvROS7bZs3IO2EmfFsd15uHvIt+Y8vEf7N7fWAU" crossorigin="anonymous">
<link href="https://fonts.googleapis.com/css?family=Lato:400,700,900|Open+Sans:400,700,800&subset=latin-ext" rel="stylesheet">
<link rel="stylesheet" type="text/css" href="./style.css">
</head>
<body>
<header>
<h1>Rock! Paper! Scissors!</h1>
</header>
<div id="trophy">
<i class="fas fa-trophy"></i>
<p id="numberOfWins"></p>
</div>
<div class="roundsCounter">
<p id="numberOfRounds"></p>
</div>
<div class="score-board">
<div id="user-label" class="badge">user</div>
<div id="computer-label" class="badge">comp</div>
<span id="user-score">0</span>:<span id="computer-score">0</span>
</div>
<div class="result">
<p>Rock beats Scissors
<br>Paper covers Rock
<br>Scissors cuts Paper</p>
</div>
<div class="newGame">
<p>New Game</p>
</div>
<p id="message"></p>
<div class="choices">
<button class="player-move" id="Rock" data-move="Rock">
<i class="fas fa-hand-rock"></i>
</button>
<button class="player-move" id="Paper" data-move="Paper">
<i class="fas fa-hand-paper"></i>
</button>
<button class="player-move" id="Scissors" data-move="Scissors">
<i class="fas fa-hand-scissors"></i>
</button>
</div>
<p class="challenge">Let me defeat you!</p>
<div class="overlay" id="modal-overlay">
<div class="modal" id="modal-one">
<i class="fas fa-times"></i>
<h2 id="endMessage">""</h2>
<h3><br>How it was?</h3>
<table>
<thead>
<tr>
<th>No.</th>
<th>Player move</th>
<th>Computer move</th>
<th>Game result</th>
</tr>
</thead>
<tbody id="resultsTableBody"></tbody>
</table>
</div>
</div>
<script src="./index.js"></script>
</body>
</html>

A issue with the javascript event Object

I am teaching myself JavaScript and to improve my programming logic I decided to make a Hangman game. Everything works but I am having a problem with the win or lose function. The logic is If the indexCompare array length is === to correctGuesses Array length. Display You win If your lives are === to 0 Display you lose. But for some reason when a correct guess is pushed to the correctGuesses Array if it is a letter that appears more then once in the word. Only 1 occurrence of that letter is added to the array. So certain words never result in a win. And the win condition is never fulfilled. And I think it has something to do with me getting the value from the event Object. I might be wrong though. Any help would be greatly appreciated.
var gameCore = window.onload = function() {
var hangmanWords = ["super", "venus", "spanish", "darkness", "tenebris", "meatball", "human", "omega", "alpha", "isochronism", "supercalifragilisticexpialidocious"];
var commentsArray = ["I belive in you! You can do the thing!", "There is still hope keep trying", "Third times a charm", "You can do this", "Think player think! The counter is almost out", "Never give up", "The last melon 0.0", "What the frog you had one job u_u"];
var hints = ["The opposite of ordinary.", "A planet in are solar system.", "One of the largest languages in the world", "The opposite of light", "A rare word for darkness", "A tasty kind of sphear AKA 'ball' ", "You are A?", "A letter in the greek alphabet.", "Another letter in the greek alphabet.", "A word about time that almost no one uses.", "A big word that you know if you have seen mary poppins but never use."]
var correctGuesses = [];
var lives = 7;
var indexCompare = [];
var choosenWord = []
var arrayCounter = [];
//get elements
var showHint = document.getElementById("hint");
var showLivesLeft = document.getElementById("lives");
var showComments = document.getElementById("comment");
var showLoseOrWin = document.getElementById("winOrLoseDisplay");
// click assigner function
var clickAssigner = function(event) {
var letterHandler = document.getElementsByClassName("letters");
for (var i = 0; i < letterHandler.length; i++) {
letterHandler[i].addEventListener("click", compare, false);
}
var hintHandler = document.getElementById("hint");
hintHandler.addEventListener("click", hint, false);
}
clickAssigner(event);
function hint(event) {
if (arrayCounter[0] === 0) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 1) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 2) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 3) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 4) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 5) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 6) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 7) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 8) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 9) {
showHint.innerHTML = hints[arrayCounter]
};
if (arrayCounter[0] === 10) {
showHint.innerHTML = hints[arrayCounter]
};
}
// word selector and display function
// arrayCounter is the same as i
function wordSelector() {
var randomNumber = Math.floor(Math.random() * (10 - 0 + 1)) + 0;
arrayCounter.push(randomNumber);
var livesContainer = document.createElement("p");
var livesNumber = lives;
showLivesLeft.setAttribute("id", "livesNumbers");
showLivesLeft.appendChild(livesContainer);
livesContainer.innerHTML = livesNumber;
var selectedWord = hangmanWords[arrayCounter];
var wordDisplay = document.getElementById("wordDisplay");
var correctWordDisplay = document.createElement("ul");
var playerGuess;
for (var i = 0; i < selectedWord.length; i++) {
correctWordDisplay.setAttribute("id", "correctWordDisplay-UL");
playerGuess = document.createElement("li");
playerGuess.setAttribute("class", "playerGuess");
playerGuess.innerHTML = "_";
indexCompare.push(playerGuess);
wordDisplay.appendChild(correctWordDisplay);
correctWordDisplay.appendChild(playerGuess);
}
}
wordSelector();
// compare function // decrement lives function // remove health bar
function compare(event) {
var livesDisplay = document.getElementById("livesNumbers");
var btnVal = event.target.value;
var word = hangmanWords[arrayCounter];
for (var i = 0; i < word.length; i++) {
if (word[i] === btnVal) {
indexCompare[i].innerHTML = btnVal;
}
}
var c = word.indexOf(btnVal);
if (c === -1) {
event.target.removeAttribute("letters");
event.target.setAttribute("class", "incorrectLetter");
event.target.removeEventListener("click", compare);
lives -= 1;
livesDisplay.innerHTML = lives;
} else {
event.target.removeAttribute("letters");
event.target.setAttribute("class", "correctLetter");
event.target.removeEventListener("click", compare);
correctGuesses.push(event.target.value);
}
comments();
winOrLose();
// console.log(event);
// console.log(word);
}
// comment function
function comments() {
if (lives === 7) {
showComments.innerHTML = "<p>" + commentsArray[0] + "</p>"
};
if (lives === 6) {
showComments.innerHTML = "<p>" + commentsArray[1] + "</p>"
};
if (lives === 5) {
showComments.innerHTML = "<p>" + commentsArray[2] + "</p>"
};
if (lives === 4) {
showComments.innerHTML = "<p>" + commentsArray[3] + "</p>"
};
if (lives === 3) {
showComments.innerHTML = "<p>" + commentsArray[4] + "</p>"
};
if (lives === 2) {
showComments.innerHTML = "<p>" + commentsArray[5] + "</p>"
};
if (lives === 1) {
showComments.innerHTML = "<p>" + commentsArray[6] + "</p>"
};
if (lives === 0) {
showComments.innerHTML = "<p>" + commentsArray[7] + "</p>"
};
}
// win or lose function
function winOrLose() {
for (var i = 0; i < indexCompare.length; i++) {
if (indexCompare.length === correctGuesses.length) {
showLoseOrWin.innerHTML = "<p>" + "YOU WIN!!! :D" + "</p>";
}
}
if (lives === 0) {
showLoseOrWin.innerHTML = "<p>" + "YOU LOSE u_u" + "</p>";
}
}
function reset() {
}
}
html {
box-sizing: border-box;
}
*,
*:before,
*:after {
box-sizing: inherit;
}
/* http://meyerweb.com/eric/tools/css/reset/
v2.0 | 20110126
License: none (public domain)
*/
html,body,div,span,applet,object,iframe,h1,h2,
h3,h4,h5,h6,p,blockquote,pre,a,abbr,acronym,address,big,cite,code,del,dfn,em,
img,ins,kbd,q,
s,samp,small,strike,strong,sub,sup,tt,var,b,u,
i,center,dl,dt,dd,ol,ul,li,fieldset,form,label,
legend,table,caption,tbody,tfoot,thead,tr,th,
td,article,aside,canvas,details,embed,figure,figcaption,
footer,header,hgroup,menu,nav,output,ruby,section,
summary,time,mark,audio,video {
margin: 0;
padding: 0;
border: 0;
font-size: 100%;
font: inherit;
vertical-align: baseline;
}
/* HTML5 display-role reset for older browsers */
article,aside,details,figcaption,figure,footer,header,hgroup,menu,nav,section {
display: block;
}
body {
line-height: 1;
}
ol,ul {
list-style: none;
}
blockquote,
q {
quotes: none;
}
blockquote:before,
blockquote:after,
q:before,
q:after {
content: '';
content: none;
}
table {
border-collapse: collapse;
border-spacing: 0;
}
#container {
overflow: hidden;
max-width: 60%;
background-color: yellowgreen;
margin: 7em auto;
padding: 1em;
}
#wordDisplay {
height: 6em;
background-color: orangered;
margin-bottom: 0.2em;
text-align: center;
padding-top: 2.4em;
font-size: 26px;
display: flex;
justify-content: center;
}
#correctWordDisplay-UL {
list-style: none;
display: flex;
justify-content: center;
}
.playerGuess {
margin: 0em 0.08em;
font-size: 30px;
}
#hint {
max-width: 26em;
padding: 1em;
background-color: skyblue;
border: 0.5em ridge gold;
font-weight: 900;
margin: 0em auto 1em auto;
text-align: center;
}
#hint:hover {
background-color: coral;
cursor: pointer;
font-style: oblique;
}
#letterDiplay {
width: 14em;
float: left;
text-align: center;
background: crimson;
padding: 1em;
}
.letters {
margin: 0.3em auto;
text-align: center;
width: 4em;
height: 3em;
font-weight: 900;
background-color: darkorange;
border: 3px ridge darkblue;
}
.letters:hover {
background: steelblue;
color: white;
cursor: pointer;
}
#theChanceCounter {
text-align: center;
float: right;
width: 14em;
background-color: crimson;
height: 28.9em;
}
/* #lives{
width: 3em;
height: 3em;
margin: 1em auto 0em auto;
background-color: teal;
color: black;
font-weight: 900;
text-align: center;
} */
#livesNumbers {
margin-top: 1em;
border: 3px solid black;
width: 3em;
height: 3em;
padding: 0.9em 0em 0em 0em;
margin: 1em auto 0em auto;
background-color: teal;
color: black;
font-weight: 900;
text-align: center;
}
.correctLetter {
margin: 0.3em auto;
text-align: center;
width: 4em;
height: 3em;
font-weight: 900;
background: green;
color: yellow;
}
.incorrectLetter {
margin: 0.3em auto;
text-align: center;
width: 4em;
height: 3em;
font-weight: 900;
background: red;
color: yellow;
}
#comment {
background-color: forestgreen;
width: 12em;
height: 4em;
padding: 1em 0.4em 0em 0.4em;
margin: 0.3em auto 0.3em auto;
border: 3px solid black;
}
#winOrLoseDisplay {
width: 18em;
padding: 1em;
background-color: skyblue;
border: 0.5em ridge orange;
font-weight: 900;
margin: 0em auto 1em 1.4em;
text-align: center;
float: left;
}
<div id="container">
<section id="wordDisplay">
</section>
<section id="hint">Click for hint.</section>
<section id="letterDiplay">
<button class="letters" value="a">A</button>
<button class="letters" value="b">B</button>
<button class="letters" value="c">C</button>
<button class="letters" value="d">D</button>
<button class="letters" value="e">E</button>
<button class="letters" value="f">F</button>
<button class="letters" value="g">G</button>
<button class="letters" value="h">H</button>
<button class="letters" value="i">I</button>
<button class="letters" value="j">J</button>
<button class="letters" value="k">K</button>
<button class="letters" value="l">L</button>
<button class="letters" value="m">M</button>
<button class="letters" value="n">N</button>
<button class="letters" value="o">O</button>
<button class="letters" value="p">P</button>
<button class="letters" value="q">Q</button>
<button class="letters" value="r">R</button>
<button class="letters" value="s">S</button>
<button class="letters" value="t">T</button>
<button class="letters" value="u">U</button>
<button class="letters" value="v">V</button>
<button class="letters" value="w">W</button>
<button class="letters" value="x">X</button>
<button class="letters" value="y">Y</button>
<button class="letters" value="z">Z</button>
</section>
<section id="winOrLoseDisplay"></section>
<section id="theChanceCounter">
<div id="lives">
</div>
<div id="comment">
</div>
</section>
</div>
</script>

Categories