Greasy Fork is available in English.
Tải truyện từ metruyenchu.com định dạng epub.
// ==UserScript==// @name MeTruyenChu downloader// @namespace https://nntoan.com/// @description Tải truyện từ metruyenchu.com định dạng epub.// @version 1.0.1// @icon https://i.imgur.com/ZOmmIGK.png// @author Toan Nguyen// @oujs:author nntoan// @license MIT; https://nntoan.mit-license.org/// @supportURL https://github.com/nntoan/UserScripts/issues// @match http://metruyenchu.com/truyen/*// @match https://metruyenchu.com/truyen/*// @require https://code.jquery.com/ui/1.12.0/jquery-ui.min.js// @require https://unpkg.com/[email protected]/dist/jszip.min.js// @require https://unpkg.com/[email protected]/ejs.min.js// @require https://unpkg.com/[email protected]/dist/jepub.min.js// @require https://unpkg.com/[email protected]/dist/FileSaver.min.js// @require https://cdn.jsdelivr.net/npm/[email protected]/src/mbDownloader.js// @connect self// @run-at document-idle// @noframes// ==/UserScript==/*global console, location*/(function ($, window, document) { // eslint-disable-line'use strict';$(document).ready(function() {$.widget('nntoan.mbDownloader', $.nntoan.mbDownloader, {_create: function () {var self = this;this._super();// Capture network requestsvar proxied = window.XMLHttpRequest.prototype.open;window.XMLHttpRequest.prototype.open = function () {if (arguments[1].includes('v2/chapters') === true) {self.options.xhr.chapter.url = arguments[1];}return proxied.apply(this, [].slice.call(arguments));};// Extending optionsthis.options.processing.ebookFileName = this.options.general.pathname.slice(8, -5);this.options.xhr.content.url = this.options.general.pathname + this.options.chapters.chapId + '/';// Styling download button for current sitethis.elements.$downloadBtn.attr('class', 'btn btn-warning btn-md btn-block text-white font-weight-semibold d-flex align-items-center justify-content-center');this.elements.$downloadBtn.html('<i class="nh-icon icon-book mr-2"></i>Tải xuống');this.elements.$downloadWrapper = $('<li></li>', {class: 'mr-3 w-150'});this.elements.$downloadWrapper.html(this.elements.$downloadBtn);this.elements.$downloadWrapper.appendTo(this.options.classNames.downloadAppendTo);document.getElementById(this.options.classNames.getChapterTrigger).click();console.time('downloadAndGenerateEpub');},/*** Get list of chapters request.** @param {Object} that Curent widget object* @param {Event} event jQuery event* @param {Element} $widget Current node element* @returns void*/getListOfChapters: function (that, event, $widget) {var options = that.options, $ajax = null;if (options.isGlocCallbackRequired) {$ajax = that._trigger('getListOfChaptersPreprocess', event, that);} else {$ajax = $.ajax(options.xhr.chapter);}$ajax.done(function (response) {if (options.isGlocCallbackRequired) {$.ajax(options.xhr.chapter).done(function (data) {that.processListOfChapters(data, that, $widget);}).fail(function (error) {$widget.text('Lỗi trước khi bị lỗi danh mục :)');that.downloadStatus('error');console.error(error); //eslint-disable-line});} else {that.processListOfChapters(response, that, $widget);}}).fail(function (error) {$widget.text('Lỗi danh mục');that.downloadStatus('error');console.error(error); //eslint-disable-line});},/*** Process with the XHR response of chapters list.** @param {jqXHR} response XHR response* @param {Object} that Curent widget object* @param {Element} $widget Current node element* @returns void*/processListOfChapters: function (response, that, $widget) {var options = that.options;options.chapters.chapList = response._data.chapters;options.chapters.chapList = options.chapters.chapList.map(function (val) {return that.chapListValueFilter(options, val);}).filter(function (chapter) {return chapter !== '';});that._trigger('chapListFiltered', null, options.chapters.chapList);that.processing.chapListSize = options.chapters.chapList.length;if (that.processing.chapListSize > 0) {that.elements.$window.on('beforeunload', function () {return 'Truyện đang được tải xuống...';});$widget.one('click', function (e) {e.preventDefault();that.saveEbook($widget);});that.getContent($widget);}},/*** Callback function to handle chap list values.** @param {Object} options* @param {String} val* @returns {String}*/chapListValueFilter: function (options, val) {val = val.slug.replace(options.general.referrer, '');val = '/' + val;return val.trim();},/*** Update CSS of download button.** @param {String} status Download status* @returns void*/downloadStatus: function (status) {var self = this,options = this.options;self.elements.$downloadBtn.removeClass(options.classNames.downloadBtnStatus);if (status === 'error') {self.elements.$downloadBtn.addClass('btn-danger');}if (status === 'warning') {self.elements.$downloadBtn.addClass('btn-warning');}if (status === 'success') {self.elements.$downloadBtn.addClass('btn-success');}},/*** Cleanup redundant charactes in chapter content.** @param {String} html Chapter content as HTML* @returns {String}*/cleanupHtml: function (html) {var options = this.options;html = html.replace(options.regularExp.chapter, '');html = html.replace(options.regularExp.novel, '');html = html.replace(options.regularExp.chineseSpecialChars, '');html = html.replace(options.regularExp.alphanumeric, function (key, attr) {if (attr) return ' ';if (!isNaN(key)) return key;if (key.split(options.regularExp.alphabet).length > 2) return ' ';if (key.split(options.regularExp.number).length > 1) return ' ';return key;});html = html.replace(options.regularExp.buttons, '');html = html.split(this.createRegExp(options.regularExp.eoctext))[0];html = html.replace('<br> <br>', '<br />');return '<div>' + html + '</div>';},});$(this).mbDownloader({readyToInit: true,createDownloadWrapper: true,processing: {ebookFileExt: '.epub'},jwt: {crypt: 'c&fjFR!WXPDPPmTj*!np2E98TPw5GMN93S43WVZDnR9fcmf@g*RA*Z',},classNames: {novelId: '#report',infoBlock: '#app .container',chapterContent: '#js-read__content',chapterNotContent: 'iframe, script, style, a, div, p:has(a[href*="metruyenchu.com"])',chapterVip: '#btnChapterVip',chapterTitle: '.nh-read__title',ebookTitle: 'h1',ebookAuthor: '.row.no-gutters .list-unstyled.mb-4 .border-secondary',ebookCover: '.row.no-gutters .nh-thumb.shadow',ebookDesc: '#nav-intro .content',ebookType: '.row.no-gutters .list-unstyled.mb-4 li .border-primary',getChapterTrigger: 'nav-tab-chap',downloadBtnStatus: 'btn-primary btn-success btn-info btn-warning btn-danger blue success warning info danger error',downloadWrapper: 'mr-3 w-150',downloadAppendTo: '.row.no-gutters .list-unstyled.d-flex.align-items-center',},ebook: {fallbackCover: 'https://static.cdnno.com/background/metruyenchu.jpg'},chapters: {chapListSlice: [6, -1],},xhr: {chapter: {type: 'GET',url: '',},content: {type: 'GET',xhrFields: {withCredentials: true}}},bookInfoUpdated: function (event, data) {var that = data.that,options = that.options,$infoBlock = that.elements.$infoBlock;options.ebook = $.extend(options.ebook, {title: $infoBlock.find(options.classNames.ebookTitle).text().trim(),author: $infoBlock.find(options.classNames.ebookAuthor).text().trim(),cover: $infoBlock.find(options.classNames.ebookCover).find('img').attr('src'),description: $infoBlock.find(options.classNames.ebookDesc).html(),});data.epubInfo = $.extend(data.epubInfo, options.ebook);console.log('Book information updated...', data.epubInfo);},chapTitleUpdated: function(event, data) {var options = data.this.options;options.xhr.content.url = location.protocol + '//' + options.general.host + options.chapters.chapId;},beforeCreateEpub: function(event, that) {console.log('Prepare generate epub...');},complete: function(event, that) {console.log('Epub downloaded successfully. Please check your Downloads folder.');console.timeEnd('downloadAndGenerateEpub');}});});})(jQuery, window, document); // eslint-disable-line