I have a news blog on asp-net.
There is a spoiler to the news. There are some news with spoilers on the page. However, if I click on any spoiler (first, second, third), then only the first opens in any case. I understand that it because of all buttons and fields have the same id. How can I implement the connection between the button and the spoiler? A specific spoiler must be opened after clicking on it, but not the first.
<div>
<label>Body</label>
<button type="button" id="button">Add spoiler</button>
<textarea id="spoilerField" asp-for="Body"></textarea>
</div>
#section scripts {
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script>
var textarea = document.getElementById("spoilerField");
var button = document.getElementById("button");
button.onclick = function () {
var len = textarea.value.length,
start = textarea.selectionStart,
end = textarea.selectionEnd,
sel = textarea.value.substring(start, end),
replace = '<input type="checkbox" id="spoiler2"/><label for="spoiler2">SEE SPOILER</label><div class="spoiler">' + sel + '</div>';
textarea.value = textarea.value.substring(0, start) + replace + textarea.value.substring(end, len);
}
</script>
}
You should still make those ids unique regardless, you could, for example, add elements to the page using a for loop with Razor and an index and joining the 2.
The id would then look something like:
id="spoiler_#i"
That aside, you should be looking at querySelectorAll or getElementsByClassName to select those elements and do what you need to do.
Related
The exercise says that my button (like a submit) must use the information set by user in input tag and create an li tag with the text as content. It was my first JavaScript class, so I'm still not familiarised with the syntax.
This is my actual code. I used a querySelector with the id of my existing ul tag, and addEventListener to create an event for the click action. I can't remember how to properly create the new li tag, and don't know how to use the content as info for it.
let myElement = document.querySelector('#add-book');
myElement.addEventListener("click", (e) => {
if (e.target.classList == 'button-add') {
let liElement = document.createElement('li');
let content = document.appendChild(liElement);
content.textContent();
}
});
I hope the button works properly, and show the element in the page by clicking the button (with the typed information).
Oversimplified, but hey, it works:
function AddLi(str)
{
var li = document.createElement('li');
li.appendChild(document.createTextNode(str))
li.innerHTML += ' <button onclick="this.parentNode.remove()">-</button>';
document.getElementById("out").appendChild(li);
}
<form>
<input type="text" name="userinput">
<input type="button" value="Add LI" onclick="AddLi(userinput.value)">
</form>
<span id="out"/>
I guess this is what you want:
(function () {
document.querySelector('#add').addEventListener('click', function () {
let input = document.querySelector('#text');
let list = document.querySelector('#list');
let item = document.createElement('li'); // create li node
let itemText = document.createTextNode(input.value); // create text node
item.appendChild(itemText); // append text node to li node
list.appendChild(item); // append li node to list
input.value = ""; // clear input
});
})();
<div>
<input id="text" type="text" />
<button id="add">Add</button>
</div>
<ul id="list">
<li>example item</li>
</ul>
But please, in the future, ask more specific questions. I don't even know what your problem is, because you don't provide all your code. Also the last sentence of your question is telling me nothing useful at all (.. "I hope the button works properly, and show the element in the page by clicking the button (with the typed information) " ..).
Try
function addBook(book) {
list.innerHTML +=
`<li>${esc(book.value)} <button onclick="del(this)">Del</button></li>`;
book.value = '';
}
function del(item) {
item.parentNode.remove();
}
function esc(s) {
return s.replace(/[&"<>]/g,c =>
({'&':"&",'"':""",'<': "<",'>':">"}[c]));
}
<ul id="list"></ul>
<input id="data" type="text" />
<button onclick="addBook(data)">Add</button>
Right now I am trying to figure out how to append CREATED text to a CREATED p element depending on what a user enters into an input text field.
If I set the text after the createTextElement method, it displays just fine when I click the button. BUT what I want is: the user enters text in the input field and then upon clicking the button, the text get's added to the end of the div tag with the id of "mydiv". Any help is appreciated.
HTML:
<body>
<div id="mydiv">
<p>Hi There</p>
<p>How are you?</p>
<p>
<input type="text" id="myresponse">
<br>
<input type="button" id="showresponse" value="Show Response">
</p>
<hr>
</div>
</body>
JAVASCRIPT:
var $ = function(id) {
return document.getElementById(id)
}
var feelings = function()
{
$("myresponse").focus();
var mypara = document.createElement("p");
var myparent = $("mydiv");
myparent.appendChild(mypara);
var myText = document.createTextNode($("myresponse").value);
mypara.setAttribute("id", "displayedresponse");
mypara.appendChild(myText);
$("displayedresponse").appendChild(myText);
}
window.onload = function() {
$("showresponse").onclick = feelings;
}
You need to apply an argument to createTextNode function
You need to read the value of the input field so you can see the text.
Since you will reference mydiv on every click, i think moving mydiv variable to parent scope will suit you better
var $ = function (id) {
return document.getElementById(id)
}
let mydiv = $('mydiv');
$("showresponse").addEventListener('click', feelings);
function feelings() {
let textInput = $('myresponse').value;
var mypara = document.createElement("p");
var myText = document.createTextNode(textInput);
mypara.setAttribute("id", "displayedresponse");
mypara.appendChild(myText);
mydiv.appendChild(mypara);
$("displayedresponse").appendChild(myText);
}
I have some simple code that allows you to enter Amazon isbns/asins and converts them to hyperlinks. These hyperlinks are Amazon.com searches for the said isbn/asin.
Example pic: http://imgur.com/a/rYgYt
Instead of the hyperlink being a search I would like the link to go directly to the products offer page.
The desired link would be as follows:
https://www.amazon.com/gp/offer-listing/ASIN/ref=dp_olp_used?ie=UTF8&condition=used
"ASIN" would be where the ASIN/ISBN would need to be populated to generate the link, for example:
Im asking if someone could help modify my existing code to create the change. My skills lack the ability to implement the change. The existing code is as follows:
<html>
<head>
</head>
<div><b>ISBN Hyperlinker</b></div> <textarea id=numbers placeholder="paste isbn numbers as csv here" style="width:100%" rows="8" >
</textarea> <div><b>Hyperlinked text:</b></div> <div id="output" style="white-space: pre"></div>
<input type="button" id="button" Value="Open All"/>
<script>
var input = document.getElementById('numbers');
var button = document.getElementById('button');
var output = document.getElementById('output')
var base =
'https://www.amazon.com/s/ref=nb_sb_noss?url=search-alias%3Daps&field-keywords='
var urls = []
//adding an event listener for change on the input box
input.addEventListener('input', handler, false);
button.addEventListener('click', openAllUrls, false);
//function that runs when the change event is emitted
function handler () {
var items = input.value.split(/\b((?:[a-z0-9A-Z]\s*?){10,13})\b/gm);
urls=[];
// Build DOM for output
var container = document.createElement('span');
items.map(function (item, index) {
if (index % 2) { // it is the part that matches the split regex:
var link = document.createElement('a');
link.textContent = item.trim();
link.setAttribute('target', '_blank');
link.setAttribute('href', base + item);
container.appendChild(link);
urls.push(base + item);//add the url to our array of urls for button click
} else { // it is the text next to the matches
container.appendChild(document.createTextNode(item))
}
});
// Replace output
output.innerHTML = '';
output.appendChild(container);
}
function openAllUrls(){
for(var i=0; i< urls.length; i++){//loop through urls and open in new windows
window.open(urls[i]);
}
}
handler(); // run on load
</script>
</html>
to modify output URL, replace
var base = ".....';
with
var basePrefix = 'https://www.amazon.com/gp/offer-listing/';
var baseSuffix = '/ref=dp_olp_used?ie=UTF8&condition=used';
and replace
base + item
with
basePrefix + item + baseSuffix
i have created text filed row in create function . i added delete button in create() function that calls delete when click on button. any help?
<body>
<input type="button" value="createDiv" onclick="create()"/>
</body>
<script type="text/javascript" defer="defer">
function create()
{
var newDiv = document.createElement('div');
newDiv.innerHTML = "<table id='e' border><tr><td><input type='text'><button onclick=del(this.value)</button></td></tr></table>";
// newDiv.className = 'newClass';
document.body.appendChild(newDiv);
}
function del (e) {
if ('function' === typeof e.remove) {
return e.remove();
}
return e.parentNode.removeChild(e);
}
Change:
<button onclick=del(this.value)
to:
<button onclick='del(this)'>
DEMO
Two problems:
You were missing the closing >.
The del function expects to receive the element to delete. The value of the element is not appropriate, especially since the button doesn't have a value.
I'm not sure this will do what you really want. This will just remove the button, it won't remove the table row. If you want to remove the whole table, you need to go up several levels of parentNode until you reach the <table> element.
Also, you should always enclose attribute values in quotes. In this case it works without them, because there are no spaces in the value, but you should get in the habit.
If you want to delete the row then the code should be something like this...
<script type="text/javascript" defer="defer">
function create()
{
var newDiv = document.createElement('div');
var rowId = "someId";
var output = "<table id='e' border><tr id='"+rowId+"'><td ><input type='text'><button onclick=del('"+ rowId +"')>delete</button></td></tr></table>";
newDiv.innerHTML = output;
newDiv.className = 'newClass';
document.body.appendChild(newDiv);
}
function del (id) {
var div = document.getElementById(id);
div.parentNode.removeChild(div);
}
</script>
If so you have done lot of mistake as Barmar Said.
I guess you are missing the quotes and the Button Tag Close tag '>'
<button onclick='del(this.value)'></button>
The HTML code for your button is incorrect. You don't have a closing bracket for the tag, and as there are no delimiters around the onclick attribute value, the closing tag will be part of the value, causing a syntax error in the script.
Try like this:
newDiv.innerHTML = '<table id="e" border><tr><td><input type="text"><button onclick="del(this.value)"></button></td></tr></table>';
I'm working on something really simple, a short quiz, and I am trying to make the items I have listed in a 2-d array each display as a <li>. I tried using the JS array.join() method but it didn't really do what I wanted. I'd like to place them into a list, and then add a radio button for each one.
I have taken the tiny little leap to Jquery, so alot of this is my unfamiliarity with the "syntax". I skimmed over something on their API, $.each...? I'm sure this works like the for statement, I just can't get it to work without crashing everything I've got.
Here's the HTML pretty interesting stuff.
<div id="main_">
<div class="facts_div">
<ul>
</ul>
</div>
<form>
<input id="x" type="button" class="myBtn" value="Press Me">
</form>
</div>
And, here is some extremely complex code. Hold on to your hats...
$(document).ready (function () {
var array = [["Fee","Fi","Fo"],
["La","Dee","Da"]];
var q = ["<li>Fee-ing?","La-ing?</li>"];
var counter = 0;
$('.myBtn').on('click', function () {
$('#main_ .facts_div').text(q[counter]);
$('.facts_div ul').append('<input type= "radio">'
+ array[counter]);
counter++;
if (counter > q.length) {
$('#main_ .facts_div').text('You are done with the quiz.');
$('.myBtn').hide();
}
});
});
Try
<div id="main_">
<div class="facts_div"> <span class="question"></span>
<ul></ul>
</div>
<form>
<input id="x" type="button" class="myBtn" value="Press Me" />
</form>
</div>
and
jQuery(function ($) {
//
var array = [
["Fee", "Fi", "Fo"],
["La", "Dee", "Da"]
];
var q = ["Fee-ing?", "La-ing?"];
var counter = 0;
//cache all the possible values since they are requested multiple times
var $facts = $('#main_ .facts_div'),
$question = $facts.find('.question'),
$ul = $facts.find('ul'),
$btn = $('.myBtn');
$btn.on('click', function () {
//display the question details only of it is available
if (counter < q.length) {
$question.text(q[counter]);
//create a single string containing all the anwers for the given question - look at the documentation for jQuery.map for details
var ansstring = $.map(array[counter], function (value) {
return '<li><input type="radio" name="ans"/>' + value + '</li>'
}).join('');
$ul.html(ansstring);
counter++;
} else {
$facts.text('You are done with the quiz.');
$(this).hide();
}
});
//
});
Demo: Fiddle
You can use $.each to iterate over array[counter] and create li elements for your options:
var list = $('.facts_div ul');
$.each(array[counter], function() {
$('<li></li>').html('<input type="radio" /> ' + this).appendTo(list);
}
The first parameter is your array and the second one is an anonymous function to do your action, in which this will hold the current element value.
Also, if you do this:
$('#main_ .facts_div').text(q[counter]);
You will be replacing the contents of your element with q[counter], losing your ul tag inside it. In this case, you could use the prepend method instead of text to add this text to the start of your tag, or create a new element just for holding this piece of text.