Though this goes in the back of the document with the rest of the back
        matter, it is not an element found under <back>.

        I don't expect to see more than one of these. Compare this method to
        make_article_info_competing_interests()
553541
def make_back_author_contributions(self, body):
        
        cont_expr = "./front/article-meta/author-notes/fn[@fn-type='con']"
        contribution = self.article.root.xpath(cont_expr)
        if contribution:
            author_contrib = deepcopy(contribution[0])
            remove_all_attributes(author_contrib)
            author_contrib.tag = 'div'
            author_contrib.attrib['id'] = 'author-contributions'
            #This title element will be parsed later
            title = etree.Element('title')
            title.text = 'Author Contributions'
            author_contrib.insert(0, title)
            body.append(author_contrib)
582055
def make_article_info_dates(self):
        
        dates_div = etree.Element('div', {'id': 'article-dates'})

        d = './front/article-meta/history/date'
        received = self.article.root.xpath(d + "[@date-type='received']")
        accepted = self.article.root.xpath(d + "[@date-type='accepted']")
        if received:
            b = etree.SubElement(dates_div, 'b')
            b.text = 'Received: '
            dt = self.date_tuple_from_date(received[0], 'Received')
            formatted_date_string = self.format_date_string(dt)
            append_new_text(dates_div, formatted_date_string + '; ')
        if accepted:
            b = etree.SubElement(dates_div, 'b')
            b.text = 'Accepted: '
            dt = self.date_tuple_from_date(accepted[0], 'Accepted')
            formatted_date_string = self.format_date_string(dt)
            append_new_text(dates_div, formatted_date_string + '; ')
        #Published date is required
        pub_date = self.article.root.xpath("./front/article-meta/pub-date[@pub-type='epub']")[0]
        b = etree.SubElement(dates_div, 'b')
        b.text = 'Published: '
        dt = self.date_tuple_from_date(pub_date, 'Published')
        formatted_date_string = self.format_date_string(dt)
        append_new_text(dates_div, formatted_date_string)

        return dates_div
1095975
function () {
            var t = this,
                documentSelection = t.doc.getSelection(),
                node = documentSelection.focusNode,
                text = new XMLSerializer().serializeToString(documentSelection.getRangeAt(0).cloneContents()),
                url,
                title,
                target;

            while (['A', 'DIV'].indexOf(node.nodeName) < 0) {
                node = node.parentNode;
            }

            if (node && node.nodeName === 'A') {
                var $a = $(node);
                text = $a.text();
                url = $a.attr('href');
                if (!t.o.minimalLinks) {
                    title = $a.attr('title');
                    target = $a.attr('target');
                }
                var range = t.doc.createRange();
                range.selectNode(node);
                documentSelection.removeAllRanges();
                documentSelection.addRange(range);
            }

            t.saveRange();

            var options = {
                url: {
                    label: 'URL',
                    required: true,
                    value: url
                },
                text: {
                    label: t.lang.text,
                    value: text
                }
            };
            if (!t.o.minimalLinks) {
                Object.assign(options, {
                    title: {
                        label: t.lang.title,
                        value: title
                    },
                    target: {
                        label: t.lang.target,
                        value: target
                    }
                });
            }

            t.openModalInsert(t.lang.createLink, options, function (v) { // v is value
                var url = t.prependUrlPrefix(v.url);
                if (!url.length) {
                    return false;
                }

                var link = $(['<a href="', url, '">', v.text || v.url, '</a>'].join(''));

                if (!t.o.minimalLinks) {
                    if (v.title.length > 0) {
                        link.attr('title', v.title);
                    }
                    if (v.target.length > 0) {
                        link.attr('target', v.target);
                    }
                }
                t.range.deleteContents();
                t.range.insertNode(link[0]);
                t.syncCode();
                t.$c.trigger('tbwchange');
                return true;
            });
        }
