JQuery - click event for specific text? - javascript

<!DOCTYPE html>
<html>
<head>
<script src="jquery.js"></script>
<script src="data_generator.js"></script>
<title> Twiddler </title>
</head>
<body class='box'>
<body>
<div class='container'>
<h1 class='title'>My Twiddler</h1>
<div class='main'>
<h2>Tweet Feed</h2>
<p class='tweets'></p>
<p class='new'></p>
<button class='button'>New Tweets</button>
</div>
</div>
<script>
$(document).ready(function(){
var $body = $('.main');
var index = streams.home.length - 1;
while(index >= 0){
var tweet = streams.home[index];
var $tweet = $('<p></p>');
$tweet.text('#' + tweet.user + ': ' + tweet.message + tweet.created_at);
$tweet.appendTo('.tweets');
index -= 1;
}
//show new tweets using button
var $button = $('.button');
$button.click(function() {
//get random tweet
//streams.home is an array of all tweets of all users
var tweet = streams.home[Math.floor(Math.random() * streams.home.length)]
var $tweet = $('<p></p>');
$tweet.text('#' + tweet.user + ': ' + tweet.message + tweet.created_at);
$tweet.appendTo('.tweets');
})
//click on user to see tweet history
$body.click(function() {
})
//styling
$('.box').css("background-image", "url('https://www.rightmixmarketing.com/wp-content/uploads/2016/04/Twitter-Background.png')");
$('.title').css('font-size', '40px').css('text-align', 'center');
$('h2').css('text-align', 'center');
});
</script>
</body>
</body>
</div>
</html>
I'm making a twitter look a like. I am trying to show a users history by being able to click on the username and displaying all current tweets. How can I go about and do this? I have it set to click on the body of my text but obviously that is not the right way. How can I specifically target the username in this case? I attached a picture of my current html

How to register the event clicking just on 'username' part of the text?
Consider the following:
<p>
<a class='click-me' >Username</a>
There is a lot of text here.
There's some more text here. I want to be able to click ...
</p>
So you just need to wrap the username in an html element which has a certain class.
Then, you specify a listener for the click event on that class:
$('.click-me').on('click', function() {
//do something
});
Now, you probably need to know which username we're talking about and how to get the specific posts, for that there are other solutions. But this one answers your question in specific.

Related

How to print out API info into HTML

