Display your learning progress in numbers

Hello.

I 'm asking if it’s possible to implement some kind of progress to your learning path.
Like this f.e.:

I working in user script right now.
The main behaviour atm is to open every .mapList by clicking on it and then gather the info.
After that add gathered values into titles.

If somebody done this before, please share, if nobody has it, I will share it once finish it.
Cheers.

4 Likes

Just a little update, it gathers data now, img below.
Next step I’m going to move data from console direct to html.

Added one user feature which displays a menu of all topics in freeCodeCamp, onClick it moves you to the corresponded topic.
I’m working on adding progress into this #user_nav div so we can understand where we are and what we have completed without spending too much time.

Data added to the #user_nav
Going to work with some styles for now

Og guys, it’s done, I will add few buttons with more features.
Here is the installation procedure:

  1. Install tamper monkey (chrome/firefox)
  2. copy user script below (you can test it in console)
  3. go to https://learn.freecodecamp.org/
  4. click on tampermonkey, click on create a new script
  5. paste the script and save
  6. reload the main page, you will see new navigation div

Here is the source.

// ==UserScript==
// @name         user_navigation
// @namespace    http://tampermonkey.net/
// @version      0.1
// @description  User navigation block on freeCodeCamp.org
// @author       Yeugen
// @match        https://learn.freecodecamp.org/
// @grant        none
// ==/UserScript==

(function(){
  // add html div#user_nav where on click element we move to a corresponded topic
  document.body.insertAdjacentHTML('beforeend', '<div id="user_nav"></div>');
  // add css div#user_nav
  document.head.insertAdjacentHTML('beforeend', '<style>#user_nav{top: 38px; width: 300px; max-height: 400px; position: fixed; right: 0px; overflow: auto;}#user_nav a{color: #006400; text-overflow: ellipsis; overflow: hidden; white-space: nowrap; } #user_nav a:hover{text-decoration: none; background-color: #80b280; color: #fff;}</style>');
  // assign let to div#user_nav
  let user_nav = document.getElementById('user_nav');

  // main vars
  let block_open = document.getElementsByClassName('block open'),
    super_block_open = document.getElementsByClassName('superblock open'),
    map_title = document.getElementsByClassName('map-title');

  // close all opened blocks
  function block_close(){

    block_open = document.getElementsByClassName('block open');
    super_block_open = document.getElementsByClassName('superblock open');

    for(let i = block_open.length - 1; i >= 0; i--){
      block_open[i].children[0].click();
    }

    for(let i = super_block_open.length - 1; i >= 0; i--){
      super_block_open[i].children[0].click();
    }

  }

  // open all blocks (.map-title)
  function openList(){

    map_title = document.getElementsByClassName('map-title');

    for(let i = 0; i < map_title.length; i++){
      map_title[i].click();
    }

  }

  // gather data from opened block, add to created div#user_nav as <a href="#user_nav_*">
  function getCompletedLi(){

    block_open = document.getElementsByClassName('block open');

    for(let i = 0, counter = 0; i < block_open.length; i++){

      for(let j = 0; j < block_open[i].children[1].children.length; j++){

        if(block_open[i].children[1].children[j].classList.length > 1){
          counter++;
        }

      }

      // assign #user_nav_* to each title (f.e."Introduction to Basic HTML and HTML5")
      block_open[i].children[0].children[1].id = 'user_nav_' + i;

      // output => <a href="#user_nav_12">[ 0/20 ] - Basic Data Structures</a>
      user_nav.insertAdjacentHTML('beforeend', '<a href="#user_nav_' + i + '">[ ' + counter + '/' + (block_open[i].children[1].children.length - 1) + ' ] - ' + block_open[i].children[0].children[1].innerText + '</a><br />')

      counter = 0;

    }

  }

  // call functions
  setTimeout(() =>{
    block_close();
    openList();
    getCompletedLi();
  }, 1e3);

})();
2 Likes

Awesome idea! There was a similar request for this feature, I think on GitHub, but I cannot find it anymore. You should open an issue there or try to find the one that already exists (if it exists). You already have the code ready, you can propose to implement this feature yourself, if you want to, or leave it for someone else to do if you dont have the time.

There is another issue that opens the basic html part of the responsive section every time you open https://learn.freecodecamp.org/ . I didnt check if your script solves this issue? If it does you can check for that issue too, there should be one for that on GitHub.

Good work! :smiley:

I didn’t look into the code, but isn’t it supposed to show me how many lessons I already finished?

I can only see 0/29 etc. for every block of lessons,
like in your example image.

Hello myrmidonut,

Thank you for your reply.
To be honest I didn’t check source of freeCodeCamp on github, but I will take time to read it with patience.
Once I finish user_navigation user script I will open a request on github (but if you want to do it by yourself, feel free, it’s open source anyway :slight_smile: )

“There is another issue that opens the basic html part of the responsive section every time you open https://learn.freecodecamp.org/
I didn’t get this type of issue, or maybe I don’t do the same steps as you do, could you share your step by step please? :smiley:

Sorry for my english.

Cheers and have a nice afternoon.

Regards,
Yeugen

Hello miku86coding and thank you for your reply,

It is exactly what is doing right now, it shows you the info completed lessons/tasks on the top-right corner of your tab, like here:
%D0%B8%D0%B7%D0%BE%D0%B1%D1%80%D0%B0%D0%B6%D0%B5%D0%BD%D0%B8%D0%B5

If you have different output or it is everything on zero but you have completed items, please share your console output, thanks.
I will add some try catch in a future to solve some kind of errors.

Cheers, and have a nice day :slight_smile:
Regards,
Yeugen

1 Like

Dude this is legendary. I definitely wanted this feature. It is awesome that you took the time to do this. Thank you so much!

“There is another issue that opens the basic html part of the responsive section every time you open https://learn.freecodecamp.org/”
I didn’t get this type of issue, or maybe I don’t do the same steps as you do, could you share your step by step please? :smiley:

Maybe you have to disable your script first to see how it behaves. When you reload https://learn.freecodecamp.org/ it always expands “Basic HTML and HTML5”. Same happens when you go back from a later challenge to the main page via the “Curriculum” button in the top left:

image

I was wondering if this behaviour changed for you when you run your script?

I debugged the code and found out,
that the IIFE runs before the classList has its second class for passing the if condition.
therefore the counter condition is always false.

Setting up a Listener for DOMContentLoaded didn’t work,
so I fixed it by changing the IIFE into an anonymous handler of the setTimeout function.

setTimeout((function(){
...
}), 10000);

Now it outputting the correct values.
Thanks for your work,

I decided to create a github.
Here it is:

If somebody wants to use it or change, feel free.
It is working as expected at the moment.

Nice! :smiley:

I think I got you confused… when I said you could post it on GitHub I meant the issue tracker for freeCodeCamp:

But I dont know if its just for problems, or if we can propose additions to the website there as well. Anyway I dont want to steal your fame :wink: so I leave it up to you to post it there.

Oh sir, you are right!
Added a github topic/issue here:

Thank you!

Hi @miku86! I was thinking that could be great if opens just in the place you’ve left. Where could I suggest that? Tks!

@maurodibert hi/hola.
It could be done with localstorage object but, to be honest, I am okay with what is doing right now.
if anyone wants to add self tailored function are very welcome, the code is open-source and free to use, reuse, recopyright and do what ever you like to do.

If you want to create a function for your own you might use a google-fu for:
offsetTop
window.scrollTo

Good luck :slight_smile: