From 820379f6fd2080034ca4f410d1638936e89992d5 Mon Sep 17 00:00:00 2001 From: Michael Date: Fri, 14 Dec 2018 22:02:19 +0100 Subject: [PATCH 01/50] bugfix for Drop Caps need to accept "float" CSS attribute. Bugfix in including style classes: per tag - had a inside

with same class name. --- web-extension/extractHtml.js | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index dbf7475..7d0b6c9 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -23,7 +23,7 @@ var tmpIdsToNewCss = {}; var supportedCss = [ 'background-color', 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', - 'color', 'font', 'font-size', 'font-weight', 'font-family', + 'color', 'float', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'list-style', 'outline', 'padding', 'quotes', @@ -364,7 +364,9 @@ function extractCss(includeStyle, appliedStyles) { if (!classNames) { classNames = pre.tagName + '-' + Math.floor(Math.random()*100000); } - } + } else { + classNames = pre.tagName + '.' + classNames; // MM: materialize class per tag. had issues with span inside paragraph + } let tmpName = cssClassesToTmpIds[classNames]; let tmpNewCss = tmpIdsToNewCss[tmpName]; if (!tmpName) { From 73a332cb72b576acb3dd0ba34dea47ed9a8e7af2 Mon Sep 17 00:00:00 2001 From: Michael Date: Tue, 12 Feb 2019 21:36:26 +0100 Subject: [PATCH 02/50] Update extractHtml.js --- web-extension/extractHtml.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index 7d0b6c9..66323aa 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -362,18 +362,19 @@ function extractCss(includeStyle, appliedStyles) { if (!classNames) { classNames = pre.getAttribute('id'); if (!classNames) { - classNames = pre.tagName + '-' + Math.floor(Math.random()*100000); + classNames = pre.tagName.toLowerCase() + '-tag'; // MM: pre.tagName + '-' + Math.floor(Math.random()*100000); + // MM test: return; // MM: if we do not want to store defaults per tag... maybe from more general css rules ... } } else { - classNames = pre.tagName + '.' + classNames; // MM: materialize class per tag. had issues with span inside paragraph + classNames = pre.tagName.toLowerCase() + '-' + classNames; // MM: materialize class per tag. had issues with span inside paragraph // do NOT concatenate with '.' here ;-) } let tmpName = cssClassesToTmpIds[classNames]; let tmpNewCss = tmpIdsToNewCss[tmpName]; if (!tmpName) { - tmpName = 'class-' + Math.floor(Math.random()*100000); + tmpName = classNames; // MM: tmpName = 'class-' + Math.floor(Math.random()*100000); cssClassesToTmpIds[classNames] = tmpName; } - if (!tmpNewCss) { + if (!tmpNewCss) { // MM: hack: take last or inner elements...... if (true) { // var style = window.getComputedStyle(pre); tmpNewCss = {}; for (let cssTagName of supportedCss) { From 93c837db03d91c33c2c8dd261e09e05bfe45104c Mon Sep 17 00:00:00 2001 From: Michael Date: Tue, 12 Feb 2019 22:58:09 +0100 Subject: [PATCH 03/50] Update extractHtml.js some fixes for smaller/more accurate formatting and CSS (experimented with iX Select and Wikipedia pages.. --- web-extension/extractHtml.js | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index 66323aa..550cbc2 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -23,8 +23,8 @@ var tmpIdsToNewCss = {}; var supportedCss = [ 'background-color', 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', - 'color', 'float', 'font', 'font-size', 'font-weight', 'font-family', - 'letter-spacing', 'line-height', + 'color', 'font', 'font-size', 'font-weight', 'font-family', + 'letter-spacing', 'line-height', 'float', 'list-style', 'outline', 'padding', 'quotes', 'text-decoration', 'text-transform', 'word-spacing', @@ -63,9 +63,11 @@ function getImageSrc(srcTxt) { } function formatPreCodeElements($jQueryElement) { +/* MM: $jQueryElement.find('pre').each(function (i, pre) { $(pre).replaceWith('

' + pre.innerText + '
'); }); +*/ $jQueryElement.find('code').each(function (i, pre) { $(pre).replaceWith('' + pre.innerText + ''); }); @@ -266,7 +268,9 @@ function sanitize(rawContentString) { return; } - results += "\n"; + // MM: results += "\n"; + // MM: helps with markup inside
 tags (\n destroys formatting )
+		results += "";
             },
             chars: function(text) {
                 if (lastTag !== '' && allowedTags.indexOf(lastTag) < 0) {
@@ -345,6 +349,10 @@ function jsonToCss(jsonObj) {
     return result;
 }
 
+// TODO: Klasse für builtin style attribute:  lookup:
+//  let classNames = pre.getAttribute('style');
+//   https://en.wikipedia.org/wiki/Data_warehouse
+
 function extractCss(includeStyle, appliedStyles) {
     if (includeStyle) {
         $('body').find('*').each((i, pre) => {
@@ -374,7 +382,7 @@ function extractCss(includeStyle, appliedStyles) {
                     tmpName = classNames; // MM:  tmpName = 'class-' + Math.floor(Math.random()*100000);
                     cssClassesToTmpIds[classNames] = tmpName;
                 }
-                if (!tmpNewCss) { // MM: hack: take last or inner elements...... if (true) {
+                if (!tmpNewCss) {// MM: hack: take last or inner elements...... if (true) { 
                     // var style = window.getComputedStyle(pre);
                     tmpNewCss = {};
                     for (let cssTagName of supportedCss) {

From e514cdf1e1aaddb318d16465123c284e21331ffc Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 13:39:21 +0100
Subject: [PATCH 04/50] Update extractHtml.js

experimental stuff to handle CSS (reuse) better - more desciptive class names and easier to merge/modify multiple articles from same site later...
---
 web-extension/extractHtml.js | 14 ++++++++------
 1 file changed, 8 insertions(+), 6 deletions(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index 550cbc2..a95a8c8 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -63,14 +63,14 @@ function getImageSrc(srcTxt) {
 }
 
 function formatPreCodeElements($jQueryElement) {
-/* MM:
+/* MM:  
 and  might be have fancy formatting (code snippets...)
     $jQueryElement.find('pre').each(function (i, pre) {
         $(pre).replaceWith('
' + pre.innerText + '
'); }); -*/ $jQueryElement.find('code').each(function (i, pre) { $(pre).replaceWith('' + pre.innerText + ''); }); +*/ } function extractMathMl($htmlObject) { @@ -269,8 +269,8 @@ function sanitize(rawContentString) { } // MM: results += "\n"; - // MM: helps with markup inside
 tags (\n destroys formatting )
-		results += "";
+				// MM: helps with markup inside 
 tags (\n destroys formatting )
+				results += "";
             },
             chars: function(text) {
                 if (lastTag !== '' && allowedTags.indexOf(lastTag) < 0) {
@@ -366,14 +366,16 @@ function extractCss(includeStyle, appliedStyles) {
             } else {
                 if (pre.tagName.toLowerCase() === 'svg') return;
 
-                let classNames = pre.getAttribute('class');
+				let classNames = pre.getAttribute('class');                 
                 if (!classNames) {
                     classNames = pre.getAttribute('id');
                     if (!classNames) {
-                        classNames =  pre.tagName.toLowerCase() + '-tag'; // MM:  pre.tagName + '-' + Math.floor(Math.random()*100000);
+                        //MMv1: classNames =  pre.tagName.toLowerCase() + '-tag'; // MM:  pre.tagName + '-' + Math.floor(Math.random()*100000);
 						// MM test: return; // MM: if we do not want to store defaults per tag... maybe from more general css rules ...
+						classNames =  pre.parentNode.tagName.toLowerCase() + '_' + pre.tagName.toLowerCase();  // MM: use the path. as  ul.li and ol.li need different list-style-type for example.					
                     }
                 } else {
+					classNames = classNames.replace(/\s/g,'_'); // MM:  ...merge multiple names,  we basically have combined css anyways.
 					classNames = pre.tagName.toLowerCase() + '-' + classNames; // MM: materialize class per tag. had issues with span inside paragraph  //  do NOT concatenate with '.' here ;-)
 				}
                 let tmpName = cssClassesToTmpIds[classNames];

From 10b3a8719e75eaa134143fe729fc88ffe3dec2fa Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 13:40:51 +0100
Subject: [PATCH 05/50] Create AdditionalCSSstyles_MM.css

just my personal notebook to keep those for future use
---
 AdditionalCSSstyles_MM.css | 61 ++++++++++++++++++++++++++++++++++++++
 1 file changed, 61 insertions(+)
 create mode 100644 AdditionalCSSstyles_MM.css

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
new file mode 100644
index 0000000..231aa70
--- /dev/null
+++ b/AdditionalCSSstyles_MM.css
@@ -0,0 +1,61 @@
+TODO: in the future, make part of:  
+save-as-ebook/web-extension/background.js
+
+---------------------------------
+*** SQLBI ***
+sqlbi\.com\/articles
+
+body>header, footer, aside,
+.download,
+.connect, .breadcrumb  {
+ display:none !important;
+}
+
+.content-wrapper, .entry-content, body {
+	padding: 1px 0 0 0 !important;
+}
+
+------------------------
+** Wikipedia Article
+
+wikipedia\.org\/wiki\/
+
+#mw-navigation {
+display: none;
+}
+
+#footer {
+display: none;
+}
+
+#mw-panel {
+display: none;
+}
+
+#mw-head {
+display: none;
+}
+
+.toc , .toc-mobile,
+.mw-jump-link, 
+.mw-editsection,
+.navigation-drawer,
+.header-container,
+#page-actions {
+display: none !important;
+}
+.mw-body {
+    margin-left: 0px !important;
+	border-style: none !important;
+}
+.noprint, .cnotice {
+display: none !important;
+}
+ul {
+  padding: 20px !important;
+  list-style-type: square !important;
+  list-style-image: none  !important;
+}
+
+-----------------------------------
+

From 895d4453f6ffdf7baf65bef7516396be2febdf75 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 13:50:49 +0100
Subject: [PATCH 06/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 1 +
 1 file changed, 1 insertion(+)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 231aa70..17618a6 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -13,6 +13,7 @@ body>header, footer, aside,
 
 .content-wrapper, .entry-content, body {
 	padding: 1px 0 0 0 !important;
+	color: #111111; 
 }
 
 ------------------------

From 74e1d3522f082733fae50a60593f734e5da774e4 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 14:21:00 +0100
Subject: [PATCH 07/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 49 +++++++++++++++++++++++++++++++++-----
 1 file changed, 43 insertions(+), 6 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 17618a6..9fed1c9 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -1,9 +1,46 @@
+/*
 TODO: in the future, make part of:  
 save-as-ebook/web-extension/background.js
 
 ---------------------------------
-*** SQLBI ***
-sqlbi\.com\/articles
+*/ 
+
+/* -----------------------------
+Name: Heise Select
+URL Regex: heise\.de\/select
+-------------------------------- */
+body {
+  font: initial !important;
+  font-family: initial !important;
+  color: #101010;  /* default text almost black for better readability */
+}
+
+main {
+	padding: 0 0 0 0 !important; 
+}
+
+span.initial {  /* Drop caps */
+   float: left;
+      font-weight:normal; 
+      font-size:320%  !important;
+      float:left  !important;; 
+      margin-top:-0.3225em  !important;; 
+      margin-bottom:-0.3245em  !important;; 
+  font-stretch: normal;
+}
+
+/* remove everything except plain article */
+a-analytics,
+body>footer,
+.topbar, .toolbar, .comment, .bottom-links, .shariff 
+{
+   display: none !important;
+}
+
+/* -----------------------------
+Name: SQLBI 
+URL Regex: sqlbi\.com\/articles
+-------------------------------- */
 
 body>header, footer, aside,
 .download,
@@ -16,10 +53,10 @@ body>header, footer, aside,
 	color: #111111; 
 }
 
-------------------------
-** Wikipedia Article
-
-wikipedia\.org\/wiki\/
+/* -----------------------------
+Name: Wikipedia Article
+URL Regex: wikipedia\.org\/wiki\/
+-------------------------------- */
 
 #mw-navigation {
 display: none;

From 92d2203a7057dee0ca850bed0afe9bef3f3d51f0 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 14:21:16 +0100
Subject: [PATCH 08/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 9fed1c9..aed1dba 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -95,5 +95,5 @@ ul {
   list-style-image: none  !important;
 }
 
------------------------------------
-
+/* ----------------------------------- */
+

From a2be4f2bae544b0b509726d16cd92e7bfcfb8be1 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 15:36:34 +0100
Subject: [PATCH 09/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 55 ++++++++++++++++++++++++++++++++++++++
 1 file changed, 55 insertions(+)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index aed1dba..8ca9c09 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -5,9 +5,61 @@ save-as-ebook/web-extension/background.js
 ---------------------------------
 */ 
 
+
+/* -----------------------------
+Name: Heise News
+URL Regex: heise\.de\/newsticker
+-------------------------------- */
+body {
+  font: initial !important;
+  font-family: initial !important;
+  color: #101010;  /* default text almost black for better readability */
+}
+
+/* TODO: Text color article-content>p  */ 
+
+main {
+	padding: 0 0 0 0 !important; 
+}
+
+div#container{
+	 margin: 1px 1px 1px 1px;
+}
+
+span.initial {  /* Drop caps */
+   float: left;
+      font-weight:normal; 
+      font-size:320%  !important;
+      float:left  !important;; 
+      margin-top:-0.3225em  !important;; 
+      margin-bottom:-0.3245em  !important;; 
+  font-stretch: normal;
+}
+
+/* remove everything except plain article */
+a-analytics,
+body>footer,
+#cboxOverlay, #colorbox, 
+.header-main__content,
+.header-main,
+.topnavigation, .ad-container,
+.article-layout__footer,
+.article-sidebar, .article-actions,
+.ho-stage-container, .bottom_up,
+.main-footer
+{
+   display: none !important;
+}
+
+
+
 /* -----------------------------
 Name: Heise Select
 URL Regex: heise\.de\/select
+
+Additional Hint: .jpeg images are provided as WebP instead which corrupts
+ the resulting books.
+ use another Chrome extension to change Request headers for *.jpg to ask for image/jpeg
 -------------------------------- */
 body {
   font: initial !important;
@@ -56,6 +108,9 @@ body>header, footer, aside,
 /* -----------------------------
 Name: Wikipedia Article
 URL Regex: wikipedia\.org\/wiki\/
+
+Additional trick: Login and personalize "Appearance" to
+ show thubnails with 400px instead of 200px 
 -------------------------------- */
 
 #mw-navigation {

From e0919806e504c6fe5be9ec23645b42cc3fd5c17f Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 16:27:10 +0100
Subject: [PATCH 10/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 27 ++++++++++++++++++++++++++-
 1 file changed, 26 insertions(+), 1 deletion(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 8ca9c09..2fb15c8 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -8,7 +8,7 @@ save-as-ebook/web-extension/background.js
 
 /* -----------------------------
 Name: Heise News
-URL Regex: heise\.de\/newsticker
+URL Regex: heise\.de\/newsticker|heise\.de\/hintergrund
 -------------------------------- */
 body {
   font: initial !important;
@@ -51,6 +51,31 @@ body>footer,
    display: none !important;
 }
 
+/* -----------------------------
+Name: Telepolis
+URL Regex: heise\.de\/tp
+-------------------------------- */
+body {
+  font: initial !important;
+  font-family: initial !important;
+  color: #101010;  /* default text almost black for better readability */
+}
+
+main {
+	padding: 0 0 0 0 !important; 
+}
+
+/* remove everything except plain article */
+a-analytics,
+body>footer,
+.ho-roof, .tp_mainheader, 
+.navbar, .nav, .navbar-nav,
+.tp_breadcrumb, .subnavi, 
+aside, article>footer,
+.printversion--hide
+{
+   display: none !important;
+}
 
 
 /* -----------------------------

From f985170573b9b2a7d953dd5aaec394e7798b0e7e Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 17:22:18 +0100
Subject: [PATCH 11/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 2fb15c8..7bd18fe 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -46,7 +46,7 @@ body>footer,
 .article-layout__footer,
 .article-sidebar, .article-actions,
 .ho-stage-container, .bottom_up,
-.main-footer
+.main-footer, .printversion--hide
 {
    display: none !important;
 }

From 373ed390d0f9e75b9cdc22d7088d57f00ba0e152 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 17:40:39 +0100
Subject: [PATCH 12/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 13 +++++++++----
 1 file changed, 9 insertions(+), 4 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 7bd18fe..4a07683 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -6,9 +6,10 @@ save-as-ebook/web-extension/background.js
 */ 
 
 
+
 /* -----------------------------
 Name: Heise News
-URL Regex: heise\.de\/newsticker|heise\.de\/hintergrund
+URL Regex: heise\.de\/(newsticker|hintergrund|developer)
 -------------------------------- */
 body {
   font: initial !important;
@@ -38,12 +39,14 @@ span.initial {  /* Drop caps */
 
 /* remove everything except plain article */
 a-analytics,
-body>footer,
-#cboxOverlay, #colorbox, 
+body>footer, article>footer,
+#cboxOverlay, #colorbox, #sitemap,
 .header-main__content,
-.header-main,
+.header-main, .main-header, .breadcrumb,
+.pre-akwa-toc, 
 .topnavigation, .ad-container,
 .article-layout__footer,
+.navbar-nav,
 .article-sidebar, .article-actions,
 .ho-stage-container, .bottom_up,
 .main-footer, .printversion--hide
@@ -51,6 +54,8 @@ body>footer,
    display: none !important;
 }
 
+
+
 /* -----------------------------
 Name: Telepolis
 URL Regex: heise\.de\/tp

From 34b6d3ab369f85261ce0fa1a199792b1c258ecc6 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 18:53:57 +0100
Subject: [PATCH 13/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 4a07683..e1fd2c0 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -137,7 +137,7 @@ body>header, footer, aside,
 
 /* -----------------------------
 Name: Wikipedia Article
-URL Regex: wikipedia\.org\/wiki\/
+URL Regex: wikipedia\.org\/(wiki|w)\/
 
 Additional trick: Login and personalize "Appearance" to
  show thubnails with 400px instead of 200px 

From 162ac0619af09feda3a053e8fe03aa7c863d5d8d Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 19:25:15 +0100
Subject: [PATCH 14/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index e1fd2c0..8988eb4 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -120,12 +120,12 @@ body>footer,
 }
 
 /* -----------------------------
-Name: SQLBI 
-URL Regex: sqlbi\.com\/articles
+Name: sqlbi.com
+URL Regex: sqlbi\.com\/(articles|blog)
 -------------------------------- */
 
 body>header, footer, aside,
-.download,
+.download, .sharing,
 .connect, .breadcrumb  {
  display:none !important;
 }
@@ -135,6 +135,7 @@ body>header, footer, aside,
 	color: #111111; 
 }
 
+
 /* -----------------------------
 Name: Wikipedia Article
 URL Regex: wikipedia\.org\/(wiki|w)\/

From ee6000a422b6a9abe082a00eaf032deba07da06a Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 19:33:38 +0100
Subject: [PATCH 15/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 8988eb4..24ef30a 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -14,7 +14,7 @@ URL Regex: heise\.de\/(newsticker|hintergrund|developer)
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #101010;  /* default text almost black for better readability */
+  color: #010101;  /* default text almost black for better readability */
 }
 
 /* TODO: Text color article-content>p  */ 
@@ -63,7 +63,7 @@ URL Regex: heise\.de\/tp
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #101010;  /* default text almost black for better readability */
+  color: #010101;  /* default text almost black for better readability */
 }
 
 main {
@@ -94,7 +94,7 @@ Additional Hint: .jpeg images are provided as WebP instead which corrupts
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #101010;  /* default text almost black for better readability */
+  color: #010101;  /* default text almost black for better readability */
 }
 
 main {
@@ -132,7 +132,7 @@ body>header, footer, aside,
 
 .content-wrapper, .entry-content, body {
 	padding: 1px 0 0 0 !important;
-	color: #111111; 
+	color: #010101; 
 }
 
 

From 3a8cac0f0a4f05cc903899dceaee3305b0e371a0 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 14 Feb 2019 23:27:14 +0100
Subject: [PATCH 16/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 24ef30a..5a2199c 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -14,7 +14,7 @@ URL Regex: heise\.de\/(newsticker|hintergrund|developer)
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #010101;  /* default text almost black for better readability */
+  color: #010101 !important;  /* default text almost black for better readability */
 }
 
 /* TODO: Text color article-content>p  */ 
@@ -63,7 +63,7 @@ URL Regex: heise\.de\/tp
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #010101;  /* default text almost black for better readability */
+  color: #010101 !important;  /* default text almost black for better readability */
 }
 
 main {
@@ -94,7 +94,7 @@ Additional Hint: .jpeg images are provided as WebP instead which corrupts
 body {
   font: initial !important;
   font-family: initial !important;
-  color: #010101;  /* default text almost black for better readability */
+  color: #010101 !important;  /* default text almost black for better readability */
 }
 
 main {
@@ -132,7 +132,7 @@ body>header, footer, aside,
 
 .content-wrapper, .entry-content, body {
 	padding: 1px 0 0 0 !important;
-	color: #010101; 
+	color: #010101;  /* default text almost black for better readability */
 }
 
 

From eb70ecbe39fa3c84a0571974093a5fd1e926fb88 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 15 Feb 2019 18:05:01 +0100
Subject: [PATCH 17/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 31 +++++++++++++++++++++++++++++++
 1 file changed, 31 insertions(+)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 5a2199c..bc70db1 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -135,6 +135,37 @@ body>header, footer, aside,
 	color: #010101;  /* default text almost black for better readability */
 }
 
+/* -----------------------------
+Name: Golem.de News
+URL Regex: golem\.de\/news
+-------------------------------- */
+body {
+  font: initial !important;
+  font-family: initial !important;
+  color: #010101 !important;  /* default text almost black for better readability */
+}
+
+article {
+	padding: 0 0 0 0 !important; 
+}
+
+#screen > div {  /* main article, screen > div.g.g6 */
+  float: none;	
+}
+
+
+/* remove everything except plain article */
+.toc, .tags,
+.social-tools, .social-tools--inverted,
+.supplementary, .narando,
+#narando-placeholder, #gservices,
+#screen > div ~ div, /* all Divs following main article... */
+.iq-site-header, footer
+{
+ display:none !important;	
+}
+
+
 
 /* -----------------------------
 Name: Wikipedia Article

From 2d13ba352275a5f71e8528b683997435c9bb866a Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 15 Feb 2019 21:31:11 +0100
Subject: [PATCH 18/50] Update extractHtml.js

---
 web-extension/extractHtml.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index a95a8c8..d1fec47 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -23,12 +23,14 @@ var tmpIdsToNewCss = {};
 var supportedCss = [
     'background-color',
     'border', 'border-top', 'border-right', 'border-bottom', 'border-left',
-    'color', 'font', 'font-size', 'font-weight', 'font-family',
+    'color', 'font-size', 'font-weight', 'font-family',
     'letter-spacing', 'line-height', 'float',
     'list-style', 'outline',
     'padding', 'quotes',
     'text-decoration', 'text-transform', 'word-spacing',
 ];
+// MM: removed "'font', " as font is shorthand of font-size, font-weight, font-family and computed style is redundant otherwise...
+
 //////
 
 function getImageSrc(srcTxt) {

From e065c7d75c9c5f230fdf8b0214cec1937cbec2aa Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 15 Feb 2019 23:27:29 +0100
Subject: [PATCH 19/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 11 ++++++++---
 1 file changed, 8 insertions(+), 3 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index bc70db1..3a9a3d2 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -140,7 +140,6 @@ Name: Golem.de News
 URL Regex: golem\.de\/news
 -------------------------------- */
 body {
-  font: initial !important;
   font-family: initial !important;
   color: #010101 !important;  /* default text almost black for better readability */
 }
@@ -149,11 +148,18 @@ article {
 	padding: 0 0 0 0 !important; 
 }
 
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should 
+   use font of ebook readers choice */
+{
+  font-family: initial !important;
+}
+
+
 #screen > div {  /* main article, screen > div.g.g6 */
   float: none;	
 }
 
-
 /* remove everything except plain article */
 .toc, .tags,
 .social-tools, .social-tools--inverted,
@@ -166,7 +172,6 @@ article {
 }
 
 
-
 /* -----------------------------
 Name: Wikipedia Article
 URL Regex: wikipedia\.org\/(wiki|w)\/

From 8b5f958f39c182023171fb760e1d2ee938db4bb0 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Sat, 16 Feb 2019 00:05:23 +0100
Subject: [PATCH 20/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 3a9a3d2..84439c2 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -55,7 +55,6 @@ body>footer, article>footer,
 }
 
 
-
 /* -----------------------------
 Name: Telepolis
 URL Regex: heise\.de\/tp
@@ -66,14 +65,21 @@ body {
   color: #010101 !important;  /* default text almost black for better readability */
 }
 
-main {
+main,
+.container,
+.row_tp_content  {
 	padding: 0 0 0 0 !important; 
 }
 
+.img-responsive, .aufmacherbild {
+	width: 100% !important;
+}
+
 /* remove everything except plain article */
-a-analytics,
+a-analytics, nav
 body>footer,
 .ho-roof, .tp_mainheader, 
+.pre-akwa-toc,
 .navbar, .nav, .navbar-nav,
 .tp_breadcrumb, .subnavi, 
 aside, article>footer,

From 7db15ac65a057a88fe56253b61fe1043b7f579f6 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Tue, 19 Feb 2019 14:26:03 +0100
Subject: [PATCH 21/50] keeping some attributes of tags (e.g. colspan)

...useful to retain table layouts as these are not covered with CSS.
---
 web-extension/extractHtml.js | 15 +++++++++++----
 1 file changed, 11 insertions(+), 4 deletions(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index d1fec47..f18b08c 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -23,14 +23,12 @@ var tmpIdsToNewCss = {};
 var supportedCss = [
     'background-color',
     'border', 'border-top', 'border-right', 'border-bottom', 'border-left',
-    'color', 'font-size', 'font-weight', 'font-family',
+    'color', 'font', 'font-size', 'font-weight', 'font-family',
     'letter-spacing', 'line-height', 'float',
     'list-style', 'outline',
     'padding', 'quotes',
-    'text-decoration', 'text-transform', 'word-spacing',
+    'text-decoration', 'text-transform', 'word-spacing'
 ];
-// MM: removed "'font', " as font is shorthand of font-size, font-weight, font-family and computed style is redundant otherwise...
-
 //////
 
 function getImageSrc(srcTxt) {
@@ -259,6 +257,15 @@ function sanitize(rawContentString) {
                             tmpAttrsTxt += ' class="' + attrs[i].value + '"';
                         }
                     }
+					// +++ MM: some more extras like colspan ...
+					var extraAttrs = [ 'colspan', 'title', 'lang', 'span', 'name' ]; 
+					for (var i = 0; i < attrs.length; i++) {						
+                        if (extraAttrs.indexOf( attrs[i].name ) != -1 ) {
+                          tmpAttrsTxt += ' '+attrs[i].name+'="' + attrs[i].value + '"'  ; 
+                        }
+                    }					
+					// +++ MM: end extras...
+					////
                     lastFragment = '<' + tag + ' ' + tmpAttrsTxt + '>';
                 }
 

From 90b53fc7b6b58a28688d0c9660c24319d9b02056 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Tue, 19 Feb 2019 15:37:28 +0100
Subject: [PATCH 22/50] allowing empty  elems.

... to retain table formatting.
---
 web-extension/extractHtml.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index f18b08c..8c4f4b7 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -107,7 +107,7 @@ function preProcess($htmlObject) {
     extractCanvasToImg($htmlObject);
     extractSvgToImg($htmlObject);
     $htmlObject.find('script, style, noscript, iframe').remove();
-    $htmlObject.find('*:empty').not('img').not('br').not('hr').remove();
+    $htmlObject.find('*:empty').not('td').not('img').not('br').not('hr').remove();  //MM: added  important for tables...
     formatPreCodeElements($htmlObject);
 }
 

From 7e098a9e12a837a562d2ccc33e95c2a3350d3fe5 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Wed, 20 Feb 2019 02:13:48 +0100
Subject: [PATCH 23/50] added css border-collapse

---
 web-extension/extractHtml.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index 8c4f4b7..f8160d1 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -22,7 +22,7 @@ var tmpIdsToNewCss = {};
 // src: https://idpf.github.io/a11y-guidelines/content/style/reference.html
 var supportedCss = [
     'background-color',
-    'border', 'border-top', 'border-right', 'border-bottom', 'border-left',
+    'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse',
     'color', 'font', 'font-size', 'font-weight', 'font-family',
     'letter-spacing', 'line-height', 'float',
     'list-style', 'outline',

From 592304ead0714ce761bcdf5ef475f93373d5873e Mon Sep 17 00:00:00 2001
From: Michael 
Date: Wed, 20 Feb 2019 10:38:07 +0100
Subject: [PATCH 24/50] Update AdditionalCSSstyles_MM.css

---
 AdditionalCSSstyles_MM.css | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/AdditionalCSSstyles_MM.css b/AdditionalCSSstyles_MM.css
index 84439c2..c54519c 100644
--- a/AdditionalCSSstyles_MM.css
+++ b/AdditionalCSSstyles_MM.css
@@ -171,7 +171,7 @@ p:not([class]), p[class=""]
 .social-tools, .social-tools--inverted,
 .supplementary, .narando,
 #narando-placeholder, #gservices,
-#screen > div ~ div, /* all Divs following main article... */
+#screen > div.g6 ~ div, /* all Divs following main article... */
 .iq-site-header, footer
 {
  display:none !important;	

From 47d8afd76698ba1bbbca9b02977aab937d5de382 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Wed, 20 Feb 2019 12:40:54 +0100
Subject: [PATCH 25/50] first config for ModHeader

---
 ModHeader-config-MM.txt | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)
 create mode 100644 ModHeader-config-MM.txt

diff --git a/ModHeader-config-MM.txt b/ModHeader-config-MM.txt
new file mode 100644
index 0000000..dd6b32b
--- /dev/null
+++ b/ModHeader-config-MM.txt
@@ -0,0 +1,18 @@
+TODO: could be a second readme ;-)
+
+Background: eBooks/ePub currently do not display images in WebP format. 
+Websites may send optimized images to the browser, as Chrome sends HTTP requests accepting image/webp, this will 
+even return WebP if a .jpg URL is requested.
+
+ModHeader is an extension which compensates this. Activate this and produce correct/better ebooks with "save-as-ebook".
+Unfortunately, there is not direct option to change Chrome's behavior.
+
+Source:
+   ModHeader, Chrome extension.
+   https://chrome.google.com/webstore/detail/modheader/idgpnmonknjnojddfkpgkljpfnnfcklj
+   https://mod-header.appspot.com
+
+Exported Config for ModHeader:
+
+{"title":"Real png/jpg/gif, NOT WebP","hideComment":true,"headers":[{"enabled":true,"name":"Accept","value":"image/png, image/jpeg, image/gif","comment":""}],"respHeaders":[],"filters":[{"enabled":true,"type":"urls","urlPattern":"*.jpg"},{"enabled":true,"type":"urls","urlPattern":"*.jpeg"},{"enabled":true,"type":"urls","urlPattern":"*.png"},{"enabled":true,"type":"urls","urlPattern":"*.gif"},{"enabled":true,"type":"urls","urlPattern":"*.JPEG"},{"enabled":true,"type":"urls","urlPattern":"*.JPG"},{"enabled":true,"type":"urls","urlPattern":"*.GIF"},{"enabled":true,"type":"urls","urlPattern":"*.PNG"}],"appendMode":""}
+

From 0a435c136aea1d2d3193ea66ae4c98a1ba341bb1 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Wed, 20 Feb 2019 12:46:56 +0100
Subject: [PATCH 26/50] Update README.md

---
 README.md | 16 ++++++++++++++--
 1 file changed, 14 insertions(+), 2 deletions(-)

diff --git a/README.md b/README.md
index 5cc03c8..8bdc3ba 100644
--- a/README.md
+++ b/README.md
@@ -1,13 +1,25 @@
 # save-as-ebook
 
-Save a web page/selection as an eBook (.epub format) - a Chrome/Firefox/Opera Web Extension
-
 
 
 ![alt ex2.png](https://github.com/alexadam/save-as-ebook/blob/master/ex2.png?raw=true)
 
 ![alt ex3.png](https://github.com/alexadam/save-as-ebook/blob/master/ex3.png?raw=true)
 
+## About this fork of the project:
+This is a fork with (currently) the following improvements:
+- leverage ModHeader extension: ensure, images in the ePub are in accepted formats, not WebP images.
+- additional CSS per sites
+- corrections in extractHTML.js:
+- additional tags, attributes, css values to generate better results.
+- generated css class names are now more descriptive to ease debugging (and calibre post-processing)
+- foster reuse in CSS styles to generate smaller files (not perfect)
+- some bug fixes around syntax highlighted 
 and  environments
+- some fixes for HTML tables
+- and some more, see commit history for now ;-) 
+
+Save a web page/selection as an eBook (.epub format) - a Chrome/Firefox/Opera Web Extension
+
 ## How to install it
 
 ### From [Chrome Web Store](https://chrome.google.com/webstore/detail/save-as-ebook/haaplkpoiimngbppjihnegfmpejdnffj)

From 9e7f8f0649e83c931bba53c7a205dd41756c4bc1 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Wed, 20 Feb 2019 12:48:05 +0100
Subject: [PATCH 27/50] Update ModHeader-config-MM.txt

---
 ModHeader-config-MM.txt | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ModHeader-config-MM.txt b/ModHeader-config-MM.txt
index dd6b32b..0f80f56 100644
--- a/ModHeader-config-MM.txt
+++ b/ModHeader-config-MM.txt
@@ -12,7 +12,7 @@ Source:
    https://chrome.google.com/webstore/detail/modheader/idgpnmonknjnojddfkpgkljpfnnfcklj
    https://mod-header.appspot.com
 
-Exported Config for ModHeader:
+Exported Config for ModHeader (copy/paste this line in the import profile box):
 
 {"title":"Real png/jpg/gif, NOT WebP","hideComment":true,"headers":[{"enabled":true,"name":"Accept","value":"image/png, image/jpeg, image/gif","comment":""}],"respHeaders":[],"filters":[{"enabled":true,"type":"urls","urlPattern":"*.jpg"},{"enabled":true,"type":"urls","urlPattern":"*.jpeg"},{"enabled":true,"type":"urls","urlPattern":"*.png"},{"enabled":true,"type":"urls","urlPattern":"*.gif"},{"enabled":true,"type":"urls","urlPattern":"*.JPEG"},{"enabled":true,"type":"urls","urlPattern":"*.JPG"},{"enabled":true,"type":"urls","urlPattern":"*.GIF"},{"enabled":true,"type":"urls","urlPattern":"*.PNG"}],"appendMode":""}
 

From 978055201dd1d282703c658a0ae2b528552acd8c Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 21 Feb 2019 21:28:02 +0100
Subject: [PATCH 28/50] remove redundant style rules

..check if parent node has exact same values..
---
 web-extension/extractHtml.js | 15 ++++++++++-----
 1 file changed, 10 insertions(+), 5 deletions(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index f8160d1..865bd26 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -393,14 +393,19 @@ function extractCss(includeStyle, appliedStyles) {
                     tmpName = classNames; // MM:  tmpName = 'class-' + Math.floor(Math.random()*100000);
                     cssClassesToTmpIds[classNames] = tmpName;
                 }
-                if (!tmpNewCss) {// MM: hack: take last or inner elements...... if (true) { 
+                if (!tmpNewCss) {
                     // var style = window.getComputedStyle(pre);
                     tmpNewCss = {};
-                    for (let cssTagName of supportedCss) {
+                    for (let cssTagName of supportedCss) {						
                         let cssValue = $pre.css(cssTagName);
-                        if (cssValue && cssValue.length > 0) {
-                            tmpNewCss[cssTagName] = cssValue;
-                        }
+						// MM: little hack: might not be perfect, but just takes rules different from (current) parent.
+						// might produce better results in most cases
+					    if (pre.parentNode) { 
+							cssValueParent = $(pre.parentNode).css(cssTagName);
+						}												
+						if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) {
+							tmpNewCss[cssTagName] = cssValue;
+						}						
                     }
                     tmpIdsToNewCss[tmpName] = tmpNewCss;
                 }

From aa3e788708357cd2b0b8106e4a23150a40bc3a62 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 21 Feb 2019 21:53:39 +0100
Subject: [PATCH 29/50] Update extractHtml.js

---
 web-extension/extractHtml.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js
index 865bd26..bb1228e 100644
--- a/web-extension/extractHtml.js
+++ b/web-extension/extractHtml.js
@@ -26,7 +26,7 @@ var supportedCss = [
     'color', 'font', 'font-size', 'font-weight', 'font-family',
     'letter-spacing', 'line-height', 'float',
     'list-style', 'outline',
-    'padding', 'quotes',
+    'padding', 'quotes', 'text-align', 'text-justify', 'hyphens',
     'text-decoration', 'text-transform', 'word-spacing'
 ];
 //////

From c68856e932c5a4948ebb15051515ae5d2fea7a93 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 21 Feb 2019 22:36:32 +0100
Subject: [PATCH 30/50] additional Userscripts

e.g. to use with Tampermonkey.
Pre-Processing for cleaner output with save-as-ebook
---
 userscripts/Golem.de.user.js                  |  66 +++++++++++
 ...Heise News (inkl TechnologyReview).user.js | 112 ++++++++++++++++++
 userscripts/Telepolis (Heise).user.js         |  70 +++++++++++
 userscripts/Wikipedia.user.js                 |  66 +++++++++++
 userscripts/sqlbi.com.user.js                 |  60 ++++++++++
 5 files changed, 374 insertions(+)
 create mode 100644 userscripts/Golem.de.user.js
 create mode 100644 userscripts/Heise News (inkl TechnologyReview).user.js
 create mode 100644 userscripts/Telepolis (Heise).user.js
 create mode 100644 userscripts/Wikipedia.user.js
 create mode 100644 userscripts/sqlbi.com.user.js

diff --git a/userscripts/Golem.de.user.js b/userscripts/Golem.de.user.js
new file mode 100644
index 0000000..80312e9
--- /dev/null
+++ b/userscripts/Golem.de.user.js
@@ -0,0 +1,66 @@
+// ==UserScript==
+// @name         Golem.de
+// @version      0.1
+// @description  IT news and articles
+// @author       M.M.
+// @include      *.golem.de/news/*
+// @exclude      *.golem.de/news
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Golem.de News
+URL Regex: golem\.de\/news
+-------------------------------- */
+body {
+  /* TODO: Removing default font so Kindle user can select needs to be done in js and/or save-as-ebook or calibre
+  font-family: initial !important;
+  */
+  color: #010101 !important;  /* default text almost black for better readability */
+  padding: 10px !important;
+}
+
+article {
+	padding: 0 0 0 0 !important;
+}
+
+body, p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  /* font-family: initial !important; */
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+
+
+#screen > div {  /* main article, screen > div.g.g6 */
+  float: none;
+}
+
+/* remove everything except plain article */
+.toc, .tags,
+.social-tools, .social-tools--inverted,
+.supplementary, .narando,
+#narando-placeholder, #gservices,
+#screen > div.g6 ~ div, /* all Divs following main article... */
+.iq-site-header, footer
+{
+ display:none !important;
+}
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
diff --git a/userscripts/Heise News (inkl TechnologyReview).user.js b/userscripts/Heise News (inkl TechnologyReview).user.js
new file mode 100644
index 0000000..61d8089
--- /dev/null
+++ b/userscripts/Heise News (inkl TechnologyReview).user.js	
@@ -0,0 +1,112 @@
+// ==UserScript==
+// @name         Heise News (inkl TechnologyReview)
+// @version      1.0
+// @description  Heise News - IT articles...
+// @author       M.M.
+// @include      *.heise.de/newsticker/*
+// @include      *.heise.de/hintergrund/*
+// @include      *.heise.de/developer/*
+// @include      *.heise.de/ratgeber/*
+// @include      *.heise.de/security/*
+// @include      *.heise.de/autos/*
+// @include      *.heise.de/make/*
+// @include      *.heise.de/tr/artikel/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Heise News
+URL Regex: heise\.de\/(newsticker|hintergrund|developer)
+-------------------------------- */
+body {
+  /* TODO: Removing default font so Kindle user can select needs to be done in js and/or save-as-ebook or calibre
+  font-family: initial !important;
+  */
+  color: #010101 !important;  /* default text almost black for better readability */
+  margin: 25px;
+  background-color: white;
+}
+
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  /* font-family: initial !important; */
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+
+/* TODO: Text color article-content>p  */
+
+main {
+	padding: 0 0 0 0 !important;
+}
+
+#container, #container_content, #mitte {
+  width: 100% !important;
+  min-width: 0px;
+  min-height: 0px;
+  margin: 1px;
+  padding: 10px;
+}
+
+#mitte_links {
+   width: 95% !important;
+}
+
+div#container{
+	 margin: 1px 1px 1px 1px;
+     padding-bottom: 0px;
+}
+
+span.initial {  /* Drop caps */
+   float: left;
+      font-weight:normal;
+      font-size:320%  !important;
+      float:left  !important;
+      margin-top:-0.3225em  !important;
+      margin-bottom:-0.3245em  !important;
+  font-stretch: normal;
+}
+
+/* remove everything except plain article */
+a-analytics,
+body>footer, header>nav,
+#cboxOverlay, #colorbox, #sitemap,
+#navi_bottom, #breadcrumb_subnav, #mitte-rechts,
+#tr-header, .shariff,
+.header-main__content,
+.header-main, .main-header, .breadcrumb,
+.pre-akwa-toc, .a-button,
+.topnavigation, .ad-container,
+ /* keep "Kommentare"-Button */
+ /* article>footer, .article-layout__footer, */
+ /* keep paginating:  .seitenweise_navigation, .paginiert */
+.navbar-nav,
+.article-sidebar, .article-actions,
+.ho-stage-container, .bottom_up,
+.main-footer, .printversion--hide,
+.mheise--preisvergleich-banner,
+.btn-toolbar, .themenseiten,
+aside
+{
+   display: none !important;
+   width: 0% !important;
+}
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/Telepolis (Heise).user.js b/userscripts/Telepolis (Heise).user.js
new file mode 100644
index 0000000..0e1c41c
--- /dev/null
+++ b/userscripts/Telepolis (Heise).user.js	
@@ -0,0 +1,70 @@
+// ==UserScript==
+// @name         Telepolis (Heise)
+// @version      0.1
+// @description  Heise Select (iX and others). eBook stylesheet and a better image quality.
+// @author       M.M.
+// @include      *.heise.de/tp/*
+// @exclude      *.heise.de/tp/
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Telepolis
+URL Regex: heise\.de\/tp
+-------------------------------- */
+body {
+  font: initial !important;
+  font-family: initial !important;
+  color: #010101 !important;  /* default text almost black for better readability */
+  margin: 25px;
+  background-color: white;
+}
+
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  font-family: initial !important;
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+
+main,
+.container,
+.row_tp_content  {
+	padding: 0 0 0 0 !important;
+}
+
+.img-responsive, .aufmacherbild {
+	width: 100% !important;
+}
+
+/* remove everything except plain article */
+a-analytics, nav
+body>footer,
+.ho-roof, .tp_mainheader,
+.pre-akwa-toc,
+.navbar, .nav, .navbar-nav,
+.tp_breadcrumb, .subnavi,
+aside, article>footer,
+.printversion--hide
+{
+   display: none !important;
+}
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/Wikipedia.user.js b/userscripts/Wikipedia.user.js
new file mode 100644
index 0000000..d73af6e
--- /dev/null
+++ b/userscripts/Wikipedia.user.js
@@ -0,0 +1,66 @@
+// ==UserScript==
+// @name         Wikipedia
+// @version      0.1
+// @description  Strip stuff from Wikipedia Articles.
+// @author       M.M.
+// @include      *.wikipedia.org/wiki/*
+// @include      *.wikipedia.org/w/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Wikipedia Article
+URL Regex: wikipedia\.org\/(wiki|w)\/
+Additional trick: Login and personalize "Appearance" to
+ show thubnails with 400px instead of 200px
+-------------------------------- */
+
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+.toc , .toc-mobile,
+.mw-jump-link,
+.mw-editsection,
+.navigation-drawer, .navbox, .catlinks,
+.header-container, .minerva-footer,
+#footer, #mw-panel, #mw-head,
+#mw-navigation,
+#page-actions {
+  display: none !important;
+}
+
+.mw-body {
+    margin-left: 0px !important;
+	border-style: none !important;
+}
+
+.noprint, .cnotice {
+   display: none !important;
+}
+ul {
+  padding: 20px !important;
+  list-style-type: square !important;
+  list-style-image: none  !important;
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/sqlbi.com.user.js b/userscripts/sqlbi.com.user.js
new file mode 100644
index 0000000..e00284e
--- /dev/null
+++ b/userscripts/sqlbi.com.user.js
@@ -0,0 +1,60 @@
+// ==UserScript==
+// @name         sqlbi.com
+// @version      0.1
+// @description  sqlbi - articles and blog entries about DAX and PowerBI.
+// @author       M.M.
+// @include      https://*.sqlbi.com/articles/*
+// @include      https://*.sqlbi.com/blog/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: sqlbi.com
+URL Regex: sqlbi\.com\/(articles|blog)
+-------------------------------- */
+
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  /* font-family: initial !important; */
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+main {
+  width: 100% !important;
+}
+
+body>header, footer, aside,
+.download, .sharing,
+.connect, .breadcrumb  {
+ display:none !important;
+}
+
+
+.content-wrapper, .entry-content, body {
+    padding: 1px 0 0 0;
+    color: #010101;  /* default text almost black for better readability */
+}
+
+body {
+    padding: 4px !important;
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+

From e6bc34b5648b2651d46948e7aea90b5443f15d57 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 22 Feb 2019 19:18:08 +0100
Subject: [PATCH 31/50] Add files via upload

---
 userscripts/WhatsApp.user.js | 39 ++++++++++++++++++++++++++++++++++++
 1 file changed, 39 insertions(+)
 create mode 100644 userscripts/WhatsApp.user.js

diff --git a/userscripts/WhatsApp.user.js b/userscripts/WhatsApp.user.js
new file mode 100644
index 0000000..8e187d7
--- /dev/null
+++ b/userscripts/WhatsApp.user.js
@@ -0,0 +1,39 @@
+// ==UserScript==
+// @name         WhatsApp
+// @version      0.1
+// @description  IT news and articles
+// @author       M.M.
+// @include      *web.whatsapp.com*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: WhatsApp
+URL *web.whatsapp.com*
+-------------------------------- */
+
+/* Chat background */
+div#main > div {
+ background-color: rgb(245,250,252) !important;
+}
+
+div.message-out {
+ background-color: rgb(220,242,250) !important;
+}
+
+.message-in {
+ /*  background-color: rgb(197, 247, 255) !important; */
+  background-color: rgb(191, 233, 249) !important;
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+

From b7c446759e1d166df0b0647feb9cb9c5c1ca376f Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 22 Feb 2019 20:18:01 +0100
Subject: [PATCH 32/50] Update WhatsApp.user.js

---
 userscripts/WhatsApp.user.js | 17 ++++++++++++++---
 1 file changed, 14 insertions(+), 3 deletions(-)

diff --git a/userscripts/WhatsApp.user.js b/userscripts/WhatsApp.user.js
index 8e187d7..60cc453 100644
--- a/userscripts/WhatsApp.user.js
+++ b/userscripts/WhatsApp.user.js
@@ -28,12 +28,23 @@ div.message-out {
  background-color: rgb(220,242,250) !important;
 }
 
-.message-in {
- /*  background-color: rgb(197, 247, 255) !important; */
+
+._12xX7, ._2nFG1, ._1sGGp  {
+  background-color: rgb(210,232,240) !important;
+}
+
+
+div.message-in {
   background-color: rgb(191, 233, 249) !important;
 }
 
+
+/* Preview box of links */
+._2nFG1, ._2lwig {
+  background-color: rgb(181, 223, 239) !important;
+}
+
+
 `;
 document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
 
-

From ada36c9091ed8eaaf67530bc474a56ddb5030699 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 22 Feb 2019 22:20:00 +0100
Subject: [PATCH 33/50] Update Heise News (inkl TechnologyReview).user.js

---
 ...Heise News (inkl TechnologyReview).user.js | 21 ++++++++++++-------
 1 file changed, 14 insertions(+), 7 deletions(-)

diff --git a/userscripts/Heise News (inkl TechnologyReview).user.js b/userscripts/Heise News (inkl TechnologyReview).user.js
index 61d8089..f9d9e2a 100644
--- a/userscripts/Heise News (inkl TechnologyReview).user.js	
+++ b/userscripts/Heise News (inkl TechnologyReview).user.js	
@@ -25,12 +25,12 @@ myCSS.innerHTML = `
 Name: Heise News
 URL Regex: heise\.de\/(newsticker|hintergrund|developer)
 -------------------------------- */
-body {
+body, .article-page {
   /* TODO: Removing default font so Kindle user can select needs to be done in js and/or save-as-ebook or calibre
   font-family: initial !important;
   */
   color: #010101 !important;  /* default text almost black for better readability */
-  margin: 25px;
+  padding: 25px !important;
   background-color: white;
 }
 
@@ -58,8 +58,17 @@ main {
   width: 100% !important;
   min-width: 0px;
   min-height: 0px;
-  margin: 1px;
-  padding: 10px;
+  margin: 0px;
+  padding: 0px;
+}
+
+.article-layout__content, .article-header {
+    min-width: 100% !important;
+}
+
+.article-image__img, .article-image, .article-layout {
+  width: 100%;
+  margin: 0px;
 }
 
 #mitte_links {
@@ -68,6 +77,7 @@ main {
 
 div#container{
 	 margin: 1px 1px 1px 1px;
+     max-width: 100% !important;
      padding-bottom: 0px;
 }
 
@@ -107,6 +117,3 @@ aside
 }
 `;
 document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
-
-
-

From 9a4d21103407d03312106546f5108cd29c1ba1f8 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Fri, 22 Feb 2019 22:20:24 +0100
Subject: [PATCH 34/50] Update Golem.de.user.js

---
 userscripts/Golem.de.user.js | 20 ++++++++++----------
 1 file changed, 10 insertions(+), 10 deletions(-)

diff --git a/userscripts/Golem.de.user.js b/userscripts/Golem.de.user.js
index 80312e9..2d7d526 100644
--- a/userscripts/Golem.de.user.js
+++ b/userscripts/Golem.de.user.js
@@ -19,19 +19,21 @@ myCSS.innerHTML = `
 Name: Golem.de News
 URL Regex: golem\.de\/news
 -------------------------------- */
-body {
-  /* TODO: Removing default font so Kindle user can select needs to be done in js and/or save-as-ebook or calibre
-  font-family: initial !important;
-  */
+body.article {
   color: #010101 !important;  /* default text almost black for better readability */
-  padding: 10px !important;
+  padding: 20px !important;
 }
 
-article {
-	padding: 0 0 0 0 !important;
+article,
+div#grandwrapper, #screen, #header,
+#footer, div.g6 {
+  padding: 0px !important;
+  margin: 0px !important;
+  border-width: none !important;
+  width: 100% !important;
 }
 
-body, p:not([class]), p[class=""]
+p:not([class]), p[class=""]
 /* All paragraphs without specific formatting should
    use font of ebook readers choice */
 {
@@ -44,8 +46,6 @@ body, p:not([class]), p[class=""]
    hyphens: auto;
 }
 
-
-
 #screen > div {  /* main article, screen > div.g.g6 */
   float: none;
 }

From b79b20cbb8fd3b83bad15355c882c22b5593a9b8 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Mon, 25 Feb 2019 19:33:17 +0100
Subject: [PATCH 35/50] Add files via upload

---
 userscripts/Chris Webb's BI Blog.user.js      |  94 ++++++++++++++++
 userscripts/PowerPivotPro.user.js             | 103 ++++++++++++++++++
 userscripts/Telepolis (Heise).user.js         |   9 +-
 userscripts/WhatsApp.user.js                  |   1 +
 .../sqlbi.com & daxpatterns.com.user.js       |  73 +++++++++++++
 5 files changed, 275 insertions(+), 5 deletions(-)
 create mode 100644 userscripts/Chris Webb's BI Blog.user.js
 create mode 100644 userscripts/PowerPivotPro.user.js
 create mode 100644 userscripts/sqlbi.com & daxpatterns.com.user.js

diff --git a/userscripts/Chris Webb's BI Blog.user.js b/userscripts/Chris Webb's BI Blog.user.js
new file mode 100644
index 0000000..fb95313
--- /dev/null
+++ b/userscripts/Chris Webb's BI Blog.user.js	
@@ -0,0 +1,94 @@
+// ==UserScript==
+// @name         Chris Webb's BI Blog
+// @version      0.2
+// @description  Power BI, Power Query and DAX related posts
+// @author       M.M.
+// @include      https://blog.crossjoin.co.uk/*/*/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+/* probably valid for most wordpress blogs? */
+// Test with:    https://prathy.com/2019/02/sync-slicers-sync-slicers-advanced-options/
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Chris Webb's BI Blog
+URL Regex: https://blog.crossjoin.co.uk/*
+-------------------------------- */
+
+header#branding, footer#colophon,
+div#secondary, div#actionbar,
+div.sd-social, div.sharedaddy,
+.post-format-icon,
+article ~ * {
+ display:none !important;
+}
+
+#page, #primary {
+  width: 100% !important;
+  max-width: 100% !important;
+  padding: 0px !important;
+  margin: 0px !important;
+  border: none;
+
+}
+
+#page:before, #page:after { /* remove box-shadow of page... */
+   display:none !important;
+}
+
+#content, .entry-title, .post-content, #content .post {
+  margin: 0px !important;
+  padding: 0px !important;
+}
+
+.entry-meta {
+  position: relative;
+  width: 100%;
+  top: 0px;
+}
+
+.syntaxhighlighter table td.gutter .line {
+    text-align: left !important;  /* line numbers in Code snippets... */
+}
+
+.entry-meta .entry-date, .entry-meta .byline, .entry-meta .entry-categories,
+.entry-meta .entry-tags, .entry-meta .edit-link, .entry-meta .comments-link,
+.entry-meta .image-info {
+    text-align: left  !important;
+}
+
+img {
+  align: center;
+}
+
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+p:not([class]), p[class=""]
+{
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+body {
+    padding: 15px !important;
+    background: none;
+    background-color: white;
+    color: #010101;  /* default text almost black for better readability */
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/PowerPivotPro.user.js b/userscripts/PowerPivotPro.user.js
new file mode 100644
index 0000000..5418a99
--- /dev/null
+++ b/userscripts/PowerPivotPro.user.js
@@ -0,0 +1,103 @@
+// ==UserScript==
+// @name         PowerPivotPro
+// @version      0.1
+// @description  Power BI, Power Query and DAX related posts
+// @author       M.M.
+// @include      https://powerpivotpro.com/*/*/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+/* probably again a wordpress based blog? */
+
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Chris Webb's BI Blog
+URL Regex: https://blog.crossjoin.co.uk/*
+-------------------------------- */
+
+header#branding, footer#colophon,
+div#secondary, div#actionbar,
+div.sd-social, div.sharedaddy,
+.post-format-icon,
+article ~ *,
+div#wpex-mobile-menu-fixed-top,
+div.post-pagination-wrap,
+div#footer-inner, div#respond,
+header#site-header, aside#sidebar,
+#top-bar, .wpex-social-share {
+ display:none !important;
+}
+
+#page, #primary {
+  width: 100% !important;
+  max-width: 100% !important;
+  padding: 0px !important;
+  margin: 0px !important;
+  border: none;
+
+}
+
+#page:before, #page:after { /* remove box-shadow of page... */
+   display:none !important;
+}
+
+#content, .entry-title, .post-content, #content .post {
+  margin: 0px !important;
+  padding: 0px !important;
+}
+
+.content-area {
+  float: none;
+}
+
+.entry-meta {
+  position: relative;
+  width: 100%;
+  top: 0px;
+}
+
+.syntaxhighlighter table td.gutter .line {
+    text-align: left !important;  /* line numbers in Code snippets... */
+}
+
+.entry-meta .entry-date, .entry-meta .byline, .entry-meta .entry-categories,
+.entry-meta .entry-tags, .entry-meta .edit-link, .entry-meta .comments-link,
+.entry-meta .image-info {
+    text-align: left  !important;
+}
+
+img {
+  align: center;
+}
+
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+p:not([class]), p[class=""]
+{
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+body {
+    padding: 15px !important;
+    background: none;
+    background-color: white;
+    color: #010101;  /* default text almost black for better readability */
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/Telepolis (Heise).user.js b/userscripts/Telepolis (Heise).user.js
index 0e1c41c..67d662e 100644
--- a/userscripts/Telepolis (Heise).user.js	
+++ b/userscripts/Telepolis (Heise).user.js	
@@ -51,14 +51,13 @@ main,
 	width: 100% !important;
 }
 
-/* remove everything except plain article */
-a-analytics, nav
+/* remove everything except plain article  article>footer, .pre-akwa-toc,  */
+a-analytics,
 body>footer,
-.ho-roof, .tp_mainheader,
-.pre-akwa-toc,
+.ho-roof, .tp_mainheader, .shariff,
 .navbar, .nav, .navbar-nav,
 .tp_breadcrumb, .subnavi,
-aside, article>footer,
+aside, .seitenweise_navigation, .paginiert,
 .printversion--hide
 {
    display: none !important;
diff --git a/userscripts/WhatsApp.user.js b/userscripts/WhatsApp.user.js
index 60cc453..a723d24 100644
--- a/userscripts/WhatsApp.user.js
+++ b/userscripts/WhatsApp.user.js
@@ -48,3 +48,4 @@ div.message-in {
 `;
 document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
 
+
diff --git a/userscripts/sqlbi.com & daxpatterns.com.user.js b/userscripts/sqlbi.com & daxpatterns.com.user.js
new file mode 100644
index 0000000..898aef7
--- /dev/null
+++ b/userscripts/sqlbi.com & daxpatterns.com.user.js	
@@ -0,0 +1,73 @@
+// ==UserScript==
+// @name         sqlbi.com & daxpatterns.com
+// @version      0.2
+// @description  sqlbi - articles and blog entries about DAX and PowerBI.
+// @author       M.M.
+// @include      https://*.sqlbi.com/articles/*
+// @include      https://www.daxpatterns.com/*
+// @include      https://*.sqlbi.com/blog/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: sqlbi.com
+URL Regex: sqlbi\.com\/(articles|blog)
+-------------------------------- */
+
+p:not([class]), p[class=""]
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+{
+  /* font-family: initial !important; */
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+main {
+  width: 100% !important;
+}
+
+body>header, footer, aside,
+.download, .sharing,
+.connect, .breadcrumb,
+#disqus_thread, .comments-note {
+ display:none !important;
+}
+
+.syntaxhighlighter table td.gutter .line,
+.gutter .line {
+    text-align: left !important;  /* line numbers in Code snippets... */
+}
+
+.content-wrapper, .entry-content, .wrapper {
+    padding: 0px !important;
+    width: 100% !important;
+    max-width: 100% !important;
+}
+
+.entry-content {
+   float: none !important;
+}
+
+body {
+    padding: 15px !important;
+    background-color: white;
+    color: #010101;  /* default text almost black for better readability */
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+

From 35611bc4c9c7571547bfa9b54fe9c6bb0b222ee3 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Mon, 25 Feb 2019 19:34:36 +0100
Subject: [PATCH 36/50] Delete sqlbi.com.user.js

---
 userscripts/sqlbi.com.user.js | 60 -----------------------------------
 1 file changed, 60 deletions(-)
 delete mode 100644 userscripts/sqlbi.com.user.js

diff --git a/userscripts/sqlbi.com.user.js b/userscripts/sqlbi.com.user.js
deleted file mode 100644
index e00284e..0000000
--- a/userscripts/sqlbi.com.user.js
+++ /dev/null
@@ -1,60 +0,0 @@
-// ==UserScript==
-// @name         sqlbi.com
-// @version      0.1
-// @description  sqlbi - articles and blog entries about DAX and PowerBI.
-// @author       M.M.
-// @include      https://*.sqlbi.com/articles/*
-// @include      https://*.sqlbi.com/blog/*
-// @grant        none
-// ==/UserScript==
-
-'use strict';
-
-//// uncomment to debug:
-// debugger;
-
-var myCSS = window.document.createElement('style');
-myCSS.innerHTML = `
-/* -----------------------------
-Name: sqlbi.com
-URL Regex: sqlbi\.com\/(articles|blog)
--------------------------------- */
-
-p:not([class]), p[class=""]
-/* All paragraphs without specific formatting should
-   use font of ebook readers choice */
-{
-  /* font-family: initial !important; */
-  text-align: justify;
-  text-justify: inter-word;
-  -webkit-hyphens: auto;
-  -moz-hyphens: auto;
-  -ms-hyphens: auto;
-   hyphens: auto;
-}
-
-main {
-  width: 100% !important;
-}
-
-body>header, footer, aside,
-.download, .sharing,
-.connect, .breadcrumb  {
- display:none !important;
-}
-
-
-.content-wrapper, .entry-content, body {
-    padding: 1px 0 0 0;
-    color: #010101;  /* default text almost black for better readability */
-}
-
-body {
-    padding: 4px !important;
-}
-
-`;
-document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
-
-
-

From 7434ce8e1fb12b027215175fee3c25cf0a755592 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Mon, 25 Feb 2019 21:46:36 +0100
Subject: [PATCH 37/50] Add files via upload

---
 userscripts/Chris Webb's BI Blog.user.js |  4 --
 userscripts/Computerworld.ch.user.js     | 78 ++++++++++++++++++++++++
 userscripts/PowerPivotPro.user.js        |  4 --
 3 files changed, 78 insertions(+), 8 deletions(-)
 create mode 100644 userscripts/Computerworld.ch.user.js

diff --git a/userscripts/Chris Webb's BI Blog.user.js b/userscripts/Chris Webb's BI Blog.user.js
index fb95313..f162509 100644
--- a/userscripts/Chris Webb's BI Blog.user.js	
+++ b/userscripts/Chris Webb's BI Blog.user.js	
@@ -64,10 +64,6 @@ article ~ * {
     text-align: left  !important;
 }
 
-img {
-  align: center;
-}
-
 /* All paragraphs without specific formatting should
    use font of ebook readers choice */
 p:not([class]), p[class=""]
diff --git a/userscripts/Computerworld.ch.user.js b/userscripts/Computerworld.ch.user.js
new file mode 100644
index 0000000..fd0447a
--- /dev/null
+++ b/userscripts/Computerworld.ch.user.js
@@ -0,0 +1,78 @@
+// ==UserScript==
+// @name         Computerworld.ch
+// @version      0.1
+// @description  Computer News
+// @author       M.M.
+// @include      https://www.computerworld.ch/*/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+/* probably again a wordpress based blog? */
+
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Computerworld.ch
+URL: https://www.computerworld.ch
+-------------------------------- */
+
+nav#breadcrumb, script,
+div.autoren ~ div.row,
+div.dachleiste-mobil,
+div.container-themenleiste,
+div.container-themenleiste ~ *,
+header.header, div#sidebar,
+div#footer, div.wrapper-top,
+.navbar-collapse {
+ display:none !important;
+}
+
+div#content, div.col-xs-30,
+div#seite, div.row {
+  position: relative;
+  width: 100%;
+  max-width: 100% !important;
+  margin: 0px !important;
+  padding: 0px !important;
+  border: none;
+}
+
+div.col-xs-30 {
+  float: none;
+}
+
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+div.fliesstext,
+p:not([class]), p[class=""]
+{
+  text-align: justify;
+  text-justify: inter-word;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+div.fliesstext > * {
+ text-align: left;
+}
+
+body {
+    padding: 15px !important;
+    background: none;
+    background-color: white;
+    color: #010101;  /* default text almost black for better readability */
+}
+
+`;
+document.getElementsByTagName("HEAD")[0].appendChild(myCSS);
+
+
+
diff --git a/userscripts/PowerPivotPro.user.js b/userscripts/PowerPivotPro.user.js
index 5418a99..f9f9402 100644
--- a/userscripts/PowerPivotPro.user.js
+++ b/userscripts/PowerPivotPro.user.js
@@ -73,10 +73,6 @@ header#site-header, aside#sidebar,
     text-align: left  !important;
 }
 
-img {
-  align: center;
-}
-
 /* All paragraphs without specific formatting should
    use font of ebook readers choice */
 p:not([class]), p[class=""]

From 9ae9fe536f815ec46cffb7d082f1e358491ed225 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 28 Feb 2019 19:29:33 +0100
Subject: [PATCH 38/50] Rename Chris Webb's BI Blog.user.js to BI Blogs_ Chris
 Webb & Kasper On BI.user.js

---
 ...I Blog.user.js => BI Blogs_ Chris Webb & Kasper On BI.user.js} | 0
 1 file changed, 0 insertions(+), 0 deletions(-)
 rename userscripts/{Chris Webb's BI Blog.user.js => BI Blogs_ Chris Webb & Kasper On BI.user.js} (100%)

diff --git a/userscripts/Chris Webb's BI Blog.user.js b/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js
similarity index 100%
rename from userscripts/Chris Webb's BI Blog.user.js
rename to userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js

From 1ac0e6ec8a1c30eca9cef6759df4bbb221081311 Mon Sep 17 00:00:00 2001
From: Michael 
Date: Thu, 28 Feb 2019 19:30:44 +0100
Subject: [PATCH 39/50] Add files via upload

---
 ...I Blogs_ Chris Webb & Kasper On BI.user.js | 19 +++-
 userscripts/Gartner Reprints.user.js          | 79 +++++++++++++++++
 userscripts/Golem.de.user.js                  |  2 +-
 userscripts/HYPE Innovation Blog.user.js      | 81 +++++++++++++++++
 ...Heise News (inkl TechnologyReview).user.js |  3 +
 userscripts/LinkedIn Pulse.user.js            | 75 ++++++++++++++++
 userscripts/Microsoft Docs.user.js            | 86 +++++++++++++++++++
 userscripts/PowerPivotPro.user.js             |  4 +-
 .../sqlbi.com & daxpatterns.com.user.js       |  1 +
 9 files changed, 343 insertions(+), 7 deletions(-)
 create mode 100644 userscripts/Gartner Reprints.user.js
 create mode 100644 userscripts/HYPE Innovation Blog.user.js
 create mode 100644 userscripts/LinkedIn Pulse.user.js
 create mode 100644 userscripts/Microsoft Docs.user.js

diff --git a/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js b/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js
index f162509..53f1709 100644
--- a/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js	
+++ b/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js	
@@ -1,9 +1,11 @@
 // ==UserScript==
-// @name         Chris Webb's BI Blog
+// @name         BI Blogs: Chris Webb & Kasper On BI
 // @version      0.2
 // @description  Power BI, Power Query and DAX related posts
 // @author       M.M.
 // @include      https://blog.crossjoin.co.uk/*/*/*
+// @include      https://www.kasperonbi.com/*/*
+// @exclude      https://www.kasperonbi.com/page/*
 // @grant        none
 // ==/UserScript==
 
@@ -18,14 +20,17 @@
 var myCSS = window.document.createElement('style');
 myCSS.innerHTML = `
 /* -----------------------------
-Name: Chris Webb's BI Blog
-URL Regex: https://blog.crossjoin.co.uk/*
+Name: BI Blogs: Chris Webb & Kasper On BI
+URL: https://blog.crossjoin.co.uk/...
+URL2: https://www.kasperonbi.com/...
 -------------------------------- */
 
 header#branding, footer#colophon,
+aside#mobile-header,
 div#secondary, div#actionbar,
+div.main-navbar, div.header-top,
 div.sd-social, div.sharedaddy,
-.post-format-icon,
+.post-format-icon, .screen-reader-text,
 article ~ * {
  display:none !important;
 }
@@ -43,6 +48,12 @@ article ~ * {
    display:none !important;
 }
 
+div.content-area {
+  float: none !important;
+  margin: 0px !important;
+  padding: 0px !important;
+}
+
 #content, .entry-title, .post-content, #content .post {
   margin: 0px !important;
   padding: 0px !important;
diff --git a/userscripts/Gartner Reprints.user.js b/userscripts/Gartner Reprints.user.js
new file mode 100644
index 0000000..13138b2
--- /dev/null
+++ b/userscripts/Gartner Reprints.user.js	
@@ -0,0 +1,79 @@
+// ==UserScript==
+// @name         Gartner Reprints
+// @version      0.1
+// @description  Gartner Magic Quadrants etc.
+// @author       M.M.
+// @include      https://www.gartner.com/doc/*
+// @grant        none
+// ==/UserScript==
+
+'use strict';
+
+//// uncomment to debug:
+// debugger;
+
+var myCSS = window.document.createElement('style');
+myCSS.innerHTML = `
+/* -----------------------------
+Name: Gartner reprints
+URL: https://www.gartner.com/doc/
+-------------------------------- */
+
+div.reprint-section > div:not(.content-section),
+div.disclaimer > div:not(.content-section),
+button[aria-label="View Columns"],
+div.footer-reprint,
+div.container, div.prms,
+div.right-rail {
+  display:none !important;
+}
+
+.content-section {
+  position: relative;
+  float: none !important;
+  margin: 0px !important;
+  padding: 0px !important;
+  width: 100% !important;
+  max-width: 100% !important;
+  flex-basis: 100% !important;
+  top: 0px;
+  border: none;
+  text-align: left !important;  /* line numbers in Code snippets... */
+}
+
+/* All paragraphs without specific formatting should
+   use font of ebook readers choice */
+div.summary,
+div.disclaimer > div.content-section,
+div.para, p:not([class]), p[class=""]
+{
+  text-align: justify !important;
+  text-justify: inter-word !important;
+  -webkit-hyphens: auto;
+  -moz-hyphens: auto;
+  -ms-hyphens: auto;
+   hyphens: auto;
+}
+
+/* fix/emulate 
  • :before */ +ul.bullets-yes>li { + list-style-type: square !important; +} + +/* fix: little svg buttons, not needed in epub/print */ +svg, .enlarge-table{ + display:none !important; +} + +body { + padding: 15px !important; + background: none; + background-color: white; + color: #010101; /* default text almost black for better readability */ +} + +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + + diff --git a/userscripts/Golem.de.user.js b/userscripts/Golem.de.user.js index 2d7d526..8f53ce8 100644 --- a/userscripts/Golem.de.user.js +++ b/userscripts/Golem.de.user.js @@ -29,7 +29,7 @@ div#grandwrapper, #screen, #header, #footer, div.g6 { padding: 0px !important; margin: 0px !important; - border-width: none !important; + border-width: 0px !important; width: 100% !important; } diff --git a/userscripts/HYPE Innovation Blog.user.js b/userscripts/HYPE Innovation Blog.user.js new file mode 100644 index 0000000..4003abb --- /dev/null +++ b/userscripts/HYPE Innovation Blog.user.js @@ -0,0 +1,81 @@ +// ==UserScript== +// @name HYPE Innovation Blog +// @version 0.1 +// @description Innovation Articles +// @author M.M. +// @include https://blog.hypeinnovation.com/* +// @grant none +// ==/UserScript== + +'use strict'; + +//// uncomment to debug: +// debugger; + +/* probably again a wordpress based blog? */ + + +var myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +/* ----------------------------- +Name: Computerworld.ch +URL: https://www.computerworld.ch +-------------------------------- */ + +.related-posts, .related-posts-wrapper, +.footer-container-wrapper, +.post-footer, +.header-right, +div.header-container-wrapper, +div.blog-post-sharing { + display:none !important; +} + +.col8, +.hs-container>div { + position: relative; + width: 100%; + max-width: 100% !important; + margin: 0px !important; + padding: 0px !important; + border: none; +} + +.hype-blog-post-banner { + background-color: rgb(200, 90, 50) !important; +} + +.row-fluid [class*="span"], +.widget-type-cell, .widget-type-blog, .hs-container { + float: none !important; +} + +/* All paragraphs without specific formatting should + use font of ebook readers choice */ +div.MMM, +p:not([class]), p[class=""] +{ + text-align: justify; + text-justify: inter-word; + -webkit-hyphens: auto; + -moz-hyphens: auto; + -ms-hyphens: auto; + hyphens: auto; +} + +div.MMM > * { + text-align: left; +} + +body { + padding: 15px !important; + background: none; + background-color: white; + color: #010101; /* default text almost black for better readability */ +} + +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + + diff --git a/userscripts/Heise News (inkl TechnologyReview).user.js b/userscripts/Heise News (inkl TechnologyReview).user.js index f9d9e2a..684d1d0 100644 --- a/userscripts/Heise News (inkl TechnologyReview).user.js +++ b/userscripts/Heise News (inkl TechnologyReview).user.js @@ -117,3 +117,6 @@ aside } `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + + diff --git a/userscripts/LinkedIn Pulse.user.js b/userscripts/LinkedIn Pulse.user.js new file mode 100644 index 0000000..5500f2a --- /dev/null +++ b/userscripts/LinkedIn Pulse.user.js @@ -0,0 +1,75 @@ +// ==UserScript== +// @name LinkedIn Pulse +// @version 0.1 +// @description Innovation Articles +// @author M.M. +// @include https://www.linkedin.com/pulse/* +// @grant none +// ==/UserScript== + +'use strict'; + +//// uncomment to debug: +// debugger; + +/* probably again a wordpress based blog? */ + + +var myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +/* ----------------------------- +Name: LinkedIn Pulse +URL: https://www.linkedin.com/pulse +-------------------------------- */ + +header.navbar, footer, +.related-articles-container, +div.article-comment__container { + display:none !important; +} + +article { + position: relative; + width: 100%; + max-width: 100% !important; + margin: 0px !important; + padding: 0px !important; + border: none; +} + +.hype-blog-post-banner { + background-color: rgb(200, 90, 50) !important; +} + +.row-fluid [class*="span"], +.widget-type-cell, .widget-type-blog, .hs-container { + float: none !important; +} + +/* All paragraphs without specific formatting should + use font of ebook readers choice */ +div.MMM, +p:not([class]), p[class=""] +{ + text-align: justify; + text-justify: inter-word; + -webkit-hyphens: auto; + -moz-hyphens: auto; + -ms-hyphens: auto; + hyphens: auto; +} + +div.MMM > * { + text-align: left; +} + +body { + padding: 15px !important; + background: none; + background-color: white; + color: #010101; /* default text almost black for better readability */ +} + +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + diff --git a/userscripts/Microsoft Docs.user.js b/userscripts/Microsoft Docs.user.js new file mode 100644 index 0000000..ef5ff1f --- /dev/null +++ b/userscripts/Microsoft Docs.user.js @@ -0,0 +1,86 @@ +// ==UserScript== +// @name Microsoft Docs +// @version 0.1 +// @description Microsoft documentation +// @author M.M. +// @include https://docs.microsoft.com/en-us/* +// @grant none +// ==/UserScript== + +'use strict'; + +//// uncomment to debug: +// debugger; + +var myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +/* ----------------------------- +Name: Gartner reprints +URL: https://docs.microsoft.com/en-us/ +-------------------------------- */ + +/* just examples: +div.reprint-section > div:not(.content-section), +div.disclaimer > div:not(.content-section), +button[aria-label="View Columns"], +*/ + +nav, .c-uhfh-actions, +.footerContainer, .action-bar, +div#openFeedbackContainer, +a.m-skip-to-main, +main ~ *, section ~ * +{ + display:none !important; +} + +.columns, .has-large-gaps, +section.primary-holder, +div.column { + position: relative; + float: none !important; + margin: 0px !important; + padding: 0px !important; + width: 100% !important; + max-width: 100% !important; + flex-basis: 100% !important; + top: 0px; + border: none; + text-align: left !important; /* line numbers in Code snippets... */ +} + +/* All paragraphs without specific formatting should + use font of ebook readers choice */ +p.x-hidden-focus, +p:not([class]), p[class=""] +{ + text-align: justify !important; + text-justify: inter-word !important; + -webkit-hyphens: auto; + -moz-hyphens: auto; + -ms-hyphens: auto; + hyphens: auto; +} + +/* fix/emulate
  • :before */ +ul.bullets-yes>li { + list-style-type: square !important; +} + +/* fix: little svg buttons, not needed in epub/print */ +svg, .enlarge-table{ + display:none !important; +} + +body { + padding: 15px !important; + background: none; + background-color: white; + color: #010101; /* default text almost black for better readability */ +} + +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + + diff --git a/userscripts/PowerPivotPro.user.js b/userscripts/PowerPivotPro.user.js index f9f9402..8887383 100644 --- a/userscripts/PowerPivotPro.user.js +++ b/userscripts/PowerPivotPro.user.js @@ -18,8 +18,8 @@ var myCSS = window.document.createElement('style'); myCSS.innerHTML = ` /* ----------------------------- -Name: Chris Webb's BI Blog -URL Regex: https://blog.crossjoin.co.uk/* +Name: PowerPivotPro +URL https://powerpivotpro.com -------------------------------- */ header#branding, footer#colophon, diff --git a/userscripts/sqlbi.com & daxpatterns.com.user.js b/userscripts/sqlbi.com & daxpatterns.com.user.js index 898aef7..a722730 100644 --- a/userscripts/sqlbi.com & daxpatterns.com.user.js +++ b/userscripts/sqlbi.com & daxpatterns.com.user.js @@ -4,6 +4,7 @@ // @description sqlbi - articles and blog entries about DAX and PowerBI. // @author M.M. // @include https://*.sqlbi.com/articles/* +// @include https://www.sqlbi.com/daxpuzzle/* // @include https://www.daxpatterns.com/* // @include https://*.sqlbi.com/blog/* // @grant none From 2c40ad11e1ab03e4c3597359e401096bd18763c2 Mon Sep 17 00:00:00 2001 From: Michael Date: Thu, 28 Feb 2019 19:33:00 +0100 Subject: [PATCH 40/50] Update Microsoft Docs.user.js --- userscripts/Microsoft Docs.user.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/userscripts/Microsoft Docs.user.js b/userscripts/Microsoft Docs.user.js index ef5ff1f..8c8a0bc 100644 --- a/userscripts/Microsoft Docs.user.js +++ b/userscripts/Microsoft Docs.user.js @@ -15,7 +15,7 @@ var myCSS = window.document.createElement('style'); myCSS.innerHTML = ` /* ----------------------------- -Name: Gartner reprints +Name: Microsoft Docs URL: https://docs.microsoft.com/en-us/ -------------------------------- */ @@ -28,6 +28,9 @@ button[aria-label="View Columns"], nav, .c-uhfh-actions, .footerContainer, .action-bar, div#openFeedbackContainer, +#sidebarContent, nav.sidebar, +div.moniker-picker, +#left-container, a.m-skip-to-main, main ~ *, section ~ * { @@ -81,6 +84,3 @@ body { `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); - - - From 91abe548d61bd7d1211588dbca6ac63b88679361 Mon Sep 17 00:00:00 2001 From: Michael Date: Sat, 2 Mar 2019 09:22:17 +0100 Subject: [PATCH 41/50] added 'display' to CSS attributes reason: some paragraphs used as list-items. --- web-extension/extractHtml.js | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index bb1228e..57fce30 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -25,10 +25,11 @@ var supportedCss = [ 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', 'color', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'float', - 'list-style', 'outline', + 'list-style', 'outline', 'display', 'padding', 'quotes', 'text-align', 'text-justify', 'hyphens', 'text-decoration', 'text-transform', 'word-spacing' ]; +// allow: display: list-item ////// function getImageSrc(srcTxt) { @@ -402,10 +403,11 @@ function extractCss(includeStyle, appliedStyles) { // might produce better results in most cases if (pre.parentNode) { cssValueParent = $(pre.parentNode).css(cssTagName); - } + } else cssValueParent = ""; if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { tmpNewCss[cssTagName] = cssValue; } + // if (classNames == "p-x") debugger; } tmpIdsToNewCss[tmpName] = tmpNewCss; } From 68a4732f5d65222fbeab8e9104508223f17ca93c Mon Sep 17 00:00:00 2001 From: Michael Date: Wed, 6 Mar 2019 22:27:54 +0100 Subject: [PATCH 42/50] avoid extra DIV below BODY tag --- web-extension/extractHtml.js | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index 57fce30..c154a4e 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -25,11 +25,10 @@ var supportedCss = [ 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', 'color', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'float', - 'list-style', 'outline', 'display', + 'list-style', 'outline', 'padding', 'quotes', 'text-align', 'text-justify', 'hyphens', 'text-decoration', 'text-transform', 'word-spacing' ]; -// allow: display: list-item ////// function getImageSrc(srcTxt) { @@ -43,7 +42,12 @@ function getImageSrc(srcTxt) { var fileExtension = getFileExtension(srcTxt); if (fileExtension === '') { - return ''; + console.log(srcTxt); + // MM: return ''; + // some image URLs have no extension + // TODO: Mime Type and Referrer would be good + // TODO2: better: reuse images already downloaded by Chrome/Firefox + fileExtension = "jpg"; } var newImgFileName = 'img-' + (Math.floor(Math.random()*1000000*Math.random()*100000)) + '.' + fileExtension; @@ -194,7 +198,9 @@ function sanitize(rawContentString) { return force($wdirty, false); } - dirty = '
    ' + $wdirty.html() + '
    '; + // MM: not sure about purpose: leads to extra top-element DIV-element in eBook? + // dirty = '
    ' + $wdirty.html() + '
    '; + dirty = $wdirty.html(); var results = ''; var lastFragment = ''; @@ -308,7 +314,7 @@ function getContent(htmlContent) { try { var tmp = document.createElement('div'); tmp.appendChild(htmlContent.cloneNode(true)); - var dirty = '
    ' + tmp.innerHTML + '
    '; + var dirty = '
    ' + tmp.innerHTML + '
    '; return sanitize(dirty); } catch (e) { console.log('Error:', e); @@ -403,11 +409,10 @@ function extractCss(includeStyle, appliedStyles) { // might produce better results in most cases if (pre.parentNode) { cssValueParent = $(pre.parentNode).css(cssTagName); - } else cssValueParent = ""; + } if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { tmpNewCss[cssTagName] = cssValue; } - // if (classNames == "p-x") debugger; } tmpIdsToNewCss[tmpName] = tmpNewCss; } From 58955374a46e757d3b59eb1d2ba5c62f4981b178 Mon Sep 17 00:00:00 2001 From: Michael Date: Wed, 6 Mar 2019 22:32:20 +0100 Subject: [PATCH 43/50] Rename BI Blogs_ Chris Webb & Kasper On BI.user.js to WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js --- ...rdPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename userscripts/{BI Blogs_ Chris Webb & Kasper On BI.user.js => WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js} (100%) diff --git a/userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js b/userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js similarity index 100% rename from userscripts/BI Blogs_ Chris Webb & Kasper On BI.user.js rename to userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js From 773fba24ea19e292db2d06eaff89c5525729ab41 Mon Sep 17 00:00:00 2001 From: Michael Date: Wed, 6 Mar 2019 22:33:50 +0100 Subject: [PATCH 44/50] Add files via upload --- userscripts/Aardvark (experimental).user.js | 92 +++++++++++++++++++ userscripts/Computerworld.ch.user.js | 22 +++++ userscripts/Gartner Reprints.user.js | 37 ++++++++ userscripts/Golem.de.user.js | 18 ++++ ...Heise News (inkl TechnologyReview).user.js | 25 ++++- userscripts/Hyphenator (for Chrome).user.js | 60 ++++++++++++ userscripts/Microsoft Docs.user.js | 36 +++++++- userscripts/PowerPivotPro.user.js | 20 ++++ userscripts/Telepolis (Heise).user.js | 20 ++++ ...s Webb,Kasper On BI, Radacad, etc..user.js | 43 +++++++-- .../sqlbi.com & daxpatterns.com.user.js | 21 +++++ 11 files changed, 383 insertions(+), 11 deletions(-) create mode 100644 userscripts/Aardvark (experimental).user.js create mode 100644 userscripts/Hyphenator (for Chrome).user.js diff --git a/userscripts/Aardvark (experimental).user.js b/userscripts/Aardvark (experimental).user.js new file mode 100644 index 0000000..2f8f949 --- /dev/null +++ b/userscripts/Aardvark (experimental).user.js @@ -0,0 +1,92 @@ +// ==UserScript== +// @name Aardvark (experimental) +// @namespace http://tampermonkey.net/ +// @version 0.1 +// @description try to take over the world! +// @author You +// @include https://* +// @include http://* +// @grant none +// ==/UserScript== + +//// uncomment to debug: +// debugger; + + // Just run the bookmarklet without a warning... + // javascript:document.getElementsByTagName('head')[0].appendChild(document.createElement('script')).setAttribute('src','http://www.karmatics.com/aardvark/bookmarklet.js') +// document.getElementsByTagName('head')[0].appendChild(document.createElement('script')).setAttribute('src','http://www.karmatics.com/aardvark/bookmarklet.js'); + + +var showHtml = function (elem) { + }; + +var aardvark = { + +isBookmarklet: true, +resourcePrefix: "http://karmatics.com/aardvark/", +srcFiles: [ + 'aardvarkStrings.js', + 'aardvarkUtils.js', + 'aardvarkDBox.js', + 'aardvarkCommands.js', + 'aardvarkMain.js' + ], + +//------------------------------------------------ +// onload function for script elements +loadObject: function (obj) { + var c = 0; + + for (var x in obj) { + if (aardvark[x] == undefined) + aardvark[x] = obj[x]; + c++; + } + + if (this.objectsLeftToLoad == undefined) { + this.objectsLeftToLoad = this.srcFiles.length; + } + this.objectsLeftToLoad--; + + if (this.objectsLeftToLoad < 1) { + // add anything here you want to happen when it is loaded + // copy our own functions etc over aardvark's + + // start aardvark and show its help tip + this.start (); + this.showHelpTip(0); + + // add our custom commands + aardvark.addCommand ("xpath", function(e) { + if (window.SimplePath) + SimplePath.showPathInSnippetEditor(e); + else + alert("please load snippet editor"); + }); + // add our custom commands + } + } +}; + + +// load the aardvark code from karmatics.com +(function () { + +// leave commented out if you wish to have it load a new +// copy each time (for dev purposes...no need to refresh page) +/*if (window.aardvark) { + aardvark.start (); + return; + } */ + +// anti caching....dev only (leave empty string otherwise) +var ensureFresh = ""; // "?" + Math.round(Math.random()*100); + +for (var i=0; i= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + + +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement( document.getElementsByTagName("article")[0] ) ; +//isolateElement( document.querySelector('div.tp_content') ) ; + + diff --git a/userscripts/Gartner Reprints.user.js b/userscripts/Gartner Reprints.user.js index 13138b2..2ac30a6 100644 --- a/userscripts/Gartner Reprints.user.js +++ b/userscripts/Gartner Reprints.user.js @@ -75,5 +75,42 @@ body { `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + +// https://stackoverflow.com/questions/16791479/how-to-wait-for-div-to-load-before-calling-another-function +function waitForElement(elementId, callBack){ + window.setTimeout(function(){ + var element = document.getElementById(elementId); + if(element){ + callBack(elementId, element); + }else{ + waitForElement(elementId, callBack); + } + },1000) +} + +//-------------------------------------------------------------- + +//debugger; +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +waitForElement("newReader",function() { + isolateElement( document.querySelector('section#newReader') ) ; +}); + + diff --git a/userscripts/Golem.de.user.js b/userscripts/Golem.de.user.js index 8f53ce8..859e745 100644 --- a/userscripts/Golem.de.user.js +++ b/userscripts/Golem.de.user.js @@ -63,4 +63,22 @@ p:not([class]), p[class=""] `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement( document.getElementsByTagName("article")[0] ) ; diff --git a/userscripts/Heise News (inkl TechnologyReview).user.js b/userscripts/Heise News (inkl TechnologyReview).user.js index 684d1d0..7b5411e 100644 --- a/userscripts/Heise News (inkl TechnologyReview).user.js +++ b/userscripts/Heise News (inkl TechnologyReview).user.js @@ -10,6 +10,7 @@ // @include *.heise.de/security/* // @include *.heise.de/autos/* // @include *.heise.de/make/* +// @include *.heise.de/mac-and-i/* // @include *.heise.de/tr/artikel/* // @grant none // ==/UserScript== @@ -19,6 +20,24 @@ //// uncomment to debug: // debugger; + +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + + var myCSS = window.document.createElement('style'); myCSS.innerHTML = ` /* ----------------------------- @@ -92,7 +111,7 @@ span.initial { /* Drop caps */ } /* remove everything except plain article */ -a-analytics, +a-analytics, a-collapse, body>footer, header>nav, #cboxOverlay, #colorbox, #sitemap, #navi_bottom, #breadcrumb_subnav, #mitte-rechts, @@ -110,6 +129,8 @@ body>footer, header>nav, .main-footer, .printversion--hide, .mheise--preisvergleich-banner, .btn-toolbar, .themenseiten, +a-paternoster, .a-paternoster-ad, +div.akwa-ad-container, aside { display: none !important; @@ -118,5 +139,7 @@ aside `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement(document.getElementsByTagName("ARTICLE")[0]) ; diff --git a/userscripts/Hyphenator (for Chrome).user.js b/userscripts/Hyphenator (for Chrome).user.js new file mode 100644 index 0000000..3ab68c8 --- /dev/null +++ b/userscripts/Hyphenator (for Chrome).user.js @@ -0,0 +1,60 @@ +// ==UserScript== +// @name Hyphenator (for Chrome) +// @version 0.1 +// @description Add Hyphenation to Chrome, which unfortunately does not have this feature (yet) +// @author M.M., using https://github.com/mnater/Hyphenator +// @include https://* +// @include http://* +// @exclude https://www.heise.de/select/* +// @grant none +// ==/UserScript== + +//// uncomment to debug: +// debugger; + +var myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +p, +p:not([class]), p[class=""] +{ + text-align: justify !important; + text-justify: inter-word !important; + -webkit-hyphens: auto; + -moz-hyphens: auto; + -ms-hyphens: auto; + hyphens: auto; +} + +bodyMMM { + padding: 15px !important; + background: none; + background-color: white; + color: #010101; /* default text almost black for better readability */ +} +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + + +// TODO: so far using the Bookmarklet, maybe switch to a different/more efficient? version of embedding the script directly... +// https://github.com/mnater/Hyphenator/blob/wiki/en_HowToUseHyphenator.md#using-hyphenator-as-a-bookmarklet + +// Just running the bookmarklet for now... +if (document.createElement) { + void(head = document.getElementsByTagName('head').item(0)); + void(script = document.createElement('script')); + //void(script.src = 'https://mnater.github.io/Hyphenator/Hyphenator.js?bm=true'); + void(script.src = 'https://mnater.github.io/Hyphenator/Hyphenator.js?bm=true&displaytogglebox=false&defaultlanguage=en'); + void(script.type = 'text/javascript'); + void(head.appendChild(script)); +} + +/* +// TODO: could explicitly embed en and de from absolute URL... remoteloading=false + + + +*/ diff --git a/userscripts/Microsoft Docs.user.js b/userscripts/Microsoft Docs.user.js index 8c8a0bc..b01a171 100644 --- a/userscripts/Microsoft Docs.user.js +++ b/userscripts/Microsoft Docs.user.js @@ -26,6 +26,7 @@ button[aria-label="View Columns"], */ nav, .c-uhfh-actions, +button.action, .contributors-holder, .footerContainer, .action-bar, div#openFeedbackContainer, #sidebarContent, nav.sidebar, @@ -65,11 +66,16 @@ p:not([class]), p[class=""] hyphens: auto; } -/* fix/emulate
  • :before */ -ul.bullets-yes>li { - list-style-type: square !important; +div.codeHeader { + background-color: rgb(190,190,190); } +.codeHeader+pre, code { + background-color: rgb(240,240,240); +} + + + /* fix: little svg buttons, not needed in epub/print */ svg, .enlarge-table{ display:none !important; @@ -84,3 +90,27 @@ body { `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + + +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement( document.getElementsByTagName("main")[0] ) ; + + + diff --git a/userscripts/PowerPivotPro.user.js b/userscripts/PowerPivotPro.user.js index 8887383..4e87f71 100644 --- a/userscripts/PowerPivotPro.user.js +++ b/userscripts/PowerPivotPro.user.js @@ -97,3 +97,23 @@ document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + + +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement( document.getElementsByTagName("main")[0] ) ; + diff --git a/userscripts/Telepolis (Heise).user.js b/userscripts/Telepolis (Heise).user.js index 67d662e..03c67cd 100644 --- a/userscripts/Telepolis (Heise).user.js +++ b/userscripts/Telepolis (Heise).user.js @@ -67,3 +67,23 @@ document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + + +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +//isolateElement( document.getElementsByTagName("main")[0] ) ; +isolateElement( document.querySelector('div.tp_content') ) ; diff --git a/userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js b/userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js index 53f1709..54599c7 100644 --- a/userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js +++ b/userscripts/WordPress Blogs_ Chris Webb,Kasper On BI, Radacad, etc..user.js @@ -1,35 +1,60 @@ // ==UserScript== -// @name BI Blogs: Chris Webb & Kasper On BI -// @version 0.2 +// @name WordPress Blogs: Chris Webb,Kasper On BI, Radacad, etc. +// @version 0.3 // @description Power BI, Power Query and DAX related posts // @author M.M. // @include https://blog.crossjoin.co.uk/*/*/* // @include https://www.kasperonbi.com/*/* // @exclude https://www.kasperonbi.com/page/* +// @include http://radacad.com/* +// @include https://radacad.com/* +// @include https://prathy.com/* // @grant none // ==/UserScript== 'use strict'; +/* probably similar for most WordPress blogs? */ +// Tested with, e.g.: +// https://prathy.com/2019/02/sync-slicers-sync-slicers-advanced-options/ +// http://radacad.com/remove-duplicate-doesnt-work-in-power-query-for-power-bi-here-is-the-solution +// https://www.kasperonbi.com/use-more-variables-in-dax-to-simplify-your-life/ +// https://blog.crossjoin.co.uk/2019/02/12/splitting-text-by-character-transition-power-bi-power-query-excel/ + //// uncomment to debug: // debugger; -/* probably valid for most wordpress blogs? */ -// Test with: https://prathy.com/2019/02/sync-slicers-sync-slicers-advanced-options/ +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- var myCSS = window.document.createElement('style'); myCSS.innerHTML = ` /* ----------------------------- -Name: BI Blogs: Chris Webb & Kasper On BI +Name: Wordpress Blogs: Chris Webb , Kasper On BI, Radacad URL: https://blog.crossjoin.co.uk/... URL2: https://www.kasperonbi.com/... +etc. see above -------------------------------- */ header#branding, footer#colophon, aside#mobile-header, div#secondary, div#actionbar, div.main-navbar, div.header-top, -div.sd-social, div.sharedaddy, +div.sd-social, div.sharedaddy, .synved-social-button, +.yarpp-related, div.post-related, div#disqus_thread, .post-format-icon, .screen-reader-text, article ~ * { display:none !important; @@ -89,7 +114,7 @@ p:not([class]), p[class=""] body { padding: 15px !important; - background: none; + background: none !important; background-color: white; color: #010101; /* default text almost black for better readability */ } @@ -97,5 +122,9 @@ body { `; document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement( document.getElementsByTagName("article")[0] ) ; +// div#page +// isolateElement( document.getElementById("page") ) ; diff --git a/userscripts/sqlbi.com & daxpatterns.com.user.js b/userscripts/sqlbi.com & daxpatterns.com.user.js index a722730..830a417 100644 --- a/userscripts/sqlbi.com & daxpatterns.com.user.js +++ b/userscripts/sqlbi.com & daxpatterns.com.user.js @@ -15,6 +15,23 @@ //// uncomment to debug: // debugger; + +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + var myCSS = window.document.createElement('style'); myCSS.innerHTML = ` /* ----------------------------- @@ -71,4 +88,8 @@ body { document.getElementsByTagName("HEAD")[0].appendChild(myCSS); +// actually, after all that work so far, we just keep the DOM-tree below "Article" ;-) +isolateElement(document.getElementsByTagName("article")[0]) ; +// TODO: extra elements may appear after this -> need to disable original page scripts somehow... +//debugger; From 5a19c24e1c621292aec9596ad07ed2e5cfbaf044 Mon Sep 17 00:00:00 2001 From: Michael Date: Thu, 7 Mar 2019 00:07:33 +0100 Subject: [PATCH 45/50] Add files via upload --- userscripts/HeiseSelect.user.js | 299 ++++++++++++++++++++++++++++++++ 1 file changed, 299 insertions(+) create mode 100644 userscripts/HeiseSelect.user.js diff --git a/userscripts/HeiseSelect.user.js b/userscripts/HeiseSelect.user.js new file mode 100644 index 0000000..93ebc5b --- /dev/null +++ b/userscripts/HeiseSelect.user.js @@ -0,0 +1,299 @@ +// ==UserScript== +// @name HeiseSelect +// @version 0.2 +// @description Heise Select (iX and others). Better image quality inline and simplified structure. +// @author M.M. +// @include https://*.heise.de/select/*/*/*/* +// @exclude https://*.heise.de/select/*/*/*/*/*.html +// @grant none +// ==/UserScript== + +'use strict'; + +//// uncomment to debug: +// debugger; + +/* +var myCSS = "/select/assets/ix/stylesheet/tabelle-20140819.css"; +// Set custom CSS: +var link = window.document.createElement('link'); +link.rel = 'stylesheet'; +link.type = 'text/css'; +link.href = myCSS; +document.getElementsByTagName("HEAD")[0].appendChild(link); +*/ + + +//------------------------------------------------------------ +// experimental to preprocess/further simplify document prior to +// producing an eBook format. +function isolateElement(o) { + if (o && o.parentNode != null) { + var clone = o.cloneNode (true); + for (var i = document.body.childNodes.length -1; i >= 0 ; i--) { + document.body.removeChild ( document.body.childNodes.item(i) ); + } + document.body.appendChild (clone); + } else { + console.log("Warning: isolate did not find element..."); + } +} +//-------------------------------------------------------------- + +/////////////////////////////////////////////////////////////////////////// +// actually, we reduce the DOM tree a bit, isolate the main "Article" ;-) +isolateElement( document.getElementsByTagName("main")[0] ) ; + +var myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +/* ----------------------------- +Name: Heise Select +Additional Hint: .jpeg images are provided as WebP instead which corrupts +the resulting books. +use another Chrome extension to change Request headers for *.jpg to ask for image/jpeg +-------------------------------- */ +body { + color: #010101 !important; /* default text almost black for better readability */ + padding: 25px !important; + background-color: white; +} + +.article__head, +main.content { + width: 100% !important; + padding: 0 0 0 0 !important; + margin: 0 0 0 0 !important; +} + +.article__header-text { + padding: 0 20px; +} + +span.initial { /* Drop caps */ + float: left; + font-weight:normal; + font-size: 4em !important; + line-height: 1.3 !important; + margin-bottom: -0.3em !important; + margin-top: -0.3em !important; + font-stretch: normal; +} + +p.normal, p:not([class]), p[class=""] +/* All paragraphs without specific formatting should + use font of ebook readers choice */ +{ + text-align: justify; + hyphens: auto; +} + +p.x, .kasten--ixtract .x { + list-style-type: square; /* looks nicer and can be distinguished from "default" while extracting CSS - TODO */ +} + +/* remove everything except plain article */ +a-analytics, body>footer, +.topbar, .toolbar, .comment, .bottom-links, .shariff +{ + display: none !important; +} +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + +myCSS = window.document.createElement('style'); +myCSS.innerHTML = ` +table { + border-collapse: collapse; + border: 2px solid black; + table-layout: auto; + width: 100%; + font-size: 5pt; +} + +th,td { + border: 1px solid black; +} + +tr:nth-child(odd) { + background-color: #eeeeee; +} + +tr.table_title { background-color: #333333; color: #eeeeee; font-style: bold; } +tr.table_columnNames { background-color: #cccccc; font-style: bold; } +tr.tr_even { background-color: #dddddd; } +tr.tr_odd { background-color: #eeeeee; } + + +ul#fixedTableLeft { + display: none !important; +} + +`; +document.getElementsByTagName("HEAD")[0].appendChild(myCSS); + + +////////////////////////////// + +// https://stackoverflow.com/questions/16791479/how-to-wait-for-div-to-load-before-calling-another-function +function waitForElement(elementId, callBack){ + window.setTimeout(function(){ + var element = document.getElementById(elementId); + if(element){ + callBack(elementId, element); + }else{ + waitForElement(elementId, callBack); + } + },1000) +} + +//lsauer.com, 2012; rev. 2014 by lo sauer +//description: transformTag fully replaces a node by a different Tag, and re-attaches all children to the newly formed Tag +// Any desired EventHandlers must be re-attached manually +//@param tagIdOrElem: an HTMLElement Id-Name or an instance of any HTMLElement +//[@param tagType]: the HTML Tag Type. Default is 'span' (HTMLSpanElement) + +function transformTag(doc, tagIdOrElem, tagType){ + var elem = (tagIdOrElem instanceof HTMLElement) ? tagIdOrElem : doc.getElementById(tagIdOrElem); + if(!elem || !(elem instanceof HTMLElement))return; + var children = elem.childNodes; + var parent = elem.parentNode; + var newNode = doc.createElement(tagType||"span"); + for(var a=0;a + // myDIV.innerHTML = ''; + myDIV.src= images[i].parentNode.href; + myDIV.height = "800px"; + // document.getElementById("table_content").innerHTML=''; + //images[i].parentNode.parentNode.appendChild(myDIV); + document.getElementsByTagName("BODY")[0].appendChild(myDIV); + */ + //////////////////////////// + var pos = document.getElementById("myMarker"); + pos.id = ""; + var newTableDIV = window.document.createElement('div'); + newTableDIV.id = "table_content123"; + pos.parentNode.insertBefore( newTableDIV, pos ); + loadTableToElement(images[i].parentNode.href, 'table_content123' ) + newTableDIV.id =""; + ///////////////////////////////////// +/* + waitForElement("table_content123",function(){ + //console.log("done"); + var myDIV=document.getElementById("table_content123"); + //myDIV2.innerHTML = myDIV.contentWindow.document.getElementsByTagName("body")[0].innerHTML; + // myDIV2.innerHTML = myDIV.contentWindow.document.getElementsByClassName("fixme")[0].innerHTML; + // myDIV.parentNode.appendChild( myDIV2 ); + + var neu = myDIV.contentWindow.document.getElementsByClassName("DONTfixme")[0].cloneNode(true); + // myDIV.parentNode.parentNode.appendChild( neu ); + var pos = document.getElementById("myMarker"); + pos.id = ""; + pos.parentNode.insertBefore( neu, pos ); + myDIV.parentNode.removeChild(myDIV); + neu.style.left = "0px"; + neu.style.top = "0px"; + neu.style.position = "relative"; + //neu.style.height = "1200px"; + //neu.style.width = "600px"; + neu.style.float = "none"; + var allElem = neu.getElementsByTagName("*"); + for (var i = 0; i < allElem.length; i++) { + allElem[i].removeAttribute("style"); + // allElem[i].style.width = null; + // allElem[i].style.height = null; + } + }); +*/ + /* ----------------------- */ + } + } + } +} + + + From 52232aba99438ca1147f0119573f95b8815674c1 Mon Sep 17 00:00:00 2001 From: Michael Date: Fri, 15 Mar 2019 02:19:59 +0100 Subject: [PATCH 46/50] handle CSS background-image attribute well, first attempt. --- web-extension/extractHtml.js | 59 +++++++++++++++++++++++++++--------- 1 file changed, 44 insertions(+), 15 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index c154a4e..d06ca4d 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -21,7 +21,7 @@ var cssClassesToTmpIds = {}; var tmpIdsToNewCss = {}; // src: https://idpf.github.io/a11y-guidelines/content/style/reference.html var supportedCss = [ - 'background-color', + 'background-color', 'background-image', 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', 'color', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'float', @@ -42,11 +42,12 @@ function getImageSrc(srcTxt) { var fileExtension = getFileExtension(srcTxt); if (fileExtension === '') { - console.log(srcTxt); + console.log("TODO: image source without handled extension: " + srcTxt); // MM: return ''; // some image URLs have no extension // TODO: Mime Type and Referrer would be good // TODO2: better: reuse images already downloaded by Chrome/Firefox + // TODO3: svg or jpg... this hack currently depends on source web site ;-) fileExtension = "jpg"; } var newImgFileName = 'img-' + (Math.floor(Math.random()*1000000*Math.random()*100000)) + '.' + fileExtension; @@ -58,6 +59,7 @@ function getImageSrc(srcTxt) { data: getBase64ImgData(srcTxt) }); } else { + // MM: console.log("MM: debug: allImages.push: "+ srcTxt + " " + newImgFileName ); allImages.push({ originalUrl: getImgDownloadUrl(srcTxt), filename: newImgFileName, // TODO name @@ -117,6 +119,7 @@ function preProcess($htmlObject) { } function force($content, withError) { + console.log("MM: debug: force() called..."); try { var tagOpen = '@@@' + generateRandomTag(); var tagClose = '###' + generateRandomTag(); @@ -184,7 +187,8 @@ function force($content, withError) { } function sanitize(rawContentString) { - allImages = []; + // MM: console.log("MM: debug: sanitize - allImages , extractedImages reset"); + // MM: allImages = []; - need to move this as background-image via CSS might already have used this... extractedImages = []; var srcTxt = ''; var dirty = null; @@ -387,7 +391,6 @@ function extractCss(includeStyle, appliedStyles) { classNames = pre.getAttribute('id'); if (!classNames) { //MMv1: classNames = pre.tagName.toLowerCase() + '-tag'; // MM: pre.tagName + '-' + Math.floor(Math.random()*100000); - // MM test: return; // MM: if we do not want to store defaults per tag... maybe from more general css rules ... classNames = pre.parentNode.tagName.toLowerCase() + '_' + pre.tagName.toLowerCase(); // MM: use the path. as ul.li and ol.li need different list-style-type for example. } } else { @@ -410,7 +413,23 @@ function extractCss(includeStyle, appliedStyles) { if (pre.parentNode) { cssValueParent = $(pre.parentNode).css(cssTagName); } - if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { + if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { + if (cssTagName == "background-image" && cssValue != "none") { + // only containing url .. but not url("data:image/... need to be rewritten... + var imgSrc = ""; + var tmp = cssValue.replace(/\s+/g, ''); // kill all whitespaces + var tmp2 = tmp.match(/url\((['"])(.*)\1\)/); // is it url(...) with matching pair of quotes ? + if (tmp2 !== null) { + var src = tmp2[2]; + if ( src.search(/^data:/) == -1 ) { // just keep embedded "data:" + imgSrc = getImageSrc(src); + console.log(cssTagName + " " + cssValue + " src: "+ imgSrc); + if (imgSrc !== '') { + cssValue = "url('"+imgSrc+"')"; + } + } + } + } tmpNewCss[cssTagName] = cssValue; } } @@ -459,22 +478,32 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => { let tmpContent = ''; let styleFile = null; - if (request.type === 'extract-page') { - styleFile = extractCss(request.includeStyle, request.appliedStyles) + console.log("chrome.runtime.onMessage.addListener() " + request.type); + if (request.type === undefined ) { + return; // MM: no need to run this on undefined... (only extract-*) + } else { + let allImages = []; //MM: instead of inside sanitize() + } + + if (request.type === 'extract-page') { + styleFile = extractCss(request.includeStyle, request.appliedStyles); pageSrc = document.getElementsByTagName('body')[0]; tmpContent = getContent(pageSrc); - } else if (request.type === 'extract-selection') { - styleFile = extractCss(request.includeStyle, request.appliedStyles) + styleFile = extractCss(request.includeStyle, request.appliedStyles); + } else if (request.type === 'extract-selection') { + styleFile = extractCss(request.includeStyle, request.appliedStyles); pageSrc = getSelectedNodes(); pageSrc.forEach((page) => { tmpContent += getContent(page); }); + } - - allImages.forEach((tmpImg) => { - imgsPromises.push(deferredAddZip(tmpImg.originalUrl, tmpImg.filename)); - }); - + + allImages.forEach((tmpImg) => { + // MM: console.log("MM: debug: deferredAddZip: " + tmpImg.originalUrl + " " + tmpImg.filename ); + imgsPromises.push(deferredAddZip(tmpImg.originalUrl, tmpImg.filename)); + }); + $.when.apply($, imgsPromises).done(() => { let tmpTitle = getPageTitle(document.title); result = { @@ -491,6 +520,6 @@ chrome.runtime.onMessage.addListener((request, sender, sendResponse) => { console.log('Error:', e); sendResponse(null) }); - + return true; }); From 970ccad34cfd5976fadbad4f5d8a1c24dc867344 Mon Sep 17 00:00:00 2001 From: Michael Date: Fri, 15 Mar 2019 22:19:17 +0100 Subject: [PATCH 47/50] huge improvements - better image filenames (most cases) - might cause de-dup on name collisions. - CSS: background-image and related attributes are now taken over with more fidelity. - handle styling of links and other exceptions better (a, strong, em - tags) TODO: need to produce better class names --- web-extension/extractHtml.js | 154 +++++++++++++++++++++++++---------- 1 file changed, 110 insertions(+), 44 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index d06ca4d..cdad056 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -19,9 +19,12 @@ var mathMLTags = [ ] var cssClassesToTmpIds = {}; var tmpIdsToNewCss = {}; + // src: https://idpf.github.io/a11y-guidelines/content/style/reference.html +// MM: maybe not the best idea, but all the extra attributes {background-image, position, z-index, background-*} go somewhat together on fancy article headers ;-) var supportedCss = [ - 'background-color', 'background-image', + 'background-color', + 'background-image', 'position', 'z-index', 'background-position', 'background-repeat', 'background-clip', 'background-origin', 'background-size', 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', 'color', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'float', @@ -31,6 +34,24 @@ var supportedCss = [ ]; ////// +function getFileName(url) { + //this removes the anchor at the end, if there is one + url = url.substring(0, (url.indexOf("#") == -1) ? url.length : url.indexOf("#")); + //this removes the query after the file name, if there is one + url = url.substring(0, (url.indexOf("?") == -1) ? url.length : url.indexOf("?")); + //this removes everything before the last slash in the path + url = url.substring(url.lastIndexOf("/") + 1, url.length); + url = decodeURI(url); + console.log("MM: debug: new image name: "+url); + return url; +} + +// MM: TODO: could turn landscape images by 90degrees for most portrait eInk readers. +// -- improve mime detection avoid (larger) svg's for better compatibility... +// -- Enahnce contrast /Eliminate background on drawing? +// -- directly save image from cache +// Related: https://zocada.com/compress-resize-images-javascript-browser/ +// https://stackoverflow.com/questions/43467909/how-to-get-img-content-type-using-javascript-after-loading function getImageSrc(srcTxt) { if (!srcTxt) { return ''; @@ -40,6 +61,7 @@ function getImageSrc(srcTxt) { return ''; } + var newImgFileName = ""; var fileExtension = getFileExtension(srcTxt); if (fileExtension === '') { console.log("TODO: image source without handled extension: " + srcTxt); @@ -49,9 +71,14 @@ function getImageSrc(srcTxt) { // TODO2: better: reuse images already downloaded by Chrome/Firefox // TODO3: svg or jpg... this hack currently depends on source web site ;-) fileExtension = "jpg"; - } - var newImgFileName = 'img-' + (Math.floor(Math.random()*1000000*Math.random()*100000)) + '.' + fileExtension; - + } else { + newImgFileName = getFileName(srcTxt); // MM: get a better filename (easier to debug and dedupes. issue: same name with different content) + } + +if (newImgFileName === '' || isBase64Img(srcTxt)) { + newImgFileName = 'img-' + (Math.floor(Math.random()*1000000*Math.random()*100000)) + '.' + fileExtension; + } + var isB64Img = isBase64Img(srcTxt); if (isB64Img) { extractedImages.push({ @@ -369,15 +396,64 @@ function jsonToCss(jsonObj) { return result; } + +// MM: refactored, improve later... +function getNodeStyle(pre) { + tmpNewCss = {}; + for (let cssTagName of supportedCss) { + let cssValue = $(pre).css(cssTagName); + // MM: little hack: might not be perfect, but just takes rules different from (current) parent. + // might produce better results in most cases + if (pre.parentNode) { + cssValueParent = $(pre.parentNode).css(cssTagName); + } + var special = ['a','em','strong']; // those do NOT inherit by default , e.g. link color... + if (special.indexOf(pre.tagName.toLowerCase()) != -1) cssValueParent = ""; + + if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { // last clause dedupes + if (cssTagName == "background-image" && cssValue != "none") { + // only containing url .. but not url("data:image/... need to be rewritten... + var imgSrc = ""; + var tmp = cssValue.replace(/\s+/g, ''); // kill all whitespaces + var tmp2 = tmp.match(/url\((['"])(.*)\1\)/); // is it url(...) with matching pair of quotes ? + if (tmp2 !== null) { + var src = tmp2[2]; + if ( src.search(/^data:/) == -1 ) { // just keep embedded "data:" + imgSrc = getImageSrc(src); + console.log(cssTagName + " " + cssValue + " src: "+ imgSrc); + if (imgSrc !== '') { + cssValue = "url('"+imgSrc+"')"; + } + } + } + } + tmpNewCss[cssTagName] = cssValue; + } + } + return tmpNewCss; +} + +// MM: ugly approach - maybe using hash later... +function styleToString(styleArr) { + var tmp=""; + for (var key in styleArr) { + tmp += key + ':' +styleArr[key] + ';'; + } + //console.log ("MM: debug: styleToString(): " + tmp); + return tmp; +} + + // TODO: Klasse für builtin style attribute: lookup: // let classNames = pre.getAttribute('style'); // https://en.wikipedia.org/wiki/Data_warehouse function extractCss(includeStyle, appliedStyles) { + styleLookup={}; if (includeStyle) { $('body').find('*').each((i, pre) => { let $pre = $(pre); - + // seems to start from end of document? verify... if (allowedTags.indexOf(pre.tagName.toLowerCase()) < 0) return; if (mathMLTags.indexOf(pre.tagName.toLowerCase()) > -1) return; @@ -392,50 +468,40 @@ function extractCss(includeStyle, appliedStyles) { if (!classNames) { //MMv1: classNames = pre.tagName.toLowerCase() + '-tag'; // MM: pre.tagName + '-' + Math.floor(Math.random()*100000); classNames = pre.parentNode.tagName.toLowerCase() + '_' + pre.tagName.toLowerCase(); // MM: use the path. as ul.li and ol.li need different list-style-type for example. + //classNames = pre.parentNode.getAttribute('data-class') + '_' + pre.tagName.toLowerCase(); + //classNames = 'class-' + Math.floor(Math.random()*100000); } } else { classNames = classNames.replace(/\s/g,'_'); // MM: ...merge multiple names, we basically have combined css anyways. classNames = pre.tagName.toLowerCase() + '-' + classNames; // MM: materialize class per tag. had issues with span inside paragraph // do NOT concatenate with '.' here ;-) } - let tmpName = cssClassesToTmpIds[classNames]; - let tmpNewCss = tmpIdsToNewCss[tmpName]; - if (!tmpName) { - tmpName = classNames; // MM: tmpName = 'class-' + Math.floor(Math.random()*100000); - cssClassesToTmpIds[classNames] = tmpName; - } - if (!tmpNewCss) { - // var style = window.getComputedStyle(pre); - tmpNewCss = {}; - for (let cssTagName of supportedCss) { - let cssValue = $pre.css(cssTagName); - // MM: little hack: might not be perfect, but just takes rules different from (current) parent. - // might produce better results in most cases - if (pre.parentNode) { - cssValueParent = $(pre.parentNode).css(cssTagName); - } - if (cssValue && cssValue.length > 0 && cssValue != cssValueParent) { - if (cssTagName == "background-image" && cssValue != "none") { - // only containing url .. but not url("data:image/... need to be rewritten... - var imgSrc = ""; - var tmp = cssValue.replace(/\s+/g, ''); // kill all whitespaces - var tmp2 = tmp.match(/url\((['"])(.*)\1\)/); // is it url(...) with matching pair of quotes ? - if (tmp2 !== null) { - var src = tmp2[2]; - if ( src.search(/^data:/) == -1 ) { // just keep embedded "data:" - imgSrc = getImageSrc(src); - console.log(cssTagName + " " + cssValue + " src: "+ imgSrc); - if (imgSrc !== '') { - cssValue = "url('"+imgSrc+"')"; - } - } - } - } - tmpNewCss[cssTagName] = cssValue; - } - } - tmpIdsToNewCss[tmpName] = tmpNewCss; - } - pre.setAttribute('data-class', tmpName); + //////////////////// + tmpNewCss = getNodeStyle(pre); + styleString = styleToString(tmpNewCss); + var tmpId = styleLookup[styleString]; + + if ( tmpId !== undefined ) { + //console.log ("MM: debug: classname: " + classNames + " dedup to: " + tmpId); + } else { + tmpId = cssClassesToTmpIds[classNames]; + if (tmpId === undefined ) { // seems to be first + //console.log ("MM: debug: first encounter with className: " + classNames); + tmpId = classNames; + cssClassesToTmpIds[classNames] = tmpId; + tmpIdsToNewCss[tmpId] = tmpNewCss; + } else { + classNames = classNames + '_' + Math.floor(Math.random()*100000); + tmpId = classNames; + //console.log ("MM: debug: need artifical className Id: " + classNames); + cssClassesToTmpIds[classNames] = tmpId; + tmpIdsToNewCss[tmpId] = tmpNewCss; + styleLookup[ styleString ] = tmpId; + } + } + ///////////////// + //console.log ("MM: debug: checking data-class=tmpId: " + tmpId); + //debugger; + pre.setAttribute('data-class', tmpId); } }); return jsonToCss(tmpIdsToNewCss); From d94a84f3b6d8825b3b7618fe9b1248e12b55c2e9 Mon Sep 17 00:00:00 2001 From: Michael Date: Fri, 15 Mar 2019 22:56:47 +0100 Subject: [PATCH 48/50] Update extractHtml.js --- web-extension/extractHtml.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index cdad056..e2c4a03 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -25,7 +25,7 @@ var tmpIdsToNewCss = {}; var supportedCss = [ 'background-color', 'background-image', 'position', 'z-index', 'background-position', 'background-repeat', 'background-clip', 'background-origin', 'background-size', - 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', + 'border', 'border-top', 'border-right', 'border-bottom', 'border-left', 'border-collapse', 'border-radius', 'color', 'font', 'font-size', 'font-weight', 'font-family', 'letter-spacing', 'line-height', 'float', 'list-style', 'outline', From 29156381d538e551915b464e710daf7653b81b63 Mon Sep 17 00:00:00 2001 From: Michael Date: Wed, 20 Mar 2019 11:16:09 +0100 Subject: [PATCH 49/50] Update README.md --- README.md | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 8bdc3ba..d3c3560 100644 --- a/README.md +++ b/README.md @@ -7,16 +7,17 @@ ![alt ex3.png](https://github.com/alexadam/save-as-ebook/blob/master/ex3.png?raw=true) ## About this fork of the project: -This is a fork with (currently) the following improvements: +This is a fork with (currently) the following improvements (mainly improvements in extractHTML.js logic): +- support for additional CSS attributes (display, colspan, border-collapse,...) +- support for fancy article headers {background-image, position, z-index, background-*} +- retain original image filenames where applicable (make editing of epub easier) +- better naming for resulting CSS rules (make editing of epub easier) +- "Dedup" of CSS rules - only store relevant changes compared to parent elements (smaller CSS files) +- additional tags and attributes +- some bug fixes (e.g. syntax highlighting in pre and code environments...) +Related: - leverage ModHeader extension: ensure, images in the ePub are in accepted formats, not WebP images. -- additional CSS per sites -- corrections in extractHTML.js: -- additional tags, attributes, css values to generate better results. -- generated css class names are now more descriptive to ease debugging (and calibre post-processing) -- foster reuse in CSS styles to generate smaller files (not perfect) -- some bug fixes around syntax highlighted
     and  environments
    -- some fixes for HTML tables
    -- and some more, see commit history for now ;-) 
    +- Pushed "page cleanups" via CSS and JavaScript to userscripts for TamperMonkey
     
     Save a web page/selection as an eBook (.epub format) - a Chrome/Firefox/Opera Web Extension
     
    
    From 507b2b8d812acbf3e4a80aee2a9bcbd8212bae79 Mon Sep 17 00:00:00 2001
    From: Michael 
    Date: Fri, 9 Jul 2021 20:53:16 +0200
    Subject: [PATCH 50/50] Update extractHtml.js
    
    added "start" attribute for 
      lists with explicit numbering --- web-extension/extractHtml.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/web-extension/extractHtml.js b/web-extension/extractHtml.js index e2c4a03..3d3bfae 100644 --- a/web-extension/extractHtml.js +++ b/web-extension/extractHtml.js @@ -295,9 +295,9 @@ function sanitize(rawContentString) { tmpAttrsTxt += ' class="' + attrs[i].value + '"'; } } - // +++ MM: some more extras like colspan ... - var extraAttrs = [ 'colspan', 'title', 'lang', 'span', 'name' ]; - for (var i = 0; i < attrs.length; i++) { + // +++ MM: some more extras like colspan ... "start" for
        numbering + var extraAttrs = [ 'colspan', 'title', 'lang', 'span', 'name', 'start' ]; + for (var i = 0; i < attrs.length; i++) { if (extraAttrs.indexOf( attrs[i].name ) != -1 ) { tmpAttrsTxt += ' '+attrs[i].name+'="' + attrs[i].value + '"' ; }