From 6027418f0399f2f0674efdd21545e5550a445dec Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 6 Nov 2025 15:52:42 +0000 Subject: [PATCH 1/3] Initial plan From 9abcf5c172e1ffb397eeb6ec01fb56a7651937e0 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 6 Nov 2025 16:03:26 +0000 Subject: [PATCH 2/3] Fix: Correct import path case sensitivity issues Co-authored-by: CoderBoyBoy <11583532+CoderBoyBoy@users.noreply.github.com> --- core/App.vue | 2 +- core/component/apisModel/requestBody.vue | 2 +- core/component/apisModel/responses.vue | 2 +- core/component/basic/attrItemList.vue | 4 ++-- core/component/basic/attrItemListView.vue | 4 ++-- core/component/basic/exampleBasic.vue | 2 +- core/component/basic/responseSchema.vue | 2 +- core/component/requestBody/index.vue | 2 +- core/component/response/index.vue | 2 +- core/extensions/formView/index.vue | 2 +- core/security/preView/index.vue | 2 +- core/server/preView/index.vue | 2 +- core/siderMenu/index.vue | 14 +++++++------- 13 files changed, 21 insertions(+), 21 deletions(-) diff --git a/core/App.vue b/core/App.vue index 6370264..c55a0f9 100644 --- a/core/App.vue +++ b/core/App.vue @@ -35,7 +35,7 @@ const Comp = defineAsyncComponent(() => import('./component/index.vue')); const ApiModel = defineAsyncComponent(() => import('./component/apisModel/index.vue')); const PathInfo = defineAsyncComponent(() => import('./pathInfo/index.vue')); -const DocInfoPreview = defineAsyncComponent(() => import('./docInfo/preview/index.vue')); +const DocInfoPreview = defineAsyncComponent(() => import('./docInfo/preView/index.vue')); const ExternalDocPreview = defineAsyncComponent(() => import('./externalDoc/preView/index.vue')); const ServerPreview = defineAsyncComponent(() => import('./server/preView/index.vue')); const SecurityPreview = defineAsyncComponent(() => import('./security/preView/index.vue')); diff --git a/core/component/apisModel/requestBody.vue b/core/component/apisModel/requestBody.vue index c3817bb..a57ec09 100644 --- a/core/component/apisModel/requestBody.vue +++ b/core/component/apisModel/requestBody.vue @@ -4,7 +4,7 @@ import { Button, TabPane, Tabs, Select } from 'ant-design-vue'; import { NotificationOutlined } from '@ant-design/icons-vue'; import { CONTENT_TYPE } from '../basic/utils'; import BodyContentTypeTab from '../basic/bodyContentTypeTab.vue'; -import Dropdown from '@/common/dropdown/index.vue'; +import Dropdown from '@/common/Dropdown/index.vue'; const descRef = ref(); const EasyMd = defineAsyncComponent(() => import('@/common/easyMd/index.vue')); diff --git a/core/component/apisModel/responses.vue b/core/component/apisModel/responses.vue index 5f30438..0b43ace 100644 --- a/core/component/apisModel/responses.vue +++ b/core/component/apisModel/responses.vue @@ -3,7 +3,7 @@ import { onMounted, ref, watch, Ref } from 'vue'; import { Button, TabPane, Tabs, Input } from 'ant-design-vue'; // import ResponseSchema from '../basic/responseSchema.vue'; import {httpStatus} from './PropTypes'; -import Dropdown from '@/common/dropdown/index.vue'; +import Dropdown from '@/common/Dropdown/index.vue'; import responseTabPane from './responseTabPane.vue'; interface Props { diff --git a/core/component/basic/attrItemList.vue b/core/component/basic/attrItemList.vue index 13be4f6..2d72dab 100644 --- a/core/component/basic/attrItemList.vue +++ b/core/component/basic/attrItemList.vue @@ -52,8 +52,8 @@ - - + + - + - - + + {{useLocal(language)('import')}} {{ useLocal(language)('export')}} + + 🌙 + ☀️ + - + {{useLocal(language)('form')}} {{useLocal(language)('code')}} {{useLocal(language)('preview')}} - - - - - - - + + + + + + + - + @@ -304,7 +317,7 @@ provide('language', language); - + @@ -339,11 +352,39 @@ provide('language', language); font-size: 13px; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; - color: #525A65; + color: var(--text-secondary); + background-color: var(--bg-secondary); +} + +.api-sidebar { + background-color: var(--bg-sidebar); + border-right: 1px solid var(--border-primary); + padding: var(--spacing-lg); + transition: all var(--transition-base); +} + +.api-content { + background-color: var(--bg-primary); + padding-left: var(--spacing-lg); +} + +.bg-primary { + background-color: var(--bg-primary); +} + +.border-b { + border-bottom: 1px solid var(--border-primary); +} + +.theme-toggle-btn { + font-size: 16px; + display: flex; + align-items: center; + justify-content: center; } .ant-input.ant-input-borderless:hover { - @apply bg-gray-200; + background-color: var(--bg-hover); } .api-root .ant-tabs.view-type-tab>.ant-tabs-nav { diff --git a/core/docInfo/formView/index.vue b/core/docInfo/formView/index.vue index 2202a88..99df4fe 100644 --- a/core/docInfo/formView/index.vue +++ b/core/docInfo/formView/index.vue @@ -73,27 +73,27 @@ const licenseTypeOpt = computed(() =>[ } ]); -const getData = () => { - const data = JSON.parse(JSON.stringify(formState.value)); +const getFormData = () => { + const formData = JSON.parse(JSON.stringify(formState.value)); const description = descRef.value.getValue(); - const {contact, license} = data; - data.description = description; + const {contact, license} = formData; + formData.description = description; if (contact && !contact.name && !contact.url && !contact.email ) { - delete data.contact; + delete formData.contact; } if (!license.name) { - delete data.contact; + delete formData.license; } else if (licenseType.value === 'identifier') { - delete data.license.url; + delete formData.license.url; } else if (licenseType.value === 'url') { - delete data.license.identifier; + delete formData.license.identifier; } - return data; + return formData; }; onMounted(() => { - getAppFunc({name: 'updateData', func: saveData}); + getAppFunc({name: 'updateData', func: saveFormData}); watch(() => props.dataSource?.info, () => { easyMdKey.value += 1; formState.value = props.dataSource?.info || {}; @@ -116,17 +116,17 @@ onMounted(() => { }); }); -const saveData = () => { - dataSource.value.info = getData(); +const saveFormData = () => { + dataSource.value.info = getFormData(); } onBeforeUnmount(() => { getAppFunc({name: 'updateData', func: null}); - saveData(); + saveFormData(); }); defineExpose({ - getData: getData + getData: getFormData }); diff --git a/core/siderMenu/index.vue b/core/siderMenu/index.vue index 91a2a8e..e5bb08d 100644 --- a/core/siderMenu/index.vue +++ b/core/siderMenu/index.vue @@ -95,10 +95,8 @@ const handlekeywordsChange = debounce(600, () => { Object.keys(apiPaths.value).forEach(path => { if (path.includes(searchKeywords.value)) { compExpandMap.value['apis'] = true; - console.log(path); } Object.keys(apiPaths.value[path]).forEach(method => { - console.log(path); if (apiPaths.value[path][method].summary.includes(searchKeywords.value)) { compExpandMap.value[path] = true; compExpandMap.value['apis'] = true; diff --git a/core/styles/forms.css b/core/styles/forms.css new file mode 100644 index 0000000..bc269b6 --- /dev/null +++ b/core/styles/forms.css @@ -0,0 +1,316 @@ +/* Form Beautification Styles */ + +/* ===== Form Container ===== */ +.api-form-container { + background-color: var(--bg-primary); + border-radius: var(--radius-lg); + padding: var(--spacing-xl); + transition: all var(--transition-base); +} + +/* ===== Form Sections ===== */ +.form-section { + margin-bottom: var(--spacing-xl); + padding: var(--spacing-lg); + background-color: var(--bg-secondary); + border: 1px solid var(--border-primary); + border-radius: var(--radius-md); + transition: all var(--transition-base); +} + +.form-section:hover { + border-color: var(--border-hover); + box-shadow: var(--card-shadow); +} + +.form-section-title { + font-size: var(--font-size-lg); + font-weight: var(--font-weight-semibold); + color: var(--text-primary); + margin-bottom: var(--spacing-md); + padding-bottom: var(--spacing-sm); + border-bottom: 2px solid var(--border-primary); +} + +/* ===== Form Items ===== */ +.ant-form-item { + margin-bottom: var(--spacing-lg); +} + +.ant-form-item-label > label { + color: var(--text-secondary); + font-weight: var(--font-weight-medium); + font-size: var(--font-size-sm); +} + +/* ===== Input Fields ===== */ +.ant-input, +.ant-input-number, +.ant-select-selector { + background-color: var(--input-bg) !important; + border-color: var(--input-border) !important; + color: var(--text-primary) !important; + border-radius: var(--radius-sm) !important; + transition: all var(--transition-fast) !important; +} + +.ant-input:hover, +.ant-input-number:hover, +.ant-select:not(.ant-select-disabled):hover .ant-select-selector { + border-color: var(--border-hover) !important; +} + +.ant-input:focus, +.ant-input-number:focus, +.ant-select-focused .ant-select-selector { + border-color: var(--input-focus-border) !important; + box-shadow: 0 0 0 2px rgba(59, 130, 246, 0.1) !important; +} + +.ant-input::placeholder { + color: var(--text-placeholder); +} + +/* ===== Textarea ===== */ +.ant-input-textarea textarea { + background-color: var(--input-bg) !important; + border-color: var(--input-border) !important; + color: var(--text-primary) !important; + border-radius: var(--radius-sm) !important; +} + +/* ===== Select Dropdown ===== */ +.ant-select-dropdown { + background-color: var(--bg-primary); + border: 1px solid var(--border-primary); + border-radius: var(--radius-md); + box-shadow: var(--card-shadow-hover); +} + +.ant-select-item { + color: var(--text-primary); +} + +.ant-select-item-option-selected { + background-color: var(--bg-hover); +} + +.ant-select-item-option-active { + background-color: var(--bg-tertiary); +} + +/* ===== Buttons ===== */ +.ant-btn { + border-radius: var(--radius-sm); + font-weight: var(--font-weight-medium); + transition: all var(--transition-fast); + border: 1px solid var(--border-primary); +} + +.ant-btn-primary { + background-color: var(--color-primary); + border-color: var(--color-primary); +} + +.ant-btn-primary:hover { + background-color: var(--color-primary-hover); + border-color: var(--color-primary-hover); +} + +.ant-btn-primary:active { + background-color: var(--color-primary-active); + border-color: var(--color-primary-active); +} + +/* ===== Radio & Checkbox ===== */ +.ant-radio-button-wrapper { + background-color: var(--bg-secondary); + border-color: var(--border-primary); + color: var(--text-secondary); +} + +.ant-radio-button-wrapper:hover { + color: var(--color-primary); +} + +.ant-radio-button-wrapper-checked { + background-color: var(--color-primary); + border-color: var(--color-primary); + color: #ffffff; +} + +/* ===== Tags ===== */ +.ant-tag { + background-color: var(--bg-tertiary); + border-color: var(--border-primary); + color: var(--text-primary); + border-radius: var(--radius-sm); + padding: 2px 8px; + font-size: var(--font-size-xs); +} + +/* ===== Cards ===== */ +.ant-card { + background-color: var(--bg-primary); + border: 1px solid var(--border-primary); + border-radius: var(--radius-md); + box-shadow: var(--card-shadow); + transition: all var(--transition-base); +} + +.ant-card:hover { + box-shadow: var(--card-shadow-hover); +} + +.ant-card-head { + border-bottom: 1px solid var(--border-primary); + color: var(--text-primary); + font-weight: var(--font-weight-semibold); +} + +/* ===== Tables ===== */ +.ant-table { + background-color: var(--bg-primary); + color: var(--text-primary); +} + +.ant-table-thead > tr > th { + background-color: var(--bg-secondary); + border-bottom: 2px solid var(--border-primary); + color: var(--text-primary); + font-weight: var(--font-weight-semibold); +} + +.ant-table-tbody > tr > td { + border-bottom: 1px solid var(--border-primary); +} + +.ant-table-tbody > tr:hover > td { + background-color: var(--bg-hover); +} + +/* ===== Modal ===== */ +.ant-modal-content { + background-color: var(--bg-primary); + border-radius: var(--radius-lg); +} + +.ant-modal-header { + background-color: var(--bg-primary); + border-bottom: 1px solid var(--border-primary); + border-radius: var(--radius-lg) var(--radius-lg) 0 0; +} + +.ant-modal-title { + color: var(--text-primary); + font-weight: var(--font-weight-semibold); +} + +.ant-modal-body { + color: var(--text-primary); +} + +.ant-modal-footer { + border-top: 1px solid var(--border-primary); +} + +/* ===== Tabs ===== */ +.ant-tabs-tab { + color: var(--text-secondary); + transition: all var(--transition-fast); +} + +.ant-tabs-tab:hover { + color: var(--color-primary); +} + +.ant-tabs-tab-active .ant-tabs-tab-btn { + color: var(--color-primary); + font-weight: var(--font-weight-semibold); +} + +.ant-tabs-ink-bar { + background-color: var(--color-primary); +} + +/* ===== Sidebar Enhancement ===== */ +.api-root .w-80 { + background-color: var(--bg-sidebar); + border-right: 1px solid var(--border-primary); + padding: var(--spacing-lg); +} + +/* ===== HTTP Method Tags ===== */ +.http-method-get { + background-color: var(--http-get); + color: white; +} + +.http-method-post { + background-color: var(--http-post); + color: white; +} + +.http-method-put { + background-color: var(--http-put); + color: white; +} + +.http-method-patch { + background-color: var(--http-patch); + color: white; +} + +.http-method-delete { + background-color: var(--http-delete); + color: white; +} + +.http-method-options { + background-color: var(--http-options); + color: white; +} + +/* ===== Improved Spacing ===== */ +.space-y-comfortable > * + * { + margin-top: var(--spacing-lg); +} + +.space-x-comfortable > * + * { + margin-left: var(--spacing-lg); +} + +/* ===== Better Visual Hierarchy ===== */ +.visual-hierarchy-1 { + font-size: var(--font-size-xl); + font-weight: var(--font-weight-bold); + color: var(--text-primary); + margin-bottom: var(--spacing-lg); +} + +.visual-hierarchy-2 { + font-size: var(--font-size-lg); + font-weight: var(--font-weight-semibold); + color: var(--text-primary); + margin-bottom: var(--spacing-md); +} + +.visual-hierarchy-3 { + font-size: var(--font-size-base); + font-weight: var(--font-weight-medium); + color: var(--text-secondary); + margin-bottom: var(--spacing-sm); +} + +/* ===== Improved Dividers ===== */ +.divider-subtle { + height: 1px; + background-color: var(--border-primary); + margin: var(--spacing-lg) 0; +} + +.divider-prominent { + height: 2px; + background-color: var(--border-secondary); + margin: var(--spacing-xl) 0; +} diff --git a/core/styles/theme.css b/core/styles/theme.css new file mode 100644 index 0000000..9f32823 --- /dev/null +++ b/core/styles/theme.css @@ -0,0 +1,169 @@ +/* Theme Variables - Light and Dark Mode Support */ + +:root { + /* ===== Light Theme (Default) ===== */ + + /* Background Colors */ + --bg-primary: #ffffff; + --bg-secondary: #f9fafb; + --bg-tertiary: #f3f4f6; + --bg-hover: #e5e7eb; + --bg-active: #d1d5db; + --bg-sidebar: #f9fafb; + + /* Text Colors */ + --text-primary: #111827; + --text-secondary: #525A65; + --text-tertiary: #6b7280; + --text-placeholder: #9ca3af; + --text-disabled: #d1d5db; + + /* Border Colors */ + --border-primary: #e5e7eb; + --border-secondary: #d1d5db; + --border-focus: #3b82f6; + --border-hover: #9ca3af; + + /* Brand Colors */ + --color-primary: #3b82f6; + --color-primary-hover: #2563eb; + --color-primary-active: #1d4ed8; + --color-primary-light: #dbeafe; + + /* Status Colors */ + --color-success: #52C41A; + --color-warning: #FFA52B; + --color-error: #F5222D; + --color-info: #2D8EFF; + + /* HTTP Method Colors */ + --http-get: #1E88E5; + --http-post: #33B782; + --http-put: #FFA726; + --http-patch: #AB47BC; + --http-delete: #FF5252; + --http-options: #009688; + + /* Component Specific */ + --input-bg: #ffffff; + --input-border: #d1d5db; + --input-focus-border: #3b82f6; + --input-disabled-bg: #f3f4f6; + + --card-shadow: 0 1px 3px 0 rgb(0 0 0 / 0.1), 0 1px 2px -1px rgb(0 0 0 / 0.1); + --card-shadow-hover: 0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1); + + /* Layout */ + --sidebar-width: 320px; + --header-height: 64px; + --spacing-xs: 4px; + --spacing-sm: 8px; + --spacing-md: 12px; + --spacing-lg: 16px; + --spacing-xl: 24px; + + /* Typography */ + --font-size-xs: 12px; + --font-size-sm: 13px; + --font-size-base: 14px; + --font-size-lg: 16px; + --font-size-xl: 20px; + + --font-weight-normal: 400; + --font-weight-medium: 500; + --font-weight-semibold: 600; + --font-weight-bold: 700; + + /* Border Radius */ + --radius-sm: 4px; + --radius-md: 6px; + --radius-lg: 8px; + + /* Transitions */ + --transition-fast: 150ms ease-in-out; + --transition-base: 200ms ease-in-out; + --transition-slow: 300ms ease-in-out; +} + +/* ===== Dark Theme ===== */ +[data-theme="dark"] { + /* Background Colors */ + --bg-primary: #1f2937; + --bg-secondary: #111827; + --bg-tertiary: #374151; + --bg-hover: #4b5563; + --bg-active: #6b7280; + --bg-sidebar: #111827; + + /* Text Colors */ + --text-primary: #f9fafb; + --text-secondary: #e5e7eb; + --text-tertiary: #d1d5db; + --text-placeholder: #9ca3af; + --text-disabled: #6b7280; + + /* Border Colors */ + --border-primary: #374151; + --border-secondary: #4b5563; + --border-focus: #60a5fa; + --border-hover: #6b7280; + + /* Brand Colors */ + --color-primary: #60a5fa; + --color-primary-hover: #3b82f6; + --color-primary-active: #2563eb; + --color-primary-light: #1e3a8a; + + /* Component Specific */ + --input-bg: #374151; + --input-border: #4b5563; + --input-focus-border: #60a5fa; + --input-disabled-bg: #1f2937; + + --card-shadow: 0 1px 3px 0 rgb(0 0 0 / 0.3), 0 1px 2px -1px rgb(0 0 0 / 0.3); + --card-shadow-hover: 0 4px 6px -1px rgb(0 0 0 / 0.3), 0 2px 4px -2px rgb(0 0 0 / 0.3); +} + +/* ===== Global Styles ===== */ + +* { + box-sizing: border-box; +} + +body { + background-color: var(--bg-primary); + color: var(--text-primary); + transition: background-color var(--transition-base), color var(--transition-base); +} + +/* Scrollbar Styling */ +::-webkit-scrollbar { + width: 8px; + height: 8px; +} + +::-webkit-scrollbar-track { + background: var(--bg-secondary); + border-radius: var(--radius-sm); +} + +::-webkit-scrollbar-thumb { + background: var(--border-secondary); + border-radius: var(--radius-sm); +} + +::-webkit-scrollbar-thumb:hover { + background: var(--border-hover); +} + +/* Focus Styles */ +*:focus-visible { + outline: 2px solid var(--border-focus); + outline-offset: 2px; +} + +/* Selection */ +::selection { + background-color: var(--color-primary-light); + color: var(--text-primary); +} diff --git a/src/main.ts b/src/main.ts index 8e5adc7..55a9ec4 100644 --- a/src/main.ts +++ b/src/main.ts @@ -1,6 +1,8 @@ import { createApp } from 'vue'; import { createI18n } from 'vue-i18n'; import App from '../core/App.vue'; +import '../core/styles/theme.css'; +import '../core/styles/forms.css'; import '../dist/open-api-designer.css'; import 'tailwindcss/tailwind.css'; import 'tailwindcss/components.css';