MediaWiki

Difference between revisions of "Gadget-Bibliography.js"

From ACES

 
(7 intermediate revisions by the same user not shown)
Line 1: Line 1:
(function ($, mw) {
(function ($, mw) {
  "use strict";
    "use strict";
  var allowedPages = ["Publications", "Home"];
    var allowedPages = ["Publications", "Home"];
  var nYearButtons = 5;
    var nYearButtons = 5;
  if (!allowedPages.includes(mw.config.get("wgPageName"))) return;
    if (!allowedPages.includes(mw.config.get("wgPageName"))) return;
  if (window.BibLoaded) return;
    if (window.BibLoaded) return;
  window.BibLoaded = true;
    window.BibLoaded = true;


  console.log("[Bibliography] 0.0.1");
    console.log("[Bibliography] 0.0.1");
  var scriptLoaded = 0;
    var scriptLoaded = 0;
  var mwConfig = mw.config.get(["wgUserName", "wgServer", "wgArticlePath"]);
    var mwConfig = mw.config.get(["wgUserName", "wgServer", "wgArticlePath"]);


  var isAnon = mwConfig.wgUserName === null;
    var isAnon = mwConfig.wgUserName === null;
  var articlePath = mwConfig.wgServer + mwConfig.wgArticlePath;
    var articlePath = mwConfig.wgServer + mwConfig.wgArticlePath;


  function download(filename, text) {
    function download(filename, text) {
    var el = document.createElement("a");
        var el = document.createElement("a");
    el.setAttribute(
        el.setAttribute(
      "href",
            "href",
      "data:text/plain;charset=utf-8," + encodeURIComponent(text)
            "data:text/plain;charset=utf-8," + encodeURIComponent(text)
    );
        );
    el.setAttribute("download", filename);
        el.setAttribute("download", filename);
 
        el.style.display = "none";
        document.body.appendChild(el);
 
        el.click();
 
        document.body.removeChild(el);
    }


     el.style.display = "none";
     function getPDF(rawBib) {
    document.body.appendChild(el);
        var pdfMap = {}
        Array.from(rawBib.matchAll(/^@.+?\{(.+?),\s*(?:\n(?!@).*?)*?\npdf\s*=\s*\{(.*)\}/mg))
            .forEach(function (m) {
                pdfMap[m[1]] = m[2]
            })
        return pdfMap
    }


     el.click();
     function genDataTable(e) {
        var Cite = window.require("citation-js");
        var yearGroup = {};
        var dataTable = undefined;
        var rawBib = $(e).find(".bibliography-data")[0].textContent;
        var pdfMap = getPDF(rawBib)
        var bib = Cite(rawBib);
        var data = [];
        var pageTitleIter = rawBib.matchAll(/^_pageName = \{(.+)\}\s*,?\s*$/gm);
        bib.data.forEach(function (entry) {
            var linkTarget = new URL(
                articlePath.replace("$1", pageTitleIter.next().value[1])
            );
            var linkEle = $("<a>").text(entry.id);
            linkEle.attr("href", linkTarget.toString());


    document.body.removeChild(el);
            var editLink = $("<a>").html(
  }
                '<span class="material-icons-outlined">edit</span>'
            );
            linkTarget.searchParams.append("action", "formedit");
            editLink.attr("href", linkTarget.toString());
            editLink.attr("target", "_blank");


  function genDataTable(e) {
            var urlData = entry.URL
    var Cite = window.require("citation-js");
            entry.URL = undefined
    var yearGroup = {};
            entry.render = Cite(entry).format("bibliography", {
    var dataTable = undefined;
                format: "html",
    var rawBib = $(e).find(".bibliography-data")[0].textContent;
                template: "apa",
    var bib = Cite(rawBib);
                lang: "en-US",
    var data = [];
            });
    var pageTitleIter = rawBib.matchAll(/^_pageName = \{(.+)\}\s*,?\s*$/gm);
            entry.URL = urlData


    bib.data.forEach(function (entry) {
            entry.pdf = pdfMap[entry.id]
      var linkTarget = new URL(
            if (entry.pdf) {
        articlePath.replace("$1", pageTitleIter.next().value[1])
                entry.render += " " + $("<a />")
      );
                    .text("[PDF]")
      var linkEle = $("<a>").text(entry.id);
                    .attr(
      linkEle.attr("href", linkTarget.toString());
                        "href",
                        new URL(articlePath.replace("$1", "Special:filepath/" + pdfMap[entry.id])).toString()
                    )
                    .prop('outerHTML');
            }
            if (urlData && urlData.startsWith("http")) {
                entry.render += " " + $("<a />")
                    .text("[URL]")
                    .attr(
                        "href",
                        urlData
                    )
                    .prop('outerHTML');
            }


      var editLink = $("<a>").html(
            entry.pageTitle = editLink[0].outerHTML + linkEle[0].outerHTML;
        '<span class="material-icons-outlined">edit</span>'
            entry.year = entry.issued && entry.issued["date-parts"] && entry.issued["date-parts"][0] && entry.issued["date-parts"][0][0] || 1970;
      );
            yearGroup[parseInt(entry.year)] = false;
      linkTarget.searchParams.append("action", "formedit");
      editLink.attr("href", linkTarget.toString());
      editLink.attr("target", "_blank");


      entry.render = Cite(entry).format("bibliography", {
            data.push(entry);
        format: "html",
         });
        template: "apa",
         lang: "en-US",
      });
      entry.pageTitle = editLink[0].outerHTML + linkEle[0].outerHTML;
      entry.year = entry.issued["date-parts"][0][0] || 1970;
      yearGroup[parseInt(entry.year)] = false;


      data.push(entry);
        var tb = $("<table></table>")[0];
    });
        e.replaceWith(tb);
        tb = $(tb);
        tb.append($("<thead>"));
        tb.append($("<tbody>"));
        tb.addClass("display");


    var tb = $("<table></table>")[0];
        // Generate buttons
    e.replaceWith(tb);
        var orderedYears = Object.keys(yearGroup).sort(function (x, y) {
    tb = $(tb);
            if (x < y) return 1;
    tb.append($("<thead>"));
            if (x > y) return -1;
    tb.append($("<tbody>"));
            return 0;
    tb.addClass("display");
        });


    // Generate buttons
        function draw(dt) {
    var orderedYears = Object.keys(yearGroup).sort(function (x, y) {
            dt.column("year:name").search(
      if (x < y) return 1;
                orderedYears
      if (x > y) return -1;
                    .filter(function (e) {
      return 0;
                        return yearGroup[e];
    });
                    })
    function draw(dt) {
                    .join("|"),
      dt.column("year:name").search(
                true,
        orderedYears
                false
          .filter(function (e) {
            );
            return yearGroup[e];
            dt.draw();
          })
        }
          .join("|"),
        var buttons = orderedYears.slice(0, nYearButtons).map(function (year) {
        true,
            return {
        false
                text: year,
      );
                action: function (e, dt, node, config) {
      dt.draw();
                    yearGroup[year] = !yearGroup[year];
    }
                    node.toggleClass("active", yearGroup[year]);
    var buttons = orderedYears.slice(0, nYearButtons).map(function (year) {
                    draw(dt);
      return {
                },
        text: year,
            };
        action: function (e, dt, node, config) {
        });
          yearGroup[year] = !yearGroup[year];
        if (orderedYears.length > nYearButtons) {
          node.toggleClass("active", yearGroup[year]);
            var statusRest = false;
          draw(dt);
            var restYears = orderedYears.slice(nYearButtons);
        },
      };
    });
    if (orderedYears.length > nYearButtons) {
      var statusRest = false;
      var restYears = orderedYears.slice(nYearButtons);


      buttons.push({
            buttons.push({
        text: "Rest",
                text: "Rest",
        action: function (e, dt, node, config) {
                action: function (e, dt, node, config) {
          statusRest = !statusRest;
                    statusRest = !statusRest;
          restYears.forEach(function (el) {
                    restYears.forEach(function (el) {
            yearGroup[el] = !yearGroup[el];
                        yearGroup[el] = !yearGroup[el];
          });
                    });
          node.toggleClass("active", statusRest);
                    node.toggleClass("active", statusRest);
          draw(dt);
                    draw(dt);
        },
                },
      });
            });
    }
        }
    // export BibTeX button
        // export BibTeX button
    buttons.push({
        buttons.push({
      text: "Export BibTeX",
            text: "Export BibTeX",
      action: function (e, dt, node, config) {
            action: function (e, dt, node, config) {
        var text = Cite(dt.rows({ page: "current" }).data().toArray()).format(
                var text = Cite(dt.rows({ page: "current" }).data().toArray()).format(
          "bibtex"
                    "bibtex"
        );
                );
        download("bibtex.bib", text);
                download("bibtex.bib", text);
      },
            },
      titleAttr: "export",
            titleAttr: "export",
    });
        });


    var options = {
        var options = {
      data: data,
            data: data,
      columns: [
            columns: [{
        {
                className: "cell-apa",
          data: "render",
                data: "render",
          title: "APA",
                title: "APA",
          render: function (data, type, row) {
                render: function (data, type, row) {
            // If display or filter data is requested, format the date
                    // If display or filter data is requested, format the date
            if (type === "sort") return row.year;
                    if (type === "sort") return row.year;
            return data;
                    return data;
          },
                },
        },
            },
        {
            {
          name: "year",
                name: "year",
          data: "year",
                data: "year",
          visible: false,
                visible: false,
        },
            },
      ],
            ],
      paging: false,
            paging: false,
      order: [[0, "desc"]],
            order: [
      rowGroup: {
                [0, "desc"]
        dataSrc: "year",
            ],
      },
            rowGroup: {
      dom: "fBrtip",
                dataSrc: "year",
      buttons: buttons,
            },
    };
            dom: "fBrtip",
    if (!isAnon) {
            buttons: buttons,
      options.columns.unshift({
        };
        data: "pageTitle",
        if (!isAnon) {
        title: "In-site Page",
            options.columns.unshift({
      });
                className: "cell-pageTitle",
      options.order[0][0] += 1;
                data: "pageTitle",
      options.order.push([0, "asc"]);
                title: "In-site Page",
            });
            options.order[0][0] += 1;
            options.order.push([0, "asc"]);
        }
        dataTable = tb.dataTable(options);
        dataTable = dataTable.DataTable();
     }
     }
    dataTable = tb.dataTable(options);
    dataTable = dataTable.DataTable();
  }


  function genList(e) {
    function genList(e) {
    var Cite = window.require("citation-js");
        var Cite = window.require("citation-js");
    var rawBib = $(e).find(".bibliography-data")[0].textContent;
        var rawBib = $(e).find(".bibliography-data")[0].textContent;
    var bib = Cite(rawBib);
        var pdfMap = getPDF(rawBib)
        var bib = Cite(rawBib);
        var ul = $("<ul  />", { class: "csl-bib-body" });
        bib.data.forEach(function (entry) {
            var li = $("<li/>", { class: "bib-entry" });
            if (pdfMap[entry.id]) {
                var link = $("<a />").text("[PDF]");
                link.attr(
                    "href",
                    new URL(articlePath.replace("$1", "Special:filepath/" + pdfMap[entry.id])).toString()
                );
                li.append(link);
                li.append(" ");
            }
            if (entry.URL) {
                var link = $("<a />").text("[URL]");
                link.attr(
                    "href",
                    entry.URL
                );
                li.append(link);
                li.append(" ");
            }


    var ul = $("<ul  />", { class: "csl-bib-body" });
            var urlData = entry.URL
    bib.data.forEach(function (entry) {
            entry.URL = undefined
      var li = $("<li/>", { class: "bib-entry" });
            li.append(
      var link = $("<a />").text("[PDF]");
                $(
      li.append(link);
                    $(
      li.append(" ");
                        Cite(entry).format("bibliography", {
      li.append(
                            format: "html",
        $(
                            template: "apa",
          $(
                            lang: "en-US",
            Cite(entry).format("bibliography", {
                        })
              format: "html",
                    ).html()
              template: "apa",
                ).css("display", "inline")
              lang: "en-US",
            );
            })
            entry.URL = urlData
          ).html()
            ul.append(li);
        ).css("display", "inline")
        });
      );
        if (e.getAttribute("data-more")) {
      ul.append(li);
            var linkMore = $("<a />").text("More...");
    });
            linkMore.attr(
                "href",
                new URL(articlePath.replace("$1", "Publications")).toString()
            );
            ul.append(linkMore);
        }
        e.replaceWith(ul[0]);
        return ul;
    }


     e.replaceWith(ul[0]);
     function run() {
    return ul;
        $(".bibliography:not(.test)").each(function (i, e) {
  }
            var style = e.getAttribute("data-style");
 
            if (style === "list") {
  function run() {
                return genList(e);
    $(".bibliography:not(.test)").each(function (i, e) {
            }
      var style = e.getAttribute("data-style");
            return genDataTable(e);
      if (style === "list") {
        });
        return genList(e);
    }
      }
      return genDataTable(e);
    });
  }


  function loadScripts(scripts, callback) {
    function loadScripts(scripts, callback) {
    function onLoaded() {
        function onLoaded() {
      scriptLoaded++;
            scriptLoaded++;
      if (scriptLoaded === scripts.length)
            if (scriptLoaded === scripts.length)
        mw.hook("wikipage.content").add(callback);
                mw.hook("wikipage.content").add(callback);
        }
        scripts.forEach(function (s) {
            mw.loader.getScript(s).then(onLoaded);
        });
     }
     }
    scripts.forEach(function (s) {
      mw.loader.getScript(s).then(onLoaded);
    });
  }


  loadScripts(
    loadScripts(
    [
        [
      "https://cdn.jsdelivr.net/npm/citation-js@0.5.1",
            "https://cdn.jsdelivr.net/npm/citation-js@0.5.1",
      "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.js",
            "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.js",
    ],
        ],
    run
        run
  );
    );
  mw.loader.load(
    mw.loader.load(
    "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.css",
        "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.css",
    "text/css"
        "text/css"
  );
    );
})(jQuery, mediaWiki);
})(jQuery, mediaWiki);

Latest revision as of 19:21, 9 November 2021

(function ($, mw) {
    "use strict";
    var allowedPages = ["Publications", "Home"];
    var nYearButtons = 5;
    if (!allowedPages.includes(mw.config.get("wgPageName"))) return;
    if (window.BibLoaded) return;
    window.BibLoaded = true;

    console.log("[Bibliography] 0.0.1");
    var scriptLoaded = 0;
    var mwConfig = mw.config.get(["wgUserName", "wgServer", "wgArticlePath"]);

    var isAnon = mwConfig.wgUserName === null;
    var articlePath = mwConfig.wgServer + mwConfig.wgArticlePath;

    function download(filename, text) {
        var el = document.createElement("a");
        el.setAttribute(
            "href",
            "data:text/plain;charset=utf-8," + encodeURIComponent(text)
        );
        el.setAttribute("download", filename);

        el.style.display = "none";
        document.body.appendChild(el);

        el.click();

        document.body.removeChild(el);
    }

    function getPDF(rawBib) {
        var pdfMap = {}
        Array.from(rawBib.matchAll(/^@.+?\{(.+?),\s*(?:\n(?!@).*?)*?\npdf\s*=\s*\{(.*)\}/mg))
            .forEach(function (m) {
                pdfMap[m[1]] = m[2]
            })
        return pdfMap
    }

    function genDataTable(e) {
        var Cite = window.require("citation-js");
        var yearGroup = {};
        var dataTable = undefined;
        var rawBib = $(e).find(".bibliography-data")[0].textContent;
        var pdfMap = getPDF(rawBib)
        var bib = Cite(rawBib);
        var data = [];
        var pageTitleIter = rawBib.matchAll(/^_pageName = \{(.+)\}\s*,?\s*$/gm);
        bib.data.forEach(function (entry) {
            var linkTarget = new URL(
                articlePath.replace("$1", pageTitleIter.next().value[1])
            );
            var linkEle = $("<a>").text(entry.id);
            linkEle.attr("href", linkTarget.toString());

            var editLink = $("<a>").html(
                '<span class="material-icons-outlined">edit</span>'
            );
            linkTarget.searchParams.append("action", "formedit");
            editLink.attr("href", linkTarget.toString());
            editLink.attr("target", "_blank");

            var urlData = entry.URL
            entry.URL = undefined
            entry.render = Cite(entry).format("bibliography", {
                format: "html",
                template: "apa",
                lang: "en-US",
            });
            entry.URL = urlData

            entry.pdf = pdfMap[entry.id]
            if (entry.pdf) {
                entry.render += " " + $("<a />")
                    .text("[PDF]")
                    .attr(
                        "href",
                        new URL(articlePath.replace("$1", "Special:filepath/" + pdfMap[entry.id])).toString()
                    )
                    .prop('outerHTML');
            }
            if (urlData && urlData.startsWith("http")) {
                entry.render += " " + $("<a />")
                    .text("[URL]")
                    .attr(
                        "href",
                        urlData
                    )
                    .prop('outerHTML');
            }

            entry.pageTitle = editLink[0].outerHTML + linkEle[0].outerHTML;
            entry.year = entry.issued && entry.issued["date-parts"] && entry.issued["date-parts"][0] && entry.issued["date-parts"][0][0] || 1970;
            yearGroup[parseInt(entry.year)] = false;

            data.push(entry);
        });

        var tb = $("<table></table>")[0];
        e.replaceWith(tb);
        tb = $(tb);
        tb.append($("<thead>"));
        tb.append($("<tbody>"));
        tb.addClass("display");

        // Generate buttons
        var orderedYears = Object.keys(yearGroup).sort(function (x, y) {
            if (x < y) return 1;
            if (x > y) return -1;
            return 0;
        });

        function draw(dt) {
            dt.column("year:name").search(
                orderedYears
                    .filter(function (e) {
                        return yearGroup[e];
                    })
                    .join("|"),
                true,
                false
            );
            dt.draw();
        }
        var buttons = orderedYears.slice(0, nYearButtons).map(function (year) {
            return {
                text: year,
                action: function (e, dt, node, config) {
                    yearGroup[year] = !yearGroup[year];
                    node.toggleClass("active", yearGroup[year]);
                    draw(dt);
                },
            };
        });
        if (orderedYears.length > nYearButtons) {
            var statusRest = false;
            var restYears = orderedYears.slice(nYearButtons);

            buttons.push({
                text: "Rest",
                action: function (e, dt, node, config) {
                    statusRest = !statusRest;
                    restYears.forEach(function (el) {
                        yearGroup[el] = !yearGroup[el];
                    });
                    node.toggleClass("active", statusRest);
                    draw(dt);
                },
            });
        }
        // export BibTeX button
        buttons.push({
            text: "Export BibTeX",
            action: function (e, dt, node, config) {
                var text = Cite(dt.rows({ page: "current" }).data().toArray()).format(
                    "bibtex"
                );
                download("bibtex.bib", text);
            },
            titleAttr: "export",
        });

        var options = {
            data: data,
            columns: [{
                className: "cell-apa",
                data: "render",
                title: "APA",
                render: function (data, type, row) {
                    // If display or filter data is requested, format the date
                    if (type === "sort") return row.year;
                    return data;
                },
            },
            {
                name: "year",
                data: "year",
                visible: false,
            },
            ],
            paging: false,
            order: [
                [0, "desc"]
            ],
            rowGroup: {
                dataSrc: "year",
            },
            dom: "fBrtip",
            buttons: buttons,
        };
        if (!isAnon) {
            options.columns.unshift({
                className: "cell-pageTitle",
                data: "pageTitle",
                title: "In-site Page",
            });
            options.order[0][0] += 1;
            options.order.push([0, "asc"]);
        }
        dataTable = tb.dataTable(options);
        dataTable = dataTable.DataTable();
    }

    function genList(e) {
        var Cite = window.require("citation-js");
        var rawBib = $(e).find(".bibliography-data")[0].textContent;
        var pdfMap = getPDF(rawBib)
        var bib = Cite(rawBib);
        var ul = $("<ul  />", { class: "csl-bib-body" });
        bib.data.forEach(function (entry) {
            var li = $("<li/>", { class: "bib-entry" });
            if (pdfMap[entry.id]) {
                var link = $("<a />").text("[PDF]");
                link.attr(
                    "href",
                    new URL(articlePath.replace("$1", "Special:filepath/" + pdfMap[entry.id])).toString()
                );
                li.append(link);
                li.append(" ");
            }
            if (entry.URL) {
                var link = $("<a />").text("[URL]");
                link.attr(
                    "href",
                    entry.URL
                );
                li.append(link);
                li.append(" ");
            }

            var urlData = entry.URL
            entry.URL = undefined
            li.append(
                $(
                    $(
                        Cite(entry).format("bibliography", {
                            format: "html",
                            template: "apa",
                            lang: "en-US",
                        })
                    ).html()
                ).css("display", "inline")
            );
            entry.URL = urlData
            ul.append(li);
        });
        if (e.getAttribute("data-more")) {
            var linkMore = $("<a />").text("More...");
            linkMore.attr(
                "href",
                new URL(articlePath.replace("$1", "Publications")).toString()
            );
            ul.append(linkMore);
        }
        e.replaceWith(ul[0]);
        return ul;
    }

    function run() {
        $(".bibliography:not(.test)").each(function (i, e) {
            var style = e.getAttribute("data-style");
            if (style === "list") {
                return genList(e);
            }
            return genDataTable(e);
        });
    }

    function loadScripts(scripts, callback) {
        function onLoaded() {
            scriptLoaded++;
            if (scriptLoaded === scripts.length)
                mw.hook("wikipage.content").add(callback);
        }
        scripts.forEach(function (s) {
            mw.loader.getScript(s).then(onLoaded);
        });
    }

    loadScripts(
        [
            "https://cdn.jsdelivr.net/npm/citation-js@0.5.1",
            "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.js",
        ],
        run
    );
    mw.loader.load(
        "https://cdn.datatables.net/v/dt/dt-1.11.1/b-2.0.0/rg-1.1.3/datatables.min.css",
        "text/css"
    );
})(jQuery, mediaWiki);