REFACTOR: full component refactoring

REFACTOR: full component refactoring

  • drops jquery
  • uses new codelayout structure
  • more explicit site setting
  • apply code standards
  • various cleanups
  • do not show an empty category-title-desription if we don’t show the category description
diff --git a/.eslintrc b/.eslintrc
new file mode 100644
index 0000000..f44c16c
--- /dev/null
+++ b/.eslintrc
@@ -0,0 +1,6 @@
+{
+  "extends": "eslint-config-discourse",
+  "globals": {
+    "settings": true
+  }
+}
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..93cab34
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,2 @@
+node_modules
+yarn-error.log
diff --git a/.template-lintrc.js b/.template-lintrc.js
new file mode 100644
index 0000000..dd2e0b9
--- /dev/null
+++ b/.template-lintrc.js
@@ -0,0 +1,4 @@
+module.exports = {
+  plugins: ["ember-template-lint-plugin-discourse"],
+  extends: "discourse:recommended"
+};
diff --git a/common/common.scss b/common/common.scss
index 6af5329..e64c274 100644
--- a/common/common.scss
+++ b/common/common.scss
@@ -4,18 +4,22 @@ div[class^="category-title-header"] {
   text-align: center;
   width: 100%;
   justify-content: center;
+
   .category-title-contents {
     max-width: 500px;
     padding: 40px;
-    svg {
+
+    .d-icon-lock {
       height: 1.5em;
       width: 1.1em;
       margin-right: 0.25em;
     }
-    h1 {
+
+    .category-title {
       display: inline;
     }
   }
+
   .category-title-description {
     a,
     a:visited {
@@ -24,6 +28,7 @@ div[class^="category-title-header"] {
     }
   }
 }
+
 .category-header {
   #main-outlet {
     padding-top: 20px;
diff --git a/common/header.html b/common/header.html
deleted file mode 100644
index bc41316..0000000
--- a/common/header.html
+++ /dev/null
@@ -1,70 +0,0 @@
-<script type="text/discourse-plugin" version="0.8">
-  const container = Discourse.__container__;
-  const { h } = require('virtual-dom');
-  const { iconNode } = require("discourse-common/lib/icon-library");
-  let lockIcon = iconNode('lock');
-
-  api.createWidget('category-header-widget', {
-      tagName: 'span',
-      html(attrs, state) {
-
-          const path = window.location.pathname;
-          let category;
-
-          const controller = container.lookup('controller:navigation/category');
-          category = controller.get("category");
-
-          const isException = category &&
-          settings.exceptions.split("|").includes(category.name);
-
-          if(/^\/c\//.test(path)) {
-              const hideMobile = (!settings.show_mobile && this.site.mobileView) ? "true" : hideMobile;
-              const subCat = (!settings.show_subcategory && category.parentCategory) ? "true" : subCat;
-              const noDesc = (settings.hide_if_no_description && !category.description_text) ? "true" : noDesc;
-
-              if(!isException && !noDesc && !subCat && !hideMobile) {
-                  $("body").addClass("category-header");
-
-                  function catDesc() {
-                      if(settings.show_description) {
-                          return h('div.cooked', {innerHTML: category.description});
-                      }
-                  }
-
-                  function ifProtected() {
-                      if(category.read_restricted) {
-                          return lockIcon;
-                      }
-                  }
-
-                  return h('div.category-title-header' + " .category-banner-" + category.slug, {
-                      "attributes" : {
-                          "style" : "background-color: #" + category.color + "; color: #" + category.text_color + ";"
-                      }
-                  }, h('div.category-title-contents', [
-                  ifProtected(),
-                  h('h1', category.name),
-                  h('div.category-title-description',catDesc())
-                  ]),
-
-                  );
-              }
-          } else {
-              $("body").removeClass("category-header");
-          }
-      }
-  }),
-
-  api.decorateWidget('category-header-widget:after', helper => {
-      helper.widget.appEvents.on('page:changed', () => {
-          helper.widget.scheduleRerender();
-      });
-  });
-</script>
-
-<script
-  type="text/x-handlebars"
-  data-template-name="/connectors/below-site-header/category-header-widget"
->
-  {{mount-widget widget="category-header-widget"}}
-</script>
diff --git a/javascripts/discourse/connectors/below-site-header/category-header-widget.hbs b/javascripts/discourse/connectors/below-site-header/category-header-widget.hbs
new file mode 100644
index 0000000..563272f
--- /dev/null
+++ b/javascripts/discourse/connectors/below-site-header/category-header-widget.hbs
@@ -0,0 +1 @@
+{{mount-widget widget="category-header-widget"}}
diff --git a/javascripts/discourse/initializers/discourse-category-banners.js.es6 b/javascripts/discourse/initializers/discourse-category-banners.js.es6
new file mode 100644
index 0000000..1c88d07
--- /dev/null
+++ b/javascripts/discourse/initializers/discourse-category-banners.js.es6
@@ -0,0 +1,15 @@
+import { withPluginApi } from "discourse/lib/plugin-api";
+
+export default {
+  name: "discourse-category-banners",
+
+  initialize() {
+    withPluginApi("0.8", (api) => {
+      api.decorateWidget("category-header-widget:after", (helper) => {
+        helper.widget.appEvents.on("page:changed", () => {
+          helper.widget.scheduleRerender();
+        });
+      });
+    });
+  },
+};
diff --git a/javascripts/discourse/widgets/category-header-widget.js.es6 b/javascripts/discourse/widgets/category-header-widget.js.es6
new file mode 100644
index 0000000..3099ebc
--- /dev/null
+++ b/javascripts/discourse/widgets/category-header-widget.js.es6
@@ -0,0 +1,73 @@
+import { h } from "virtual-dom";
+import { iconNode } from "discourse-common/lib/icon-library";
+import { createWidget } from "discourse/widgets/widget";
+
+function buildCategory(category) {
+  const content = [];
+
+  if (category.read_restricted) {
+    content.push(iconNode("lock"));
+  }
+
+  content.push(h("h1.category-title", category.name));
+
+  if (settings.show_description) {
+    content.push(
+      h(
+        "div.category-title-description",
+        h("div.cooked", { innerHTML: category.description })
+      )
+    );
+  }
+
+  return content;
+}
+
+export default createWidget("category-header-widget", {
+  tagName: "span.discourse-category-banners",
+
+  html() {
+    const path = window.location.pathname;
+    const category = this.register
+      .lookup("controller:navigation/category")
+      .get("category");
+
+    if (!category) {
+      return;
+    }
+
+    const isException = settings.exceptions
+      .split("|")
+      .filter(Boolean)
+      .includes(category.name);
+
+    if (/^\/c\//.test(path)) {
+      const hideMobile = !settings.show_mobile && this.site.mobileView;
+      const isSubCategory =
+        !settings.show_subcategory && category.parentCategory;
+      const hasNoCategoryDescription =
+        settings.hide_if_no_description && !category.description_text;
+
+      if (
+        !isException &&
+        !hasNoCategoryDescription &&
+        !isSubCategory &&
+        !hideMobile
+      ) {
+        document.body.classList.add("category-header");
+
+        return h(
+          `div.category-title-header.category-banner-${category.slug}`,
+          {
+            attributes: {
+              style: `background-color: #${category.color}; color: #${category.text_color};`,
+            },
+          },
+          h("div.category-title-contents", buildCategory(category))
+        );
+      }
+    } else {
+      document.body.classList.remove("category-header");
+    }
+  },
+});
diff --git a/package.json b/package.json
new file mode 100644
index 0000000..9df2b90
--- /dev/null
+++ b/package.json
@@ -0,0 +1,7 @@
+{
+  "author": "Discourse",
+  "license": "MIT",
+  "devDependencies": {
+    "eslint-config-discourse": "latest"
+  }
+}
diff --git a/settings.yml b/settings.yml
index f227a55..62463b6 100644
--- a/settings.yml
+++ b/settings.yml
@@ -18,4 +18,4 @@ exceptions:
   default: ""
   type: list
   list_type: simple
-  description: "Banner will not show for these categories"

[... diff too long, it was truncated ...]

GitHub sha: ac66be79

1 Like