This question regards a university homework project.
I need to print out in HTML some information about a public API. I have managed to call on the public API and print out the list of radio channels into the menu on the left (no click function added yet), but now I need to show the current schedule for the day for each channels. The schedule are supposed to show inside the html tag "info".
I'm struggling because of the API link in the tag scheduleurl. How can I show each channel's schedule for the day when I click on each channel in the menu?
Things to know: I'm not allowed to modify the HTML file. My own js code starting point is marked by a comment.
HTML code:
<!DOCTYPE html>
<html lang="se">
<head>
<title>Sveriges Radio</title>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link href='http://fonts.googleapis.com/css?family=Oswald:400,300,700' rel='stylesheet' type='text/css'>
<link href='https://fonts.googleapis.com/css?family=Play:400,700' rel='stylesheet' type='text/css'>
<link rel="stylesheet" href="css/styles.css" type="text/css">
</head>
<body>
<header id="mainheader">
<div class="contain">
<h1 id="logo">DT084G - Projekt</h1>
<section id="player">
<select id="playchannel" class="form-control"></select>
<button id="playbutton" class="btn btn-primary">Spela</button>
</section>
<!-- /#search -->
</div>
<!-- /.contain -->
</header>
<div class="container">
<h2>SR - Sveriges Radio</h2>
<div class="left">
<section class="clist">
<h3>Bläddra via kanal</h3>
<nav id="mainnav">
<ul id="mainnavlist"></ul>
<div class="spacer" id="shownumrows">
<label for="numrows">Max antal: </label><input type="number" id="numrows" value="10" min="1" max="2000">
</div>
</nav>
</section>
<!-- /#lan -->
</div>
<!-- /.left -->
<div class="right">
<div id="info"></div>
<!-- /#info -->
</div>
<!-- /.right -->
<footer>
<p>Projektuppgift för kursen DT084G, Introduktion till programmering med JavaScript.</p>
<div id="radioplayer"></div>
</footer>
</div>
<!-- /.container -->
<script src="js/main.js"></script>
</body>
</html>
My so far written js code:
// Denna fil ska innehålla er lösning till projektuppgiften.
"use strict";
/* Delar till ej obligatorisk funktionalitet, som kan ge poäng för högre betyg
* Radera rader för funktioner du vill visa på webbsidan. */
//document.getElementById("player").style.display = "none"; // Radera denna rad för att visa musikspelare
//document.getElementById("shownumrows").style.display = "none"; // Radera denna rad för att visa antal träffar
/* Här under börjar du skriva din JavaScript-kod */
// HERE STARTS MY CODE
// variabler
var mainnavlistEl = document.getElementById("mainnavlist");
var i;
var restUrl = "http://api.sr.se/api/v2/channels/?format=json";
//funktion för ajax-anrop navigation vänster
window.onload = loadData;
function loadData() {
//ajax-antop
var xhr = new XMLHttpRequest();
xhr.onload = function () {
//check for answer
if (xhr.status === 200) {
var jsonStr = JSON.parse(xhr.responseText);
var channelsArr = jsonStr.channels;
//navigation vänster
// Inkluderat unika id och tagline för varje alternativ
for (i = 0; i < channelsArr.length; i++) {
// element
document.getElementById("mainnavlist").innerHTML += "<li id='" + channelsArr[i].id + "' title= '" + channelsArr[i].tagline + "'>" + channelsArr[i].name + "</li>";
}
console.log(channelsArr);
} else {
mainnavlistEl.innerHTML = "Fel vid anrop: " + xhr.status;
}
// Dropdown list
// Inkluderat unika id och tagline för varje alternativ
for (i = 0; i < channelsArr.length; i++) {
document.getElementById("playchannel").innerHTML += "<option id='" + channelsArr[i].id + "'" + "title='" + channelsArr[i].tagline + "'>" + channelsArr[i].name + "</option>";
}
}
//Send Ajax
xhr.open('GET', restUrl, true);
xhr.send(null);
}
// schedule
//variabel för id
document.getElementById("mainnavlist").addEventListener("click", function infoData(e){
var URL = "http://api.sr.se/api/v2/scheduledepisodes?channelid=" + e.target.id + "&format=json&indent=true";
//document.getElementById("info").innerHTML = URL ;
var idEl = document.getElementById("mainnavlist");
var restUrl2 = "http://api.sr.se/api/v2/scheduledepisodes";
var xhr = new XMLHttpRequest();
xhr.onclick = function () {
//check answer
if(xhr.status === 200) {
var jsonStr = JSON.parse(xhr.responseText);
var scheduleArr = jsonStr.title;
for(i = 0; i < scheduleArr.length; i++) {
document.getElementById("info").innerHTML += "<p>" + scheduleArr[i].title + "</p>";
}
}
}
xhr.open('GET', URL, true);
xhr.send(null);
})
Data inside the "scheduleurl tag in the channels json file
An example for one of the channels in the public API structure:
0: {image: "https://static-cdn.sr.se/sida/images/132/2186745_512_512.jpg?preset=api-default-square", imagetemplate: "https://static-cdn.sr.se/sida/images/132/2186745_512_512.jpg", color: "31a1bd", tagline: "Talat innehåll om samhälle, kultur och vetenskap. …ng och upplevelser till exempel i form av teater.", siteurl: "https://sverigesradio.se/p1", …}
1:
channeltype: "Rikskanal"
color: "ff5a00"
id: 163
image: "https://static-cdn.sr.se/sida/images/163/2186754_512_512.jpg?preset=api-default-square"
imagetemplate: "https://static-cdn.sr.se/sida/images/163/2186754_512_512.jpg"
liveaudio: {id: 163, url: "http://sverigesradio.se/topsy/direkt/srapi/163.mp3", statkey: "/app/direkt/p2[k(163)]"}
name: "P2"
scheduleurl: "http://api.sr.se/v2/scheduledepisodes?channelid=163"
siteurl: "https://sverigesradio.se/p2"
tagline: "P2 är den klassiska musikkanalen som även erbjuder jazz samt folk- och världsmusik. Digitalt sänder vi musikprogram dygnet runt, i FM finns även program på andra språk än svenska."
xmltvid: "p2.sr.se"
__proto__: Object
You are only getting the name. You need to get the other items and add the also. e.g. part of the code:
// On click pass id to the function
function myFunction(id) {
// put id in a variable
var id = id;
//use the variable in the url
var url = `http://example.com?id=id`;
// loop through elements for this id
for(var i=0; i<len; i++){
var id = response[i].id;
var slug = response[i].slug;
var excerpt = response[i].excerpt.rendered;
var link = response[i].link;
//put them all together in a variable in the html format you require
var tr_str =
'<td>'+
'<div class="card" style="width: 250px;">' +
'<div class="card-divider">' + id + ' ' + slug + '</div>' +
'<p>' + excerpt + '</p>' +
'<a href="' + link + ' " target="_blank">'+
'<input type="button" value="read more" style="margin-right: 15px;">' +
'</input>' +
' </a>' +
' </div>' +
'</div>'+
'</td>'
;
//append the variable to the dom element
document.getElementById("info").innerHTML += tr_str;
First off, I am not the best at either JavasSript or handling JSON, but maybe you could just consider me a rubber ducky of sorts, then it might lead you to a nice solution.
I went to the api url and looked at the data. It seems to me that the schedule portion of the json (hash, dictionary, what have you) is simply a link to THAT specific data... (which happens to be xml).
What I would do, if I were you, is before parsing the JSON into a string, I'd try to grab the schedule url, and and parse the xml into a useful format while parsing the JSON.
Once again, I'm not the best at this, but like rubber duckies, I do squeak. What do you think?
OK so I had to revise my answer, I think finally I understand what you want to do.
I'd replace for loop part of your code:
// create variable for the markup
let markup = '';
// using 'for of' loop for readibility
for (const channel of channelsArr) {
markup += `<li class="mainnavlist__item" id="${channel.id}">${channel.name}</li>`;
}
// once you have the whole markup constructed, replace the html content.
document.getElementById("mainnavlist").innerHTML(markup);
// now you would need an event listener, for example
document.addEventListener('click', function(event) {
if (event.target.classList.contains("mainnavlist__item")) {
// this function will render info html
showInfoData(event.target.id);
}
})
function showInfoData(id) {
// you need to gather the details you want to render into the info tag. This will give back the details of the clicked channel from the array, or here call another API, depends on from where you get the info
let currentChannel = channelsArr.filter(channel => channel.id === id)[0];
let infoMarkup = currentChannel.tagline;
document.getElementById("info").innerHTML(infoMarkup);
}
You also need to make sure to empty the info's innerHTML when you need to hide it (click outside, or on a close btn, etc). I hope I understood you right.
I had some trouble understanding what you want to achieve, but if it seems like you have made a successfull call to an API, and managed to display the names of the radiostation(?) in a list. What you want to do next i to be able to click on the items in the list on the left side, and then display some information on the right side?
The information you want to display should come from a API call to e.g:
"http://api.sr.se/v2/scheduledepisodes?channelid=163"
Now, what you are struggling with is how you can do this, and how to specify which ID to use when you call the API?
You already have the different ID's (the radiostation ID that goes on the end of the scheduleUrl string) as you HTML id for your list elements, right?
What i would do it create a listener event on your list elements. This listener should make a XHR-request to the scheduleUrl. You can use the ID from the HTML list element that you click as argument for you API call.
function listener(event){
url = "http://api.sr.se/v2/scheduledepisodes?channelid=";
id = event.target.id;
new_url = url + id;
// Make a new XHR-request here
// and display the received infomration
// where you want
}
However, to make this work, there are a few changes you need to make to your code.
When creating your list-elements, you use 'innerHTML'. This is not the best choice.
You should rather create an HTML DOM object, and then append this element to the 'unordered-list' element.
https://www.w3schools.com/jsref/met_node_appendchild.asp
You can also set the id, and other attributed directly to this 'child element'.
https://developer.mozilla.org/en-US/docs/Web/API/Element/setAttribute
It is when you create the list-elements you should add the event listener.
https://www.w3schools.com/js/js_htmldom_eventlistener.asp
So, to summarize:
You should change how you create you list-elements
You should add an click-listener to the list elements
The click listener should make a XHR-request based on the list-elements id (which is the same as the radiochannel id)

How to copy without losing selection javascript?

I am using a code in which it inserts a text containing the url of the current page after the person copies the selection (ctrl-c) and does this in a hidden part of the page, however when the person presses ctrl-c the selection some, would you have some way to copy and include the url of the current page without losing the selection? Sorry for the english, it was translated via google translator
<!DOCTYPE html>
<html>
<head>
<script>
function addLink() {
//Get the selected text and append the extra info
var selection = window.getSelection(),
pagelink = '<br /><br /> Read more at: ' + document.location.href,
copytext = selection + pagelink,
newdiv = document.createElement('div');
//hide the newly created container
newdiv.style.position = 'absolute';
newdiv.style.left = '-99999px';
//insert the container, fill it with the extended text, and define the new selection
document.body.appendChild(newdiv);
newdiv.innerHTML = copytext.replace(/\n/g, "<br />");
selection.selectAllChildren(newdiv);
//remove a novadiv
window.setTimeout(function () {
document.body.removeChild(newdiv);
}, 100);
}
document.addEventListener('copy', addLink);
</script>
</head>
<body>
<div id='perg'>Text to copy</div>
</body>
</html>
Not sure this is what you want. I actually created a div (displayed) that is just static and not dynamically created like you have for demo purposes. If I understand correctly you want to keep the current selection selected while copying the text and the location href to that div ? If you want the text you actually can use .toString(), and in your code, when you use selection.selectAllChildren you are deselecting the text that you copied from. Hard to undestand really exactly what you are asking.
<!DOCTYPE html>
<html>
<head>
<script>
function addLink() {
let hiddendiv = document.getElementById('copiedstuff');
let selection = window.getSelection();
let selectiontext = window.getSelection().toString();
pagelink = '<br /><br /> Read more at: ' + document.location.href;
copytext = selectiontext + pagelink;
hiddendiv.innerHTML = copytext.replace(/\n/g, "<br />");
}
document.addEventListener('copy', addLink);
</script>
</head>
<body>
<div id='perg'>Text to copy</div>
<div id='perg1'>Something Else</div>
<div style = "margin-top:20px;border:1px solid black;">
<div id='copiedstuff'></div>
</div>
</body>
</html>

How to create 'add to favourite' feature in a html cordova android app?

I am creating a song book app using phonegap. In index.html i have list of songs in li tags. when i click on a particular song it will open that particular song's lyrics in another local html file.
I want to add a 'favourite button'. When the favourite button is clicked I want that particular song to be added to the favourites list. When user open the favourite page it should display list of their favourite songs, and when they click a song in favourite page it should open that particular song's lyrics html page.
I am an intermediate user of HTML and a beginner in JavaScript.
Please help me accomplish this,
Thanks in advance.
Because this is a 'pretty broad' question, it is hard to find an answer for this, but I'd suggest making an array, storing the favorite songs into it, then when you open the favorites.html page, it gets the array, and writes the information to the page.
e.g. when a favorite button is clicked on a song page, it writes: the name of the song(exampleSong), the page of the song(exampleSong.html), and other random details that you need, and going to the favorites.html should get a document ready function that reads the array and writes the page.
Sorry if I can't help that much, but this was a really broad question.
If you need help, here are some examples that I created
(This gets the array of favorites, and prints them out)
var favorites = [
["ExampleSong", "exampleSong.html"],
["LorddirtCoolSong", "LorddirtCoolSong.html"],
["StackOverflowIsAwesome", "StackOverflowIsAwesome.html"]
];
var containerA = document.getElementById("favoritesA");
for (var i in favorites)
{
for (var j in favorites[i])
{
var newElement = document.createElement("p");
newElement.innerHTML = favorites[i][j];
containerA.appendChild(newElement);
}
}
var containerB = document.getElementById("favoritesB");
for (var i in favorites)
{
var newElement = document.createElement("p");
newElement.innerHTML = "<h4>Favorite Song " + i + "</h4>";
containerB.appendChild(newElement);
for (var j in favorites[i])
{
var newElement = document.createElement("p");
newElement.innerHTML = favorites[i][j];
containerB.appendChild(newElement);
}
}
var containerC = document.getElementById("favoritesC");
for (var i in favorites)
{
var newElement = document.createElement("p");
newElement.innerHTML = "<h4>Favorite Song " + i + "</h4>";
containerC.appendChild(newElement);
for (var j in favorites[i])
{
if(j == 1){
}else{
var newElement = document.createElement("p");
newElement.innerHTML = "<a href='" + favorites[i][1] + "'>" + favorites[i][j] + "</a>";
containerC.appendChild(newElement);
}
}
}
.favoriteSongs{
border: 2px solid black;
display: block;
}
<!--
EXAMPLE 1A: Print out the Favorites
-->
<hr>
<h2>Example 1A: Print favorites out</h2>
<div id='favoritesA' class='favorites'>
</div>
<hr>
<!--
EXAMPLE 1B: Now you know the order of the songs!
-->
<h2>Example 1B: Print favorites out with formatting</h2>
<div id='favoritesB' class='favorites'>
</div>
<hr>
<!--
EXAMPLE 1C: Link them
-->
<h2>Example 1C: Link to the page</h2>
<div id='favoritesC' class='favorites'>
</div>
<hr>
Very self explanatory, it gets the array of favorite songs, with the name and url, gets the container, which is <div id='favorites'></div> and writes the contents into it.
(oh wait, i just noticed I spent so long working on this hahaha.)
Examples:
1A: All I did was search the array favorites, and print out every single thing in the array. Simple.
1B: Slightly different, it's the same as the last, but I added a <h4> tag before every array in the array. (Yes, arrays inside arrays inside arrays are confusing).
1C: Instead of printing out both of the arrays inside the arrays, just print out the first thing inside the arrays in the arrays, and add a link pointing to the second thing inside the arrays in the arrays. Confused already? Just read it through and you'll understand.
Hi I found a solution using another SO question.
First we will create a local storage and store song details in that local storage key.
then we will retrieve that information in favorite.html using localStorage.getItem(key);
The following is my code for first song song1.html
when button pressed song link will be appended to local storage
<!DOCTYPE html>
<html>
<body onload="mySong()">
<button onclick="mySongOne()">add to favorite</button>
<script>
function mySong() {
localStorage.setItem("favsong", "");
}
function appendToStorage(name, data){
var old = localStorage.getItem(name);
if(old === null) old = "";
localStorage.setItem(name, old + data);
}
function mySongOne() {
appendToStorage("favsong", "<a href='https://www.song1.com'><h1>song1</h1></a>");
}
</script>
</body>
</html>
for another song song2.html
when button pressed second song link will be appended to local storage
<!DOCTYPE html>
<html>
<body>
<button onclick="mySongTwo()">add to favorite</button>
<script>
function appendToStorage(name, data){
var old = localStorage.getItem(name);
if(old === null) old = "";
localStorage.setItem(name, old + data);
}
function mySongTwo() {
appendToStorage("favsong", "<a href='https://song2.com'><h1>song2</h1></a>");
}
</script>
</body>
</html>
and favorite.html
on page load it will show details from local storage
<!DOCTYPE html>
<html>
<body onload="yourFunction()">
<div id="result"></div>
<script>
function yourFunction() {
document.getElementById("result").innerHTML = localStorage.getItem("favsong");
}
</script>
</body>
</html>

Making table with objects in array?

I'm a beginner in javascript and I have a little problem with my code. I found an exercise and i'm trying to do it. I have to write a function that will insert text from variable into table. I never met something like this. This variable looks like four objects in array. I want to show text in the table when I press a button. There are two buttons. When I press "Fizyka" button i should see:
Fizyka
Ola Kowal
Ela Nowak
and when I press "Chemia":
Chemia
Ala Goral
Ula Szpak
So this is my code. All i can edit is function show(study):
<!DOCTYPE html>
<html lang="pl">
<head>
<meta charset="utf-8">
</head>
<body>
<button onclick="show('fizyka')">Fizyka</button>
<button onclick="show('chemia')">Chemia</button>
<div id="list"></div>
<script>
var student=[
{name:"Ola", second_name:"Kowal", study:"fizyka"},
{name:"Ela", second_name:"Nowak", study:"fizyka"},
{name:"Ala", second_name:"Goral", study:"chemia"},
{name:"Ula", second_name:"Szpak", study:"chemia"},
];
function show(study)
{
if (study==='fizyka')
{
document.getElementById("list").innerHTML = "<h2>student.kierunek</h2><ul><li>student.name + " " + student.second_name</li><li>student.name + " " + student.second_name</li></ul>";
}
if (study==='chemia')
{
document.getElementById("list").innerHTML = "<h2>student.kierunek</h2><ul><li>student.name + " " + student.second_name</li><li>student.name + " " + student.second_name</li></ul>";
}
}
</script>
</body>
</html>
It's not working. I don't know how to insert text from this variable into table.
There is several problem with your code. I have written piece of code which is working and you can use it and inspire.
<button onclick="show('fizyka')">Fizyka</button>
<button onclick="show('chemia')">Chemia</button>
<div id="list"><h2></h2><ul></ul></div>
<script>
//Student array
var student=[
{name:"Ola", second_name:"Kowal", study:"fizyka"},
{name:"Ela", second_name:"Nowak", study:"fizyka"},
{name:"Ala", second_name:"Goral", study:"chemia"},
{name:"Ula", second_name:"Szpak", study:"chemia"},
];
function show(study)
{
console.log('ENTER show('+study+')');
//Select h2 element
var header = document.getElementById("list").firstChild;
//Set h2 element text
header.innerHTML = study;
//Select ul element
var list = document.getElementById("list").lastChild;
//Set inner html to empty string to clear the content
list.innerHTML = "";
//loop through students and set the appropriate html element values
for(var i = 0; i < student.length; i++){
//check whether student[i] studies study which is put as a paramter into the function
if(student[i].study === study){
//Create new li element
var li = document.createElement('li');
//Into li element add a new text node which contains all data about the student
li.appendChild(document.createTextNode(student[i].name + ' ' + student[i].second_name));
//add li element into ul
list.appendChild(li);
}
}
console.log('LEAVE show('+study+')');
}
</script>

How to check what the last dynamically added element was and run a Particular Function

I am trying to write a code for a chat application. What I want is, When someone types something and clicks on send, I want to add a 'row' (dynamically) inside a container called 'chat'. The 'row' contains the message in another container called 'message' (which is also created dynamically). I was able to do that. But what I want to do is this, when someone types two message in a row (i mean before getting any reply from the person he/she is chatting with) and hits send I don't want add an entire 'row' in the 'chat'. I just want to append the 'message' inside the row, something like :
$('button').on('click', function() {
if(last added element was .row.user) {
$('.row').appnd('<div class="message">/div>');
} else {
}
});
Is there anyway to achieve what I described is pseudo code?
here is the HTML
<div class="chat">
<div class="row">
<div class="message"></div>
</div>
</div>
This can be done like this:
function addMessage(message, user) {
chat = $("#chat"); //Get a reference to the chat div.
lastRow = chat.find(".row:last"); //Get a reference to the last row of the chat.
if(lastRow.attr("data-user") == user) {
//Its the same user who posted last time.
lastRow.append("<div class='message'>" + message + "</div>");
}
else {
//It's a different user.
chat.append('<div class="row" data-user="' + user + '"><div class="message">' + message + '</div></div>');
}
}
Working JSFiddle.
What about this:?
<html>
<head>
<style>
.row{
border: 1px solid;
padding: 5px;
margin: 5px;
}
</style>
</head>
<body>
<div class="chat"></div>
Message: <input type="text" id="message"/>
<br/><br/>
<button onclick="sendMessage('userA');">Send Message as User A</button>
<button onclick="sendMessage('userB');">Send Message as User B</button>
<script>
var lastUser = null;
function sendMessage(user){
var chat = document.querySelector('.chat');
var message = document.getElementById('message');
if(user != lastUser){
var newRow = document.createElement('div');
newRow.className = 'row';
var newMessage = document.createElement('div');
newMessage.className = 'message';
newMessage.innerHTML = '<strong>' + user + '</strong><br/>';
newMessage.innerHTML += message.value;
newRow.appendChild(newMessage);
chat.appendChild(newRow);
lastUser = user;
}else{
var rows = document.querySelectorAll('.chat .row');
var lastRow = rows[rows.length - 1];
var lastMessage = lastRow.querySelector('.message');
lastMessage.innerHTML += '<br/>' + message.value;
}
message.value = '';
}
</script>
</body>
</html>

Categories