1

I need your help folks!

I would like to know the best practice of how to retrieve a variable from a page other than the one that's loaded.

For example, let us assume this is a blog website.

A span tag is used to have a class of label and has inner text such as "Adventure" or "Culture".

   <span class="label label-success">Adventure</span>
   <span class="label label-info">Culture</span>

These will be used for various blogs previews on the "index.html" page. On "page2.html" there is a sidebar that shows the categories "Adventure" and "Culture" among some others.

Each label used in the sidebar will also use Bootstrap badge class to show the count of blogs containing that span with each category text.

I'm new to Jquery, but I know that using global variables is bad. I've read other people using the window object to create variables while keeping global scope clean. This is over my head and none of the examples I've read make it seem like it is being used over several pages.

I need to count the number of occurrences of each category that will be inner text of a span with label class.

This number will come from the index page.

Here's two examples of the blog previews that will contain the category in a span:

<section class="blog-post">
<div class="panel panel-default">
<img src="img/this_is_an_image.jpg" class="img-responsive" />
<div class="panel-body">
  <div class="blog-post-meta">
    <span class="label label-light label-danger">Adventure</span>
    <p class="blog-post-date pull-right">February 16, 2016</p>
  </div>
  <div class="blog-post-content">
    <a href="post-image.html">
      <h2 class="blog-post-title">Blog 1</h2>
    </a>
    <p>Donec ut libero sed arcu vehicula ultricies a non tortor. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean ut gravida lorem.</p>
    <a class="btn btn-info" href="post-image.html">Read more</a>
    <a class="blog-post-share pull-right" href="#">
      <i class="material-icons">&#xE80D;</i>
    </a>
  </div>
</div>
</div>
</section>

<section class="blog-post">
<div class="panel panel-default">
<img src="img/this_is_an_image_2.jpg" class="img-responsive" />
<div class="panel-body">
  <div class="blog-post-meta">
    <span class="label label-light label-success">Culture</span>
    <p class="blog-post-date pull-right">February 16, 2016</p>
  </div>
  <div class="blog-post-content">
    <a href="post-image.html">
      <h2 class="blog-post-title">Blog 2</h2>
    </a>
    <p>Donec ut libero sed arcu vehicula ultricies a non tortor. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean ut gravida lorem.</p>
    <a class="btn btn-info" href="post-image.html">Read more</a>
    <a class="blog-post-share pull-right" href="#">
      <i class="material-icons">&#xE80D;</i>
    </a>
  </div>
  </div>
  </div>
  </section>

It will be used in the spans of this sidebar on page2.html:

   <div class="sidebar-module">
<div class="panel panel-default">
  <div class="panel-body">
    <h4>Category</h4>
    <ol class="categories list-unstyled">
      <li>
        <a class="label label-light label-primary" href="filter-category.html">Adventure</a>
        <span class="label label-light label-default pull-right">1</span>
      </li>
      <li>
        <a class="label label-light label-warning" href="filter-category.html">Food</a>
        <span class="label label-light label-default pull-right">0</span>
      </li>
      <li>
        <a class="label label-light label-info" href="filter-category.html">Culture</a>
        <span class="label label-light label-default pull-right">1</span>
      </li>
      <li>
        <a class="label label-light label-danger" href="filter-category.html">Nature</a>
        <span class="label label-light label-default pull-right">0</span>
      </li>
      <li>
        <a class="label label-light label-success" href="filter-category.html">Beach</a>
        <span class="label label-light label-default pull-right">0</span>
      </li>
      <li>
        <a class="label label-light label-inverse" href="filter-category.html">Sites</a>
        <span class="label label-light label-default pull-right">0</span>
      </li>
    </ol>
  </div>
</div>

I'm sure it is something easy, but I'm learning so any instruction in layman's terms would be great! Thanks in advance for your time, consideration, and willingness to teach.

@charlietfl, I've done a bit more research and have another question for you. I may put the blog articles into JSON format and use $.getJSON() to format it. Maybe something similar to this:

$.getJSON('blog.json', function(data) {
var output = '<ul>';
$.each(data, function(key, val) {
    output += '<li>' + val.blogtitle + '</li>';
});
output +='</ul>';
$('#update').append(output);
});

Is this what you meant? So now that I'm loading a JSON file that will hold all of the blog info it can be read into the index.html and retrieved on the second page where I need to count the entries, right? I know this code isn't correct yet. Am I heading in the right direction?


@ zer00ne - I apologize, but maybe I'm too noobish to understand what you're recommending for me. I do appreciate your help though. Thanks for the patience.

This code is from a modified template:

A section represents a blog post. A blog post has a few pieces of info. There is a category specifying what the subject of the blog is about and I was hoping to use to count the number of blogs aka sections containing it.

The category is found on this line for this one blog:

<span class="label label-light label-danger">Adventure</span>

