您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
Browse trough the articles with left and right cursor keys
当前为
// ==UserScript== // @name Better Movie-blog // @namespace hoehleg.userscripts.private // @version 0.5.0 // @description Browse trough the articles with left and right cursor keys // @author Gerrit Höhle // @match http://www.movie-blog.org/ // @match http://www.movie-blog.org/page/* // @match http://www.movie-blog.org/category/* // @match http://movie-blog.to/ // @match http://movie-blog.to/page/* // @match http://movie-blog.to/category/* // @require https://greasyforks.org/scripts/390752-comparator/code/Comparator.js?version=738265 // @grant GM_xmlhttpRequest // @grant GM_addStyle // ==/UserScript== GM_addStyle(` #page { background-size: 98%; width: auto; height: auto; } #archiv, #content { margin: 0px 0px 0px 0px; padding: 0px 0px 0px 6%; width: 63%; height: 5000px } #sidebar { position: absolute; top: 440px; right: 0px; } #cur-beitrag-img { position: fixed; margin: auto; top: 2px; left: 930px; max-width: 400px; z-index: 1; } #beitrag-info { position: fixed; top: 2px; left: 80px; } #show-container { position: relative; top: 30px; } .beitrag4, .beitrag2 { width: 840px } `); (function() { 'use strict'; const CONFIG = { // number of pages to load Beitraege to one page PAGES_LOAD_COUNT: 2, } const CONST = (() => { const URL_PATH = (() => { const path = document.location.pathname.split("/").filter(str => str.length > 0); return path === null ? [] : path; })(); const TABLE_HEADER_NAMES = { NUM: "#", RATING: "IMDb", SIZE: "Größe", LINK: "Link", DATE: "Datum", TYPE: "Typ", JAHR: "Jahr", DURATION: "Dauer" } const HTML_CLASSES = { DATE: "date", BEITRAG: "beitrag4", TABLE_TD_NUM: "col-num", TABLE_TD_RATING: "col-rating", TABLE_TD_SIZE: "col-size", TABLE_TD_LINK: "col-link", TABLE_TD_DATE: "col-date", TABLE_TD_TYPE: "col-type", TABLE_TD_JAHR: "col-jahr", TABLE_TD_DURATION: "col-duration" }; const HTML_IDS = { SHOW_CONTAINER: "show-container", BEITRAG_INFO: "beitrag-info", PAGE_NUMBER: "page-number", BEITRAG_NUMBER: "beitrag-number", BEITRAG_COUNT: "beitrag-count", FILM_DATA_IMDB_RATING: "film-data-imdb-rating", FILM_DATA_GROESSE: "film-data-groesse", FILM_DATA_DAUER: "film-data-dauer", PAGE_PREV: "page-prev", PAGE_NEXT: "page-next", BEITRAG_PREV: "beitrag-prev", BEITRAG_NEXT: "beitrag-next", LISTE_BEITRAEGE: "liste-beitraege", HEAD: "head", CONTENT: "content", TABLE_TR_NUM: "tr-num", SIDEBAR: "sidebar", CUR_BEITRAG_IMG: "cur-beitrag-img" }; const MONTH_NAMES = ["JANUAR", "FEBRUAR", "MÄRZ", "APRIL", "MAI", "JUNI", "JULI", "AUGUST", "SEPTEMBER" ,"OKTOBER" ,"NOVEMBER" ,"DEZEMBER"]; if (URL_PATH && URL_PATH[0] === "category") { Object.assign(HTML_CLASSES, { DATE: "date_x", BEITRAG : "beitrag2" }); Object.assign(HTML_IDS, { CONTENT : "archiv" }); } return { URL_PATH:URL_PATH, TABLE_HEADER_NAMES:TABLE_HEADER_NAMES, HTML_CLASSES:HTML_CLASSES, HTML_IDS:HTML_IDS, MONTH_NAMES:MONTH_NAMES } })(); const Util = (() => { return { getPageAsync: (url, onSuccess, onError = () => {}) => { return GM_xmlhttpRequest({ method: 'GET', url: url, onload: (resp) => { switch (resp.status) { case 200: case 304: resp.html = new DOMParser().parseFromString(resp.responseText, 'text/html'); onSuccess(resp); return; default: onError(resp); return; } }, onerror: onError }); }, createInputElement: (id, type, width, maxLength = 3, textAlign = "left") => { const inputElement = document.createElement("INPUT"); inputElement.id = id; inputElement.type = type; inputElement.maxLength = maxLength; inputElement.style = `text-align:${textAlign};width:${width}` return inputElement; }, createShowContainer: () => { const oldContainer = document.getElementById(CONST.HTML_IDS.SHOW_CONTAINER); if (!oldContainer) { const divHead = document.getElementById(CONST.HTML_IDS.HEAD); divHead.parentNode.removeChild(divHead); const divContent = document.getElementById(CONST.HTML_IDS.CONTENT); divContent.innerHTML = ""; const newContainer = divContent.insertBefore(document.createElement("DIV"), divContent.firstChild); newContainer.id = CONST.HTML_IDS.SHOW_CONTAINER; const divBeitragInfo = newContainer.appendChild(document.createElement("DIV")); divBeitragInfo.id = CONST.HTML_IDS.BEITRAG_INFO; divBeitragInfo.appendChild(document.createTextNode("Seite: ")); divBeitragInfo.appendChild(Util.createInputElement(CONST.HTML_IDS.PAGE_NUMBER, "number", "3em", 3, "center")); divBeitragInfo.appendChild(document.createTextNode(", Beitrag: ")); divBeitragInfo.appendChild(Util.createInputElement(CONST.HTML_IDS.BEITRAG_NUMBER, "number", "3em", 2, "center")); divBeitragInfo.appendChild(document.createTextNode(" / ")); divBeitragInfo.appendChild(Util.createInputElement(CONST.HTML_IDS.BEITRAG_COUNT, "number", "3em", 2, "center")).disabled = true; divBeitragInfo.appendChild(document.createTextNode(", IMDb: ")); divBeitragInfo.appendChild(Util.createInputElement(CONST.HTML_IDS.FILM_DATA_IMDB_RATING, "text", "3em", 4, "center")).disabled = true; divBeitragInfo.appendChild(document.createTextNode(", Größe: ")); divBeitragInfo.appendChild(Util.createInputElement(CONST.HTML_IDS.FILM_DATA_GROESSE, "text", "7em", 9, "center")).disabled = true; return true; } else { for (let divBeitragOld of oldContainer.querySelectorAll(`DIV.${CONST.HTML_CLASSES.BEITRAG}`)) { oldContainer.removeChild(divBeitragOld); } return false; } }, parseInt: (str, maxIntPlaces = 1, fallbackValue = null) => { let regex = "\\d"; if (maxIntPlaces > 1) { regex += "{1," + maxIntPlaces + "}"; } return Util.parseIntWithRegex(str, new RegExp(regex), fallbackValue); }, parseFloat: (str, maxIntPlaces = 1, maxDecPlaces = 0, fallbackValue = null) => { let regex = "\\d"; if (maxIntPlaces > 1) { regex += "{1," + maxIntPlaces + "}"; } if (maxDecPlaces > 0) { regex += "\\s?[,\.]?\\s?\\d{0," + maxDecPlaces + "}"; } return Util.parseFloatWithRegex(str, new RegExp(regex), fallbackValue); }, parseIntWithRegex: (str, regex, fallbackValue = null) => { const match = Util.parseStrWithRegex(str, regex); const value = parseInt(match); return Number.isNaN(value) ? fallbackValue : value; }, parseFloatWithRegex: (str, regex, fallbackValue = null) => { const match = Util.parseStrWithRegex(str, regex, "").replace(",","."); const value = parseFloat(match); return Number.isNaN(value) ? fallbackValue : value; }, parseStrWithRegex: (str, regex, fallbackValue = null) => { const match = regex.exec(str || ""); return (match && match.length >= 1) ? match[0] : fallbackValue; }, monthNameToNumber: (monthName) => { return CONST.MONTH_NAMES.indexOf(String(monthName).toUpperCase()); }, createTable(data, cellAttributes = {}, headerAttributes = cellAttributes) { function configRow(cellElement, content, attributes) { cellElement.appendChild(content instanceof Element ? content : document.createTextNode(String(content))); for (let attrName of Object.keys(attributes)) { cellElement[attrName] = attributes[attrName]; } } const table = document.createElement("TABLE"); if (data) { for (let element of data) { const row = table.insertRow(); for (let key of Object.keys(element)) { const td = row.insertCell(); const content = element[key]; const attributes = cellAttributes[key] || {}; configRow(td, content, attributes); } } const thead = table.createTHead(); const row = thead.insertRow(); for (let key of Object.keys(data[0])) { const th = document.createElement("TH"); const attributes = headerAttributes[key] || {}; row.appendChild(th); configRow(th, key, attributes) } } return table; }, } })(); const Beitrag = (() => { const computeImdbLink = (containerElement, fallbackValue = null) => { for (let a of Array.from(containerElement.getElementsByTagName("A"))) { const linkTextUpper = a.textContent.toUpperCase(); if (linkTextUpper.includes("IMDB")) { return a; } } for (let elStrong of containerElement.querySelectorAll("STRONG, B")) { if (elStrong.textContent.toUpperCase().includes("IMDB")) { const nextEl = elStrong.nextSibling; if (nextEl && nextEl.tagName === "A") { return nextEl; } } } return fallbackValue; }; const computeImdbRating = (containerElement, fallbackValue = null) => { const a = computeImdbLink(containerElement); if (a !== null) { let rating = Util.parseFloat(a.textContent.toUpperCase(), 2, 1); if (rating === null) { const nextEl = a.nextSibling; if (nextEl && nextEl.nodeType === Node.TEXT_NODE) { rating = Util.parseFloat(nextEl.textContent.toUpperCase(), 2, 1); } } if (rating !== null) { return rating; } } return fallbackValue; }; const computeDauer = (containerElement, fallbackValue = null) => { for (let elStrong of containerElement.querySelectorAll("STRONG, B")) { if (elStrong.textContent.toUpperCase().includes("DAUER")) { const nextEl = elStrong.nextSibling; if (nextEl) { const textContentUpper = nextEl.textContent.toUpperCase(); const hours = Util.parseFloatWithRegex(textContentUpper, /(\d{1,2}\s?[,\.]?\s?\d{0,2})\s?(H|STUNDEN|HOURS)/); const minutes = Util.parseIntWithRegex(textContentUpper, /(\d{1,4})\s?(M|MIN|MINUTEN|MINUTES)/); if (hours !== null || minutes !== null) { return (hours === null ? 0 : hours * 60) + (minutes === null ? 0 : minutes); } } } } return fallbackValue; }; const computeMirrors = (containerElement) => { return Array.from(containerElement.querySelectorAll("STRONG + A, B + A")).filter(a => { const strong = a.previousElementSibling; const strongTextContentUpper = strong.textContent.toUpperCase(); return ["DOWNLOAD", "MIRROR"].some(str => strongTextContentUpper.includes(str)); }).filter(a => { const isWerbeLink = !a.hostname || a.hostname.toUpperCase().includes("MOVIE-BLOG"); return !isWerbeLink; }); }; const computeDatum = (containerElement, fallbackValue = null) => { const reDay = "\\d{1,2}"; const reMonth = CONST.MONTH_NAMES.reduce((a, b) => a + "|" + b); const reYear = "\\d{4}"; const reHour = "\\d{1,2}"; const reMin = "\\d{2}"; for (let elDatum of containerElement.getElementsByClassName(CONST.HTML_CLASSES.DATE)) { const match = new RegExp("(" + reDay + ")\\.\\s(" + reMonth + ")\\s(" + reYear + ")\\s(" + reHour + "):(" + reMin + ")", "i").exec(elDatum.textContent); if (match && match.length === 6) { const day = Number.parseInt(match[1]); const month = Util.monthNameToNumber(match[2]); const year = Number.parseInt(match[3]); const hour = Number.parseInt(match[4]); const minute = Number.parseInt(match[5]); return (new Date(year, month, day, hour, minute)); } } return fallbackValue; }; const computeLink = (containerElement, fallbackValue = null) => { const datum = computeDatum(containerElement); if (datum !== null) { const yearFourDigits = datum.getFullYear(); const monthTwoDigits = ('00' + (datum.getMonth() + 1)).slice(-2); const dayTwoDigits = ('00' + datum.getDate()).slice(-2); const urlPath = "/" + [yearFourDigits, monthTwoDigits, dayTwoDigits].reduce((a, b) => a + "/" + b) + "/"; for (let h1 of containerElement.getElementsByTagName("H1")) { for (let a of h1.getElementsByTagName("A")) { if (a.href.includes(urlPath)) { return a.cloneNode(true); } } } } return fallbackValue; }; const computeGroesse = (containerElement, fallbackValue = null) => { for (let elStrong of containerElement.querySelectorAll("STRONG, B")) { if (elStrong.textContent.toUpperCase().includes("GRÖSSE")) { const nextEl = elStrong.nextSibling; if (nextEl) { const textContentUpper = nextEl.textContent.toUpperCase(); const gb = Util.parseFloatWithRegex(textContentUpper, /(\d{1,4}\s?[,\.]?\s?\d{0,3})\s?(GB|GIGABYTE)/); const mb = Util.parseIntWithRegex(textContentUpper, /(\d{1,7}?)\s?(MB|MEGABYTE)/); if (gb !== null || mb !== null) { return (gb === null ? 0 : gb * 1024) + (mb === null ? 0 : mb); } } } } return fallbackValue; }; const computeImgElement = (containerElement, fallbackValue = null) => { const img = containerElement.querySelectorAll("P > IMG"); return img.length > 0 ? img[0] : fallbackValue; } const defaultCompare = new Comparator(...[ beitrag => [Beitrag.TYPEN.FILM, Beitrag.TYPEN.DOKU, Beitrag.TYPEN.SERIE, Beitrag.TYPEN.WERBUNG].indexOf(beitrag.typ), beitrag => beitrag.groesse > 25 * 1024, new Comparator(beitrag => beitrag.imdbRating).reverse() ]).compareFnc; const TYPEN = Object.freeze({ FILM: "Film", SERIE: "Serie", DOKU: "Doku", WERBUNG: "Werbung" }); const _privateSpace = (() => { // { propertyName, Symbol } const propertySymbols = {}; return (thisObj, propertyName, computeFunctionOrValue) => { const propertySymbol = propertySymbols[propertyName] || (propertySymbols[propertyName] = Symbol(propertyName)); let value = thisObj[propertySymbol] if (typeof value === "undefined") { value = (typeof computeFunctionOrValue === 'function') ? computeFunctionOrValue() : computeFunctionOrValue; thisObj[propertySymbol] = value; } return value; }; })(); return class { constructor(divElement) { Object.defineProperty(this, "_", { value: _privateSpace.bind(null, this) }); this._("divElement", divElement); } get divElement() { return this._("divElement"); } get imdbLink() { return this._("imdbLink", () => computeImdbLink(this.divElement, null)); } get imdbRating() { return this._("imdbRating", () => computeImdbRating(this.divElement, 0)); } get imdbId() { return this._("imdbId", () => this.imdbLink === null ? "" : Util.parseStrWithRegex(this.imdbLink, /tt\d{7,8}/, "")); } get dauer() { return this._("dauer", () => computeDauer(this.divElement, 0)); } get groesse() { return this._("groesse", () => computeGroesse(this.divElement, 0)); } getGroesseAsText(unit = this.groesse > 1024 ? "GB" : "MB") { switch (unit.toUpperCase()) { case "GB": return Number(Math.round(this.groesse / 1024 + 'e1') + 'e-1').toLocaleString(undefined, { maximumFractionDigits: 1 }) + " GB"; } return this.groesse.toLocaleString() + " MB"; } get link() { return this._("link", () => computeLink(this.divElement, null)); } get linkText() { return this.link ? this.link.textContent : ""; } get mirrors() { return this._("mirrors", () => computeMirrors(this.divElement)); } get imgElement() { return this._("imgElement", () => computeImgElement(this.divElement)); } get typ() { return this._("typ", () => { if (this.mirrors.length === 0 || this.linkText.toUpperCase().includes('-HELD')) { return Beitrag.TYPEN.WERBUNG; } if (/\.DO[KC]U/i.test(this.linkText)) { return Beitrag.TYPEN.DOKU; } if (/\.S\d\d?(E\d\d?)?(-S\d\d?(E\d\d?)?)?\./i.test(this.linkText)) { return Beitrag.TYPEN.SERIE; } return ""; }); } get datum() { return this._("datum", () => computeDatum(this.divElement, null)); } get releasedYear() { return this._("releasedYear", () => { const match = /\.(\d{4})\./.exec(this.linkText); if (!match || match.length <= 1) { return null; } return parseInt(match[1]) || null; }); } static get TYPEN() { return TYPEN; } static get defaultCompare() { return defaultCompare; } } })(); const View = (() => { const addBeitraegeAsync = (beitraege, fromNumOfPage, toNumOfPage, onSuccess, onError) => { const urlPath = document.location.href.replace('page/', '').replace('#',''); Util.getPageAsync(`${urlPath}page/${fromNumOfPage + 1}/`, resp => { // add Beitraege beitraege.push(...Array.from(resp.html.querySelectorAll(`DIV.${CONST.HTML_CLASSES.BEITRAG}`)).map(div => new Beitrag(div))); if (fromNumOfPage < toNumOfPage) { // load further Beitraege addBeitraegeAsync(beitraege, fromNumOfPage + 1, toNumOfPage, onSuccess, onError); return; } // Beitreage of last page loaded successfully onSuccess(); }, onError); }; return class { constructor(numOfPage = 0, numOfBeitrag = 0, pageSteps = CONFIG.PAGES_LOAD_COUNT) { this.pageSteps = pageSteps this.numOfPage = numOfPage; this.numOfBeitrag = numOfBeitrag; this.beitraege = []; this.gotoPage(); } get beitragCount() { return this.beitraege.length; } setBrowsingEnabled(isBrowsingEnabled) { this.isPageLoading = !isBrowsingEnabled; [ document.getElementById(CONST.HTML_IDS.PAGE_NUMBER) || {}, document.getElementById(CONST.HTML_IDS.BEITRAG_NUMBER) || {} ].forEach(inputElement => { inputElement.disabled = !isBrowsingEnabled; }); } gotoPage(numOfPage = this.numOfPage, numOfBeitrag = -1) { // disable page browsing this.setBrowsingEnabled(false); const onSuccess = () => { if (0 <= numOfBeitrag && numOfBeitrag < this.beitragCount) { this.numOfBeitrag = numOfBeitrag; } else { this.numOfBeitrag = (numOfPage < this.numOfPage) ? this.beitragCount - 1 : 0; } this.numOfPage = numOfPage; // distinct for links const beitraegeByLinks = new Map(this.beitraege.map(b => [ b.link.href, b ])); this.beitraege = Array.from(beitraegeByLinks.values()); // sort Beitraege by IMDb rating this.beitraege.sort((a, b) => Beitrag.defaultCompare(a, b)); this.showBeitrag(); this.showTable(); this.highlightTableRow(0); this.setBrowsingEnabled(true); } const onError = resp => this.setBrowsingEnabled(true); // merge Beitraege of 'pageSteps' pages this.beitraege = []; let numOfPageFirst = numOfPage * this.pageSteps; let numOfPageLast = numOfPageFirst + this.pageSteps - 1; addBeitraegeAsync(this.beitraege, numOfPageFirst, numOfPageLast, onSuccess, onError); } indexOfBeitrag(beitrag) { return this.beitraege.indexOf(beitrag); } gotoBeitrag(numOfBeitrag = this.numOfBeitrag) { this.highlightTableRow(this.numOfBeitrag, false); this.numOfBeitrag = numOfBeitrag; this.showBeitrag(); this.highlightTableRow(this.numOfBeitrag, true); } showBeitrag() { // get a clean show container const isNewShowContainer = Util.createShowContainer(); // clone Beitrag into show container const beitrag = this.beitraege[this.numOfBeitrag]; const divBeitrag = beitrag ? beitrag.divElement : null; if (divBeitrag) { const beitragContent = document.getElementById(CONST.HTML_IDS.SHOW_CONTAINER); const beitragInfo = document.getElementById(CONST.HTML_IDS.BEITRAG_INFO); const inputPageNum = document.getElementById(CONST.HTML_IDS.PAGE_NUMBER); inputPageNum.value = this.numOfPage + 1; inputPageNum.min = 1; inputPageNum.max = 9999; const inputBeitragNum = document.getElementById(CONST.HTML_IDS.BEITRAG_NUMBER); inputBeitragNum.value = this.numOfBeitrag + 1 inputBeitragNum.min = 1; inputBeitragNum.max = this.beitragCount; if (isNewShowContainer) { inputPageNum.addEventListener("change", () => { if (!this.isPageLoading) { let pageNum = parseInt(inputPageNum.value) - 1; pageNum = Math.max(0, pageNum); this.gotoPage(pageNum, 0); } }); inputBeitragNum.addEventListener("change", () => { if (!this.isPageLoading) { let beitragNum = parseInt(inputBeitragNum.value) - 1; beitragNum = Math.max(beitragNum, 0); beitragNum = Math.min(beitragNum, this.beitragCount - 1); this.gotoBeitrag(beitragNum); } }); } document.getElementById(CONST.HTML_IDS.BEITRAG_COUNT).value = this.beitragCount; document.getElementById(CONST.HTML_IDS.FILM_DATA_IMDB_RATING).value = beitrag.imdbRating; document.getElementById(CONST.HTML_IDS.FILM_DATA_GROESSE).value = beitrag.getGroesseAsText(); // remove former image from sidebar const curImage = document.getElementById(CONST.HTML_IDS.CUR_BEITRAG_IMG); if (curImage !== null) { curImage.parentElement.removeChild(curImage) } // insert image to sidebar const divSidebar = document.getElementById(CONST.HTML_IDS.SIDEBAR); const imgElement = beitrag.imgElement; if (divSidebar && imgElement) { imgElement.id = CONST.HTML_IDS.CUR_BEITRAG_IMG divSidebar.insertBefore(imgElement, divSidebar.firstChild); } divBeitrag.style = "margin: -2em;"; return beitragContent.appendChild(divBeitrag) ? true : false; } return false; } highlightTableRow(numOfBeitrag, isHighlight = true) { const tableRow = document.getElementById(`${CONST.HTML_IDS.TABLE_TR_NUM}_${numOfBeitrag + 1}`); if (tableRow) { tableRow.style["font-weight"] = isHighlight ? "bold" : ""; } } showTable() { const sortByColumn = (columnKey, sortFunction) => { const curBeitrag = this.beitraege[this.numOfBeitrag]; if (this.lastSortedColumnKey !== columnKey) { this.beitraege.sort(sortFunction); this.lastSortedColumnKey = columnKey; } else { this.beitraege.reverse(); this.lastSortedColumnKey = undefined; } this.gotoBeitrag(this.indexOfBeitrag(curBeitrag)); this.showTable(); }; const tableData = this.beitraege.map((b, i) => ({ [CONST.TABLE_HEADER_NAMES.NUM]: (() => { const a = document.createElement("A"); a.appendChild(document.createTextNode((i + 1).toString())); a.href = "#"; a.onclick = () => this.gotoBeitrag(i); return a; })(), [CONST.TABLE_HEADER_NAMES.RATING]: b.imdbRating, [CONST.TABLE_HEADER_NAMES.JAHR]: b.releasedYear || "", [CONST.TABLE_HEADER_NAMES.LINK]: (() => { const link = b.link.cloneNode(true); // Textformatierungen entfernen while(link.firstChild) { link.removeChild(link.firstChild); } link.textContent = b.linkText; const MAX_LINK_LENGTH = 55; if (link.textContent.length > MAX_LINK_LENGTH) { link.textContent = link.textContent.substr(0, MAX_LINK_LENGTH-4) + "..."; } return link; })(), [CONST.TABLE_HEADER_NAMES.DURATION]: b.dauer, [CONST.TABLE_HEADER_NAMES.SIZE]: b.getGroesseAsText("GB"), [CONST.TABLE_HEADER_NAMES.TYPE]: b.typ, [CONST.TABLE_HEADER_NAMES.DATE]: b.datum.toLocaleDateString(undefined, { dateStyle: "short", timeStyle: "short" }), })); const tdAttributes = { [CONST.TABLE_HEADER_NAMES.NUM]: { style: "text-align:right;", className: CONST.HTML_CLASSES.TABLE_TD_NUM }, [CONST.TABLE_HEADER_NAMES.RATING]: { style: "text-align:center;", className: CONST.HTML_CLASSES.TABLE_TD_RATING }, [CONST.TABLE_HEADER_NAMES.JAHR]: { style: "text-align:right;", className: CONST.HTML_CLASSES.TABLE_TD_JAHR }, [CONST.TABLE_HEADER_NAMES.LINK]: { style: "text-align:left;width=20em", className: CONST.HTML_CLASSES.TABLE_TD_LINK }, [CONST.TABLE_HEADER_NAMES.DURATION]: { style: "text-align:right;", className: CONST.HTML_CLASSES.TABLE_TD_DURATION }, [CONST.TABLE_HEADER_NAMES.SIZE]: { style: "text-align:right;", className: CONST.HTML_CLASSES.TABLE_TD_SIZE }, [CONST.TABLE_HEADER_NAMES.TYPE]: { style: "text-align:left;", className: CONST.HTML_CLASSES.TABLE_TD_TYPE }, [CONST.TABLE_HEADER_NAMES.DATE]: { style: "text-align:left;", className: CONST.HTML_CLASSES.TABLE_TD_DATE }, }; const thAttributes = { [CONST.TABLE_HEADER_NAMES.NUM]: { style: "text-align:right;", onclick: () => sortByColumn("#", Beitrag.defaultCompare) }, [CONST.TABLE_HEADER_NAMES.RATING]: { onclick: () => sortByColumn("IMDb", new Comparator(b => b.imdbRating).reverse().compareFnc) }, [CONST.TABLE_HEADER_NAMES.JAHR]: { onclick: () => sortByColumn("Jahr", new Comparator(b => b.releasedYear).compareFnc) }, [CONST.TABLE_HEADER_NAMES.LINK]: { onclick: () => sortByColumn("Link", new Comparator(b => b.linkText).compareFnc) }, [CONST.TABLE_HEADER_NAMES.DURATION]: { onclick: () => sortByColumn("Typ", new Comparator(b => b.datum).compareFnc) }, [CONST.TABLE_HEADER_NAMES.SIZE]: { onclick: () => sortByColumn("Größe", new Comparator(b => b.groesse).reverse().compareFnc) }, [CONST.TABLE_HEADER_NAMES.TYPE]: { onclick: () => sortByColumn("Typ", new Comparator(b => b.typ).compareFnc) }, [CONST.TABLE_HEADER_NAMES.DATE]: { onclick: () => sortByColumn("Datum", new Comparator(b => b.datum.valueOf()).compareFnc) }, }; const table = Util.createTable(tableData, tdAttributes, thAttributes); for (let tr of table.getElementsByTagName("TR")) { const tdNum = tr.getElementsByClassName(CONST.HTML_CLASSES.TABLE_TD_NUM); const num = tdNum.length > 0 ? Util.parseInt(tdNum[0].textContent, 3) : null; if (num !== null) { tr.id = `${CONST.HTML_IDS.TABLE_TR_NUM}_${num}`; } } let tableDiv = document.getElementById(CONST.HTML_IDS.LISTE_BEITRAEGE); if (!tableDiv) { const beitragInfoDiv = document.getElementById(CONST.HTML_IDS.BEITRAG_INFO); const beitragContent = document.getElementById(CONST.HTML_IDS.SHOW_CONTAINER); tableDiv = beitragInfoDiv.parentNode.insertBefore(document.createElement("DIV"), beitragInfoDiv); tableDiv.id = CONST.HTML_IDS.LISTE_BEITRAEGE; } else { while (tableDiv.firstChild) { tableDiv.removeChild(tableDiv.firstChild); } } tableDiv.appendChild(table); } } })(); let view = new View(); const browseBeitrag = function(distance) { if (view.isPageLoading) { return; } const numOfNextBeitrag = view.numOfBeitrag + distance; if (numOfNextBeitrag < 0) { if (view.numOfPage > 0) { view.gotoPage(view.numOfPage - 1); } } else if (numOfNextBeitrag >= view.beitragCount) { view.gotoPage(view.numOfPage + 1); } else { view.gotoBeitrag(numOfNextBeitrag); } }; document.onkeydown = function (e) { switch (e.keyCode) { case 37: // key left browseBeitrag(-1); return false; case 39: // key right browseBeitrag(1); return false; case 33: // page up view.gotoPage(Math.max(0, view.numOfPage - 1), 0); return false; case 34: // page down view.gotoPage(view.numOfPage + 1, 0); return false; } }; })();