Latest news about Bitcoin and all cryptocurrencies. Your daily crypto news habit.
Let me start with a simple scenario. In the below example, We have a user, Bill, who wants to access our database of books. He searches for books from 1985. We make an API call, and deliver the results to the page. The main question here is, how should we display the data once itās been retrieved?
Above is a pretty typical layout for displaying the data. The search bar at the top, and the results below the search bar, once the data is loaded. However, this creates a minor problem, scrolling. Now, we are requiring the user to scroll through so much data to find what theyāre looking for. Maybe Bill doesnāt mind. But suppose heās searching for an obscure book from 1985. Maybe he would recognize the title if he saw it, but heās got to scroll all the way to the bottom, then go to page 2 and then page 3 and then page 4 before he finds it. What weāre requiring Bill to do might look likeĀ this:
Now, in all fairness, this is pretty typical and so, as users, weāve come to expect this from many sites, and so the average user probably doesnāt mind much anyway. But, just for the sake of fairness, letās create a more elegant, 1 page design for Bill, using JavaScript and JQuery. I like to draw my ideas out first, so hereās what I had inĀ mind:
In this crude example, weāve completely cleaned up the site, and leave lots of breathing room and negative space which Iām sure Bill will appreciate. Weāve created a side panel where all the controls will be. The user will search here, and see the results in the same panel. In our simple case, we donāt even need to display all the data for every book. We could simply display the title of each book. Then, when itās clicked on, the full synopsis, image and information would appear on the main contentĀ area.
The data, in this case doesnāt really matter. This could be for toy airplanes, books, video games, or princess dolls. In either case, for me personally, I prefer the simple, clean, Single PageĀ design.
STEP 1Ā :Ā HTML
The HTML could be prettyĀ basic.
<body> <div id="sidepanel" class="sidepanel"><input id="input" placeholder="what do you want?" /><button type="submit" id="submitBtn">Go</button>
<div id="dynamicSideContent">
//--Content goes here--//</div>
</div><div id="content" class="content">
//--Content goes here--//
</div>
</body>
Depending on the scenario, this is really all we need. Yes, eventually weāll pretty it up with a banner and a logo and all the stuff that real sites usually have. But at the end of the day, since all our data is going to be dynamically generated, this is all weĀ need.
We have:
A) sideĀ panel1) SearchĀ Bar2) Content LoadingĀ AreaB) ContentĀ Div1) Content LoadingĀ Area
Step 2: Make the APIĀ Call
$(window).load(function() { console.log("talking");
fetch('myApi_URL_thingy').then(function(response) { if (response.status != 200) { window.alert("Oopsie Daisy"); return; }
response.json().then(function(data) {
Step3: Parse theĀ Data
We have our data now, in some shape or form. Our end goal here, is to get some book titles, or whatever, do display in our sidepanel. Here are a couple of problems we may face in doingĀ that:
ProblemĀ :
Each button will correspond to a book within our data. Each button will have a book title inside it. We donāt want to use a link, since that will navigate us to a new page. Instead, we want to display it in our content area to the right. If we were using links, we could simply store the links in our data file. when the user clicks on a link, we would pull that piece of the data, access the url and redirect the user. But we donāt want to do that. To get around this, weāll need to dynamically create idās for each button, and then, store data in the button id about each book so that we can access and display it in the content area. We can do that with a for loop when we parse ourĀ data.
In the below example, Iām going to instead use the scenario that our user, Bill is searching by author instead of Date, because thatās just moreĀ fun.
let input = document.getElementById('input'); let submit = document.getElementById('submitBtn'); submit.onclick = searchData;
function searchData () { let currentBook = []; let input = document.getElementById('input'); for (var i = 0; i < books.length; i++) { let val3 = input.value; let val2 = val3.toLowerCase(); let value = val2.replace(/ /g, ''); let text3 = books[i].author; let text2 = text3.toLowerCase(); let text = text2.replace(/ /g, ''); console.log(text.indexOf(value) >= 0); console.log(text); console.log(value); if (text.indexOf(value) >= 0) { currentBook.push([books[i], i]); }
}
What I did here, is try to think of what a User might do. Bill might want a book by Dr. Laura Ingram. But, poor Bill, his memory is fadingā¦and all he can remember is āLauraā. So he searches for authors by submitting āLauraā into the input. What the above does, is it converts the input to lowercase, then removes any spaces in the input. Then for the current API entry, I do the same thing to the author. This way, if Bill Searches for āLauraā and the actual author is listed as āDr. Laura Ingramā, JavaScript is actually comparing these twoĀ strings:
ālauraā and ādr.lauraingramā.
If we hadnāt done that, it would be comparing:
āLauraā to āDr. LauraĀ Ingramā,
and it might be more difficult to match the results with the uppercase and additional spaces. We want to compare apples to apples instead of apples to oranges. Now that we have two similar strings, we doĀ this:
if (text.indexOf(value) >= 0) { currentBook.push([books[i], i]); }
What weāre doing now that we have these two strings, is seeing if the current iterable book author contains a substring of the user Input. Since ādr.lauraingramā does have the substring ālauraā, it would make the match. Now, again, this could create a host of other problems that we would have to tackle, like lots of results that arenāt what Bill intended, but letās not forget, itās Bills fault, and his memory problems that got us into this mess in the first place! MovingĀ onā¦
In any case, at this point, we should have the book that Bill is searching for, and weāre displaying it, and any other matches in the side column. But remember, we want to put the content of the book in the button IdĀ somehow.
Weāve just pushed all the matched books to an array called currentAuthor. Letās dissect that array with a for loop, and create buttons using backticks. Then weāll insert the ID into the button using the template expression.
for (var i = 0; i < currentBook.length; i++) { currentBook[i] = ` <button id="id_${currentBook[i][1]}" class="btn7"> ${currentBook[i][0].author}-${currentBook[i][0].title} </button> `; document.getElementById('dynamicSideContent').innerHTML += currentQuote[i]; } }
So, what Iāve done here is looped through currentBook. Then, for each entry in the array, Iām assigning it a new value with a template expression. The template expression consists of just a button with an ID, a class and text inside theĀ button:
<button id="id_${currentBook[i][1]}" class="btn7"> ${currentBook[i][0].author}-${currentBook[i][0].title}</button>
Now, if you noticed, when I looped through my initial book array, I pushed the matched books, ābooks[i]ā, but I also pushed the iteration number āiā, both into an array. Since each iteration number is unique, I can use that as part of my button ID, which I did there. The button, defined in the template expression isĀ :
id_${currentBook[i][1]}
But, which means that each book ID will actually be āid_1ā, āid_2āā¦and soĀ on.
One other thing to point out is that the class is ābtn7ā. Because we canāt access those IDs within JavaScript, weāll actually use JQuery to access the class first, and then get the ID after we have accessed the class. Weāll simply do that with each buttonĀ click.
The pseudo code would be, āIf a button with btn7 class is clicked, do somethingā.
Hereās how weāll write that with the help ofĀ JQuery:
$(document).on('click', '.btn7', function () { let currentBook = []; let id = this.id; let currentId = id.split("_"); let idNumber = parseInt(currentId[1]); let disregard = parseInt(currentId[0]); for (var i = 0; i < books.length; i++) { if(i == idNumber ) { currentBook.push(books[i]); } }
What Iāve done here is just that. We listen for any time that a button with the class ābtn7ā is clicked. We know that button has an ID, so we access it with āthis.idā and assign it to a variable called āidā. Then, we split that IDĀ string:
let currentId = id.split("_");
Our Idās all start with āidā followed by an underscore and then a number. string.split() will turn that into an array, we donāt need the id, or the underscore nowā¦we only want the number. We get that by converting the currentID variable into aĀ number
let idNumber = parseInt(currentId[1]);
Then, in our for loop, we see if the idNumber matches the iteration of the current book. If thereās a match, thatās the one weĀ want.
for (var i = 0; i < books.length; i++) { if(i == idNumber ) { currentBook.push(books[i]); }
When we initially searched our array, we saved that index value, and then weāre using it again to make sure we match the dynamic button that the userĀ clicked.
Now that Bill clicked what he wanted, we need to display that in our content area. Weāll use the same template expression format we used earlier to create that and send it to theĀ HTML.
for (var i = 0; i < currentBook.length; i++) { currentBook[i] = ` <span class="container"> <h1 class="bookTitle">${currentBook[i].author} - ${currentBook[i].title}</h1> <p class="synopsis">${currentBook[i].text}</p> </span> ` document.getElementById('content').innerHTML += currentBook[i]; }
At this point, weāre just parsing the array we just created with a for loop. Unless we also need to do something with this data, we donāt need to create the IDās again, but we could do that again if we needed to. Here, weāre just taking that button click, and putting the matching book onto the mainĀ display.
Again, there are many, many ways to do something like this, and probably a lot that are way better and simpler than mine, but I think itās at least a step in the right direction. Let me know if you have any feedback. Thanks!
Converting Multi-page Layouts To Clean SPAs with JavaScript and JQuery was originally published in Hacker Noon on Medium, where people are continuing the conversation by highlighting and responding to this story.
Disclaimer
The views and opinions expressed in this article are solely those of the authors and do not reflect the views of Bitcoin Insider. Every investment and trading move involves risk - this is especially true for cryptocurrencies given their volatility. We strongly advise our readers to conduct their own research when making a decision.