This blog has a category of "Adventure". It is likely the only line worth looking at for this purpose.

On page2.html my sidebar has a li like this:

<li>
    <!-- Here the innerHTML is "Adventure" -->
    <a class="label label-light label-primary" href="filter-category.html">Adventure</a> 
    <!-- Span below contains a hard coded "1" for innerHTML. I need the count of index.html's spans that have a class of label containing innerHTML of "Adventure" to increase the count by 1 to be placed as the innerHTML of this span on page2.html. -->
    <span class="label label-light label-default pull-right">1</span>
</li>

I'm fully aware that you are much more, far more experienced than I am. I consider this to be my lack of knowledge. With the broken up code I am confused as to what goes where. I suppose you want me to change the tags of my code to more accurate descriptions. In doing so, the scripts will then work?

I am currently looking into using JSON data instead of facing this mess. I think it may be far easier.

So far my example JSON file will look like this:

{"blogs": [
          {
          "image":"img/blog1image.jpg",
          "category":"Adventure",
          "date":"January 1, 2011",
          "title": "First Blog's Title",
          "preview":"This is an intro for the first blog. Short and concise."
          },
          {
          "image":"img/blog2image.jpg",
          "category":"Culture",
          "date":"February 2, 2012",
          "title": "Second Blog's Title",
          "preview":"This is an intro for the second blog. Short and concise."
          },
          {
          "image":"img/blog3image.jpg",
          "category":"Culture",
          "date":"March 3, 2013",
          "title": "This is the third blog's title",
          "preview":"This is an intro for the third blog. Short and concise."
          }
]}

Being absolutely new to this I'm still tinkering with Jquery to count this data.

