Created
April 12, 2015 08:27
-
-
Save anonymous/18418a6f275b9cfbe154 to your computer and use it in GitHub Desktop.
Duolingo Course Progress Script 2.5d by Martin (https://github.com/kane77/userscripts/tree/new) Mods by Dessamator (added gold skill count and next lesson)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// ==UserScript== | |
// @name Duolingo Course Progress | |
// @namespace https://github.com/kane77/userscripts | |
// @include https://www.duolingo.com/* | |
// @author Martin Harvan | |
// @version 2.5d | |
// @grant GM_getValue | |
// ==/UserScript== | |
//Mods by Dessamator | |
// Added golden skill count | |
// Added next skill | |
function inject(f) { //Inject the script into the document | |
var script; | |
script = document.createElement('script'); | |
script.type = 'text/javascript'; | |
script.setAttribute('name', 'lesson_stats'); | |
script.textContent = '(' + f.toString() + ')(jQuery)'; | |
document.head.appendChild(script); | |
} | |
inject(f); | |
function f($) { | |
function duolingoStats() { | |
try { | |
var language = window.duo.user.attributes.learning_language; | |
var langData = window.duo.user.attributes.language_data[language]; | |
var totalSkills = langData.skills.models.length; | |
var doneSkills = 0; | |
var totalActivities = 0; | |
var doneActivities = 0; | |
var iGoldenSkills=0; | |
var iStartedSkills=0; | |
for (var i = 0; i < langData.skills.models.length; i++) { | |
var skill = langData.skills.models[i]; | |
totalActivities += skill.attributes.num_lessons; | |
doneActivities += skill.attributes.num_lessons - skill.attributes.missing_lessons; | |
if (skill.attributes.missing_lessons === 0) { | |
doneSkills += 1; | |
} | |
if (skill.attributes.locked===false) { | |
iStartedSkills +=1; | |
} | |
if (skill.attributes.strength === 1) { | |
iGoldenSkills++; | |
} | |
} | |
if (langData.bonus_skills) { | |
var tBoughtSkills = duo.user.getOwnedBonusSkills(); | |
totalSkills +=duo.user.getOwnedBonusSkills().length; | |
for (var i = 0; i < langData.bonus_skills.models.length; i++) { | |
var skill = langData.bonus_skills.models[i]; | |
for (var j = 0; j < tBoughtSkills.length;j++){ | |
if(tBoughtSkills[j].short_name ==skill.attributes.short) { | |
if (skill.attributes.num_missing < skill.attributes.num_lessons) { | |
iStartedSkills += 1; | |
} | |
totalActivities += skill.attributes.num_lessons; | |
doneActivities += skill.attributes.num_lessons - skill.attributes.missing_lessons; | |
if ( skill.attributes.missing_lessons === 0 ) { | |
doneSkills += 1; | |
} | |
if (skill.attributes.strength === 1) { | |
iGoldenSkills++; | |
} | |
} | |
} | |
} | |
} | |
storeDCPItems(new Date(), doneSkills, doneActivities, language); | |
var lessonPercent = Math.round(doneActivities / totalActivities * 100); | |
var skillPercent = Math.round(doneSkills / totalSkills * 100); | |
var iSkillsLeft = totalSkills - doneSkills; | |
var iLessonsLeft = totalActivities -doneActivities; | |
var skillElem = createElem(doneSkills + "/" + totalSkills + ' ('+iSkillsLeft+')', skillPercent + "%", 'Skills', 'S'); | |
var lessonElem = createElem(doneActivities + "/" + totalActivities + ' ('+iLessonsLeft+')', lessonPercent + "%", 'Lessons', 'L'); | |
var goldElem = createElem(iGoldenSkills + "/" + doneSkills +" Golden", (doneSkills - iGoldenSkills) +" left to gild" , 'skills', 'G'); | |
var completeElem; | |
var stats = $('<ul class="sidebar-stats lesson-progress"></ul>'); | |
if (doneSkills == totalSkills){ | |
completeElem = createElem("Tree complete",":)","","C"); | |
completeElem.appendTo(stats); | |
} | |
else{ | |
if (langData.next_lesson) { | |
var sNextSkillUrl = langData.next_lesson.skill_url ; | |
var sUrl = 'https://'+document.domain + "/skill/"+language+"/" +langData.next_lesson.skill_url + '/'+langData.next_lesson.lesson_number; | |
var sLink = '<a href="'+sUrl+'">'+sNextSkillUrl+'</a>' | |
var sNextSkill = createElem('Next skill ('+sLink+')','Lesson; no.:'+langData.next_lesson.lesson_number,'','N') | |
sNextSkill.appendTo(stats); | |
} | |
skillElem.appendTo(stats); | |
lessonElem.appendTo(stats); | |
var lessonDiff = (doneActivities - parseInt(getLSItem('lessons', language, 1))); | |
if (lessonDiff > 0) { | |
var timeDiff = (new Date() - new Date(getLSItem('date', language, 1))); | |
var timePerLesson = timeDiff / lessonDiff; | |
var estTime = (totalActivities - doneActivities) * timePerLesson; | |
var finishDate = new Date(new Date().getTime() + estTime).toLocaleDateString(); | |
var days = Math.round(estTime / (1000 * 3600 * 24)); | |
if (!$('#estimate_stats').length) { | |
var estText = createElem(finishDate, days + " days remaining", "Estimate", "E" ); | |
estText.appendTo(stats); | |
} | |
} | |
} | |
goldElem.appendTo(stats); | |
if ($('#app').hasClass('home') && !$('.lesson-progress').length) { | |
$('.strengthen-skills-container').before(stats); | |
} | |
} catch (ex) { | |
console.log(ex); | |
} | |
} | |
function createElem(normalText, altText, name, icon) { | |
var elemText = $('<span id="' + name + '_text"><strong>' + normalText + '</strong> ' + name + '</span>'); | |
var percentage = $('<span id="' + name + '_percent"><strong>' + altText + '</strong></span>'); | |
percentage.hide(); | |
var elem = $('<li style="text-align: left; display: block; margin-top: 2px;" id="' + name + '_stats" title="' + altText + '"><span class="icon icon-words-small ' + name + '-icon">' + icon + '</span></li>'); | |
elem.append(elemText); | |
elem.append(percentage); | |
$('.' + name + '-icon').mouseover(function () { | |
$('#' + name + '_text').hide(); | |
$('#' + name + '_percent').css('display', 'inline-block'); | |
}).mouseout(function () { | |
$('#' + name + '_percent').hide(); | |
$('#' + name + '_text').show(); | |
}); | |
return elem; | |
} | |
$(document).ready(function () { | |
duolingoStats(); | |
}); | |
$(document).ajaxComplete(function () { | |
duolingoStats(); | |
}); | |
function getLSItem(name, language, id) { | |
if (id) { | |
return localStorage['dcp_' + language + '_' + name + '_' + id]; | |
} else { | |
return localStorage['dcp_' + language + '_' + name]; | |
} | |
} | |
function setLSItem(name, language, id, value) { | |
localStorage['dcp_' + language + '_' + name + '_' + id] = value; | |
} | |
function storeDCPItems(date, skills, lessons, language) { | |
var lastIndex = getLSItem('last_index', language); | |
if (!lastIndex) { | |
lastIndex = 1; | |
} else { | |
if (lessons <= parseInt(getLSItem('lessons', language, lastIndex)) && | |
skills <= parseInt(getLSItem('skills', language, lastIndex))) { | |
return; | |
} | |
lastIndex++; | |
} | |
setLSItem('date', language, lastIndex, date); | |
setLSItem('skills', language, lastIndex, skills); | |
setLSItem('lessons', language, lastIndex, lessons); | |
localStorage['dcp_' + language + '_last_index'] = lastIndex; | |
} | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment