Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(docs): add setting editor #83

Closed
wants to merge 3 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -300,6 +300,7 @@ lib
.pnp.*

.DS_Store
.idea

# dumi

Expand Down
12 changes: 7 additions & 5 deletions apps/docs/.dumi/theme/styles/heti.less
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,10 @@

@font-face {
font-family: 'Heti Hei SC';
src: local('PingFang SC Regular'), local('Heiti SC Regular'), local('Microsoft YaHei'),
local('Source Han Sans CN Regular'), local('Noto Sans CJK SC Regular'),
local('WenQuanYi Micro Hei'), local('Droid Sans Fallback');
src: local('PingFang SC Regular'), local('Heiti SC Regular'),
local('Microsoft YaHei'), local('Source Han Sans CN Regular'),
local('Noto Sans CJK SC Regular'), local('WenQuanYi Micro Hei'),
local('Droid Sans Fallback');
}

@font-face {
Expand Down Expand Up @@ -45,8 +46,9 @@
@font-face {
font-family: 'Heti Hei SC Light';
font-weight: 200;
src: local('PingFang SC Light'), local('Heiti SC Light'), 'Heti Hei SC Light Fallback',
local('Source Han Sans CN Light'), local('Noto Sans CJK SC Light');
src: local('PingFang SC Light'), local('Heiti SC Light'),
'Heti Hei SC Light Fallback', local('Source Han Sans CN Light'),
local('Noto Sans CJK SC Light');
}

@font-face {
Expand Down
2 changes: 2 additions & 0 deletions apps/docs/src/application-react/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { langBundles, l10n, L10nLang } from '@difizen/mana-l10n';

import { AntdMenuModule } from './antd-menu/index.js';
import { CommandPalette } from './command-palette/index.js';
import { ConfigurtionMenuModule } from './setting-editor/index.js';
import { ContentModule } from './content/index.js';
import { FileModule } from './file/index.js';
import styles from './index.module.less';
Expand All @@ -26,6 +27,7 @@ export default function App(): JSX.Element {
WorkbenchModule,
AntdMenuModule,
ContentModule,
ConfigurtionMenuModule,
LogoModule,
UerModule,
CommandPalette,
Expand Down
160 changes: 160 additions & 0 deletions apps/docs/src/application-react/setting-editor/configs.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,160 @@
import type { ConfigurationNode } from '@difizen/mana-app';
import { LocalConfigurationStorage } from '@difizen/mana-app';
import { l10n } from '@difizen/mana-l10n';

export const FontSize: ConfigurationNode<number> = {
id: 'libro.user.codeeditor.fontsize',
description: l10n.t('代码编辑区域字体大小'),
title: l10n.t('代码字号'),
type: 'inputnumber',
defaultValue: 13,
schema: {
type: 'number',
},
};

export const LineHeight: ConfigurationNode<number> = {
id: 'libro.user.codeeditor.lineheight',
description: l10n.t('代码编辑区域字体行高'),
title: l10n.t('代码行高'),
type: 'inputnumber',
defaultValue: 20,
schema: {
type: 'number',
},
};

export const TabSize: ConfigurationNode<number> = {
id: 'libro.user.codeeditor.tabsize',
description: l10n.t('tab转换为几个空格大小'),
title: l10n.t('tab大小'),
type: 'inputnumber',
defaultValue: 4,
schema: {
type: 'number',
},
};

export const InsertSpaces: ConfigurationNode<boolean> = {
id: 'libro.user.codeeditor.insertspaces',
description: l10n.t('输入tab是否转换为空格'),
title: l10n.t('tab转空格'),
type: 'checkbox',
defaultValue: true,
schema: {
type: 'boolean',
},
};

export const LineWarp: ConfigurationNode<'wordWrapColumn' | 'off' | 'on' | 'bounded'> =
{
id: 'libro.user.codeeditor.linewarp',
description: l10n.t(`自动换行策略:
- "off", lines will never wrap.
- "on", lines will wrap at the viewport border.
- "wordWrapColumn", lines will wrap at 'wordWrapColumn'.
- "bounded", lines will wrap at minimum between viewport width and wordWrapColumn.`),
title: l10n.t('自动换行'),
type: 'select',
defaultValue: 'off',
schema: {
type: 'string',
enum: ['off', 'on', 'wordWrapColumn', 'bounded'],
},
};

export const WordWrapColumn: ConfigurationNode<number> = {
id: 'libro.user.codeeditor.wordWrapColumn',
description: l10n.t('开启自动换行后,自动换行的列数'),
title: l10n.t('自动换行列数'),
type: 'inputnumber',
defaultValue: 80,
schema: {
type: 'number',
},
};

export const LSPEnabled: ConfigurationNode<boolean> = {
id: 'libro.user.codeeditor.lspenabled',
description: l10n.t(
'开启语言服务后,编辑器能提供更多辅助编码能力,包括:自动提示、代码诊断、hover提示、格式化、代码跳转、重命名等等',
),
title: l10n.t('开启语言服务'),
type: 'checkbox',
defaultValue: false,
schema: {
type: 'boolean',
},
};

export const DemoStringConfig: ConfigurationNode<string> = {
id: 'test.demostring',
description: 'input string',
title: 'input',
type: 'input',
defaultValue: 'this value stored in localstorage',
schema: {
type: 'string',
},
storage: LocalConfigurationStorage,
};

export const DemoNumberConfig: ConfigurationNode<number> = {
id: 'test.demonumber',
description: 'input a number',
title: 'inputnumber',
type: 'inputnumber',
defaultValue: 5,
schema: {
type: 'integer',
minimum: 0,
maximum: 10,
},
};

export const DemoBooleanConfig: ConfigurationNode<boolean> = {
id: 'test.democheckbox',
description: 'select checkbox',
title: 'checkbox',
type: 'checkbox',
defaultValue: false,
schema: {
type: 'boolean',
},
};

export const mockOptions = ['banana', 'grapes', 'orange'];

export const DemoSelectConfig: ConfigurationNode<string> = {
id: 'test.demoselect',
description: 'select an option',
title: 'select',
type: 'select',
defaultValue: 'banana',
schema: {
type: 'string',
enum: mockOptions,
},
};

export const DemoSwitchConfig: ConfigurationNode<boolean> = {
id: 'test.demoswitch',
description: 'switch it',
title: 'switch',
type: 'switch',
defaultValue: false,
schema: {
type: 'boolean',
},
};

export const DemoDateConfig: ConfigurationNode<string> = {
id: 'test.datepicker',
description: 'select date',
title: 'datepicker',
type: 'datepicker',
defaultValue: '2022/10/1',
schema: {
type: 'string',
},
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
import type { ConfigurationNode } from '@difizen/mana-app';
import {
BaseView,
ConfigurationRenderRegistry,
prop,
SchemaValidator,
transient,
useConfigurationValue,
useInject,
view,
ViewInstance,
} from '@difizen/mana-app';
import { Form } from 'antd';
import React from 'react';

import './index.less';

const layout = {
labelCol: { span: 8 },
wrapperCol: { span: 16 },
};

// eslint-disable-next-line @typescript-eslint/no-explicit-any
export const ConfigurationNodeRender: React.FC<{ node: ConfigurationNode<any> }> = ({
node,
}) => {
const configurationRenderRegistry = useInject(ConfigurationRenderRegistry);
const schemaValidator = useInject(SchemaValidator);
const Render = configurationRenderRegistry.getConfigurationRender(node);
const [value, setValue] = useConfigurationValue(node);
return (
<div key={node.id}>
{Render && (
<div id={node.id}>
<Form.Item
label={node.title}
extra={node.description}
rules={[
{
validator: (_, currentVal) => {
const valid = schemaValidator.validateNode(node, currentVal);
if (valid) {
return Promise.resolve();
}
return Promise.reject(new Error('invalid value'));
},
},
]}
hasFeedback
>
<Render
label={node.title}
value={value}
schema={node.schema}
onChange={(val) => {
setValue(val);
}}
/>
</Form.Item>
</div>
)}
</div>
);
};

export const DefaultConfigurationViewComponent: React.FC = () => {
const [form] = Form.useForm();
const viewInstance = useInject<ConfigurationPanelView>(ViewInstance);
const configs = viewInstance.configurationNodes;
return (
<Form
{...layout}
form={form}
className={`ai-infra-configuration-siteCard ${viewInstance.className}`}
>
{configs?.map((config) => {
return <ConfigurationNodeRender node={config} key={config.id} />;
})}
</Form>
);
};

@transient()
@view('ConfigurationPanel')
export class ConfigurationPanelView extends BaseView {
override view = DefaultConfigurationViewComponent;

@prop() // eslint-disable-next-line @typescript-eslint/no-explicit-any
configurationNodes: ConfigurationNode<any>[] = [];
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
import { singleton } from '@difizen/mana-app';
import type { ConfigurationRender } from '@difizen/mana-core';
import { ConfigurationRenderContribution } from '@difizen/mana-core';

import {
DefaultCheckbox,
DefaultInput,
DefaultInputNumber,
DefaultSelect,
DefaultSwitch,
DefaultDatePicker,
} from './default-node-render.js';

@singleton({ contrib: [ConfigurationRenderContribution] })
export class DefaultConfigurationRenderContribution
implements ConfigurationRenderContribution
{
registerConfigurationRenders(): ConfigurationRender[] {
return [
{
canHandle: (config) => {
if (config.type === 'input') {
return 1;
} else {
return false;
}
},
component: DefaultInput,
},
{
canHandle: (config) => {
if (config.type === 'checkbox') {
return 1;
} else {
return false;
}
},
component: DefaultCheckbox,
},
{
canHandle: (config) => {
if (config.type === 'switch') {
return 1;
} else {
return false;
}
},
component: DefaultSwitch,
},
{
canHandle: (config) => {
if (config.type === 'inputnumber') {
return 1;
} else {
return false;
}
},
component: DefaultInputNumber,
},
{
canHandle: (config) => {
if (config.type === 'select') {
return 1;
} else {
return false;
}
},
component: DefaultSelect,
},
{
canHandle: (config) => {
if (config.type === 'datepicker') {
return 1;
} else {
return false;
}
},
component: DefaultDatePicker,
},
];
}
}
Loading
Loading