472618
function (doc) {
    var self = this;
    var id = doc._id;
    if (self._published.has(id))
      throw Error("tried to add something already published " + id);
    if (self._limit && self._unpublishedBuffer.has(id))
      throw Error("tried to add something already existed in buffer " + id);

    var limit = self._limit;
    var comparator = self._comparator;
    var maxPublished = (limit && self._published.size() > 0) ?
      self._published.get(self._published.maxElementId()) : null;
    var maxBuffered = (limit && self._unpublishedBuffer.size() > 0) ?
      self._unpublishedBuffer.get(self._unpublishedBuffer.maxElementId()) : null;
    // The query is unlimited or didn't publish enough documents yet or the new
    // document would fit into published set pushing the maximum element out,
    // then we need to publish the doc.
    var toPublish = ! limit || self._published.size() < limit ||
                    comparator(doc, maxPublished) < 0;

    // Otherwise we might need to buffer it (only in case of limited query).
    // Buffering is allowed if the buffer is not filled up yet and all matching
    // docs are either in the published set or in the buffer.
    var canAppendToBuffer = !toPublish && self._safeAppendToBuffer &&
                            self._unpublishedBuffer.size() < limit;

    // Or if it is small enough to be safely inserted to the middle or the
    // beginning of the buffer.
    var canInsertIntoBuffer = !toPublish && maxBuffered &&
                              comparator(doc, maxBuffered) <= 0;

    var toBuffer = canAppendToBuffer || canInsertIntoBuffer;

    if (toPublish) {
      self._addPublished(id, doc);
    } else if (toBuffer) {
      self._addBuffered(id, doc);
    } else {
      // dropping it and not saving to the cache
      self._safeAppendToBuffer = false;
    }
  }
820968
def highlightBlock(self, text):
        

        # I need to know where in the document we are,
        # because our formatting info is global to
        # the document
        cb = self.currentBlock()
        p = cb.position()

        # The \n is not really needed, but sometimes
        # you are in an empty last block, so your position is
        # **after** the end of the document.
        text = str(self.document().toPlainText()) + '\n'

        # Yes, re-highlight the whole document.
        # There **must** be some optimizacion possibilities
        # but it seems fast enough.
        highlight(text, self.lexer, self.formatter)

        # Just apply the formatting to this block.
        # For titles, it may be necessary to backtrack
        # and format a couple of blocks **earlier**.
        for i in range(len(str(text))):
            try:
                self.setFormat(i, 1, self.formatter.data[p + i])
            except IndexError:
                pass

        # I may need to do something about this being called
        # too quickly.
        self.tstamp = time.time()
899243
def rewrite_subject_group(root, subjects, subject_group_type, overwrite=True):
    ""
    parent_tag_name = 'subj-group'
    tag_name = 'subject'
    wrap_tag_name = 'article-categories'
    tag_attribute = 'subj-group-type'
    # the parent tag where it should be found
    xpath_parent = './/front/article-meta/article-categories'
    # the wraping tag in case article-categories does not exist
    xpath_article_meta = './/front/article-meta'
    # the xpath to find the subject tags we are interested in
    xpath = './/{parent_tag_name}[@{tag_attribute}="{group_type}"]'.format(
        parent_tag_name=parent_tag_name,
        tag_attribute=tag_attribute,
        group_type=subject_group_type)

    count = 0
    # get the parent tag
    parent_tag = root.find(xpath_parent)
    if parent_tag is None:
        # parent tag not found, add one
        wrap_tag = root.find(xpath_article_meta)
        article_categories_tag = SubElement(wrap_tag, wrap_tag_name)
        parent_tag = article_categories_tag
    insert_index = 0
    # iterate all tags to find the index of the first tag we are interested in
    if parent_tag is not None:
        for tag_index, tag in enumerate(parent_tag.findall('*')):
            if tag.tag == parent_tag_name and tag.get(tag_attribute) == subject_group_type:
                insert_index = tag_index
                if overwrite is True:
                    # if overwriting use the first one found
                    break
            # if not overwriting, use the last one found + 1
            if overwrite is not True:
                insert_index += 1
    # remove the tag if overwriting the existing values
    if overwrite is True:
        # remove all the tags
        for tag in root.findall(xpath):
            parent_tag.remove(tag)
    # add the subjects
    for subject in subjects:
        subj_group_tag = Element(parent_tag_name)
        subj_group_tag.set(tag_attribute, subject_group_type)
        subject_tag = SubElement(subj_group_tag, tag_name)
        subject_tag.text = subject
        parent_tag.insert(insert_index, subj_group_tag)
        count += 1
        insert_index += 1
    return count
