From 155d6152178cb731af6e5b32cdee81efc121822a Mon Sep 17 00:00:00 2001 From: Davide Iadeluca <146922689+DavideIadeluca@users.noreply.github.com> Date: Fri, 29 Nov 2024 19:14:17 +0100 Subject: [PATCH] refactor: improve extensibility (#113) * refactor: improve extensibility * chore * chore: further improve extensibility * chore --- js/src/forum/components/SolvedFilter.tsx | 67 ++++++++++++++++++++++ js/src/forum/components/index.ts | 2 + js/src/forum/extenders/extendIndexPage.tsx | 54 +---------------- 3 files changed, 71 insertions(+), 52 deletions(-) create mode 100644 js/src/forum/components/SolvedFilter.tsx diff --git a/js/src/forum/components/SolvedFilter.tsx b/js/src/forum/components/SolvedFilter.tsx new file mode 100644 index 0000000..370b828 --- /dev/null +++ b/js/src/forum/components/SolvedFilter.tsx @@ -0,0 +1,67 @@ +import app from 'flarum/forum/app'; +import Component, { ComponentAttrs } from 'flarum/common/Component'; +import Dropdown from 'flarum/common/components/Dropdown'; +import Button from 'flarum/common/components/Button'; +import type Tag from 'flarum/tags/common/models/Tag'; + +export interface SolvedFilterAttrs extends ComponentAttrs { + alwaysShow?: boolean; +} + +export default class SolvedFilter extends Component { + view() { + if (!this.shouldShowFilter()) return null; + + const selected = app.discussions.bestAnswer as unknown as number; + const options = ['all', 'solved', 'unsolved']; + + return Dropdown.component( + { + buttonClassName: 'Button', + label: app.translator.trans( + `fof-best-answer.forum.filter.${options[selected] || Object.keys(options).map((key) => options[Number(key)])[0]}_label` + ), + accessibleToggleLabel: app.translator.trans('fof-best-answer.forum.filter.accessible_label'), + }, + Object.keys(options).map((value) => { + const label = options[Number(value)]; + const active = (selected || Object.keys(options)[0]) === value; + + return Button.component( + { + icon: active ? 'fas fa-check' : true, + active: active, + onclick: () => { + app.discussions.bestAnswer = value; + if (value === '0') { + delete app.discussions.bestAnswer; + } + app.discussions.refresh(); + }, + }, + app.translator.trans(`fof-best-answer.forum.filter.${label}_label`) + ); + }) + ); + } + + shouldShowFilter() { + const { alwaysShow } = this.attrs; + + if (alwaysShow) return true; + + if (!app.forum.attribute('showBestAnswerFilterUi')) return false; + + const tag: Tag = app.current.get('tag'); + + if (!tag?.isQnA?.()) { + if (app.discussions.bestAnswer) { + delete app.discussions.bestAnswer; + app.discussions.refresh(); + } + return false; + } + + return true; + } +} diff --git a/js/src/forum/components/index.ts b/js/src/forum/components/index.ts index 7970eae..f092908 100644 --- a/js/src/forum/components/index.ts +++ b/js/src/forum/components/index.ts @@ -6,6 +6,7 @@ import SelectBestAnswerItem from './SelectBestAnswerItem'; import SelectBestAnswerNotification from './SelectBestAnswerNotification'; import SolutionSearchItem from './SolutionSearchItem'; import SolutionSearchSource from './SolutionSearchSource'; +import SolvedFilter from './SolvedFilter'; export const components = { SelectBestAnswerItem, @@ -16,4 +17,5 @@ export const components = { BestAnswerInDiscussionNotification, SelectBestAnswerNotification, SolutionSearchItem, + SolvedFilter, }; diff --git a/js/src/forum/extenders/extendIndexPage.tsx b/js/src/forum/extenders/extendIndexPage.tsx index d331f5a..f769d08 100644 --- a/js/src/forum/extenders/extendIndexPage.tsx +++ b/js/src/forum/extenders/extendIndexPage.tsx @@ -1,8 +1,7 @@ import app from 'flarum/forum/app'; import { extend } from 'flarum/common/extend'; import IndexPage from 'flarum/forum/components/IndexPage'; -import Dropdown from 'flarum/common/components/Dropdown'; -import Button from 'flarum/common/components/Button'; +import SolvedFilter from '../components/SolvedFilter'; export default function extendIndexPage() { extend(IndexPage.prototype, 'sidebarItems', function (items) { @@ -22,55 +21,6 @@ export default function extendIndexPage() { }); extend(IndexPage.prototype, 'viewItems', function (items) { - if (!app.forum.attribute('showBestAnswerFilterUi')) { - return; - } - - const tag = this.currentTag(); - - if (!tag?.isQnA?.()) { - if (app.discussions.bestAnswer) { - delete app.discussions.bestAnswer; - app.discussions.refresh(); - } - - return; - } - - const options = ['all', 'solved', 'unsolved']; - - const selected = app.discussions.bestAnswer as unknown as number; - - items.add( - 'solved-filter', - Dropdown.component( - { - buttonClassName: 'Button', - label: app.translator.trans( - `fof-best-answer.forum.filter.${options[selected] || Object.keys(options).map((key) => options[Number(key)])[0]}_label` - ), - accessibleToggleLabel: app.translator.trans('fof-best-answer.forum.filter.accessible_label'), - }, - Object.keys(options).map((value) => { - const label = options[Number(value)]; - const active = (selected || Object.keys(options)[0]) === value; - - return Button.component( - { - icon: active ? 'fas fa-check' : true, - active: active, - onclick: () => { - app.discussions.bestAnswer = value; - if (value === '0') { - delete app.discussions.bestAnswer; - } - app.discussions.refresh(); - }, - }, - app.translator.trans(`fof-best-answer.forum.filter.${label}_label`) - ); - }) - ) - ); + items.add('solved-filter', ); }); }