From ed00f8f60e6a84772cd1b3dda9ec3777e15bd7c9 Mon Sep 17 00:00:00 2001 From: Elio Struyf Date: Wed, 4 Oct 2023 13:37:30 +0200 Subject: [PATCH] #517 - Added `frontMatter.panel.actions.disabled` setting to define which actions should be hidden --- CHANGELOG.md | 1 + l10n/bundle.l10n.json | 1 - src/constants/settings.ts | 1 + src/helpers/PanelSettings.ts | 10 ++- src/hooks/useContentType.tsx | 2 +- src/localization/localization.enum.ts | 4 - src/models/PanelSettings.ts | 10 +++ src/panelWebView/ViewPanel.tsx | 2 +- src/panelWebView/components/Actions.tsx | 107 +++++++++++++++++------ src/panelWebView/components/BaseView.tsx | 64 +------------- src/panelWebView/components/Preview.tsx | 12 +-- 11 files changed, 108 insertions(+), 106 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d6361436..e41dceb8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,7 @@ ### 🎨 Enhancements - [#517](https://github.com/estruyf/vscode-front-matter/issues/517): Add `contentTypes` property to custom scripts to show/hide custom actions +- [#517](https://github.com/estruyf/vscode-front-matter/issues/517): Added `frontMatter.panel.actions.disabled` setting to define which actions should be hidden - [#638](https://github.com/estruyf/vscode-front-matter/issues/638): Add Hexo support for the `_drafts` folder - [#659](https://github.com/estruyf/vscode-front-matter/issues/659): Implement a filter for the taxonomy dashboard - [#662](https://github.com/estruyf/vscode-front-matter/issues/662): Always show the `all articles` tab with the page counter diff --git a/l10n/bundle.l10n.json b/l10n/bundle.l10n.json index 91d25cf3..2bcf9160 100644 --- a/l10n/bundle.l10n.json +++ b/l10n/bundle.l10n.json @@ -377,7 +377,6 @@ "panel.baseView.initialize": "Initialize project", "panel.baseView.actions.title": "Actions", "panel.baseView.action.openDashboard": "Open dashboard", - "panel.baseView.action.openPreview": "Open preview", "panel.baseView.action.createContent": "Create content", "panel.baseView.empty": "Open a file to see more actions", diff --git a/src/constants/settings.ts b/src/constants/settings.ts index c5829b38..02a818b8 100644 --- a/src/constants/settings.ts +++ b/src/constants/settings.ts @@ -46,6 +46,7 @@ export const SETTING_TEMPLATES_ENABLED = 'templates.enabled'; export const SETTING_TELEMETRY_DISABLE = 'telemetry.disable'; export const SETTING_PANEL_FREEFORM = 'panel.freeform'; +export const SETTING_PANEL_ACTIONS_DISABLED = 'panel.actions.disabled'; export const SETTING_PREVIEW_HOST = 'preview.host'; export const SETTING_PREVIEW_PATHNAME = 'preview.pathName'; diff --git a/src/helpers/PanelSettings.ts b/src/helpers/PanelSettings.ts index 19c24584..160d7d9c 100644 --- a/src/helpers/PanelSettings.ts +++ b/src/helpers/PanelSettings.ts @@ -1,4 +1,8 @@ -import { SETTING_SPONSORS_AI_ENABLED, SETTING_WEBSITE_URL } from './../constants/settings'; +import { + SETTING_PANEL_ACTIONS_DISABLED, + SETTING_SPONSORS_AI_ENABLED, + SETTING_WEBSITE_URL +} from './../constants/settings'; import { workspace } from 'vscode'; import { ContentType, Extension, Settings, TaxonomyHelper } from '.'; import { Dashboard } from '../commands/Dashboard'; @@ -38,6 +42,7 @@ import { DraftField, FieldGroup, PanelSettings as IPanelSettings, + PanelAction, ScriptType, TaxonomyType } from '../models'; @@ -97,7 +102,8 @@ export class PanelSettings { dataTypes: Settings.get(SETTING_DATA_TYPES), fieldGroups: Settings.get(SETTING_TAXONOMY_FIELD_GROUPS), contentFolders: Folders.get(), - websiteUrl: Settings.get(SETTING_WEBSITE_URL) || '' + websiteUrl: Settings.get(SETTING_WEBSITE_URL) || '', + disabledActions: Settings.get(SETTING_PANEL_ACTIONS_DISABLED) || [] }; } diff --git a/src/hooks/useContentType.tsx b/src/hooks/useContentType.tsx index 25c630ab..a0ab0fde 100644 --- a/src/hooks/useContentType.tsx +++ b/src/hooks/useContentType.tsx @@ -10,7 +10,7 @@ export default function useContentType( const [contentType, setContentType] = useState(null); useEffect(() => { - if (settings) { + if (settings && metadata) { let contentTypeName = DEFAULT_CONTENT_TYPE_NAME; if (metadata?.type) { diff --git a/src/localization/localization.enum.ts b/src/localization/localization.enum.ts index 3788da89..64c5e11c 100644 --- a/src/localization/localization.enum.ts +++ b/src/localization/localization.enum.ts @@ -1208,10 +1208,6 @@ export enum LocalizationKey { * Open dashboard */ panelBaseViewActionOpenDashboard = 'panel.baseView.action.openDashboard', - /** - * Open preview - */ - panelBaseViewActionOpenPreview = 'panel.baseView.action.openPreview', /** * Create content */ diff --git a/src/models/PanelSettings.ts b/src/models/PanelSettings.ts index 542d59e7..b7dbb7bb 100644 --- a/src/models/PanelSettings.ts +++ b/src/models/PanelSettings.ts @@ -31,8 +31,18 @@ export interface PanelSettings { aiEnabled: boolean; contentFolders: ContentFolder[]; websiteUrl: string; + disabledActions: PanelAction[]; } +export type PanelAction = + | 'openDashboard' + | 'createContent' + | 'optimizeSlug' + | 'preview' + | 'openOnWebsite' + | 'startStopServer' + | 'customActions'; + export interface FieldGroup { id: string; labelField?: string; diff --git a/src/panelWebView/ViewPanel.tsx b/src/panelWebView/ViewPanel.tsx index edc9e3dc..de78eb23 100644 --- a/src/panelWebView/ViewPanel.tsx +++ b/src/panelWebView/ViewPanel.tsx @@ -134,7 +134,7 @@ export const ViewPanel: React.FunctionComponent = ( )} {settings && metadata && ( - + )} diff --git a/src/panelWebView/components/Actions.tsx b/src/panelWebView/components/Actions.tsx index 5138f47f..fa62f05d 100644 --- a/src/panelWebView/components/Actions.tsx +++ b/src/panelWebView/components/Actions.tsx @@ -1,5 +1,5 @@ import * as React from 'react'; -import { PanelSettings } from '../../models/PanelSettings'; +import { PanelSettings, CustomScript as ICustomScript } from '../../models'; import { Collapsible } from './Collapsible'; import { CustomScript } from './CustomScript'; import { Preview } from './Preview'; @@ -9,59 +9,114 @@ import * as l10n from '@vscode/l10n'; import { LocalizationKey } from '../../localization'; import { OpenOnWebsiteAction } from './Actions/OpenOnWebsiteAction'; import useContentType from '../../hooks/useContentType'; +import { messageHandler } from '@estruyf/vscode/dist/client'; +import { CommandToCode } from '../CommandToCode'; export interface IActionsProps { - metadata: any; + metadata?: any; settings: PanelSettings; + scripts?: ICustomScript[]; } const Actions: React.FunctionComponent = ({ metadata, - settings + settings, + scripts = [] }: React.PropsWithChildren) => { const contentType = useContentType(settings, metadata); + const disableActions = settings.disabledActions || []; + + const openDashboard = () => { + messageHandler.send(CommandToCode.openDashboard); + }; + + const createContent = () => { + messageHandler.send(CommandToCode.createContent); + }; const actions = React.useMemo(() => { let allActions: JSX.Element[] = []; - let scripts = settings.scripts || []; - if (contentType?.name) { - scripts = scripts.filter((script) => { - if (script.contentTypes && script.contentTypes.length > 0) { - return script.contentTypes.includes(contentType.name); - } + if (!disableActions.includes(`openDashboard`)) { + allActions.push( + + ); + } + + if (metadata?.title && !disableActions.includes(`optimizeSlug`)) { + allActions.push(); + } + + if (settings?.preview?.host && !disableActions.includes(`preview`)) { + if ((metadata && metadata.slug) || !metadata) { + allActions.push(); + } + } + + if (!disableActions.includes(`openOnWebsite`) && metadata?.slug) { + allActions.push(); + } + + if (!disableActions.includes(`startStopServer`)) { + allActions.push(); + } - return true; - }); + if (!disableActions.includes(`createContent`)) { + allActions.push( + + ); } - allActions = scripts.map((value, idx) => ( - - )) + return allActions; + }, [metadata, settings, disableActions]); + + + const customActions = React.useMemo(() => { + let allActions: JSX.Element[] = []; + + if (!disableActions.includes(`customActions`)) { + if (contentType?.name) { + scripts = scripts.filter((script) => { + if (script.contentTypes && script.contentTypes.length > 0) { + return script.contentTypes.includes(contentType.name); + } + + return true; + }); + } + + allActions = scripts.map((value, idx) => ( + + )) + } return allActions; - }, [settings.scripts, contentType]); + }, [scripts, contentType, disableActions]); - if (!metadata || Object.keys(metadata).length === 0 || !settings) { + if (!settings || (customActions.length === 0 && actions.length === 0)) { return null; } return (
- {metadata && metadata.title && } - - {settings?.preview?.host && } - - - - + {...actions} - {settings && settings.scripts && settings.scripts.length > 0 && ( + {customActions?.length > 0 && ( <> -
+ {actions?.length > 0 &&
} - {...actions} + {...customActions} )}
diff --git a/src/panelWebView/components/BaseView.tsx b/src/panelWebView/components/BaseView.tsx index 632a427e..5821bdbd 100644 --- a/src/panelWebView/components/BaseView.tsx +++ b/src/panelWebView/components/BaseView.tsx @@ -1,20 +1,17 @@ import * as React from 'react'; -import { CustomScript, FolderInfo, Mode, PanelSettings } from '../../models'; -import { CommandToCode } from '../CommandToCode'; -import { Collapsible } from './Collapsible'; +import { FolderInfo, Mode, PanelSettings } from '../../models'; import { GlobalSettings } from './GlobalSettings'; import { OtherActions } from './OtherActions'; import { FolderAndFiles } from './FolderAndFiles'; import { SponsorMsg } from './SponsorMsg'; -import { StartServerButton } from './StartServerButton'; import { FeatureFlag } from '../../components/features/FeatureFlag'; import { FEATURE_FLAG } from '../../constants/Features'; -import { Messenger } from '@estruyf/vscode/dist/client'; import { GitAction } from './Git/GitAction'; import { useMemo } from 'react'; import * as l10n from "@vscode/l10n" import { LocalizationKey } from '../../localization'; import { InitializeAction } from './InitializeAction'; +import { Actions } from './Actions'; export interface IBaseViewProps { settings: PanelSettings | undefined; @@ -27,25 +24,6 @@ const BaseView: React.FunctionComponent = ({ folderAndFiles, mode }: React.PropsWithChildren) => { - const openDashboard = () => { - Messenger.send(CommandToCode.openDashboard); - }; - - const createContent = () => { - Messenger.send(CommandToCode.createContent); - }; - - const openPreview = () => { - Messenger.send(CommandToCode.openPreview); - }; - - const runBulkScript = (script: CustomScript) => { - Messenger.send(CommandToCode.runCustomScript, { - title: script.title, - script - }); - }; - const customActions: any[] = (settings?.scripts || []).filter( (s) => s.bulk && (s.type === 'content' || !s.type) ); @@ -83,43 +61,7 @@ const BaseView: React.FunctionComponent = ({ - -
- - - - - - - - - {customActions.map((script) => ( - - ))} -
-
+
)} diff --git a/src/panelWebView/components/Preview.tsx b/src/panelWebView/components/Preview.tsx index 0a453562..5b8629f1 100644 --- a/src/panelWebView/components/Preview.tsx +++ b/src/panelWebView/components/Preview.tsx @@ -5,21 +5,13 @@ import { ActionButton } from './ActionButton'; import * as l10n from '@vscode/l10n'; import { LocalizationKey } from '../../localization'; -export interface IPreviewProps { - slug: string; -} +export interface IPreviewProps { } -const Preview: React.FunctionComponent = ({ - slug -}: React.PropsWithChildren) => { +const Preview: React.FunctionComponent = (_: React.PropsWithChildren) => { const open = () => { Messenger.send(CommandToCode.openPreview); }; - if (!slug) { - return null; - } - return ; };