1094668
function shortenIDs(startNumber) {
  if(_.isUndefined(startNumber)) {
    startNumber = 1;
  }
  var $identifiedElements = $('[id]');
  var referencedIDs = findReferencedElements();

  // scour:
  // > Make idList (list of idnames) sorted by reference count
  // > descending, so the highest reference count is first.
  // > First check that there's actually a defining element for the current ID name.
  // > (Cyn: I've seen documents with #id references but no element with that ID!)

  var idList = _(_(referencedIDs).keys()).filter(function(id) {
    return ($identifiedElements.find('#' + id).length > 0);
  });
  idList = _(idList).sortBy(function(id) {
    return referencedIDs[id].length;
  }).reverse();

  _(idList).each(function(id) {
    var shortendID = intToID(startNumber++);

    // scour:
    // > First make sure that *this* element isn't already using
    // > the ID name we want to give it.
    if(id == shortendID) {
      return;
    }
    // scour:
    // > Then, skip ahead if the new ID is already in identifiedElement
    while($identifiedElements.find('#' + shortendID).length > 0) {
      shortendID = intToID(startNumber++);
    }
    // scour:
    // > Then go rename it.
    renameID(id, shortendID, $identifiedElements, referencedIDs);
    
  });

}
365597
def p_article(self, article):
        ''''''
        article[0] = Article(article[1][4], article[2], article[3], article[1][0],
                             article[1][1], article[1][2], article[1][3], article[1][5])
291507
function (element) {
      var docDomEl = $document[0];
      var offsetParent = element.offsetParent || docDomEl;
      while (offsetParent && offsetParent !== docDomEl && isStaticPositioned(offsetParent) ) {
        offsetParent = offsetParent.offsetParent;
      }
      return offsetParent || docDomEl;
    }
316605
function selectionIsInverted(selection) {
  if (selection.anchorNode == selection.focusNode) return selection.anchorOffset > selection.focusOffset
  return selection.anchorNode.compareDocumentPosition(selection.focusNode) == Node.DOCUMENT_POSITION_FOLLOWING
}
634649
function () {
      var element = this.$el.get(0);
      
      // check if we are in an iframe
      // we need to alter positioning logic if using an iframe
      if (this.$el.prop('ownerDocument') !== document && window.frames.length) {
        for (var iframeIndex = 0; iframeIndex < window.frames.length; iframeIndex++) {
          if (this.$el.prop('ownerDocument') === window.frames[iframeIndex].document) {
            this.$iframe = $(window.frames[iframeIndex].frameElement);
            break;
          }
        }
      }
      
      
      // Initialize view objects.
      this.dropdown = new $.fn.textcomplete.Dropdown(element, this, this.option);
      var Adapter, viewName;
      if (this.option.adapter) {
        Adapter = this.option.adapter;
      } else {
        if (this.$el.is('textarea') || this.$el.is('input[type=text]') || this.$el.is('input[type=search]')) {
          viewName = typeof element.selectionEnd === 'number' ? 'Textarea' : 'IETextarea';
        } else {
          viewName = 'ContentEditable';
        }
        Adapter = $.fn.textcomplete[viewName];
      }
      this.adapter = new Adapter(element, this, this.option);
    }
59474
function() {
      var frag = doc.createDocumentFragment();
      var root = doc.firstChild;
      while(root.hasChildNodes()) {
        frag.appendChild(root.firstChild);
      }
      return frag;
    }
760294
def create_back_links(env):
    
    if env.needs_workflow['backlink_creation']:
        return

    needs = env.needs_all_needs
    for key, need in needs.items():
        for link in need["links"]:
            link_main = link.split('.')[0]
            try:
                link_part = link.split('.')[1]
            except IndexError:
                link_part = None

            if link_main in needs:
                if key not in needs[link_main]["links_back"]:
                    needs[link_main]["links_back"].append(key)

                # Handling of links to need_parts inside a need
                if link_part is not None:
                    if link_part in needs[link_main]['parts']:
                        if 'links_back' not in needs[link_main]['parts'][link_part].keys():
                            needs[link_main]['parts'][link_part]['links_back'] = []
                        needs[link_main]['parts'][link_part]['links_back'].append(key)

    env.needs_workflow['backlink_creation'] = True
