docs: function(){
  		var articleRect = this.article.getBoundingClientRect();
  
  		var buttons = this.buttons;
  
  
  		var positions = this.titles.map(function(header, i){
  			return {
  				header: header,
  				rect: header.getBoundingClientRect(),
  				button: buttons[i]
  			};
  		});
  		// this simulates a header at the end of the page
  		positions.push({
  			rect: {
  				top: articleRect.top + this.article.scrollHeight - this.article.scrollTop
  			}
  		});
  		// loop through the actual headers and their positions
  		positions.slice(0, positions.length - 1).forEach(function(position, index){
  
  			position.button.classList.remove("completed","active");
  
  			var curRect = position.rect;
  			var curDistance = curRect.top - articleRect.top;
  
  			var nextRect = positions[index+1].rect;
  			var nextDistance = nextRect.top - articleRect.top;
  
  			// =====[CUR=NEXT]===
  			if( nextDistance >= 0 && nextDistance <= articleRect.height && curDistance >= 0 && curDistance <= articleRect.height ) {
  				position.button.classList.add("active");
  			}
  			// =======CUR=====[=NEXT=|===]======
  			// =======CUR=======NEXT=====[===|===]===
  			else if( nextDistance < (articleRect.height / 2) ) {
  				position.button.classList.add("completed");
  			}
  			// ======[=CUR=|=NEXT=]======
  			// ======[=CUR=|===]=NEXT====
  			// ====CUR=[===|=NEXT]=======
  			// ====CUR=[===|===]=NEXT====
  			else if( nextDistance >= (articleRect.height / 2) && curDistance < (articleRect.height / 2) ) {
  				position.button.classList.add("active");
  			}
  		});
  		var elementToScroll = this.outlineScrollElement;
  
  		if(elementToScroll) {
  			// find out where the midpoint is
  			var distance = (this.article.scrollTop + this.article.offsetHeight / 2) / this.article.scrollHeight;
  			elementToScroll.scrollTop = (elementToScroll.scrollHeight * distance) - (elementToScroll.offsetHeight / 2);
  		}
  	}