$.ajax({
url: 'json/blogs.json',
dataType: 'json',
type: 'get',
cache: false,
success: function(data){
  var count = 0;,
  $(data.blogs).each(function(index, value){
    if("category" == "Adventure"){
      count++;
    )
}
})

This code is not correct, inside the each function, and I am sure there is a better way. Just trying to research all the methods/loops that might help me.

I apologize for the steep learning curve that I have to overcome. I am extremely grateful to have you and other members assisting me in finding the best solution.

DavidG
  • 785
  • 8
  • 23
  • 1
    take a look at localStorage. It is easy to use http://www.w3schools.com/HTML/html5_webstorage.asp – Bindrid Dec 31 '16 at 19:29
  • Great. +1 for simplicity. I forgot all about localStorage. Thanks much. Let me do a quick refresher and see if I can solve the problem. – DavidG Dec 31 '16 at 19:34

2 Answers2

1

Simple start approach would be add a class to each post <section> that represents the category

<section class="blog-post Culture">

Then put a similar data attribute on the total display spans along with a common class like cat-total

<span data-cat="Culture" class="cat-total label ...">1</span>

Now it is a simple loop through all the cat-total spans

$('.cat-total').text(function(){
  var cat = $(this).data('cat');
  return $('.' +cat).length)// get the number of sections with this category class
})
charlietfl
  • 170,828
  • 13
  • 121
  • 150
  • Will this work if all of my sections are on index.html and spans are on a different html file? – DavidG Dec 31 '16 at 19:37
  • No...but you could use ajax to get index and do the counting in ajax success callback. Are you not using a server side language to render all the posts or database to store all the posts? How the data is stored would be the important issue as theer are probably simple was to get what is needed from there – charlietfl Dec 31 '16 at 19:41
  • No. Honestly, this is me just tinkering. I'm a self taught web developer. Very new to the subject. I was going to just keep them all in HTML because there aren't any right now. lol. Any recommended resources to teach me how to do that? When I get home from vacation I'll reopen HTML books to see if it covers AJAX and using databases. Thanks for the insight. – DavidG Dec 31 '16 at 19:50
  • Am 100% self taught myself. If you don't want to use a server side dynamic language, you could store the data in a cloud storage like firebase and render all the data in page using ajax and template engine. Counting would be similar, request the data and count the categories – charlietfl Dec 31 '16 at 19:52
  • I will definitely look into this. Thank you very much! – DavidG Dec 31 '16 at 20:02
  • I've added some to the main post. Would you give me your thoughts? – DavidG Jan 01 '17 at 06:09
1

Using JQuery on a page to look at various page and get .size()

.size is deprecated since v.1.8 and removed entirely from v.3.0. Use the .length property instead.

I need to count the number of occurrences of each category that will be inner text of a span with label class.

This is very confusing and your HTML was too hard to follow. I took the liberty of rewriting the HTML so hopefully it'll be easy for other readers to follow. If you want to cut to the chase, here's the working demo comprising of 2 HTML files and an external CSS file.

PLUNKER

index.html

Step 1 - Find each <section> and count the number of <article>s each <section> has.

  $('.sec').each(function() {
   var articles = $(this).find('article');
   var total = articles.length;
   ...

.each().find()

Step 2 - Display the data for each <section>

  $(this).find('.qty').text(total);

.text()

Step 3 - When the link to page2.html is clicked, gather each <output class='qty'> and store their content in an array.

  $('a').on('click', function() {
    var data = [];
    $('.qty').each(function() {
      var txt = $(this).text();
      data.push(txt);
    });
  ...

.on().push()

Step 4 - Stringify the array and store it in localStorage

localStorage.setItem("data", JSON.stringify(data));

localStorage.setItem()JSON.stringify()


Difference Between JSON.stringify() and JSON.parse()

Store an Array in localStorage


page2.html

Step 5 - Get the stringified array and parse it back into an array.

var dataTxt = JSON.parse(localStorage.getItem("data"));

localStorage.getItem()JSON.parse()

Step 6 - Collect <output class='qty'> and iterate (loop) through them. In each iteration, assign the array's data, corresponding to each <output>'s indexed position.

var F = document.forms[0];
var total = F.elements.length;
for (let i = 0; i < total; i++) {
  F.elements[i].value = dataTxt[i];
}

Forms Collection

Community
  • 1
  • 1
zer00ne
  • 41,936
  • 6
  • 41
  • 68
  • Clarification: The span's containing the blog's category is found in the index.html here: Culture This one's category is "Culture". On page2.html the sidebar contains the following:
  • Culture 1
  • I'm hoping to find a way to make this span's innerHTML of "1" be found dynamically based on the number of blogs with a category of "Culture" in index.html. – DavidG Jan 01 '17 at 16:11
  • In your layout...what element represents a blog. My layout represents a blog with the element `
    `. Each category is represented by a `
    ` Do you see those numbers? Count the articles for each category on index.html are they accurate? Add an article by hardcode (an edit)...Is it still counting the `
    `s? Look on page2.html, are the numbers identical? The elements I have picked are semantically sound, and are more descriptive than a div or span with several classes. If for some reason your blogs are scattered with no rhyme or reason (that's what tags are for), then each...
    – zer00ne Jan 01 '17 at 16:51
  • ...(Cont) can have a class representing it's category. If that is how your layout is, then it's a simple modification adding conditionals and/or filters. Just looking around the other answers, I see @charlietfl suggests the same strategy. – zer00ne Jan 01 '17 at 16:55
  • I added a blurb to my original post. Thanks for your patience and help. – DavidG Jan 01 '17 at 19:42
  • @DavidG Did you try the Plunker? http://embed.plnkr.co/byeo8pkVpdIMKx7u9HtR/ It does exactly what you want but you need to establish a different way of thinking, you must understand DOM and arrays. You are concentrating too much on a node's content which is not a very stable aspect to base you logic on. Trying to get "hooks" into content rather than DOM, attributes, or even properties is like building a house with cotton candy. – zer00ne Jan 01 '17 at 20:26
  • I can understand that. While I've never tried to do something like this across multiple pages before, In writing basic HTML pages using CSS and simple JQuery I do normally go for the 'id' attribute, but I guess for this I felt a little overwhelmed and wasn't applying the fundamentals. I do appreciate the advice. I'll check out the Plunker. I've got so much to learn. Thanks for helping me in the right direction. – DavidG Jan 02 '17 at 00:50
  • 1
    Not a problem, I put in some extra effort because I see that you are as well. – zer00ne Jan 02 '17 at 01:59
  • 1
    I gave your responses some extra thought and wanted to give you an update on what I did. I was using a template I purchased because I thought it looked good. The problem with it is that it was not semantically correct. The developer lacked a lot of functionality that the page appears to have when it is rendered in the browser. My question was geared to make this template work. After taking your advice to heart I realized that I had compromised the fundamentals of programming. I suppose the reason why, as a relatively noob developer, it was overwhelming and difficult to find the – DavidG Jan 02 '17 at 21:48
  • 1
    ... (Cont) solution to this problem was because I settled for the easy road despite the fundamental teachings of web development. In the long run, even if I had made this work I would have a hard time managing it down the road. Because of this revelation, I've scrapped the template. I've also discovered isotype.js which offers the filtering and display flexibility I was seeking or like better than the template. I do appreciate the advice and help. I'd be slightly embarrassed if a potential employer or client discovered this post in the future, but I'll leave it anyway. Time to do it the right – DavidG Jan 02 '17 at 21:53
  • ...(Cont) way. Thanks again for your help. – DavidG Jan 02 '17 at 21:55
  • You are welcome, sir. Very astute observations, although your'e a bit hard on yourself. Some of the best web developers out there use WordPress for their personal blogs. The balance between time, quality, and practicality is delicate. Most employers appreciate consistency over innovation, and efficiency over semantics. – zer00ne Jan 03 '17 at 00:31