Greasy Fork is available in English.

知乎重排for印象笔记

增加一个“重排”链接于导航栏,点击后重排页面,只保留问题和答案,然后可用“印象笔记·剪藏”收藏。

La data de 10-09-2018. Vezi ultima versiune.

// ==UserScript==
// @name         知乎重排for印象笔记
// @namespace    http://tampermonkey.net/
// @version      0.2
// @description  增加一个“重排”链接于导航栏,点击后重排页面,只保留问题和答案,然后可用“印象笔记·剪藏”收藏。
// @author       twchen
// @include      https://www.zhihu.com/question/*/answer/*
// @include      https://zhuanlan.zhihu.com/p/*
// @grant        GM_xmlhttpRequest
// ==/UserScript==

(function() {
  "use strict";

  const body = document.querySelector("body");

  function removeAllChildren(el) {
    while (el.firstChild) {
      el.removeChild(el.firstChild);
    }
  }

  function formatAnswer() {
    const showMoreBtn = document.querySelector(
      "button.Button.QuestionRichText-more"
    );
    if (showMoreBtn !== null) showMoreBtn.click();
    const title = document.querySelector("h1.QuestionHeader-title");
    const detail = document.querySelector("div.QuestionHeader-detail");
    const answer = document.querySelector("div.Card.AnswerCard");

    const div = document.createElement("div");
    div.appendChild(title);
    div.appendChild(detail);

    Object.assign(div.style, {
      backgroundColor: "white",
      margin: "0.8rem 0",
      padding: "0.2rem 1rem 1rem"
    });

    removeAllChildren(body);

    body.appendChild(div);
    body.appendChild(answer);
    replaceVideosByLinks();
  }

  function addLinkToNav() {
    const nav = document.querySelector("nav.AppHeader-nav");
    const a = document.createElement("a");
    a.href = "#";
    a.text = "重排";
    a.classList.add("AppHeader-navItem");
    a.onclick = function(event) {
      event.preventDefault();
      formatAnswer();
    };
    nav.appendChild(a);
  }

  function getVideoInfo(id, callback) {
    GM_xmlhttpRequest({
      method: "GET",
      url: `https://lens.zhihu.com/api/videos/${id}`,
      headers: {
        "Content-Type": "application/json",
        Origin: "https://v.vzuu.com",
        Referer: `https://v.vzuu.com/video/${id}`
      },
      onload: response => {
        const json = JSON.parse(response.responseText);
        const title = json.title;
        const thumbnail = json.cover_info.thumbnail;
        callback(title, thumbnail);
      }
    });
  }

  function replaceVideosByLinks() {
    const videoDIVs = document.querySelectorAll("div.RichText-video");
    videoDIVs.forEach(div => {
      try {
        const attr = div.attributes["data-za-extra-module"];
        const videoId = JSON.parse(attr.value).card.content.video_id;
        const href = "https://www.zhihu.com/video/" + videoId;
        getVideoInfo(videoId, (title, thumbnail) => {
          const a = document.createElement("a");
          a.href = href;
          if (title) {
            const span = document.createElement("span");
            span.style.display = "block";
            span.innerHTML = "视频: " + title;
            a.appendChild(span);
          }
          if (thumbnail) {
            // TODO: add a play icon over the center of thumbnail
            const img = document.createElement("img");
            img.src = thumbnail;
            a.appendChild(img);
          }
          if (!title && !thumbnail) {
            a.text = "视频: " + href;
          }
          div.replaceWith(a);
        });
      } catch (error) {
        console.error(`Error replacing video: ${error.message}`);
      }
    });
  }

  function addBtnToNav() {
    const pageHeader = document.querySelector("div.ColumnPageHeader-Button");
    const btn = document.createElement("button");
    btn.setAttribute("type", "button");
    btn.innerText = "重新排版";
    btn.classList.add("Button", "Button--blue");
    btn.style.marginRight = "1rem";
    btn.onclick = () => {
      formatZhuanlan();
    };
    pageHeader.prepend(btn);
  }

  function formatZhuanlan() {
    const header = document.querySelector("header.Post-Header");
    const title = header.querySelector(".Post-Title");
    Object.assign(title.style, {
      fontSize: "2rem",
      fontWeight: "bold",
      marginBottom: "1rem"
    });

    const post = document.querySelector("div.Post-RichText");
    const time = document.querySelector("div.ContentItem-time");
    const topics = document.querySelector("div.Post-topicsAndReviewer");

    const div = document.createElement("div");
    div.append(header, post, time, topics);
    div.style.margin = "1rem";

    removeAllChildren(body);
    body.appendChild(div);
    replaceVideosByLinks();
  }

  function injectToNav() {
    const url = window.location.href;
    if (url.includes("zhuanlan")) {
      addBtnToNav();
    } else {
      addLinkToNav();
    }
  }

  injectToNav();
})();