1277697
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);
		}
	}
1059440
def build_related_articles(related_articles):
    
    article_list = []

    for related_article in related_articles:
        article = ea.RelatedArticle()
        if related_article.get('xlink_href'):
            article.xlink_href = related_article.get('xlink_href')
        if related_article.get('related_article_type'):
            article.related_article_type = related_article.get('related_article_type')
        if related_article.get('ext_link_type'):
            article.ext_link_type = related_article.get('ext_link_type')

        # Append it to our list
        article_list.append(article)

    return article_list
539551
private int internalRepositionPlaceholder(int x, int y) {

        int indexCorrection = 0;
        int previousTop = 0;
        int documentScrollTop = getElement().getOwnerDocument().getScrollTop();
        int documentScrollLeft = getElement().getOwnerDocument().getScrollLeft();
        for (int index = 0; index < m_elementPositions.size(); index++) {
            ElementPositionInfo info = m_elementPositions.get(index);
            if (info.getElement() == m_placeholder) {
                indexCorrection = 1;
            }
            if (info.isAbsolute() || !info.isVisible()) {
                continue;
            }

            int top = info.getRelativeTop(y, documentScrollTop);

            if ((top <= 0) || (top >= info.getElementPosition().getHeight())) {
                previousTop = top;
                continue;
            }
            int left = info.getRelativeLeft(x, documentScrollLeft);
            if ((left <= 0) || (left >= info.getElementPosition().getWidth())) {
                previousTop = top;
                continue;
            }
            boolean floatSort = info.isFloating() && (top != 0) && (top == previousTop);
            previousTop = top;
            if (info.getElement() != m_placeholder) {
                if (floatSort) {
                    boolean insertBefore = false;
                    if (left < (info.getElementPosition().getWidth() / 2)) {
                        if (info.isFloatLeft()) {
                            insertBefore = true;
                        }
                    } else if (info.isFloatRight()) {
                        insertBefore = true;
                    }
                    if (insertBefore) {
                        getElement().insertBefore(m_placeholder, info.getElement());
                        return index - indexCorrection;
                    } else {
                        getElement().insertAfter(m_placeholder, info.getElement());
                        return (index + 1) - indexCorrection;
                    }
                } else {
                    if (top < (info.getElementPosition().getHeight() / 2)) {
                        getElement().insertBefore(m_placeholder, info.getElement());
                        return index - indexCorrection;
                    } else {
                        getElement().insertAfter(m_placeholder, info.getElement());
                        return (index + 1) - indexCorrection;
                    }
                }
            } else {
                return index;
            }
        }

        // not over any child position
        if ((m_placeholderIndex >= 0) && (m_placeholder.getParentElement() == getElement())) {
            // element is already attached to this parent and no new position available
            // don't do anything
            return m_placeholderIndex;
        }
        int top = CmsDomUtil.getRelativeY(y, getElement());
        int offsetHeight = getElement().getOffsetHeight();
        if ((top >= (offsetHeight / 2))) {
            // over top half, insert as first child
            getElement().insertFirst(m_placeholder);
            return 0;
        }
        // over bottom half, insert as last child
        getElement().appendChild(m_placeholder);
        return getElement().getChildCount() - 1;
    }
127369
def tag_supplementary_material_sibling_ordinal(tag):
    
    if hasattr(tag, 'name') and tag.name != 'supplementary-material':
        return None

    nodenames = ['fig','media','sub-article']
    first_parent_tag = first_parent(tag, nodenames)

    sibling_ordinal = 1

    if first_parent_tag:
        # Within the parent tag of interest, count the tags
        #  having the same asset value
        for supp_tag in first_parent_tag.find_all(tag.name):
            if tag == supp_tag:
                # Stop once we reach the same tag we are checking
                break
            if supp_asset(supp_tag) == supp_asset(tag):
                sibling_ordinal += 1

    else:
        # Look in all previous elements that do not have a parent
        #  and count the tags having the same asset value
        for prev_tag in tag.find_all_previous(tag.name):
            if not first_parent(prev_tag, nodenames):
                if supp_asset(prev_tag) == supp_asset(tag):
                    sibling_ordinal += 1

    return sibling_ordinal