This is an automated email from the ASF dual-hosted git repository.

nicholasjiang pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-paimon-webui.git


The following commit(s) were added to refs/heads/main by this push:
     new 21dbca4  [Feature] Introduce Playground (#42)
21dbca4 is described below

commit 21dbca4a6e027dd615854658695cf1d604b5c6d9
Author: labbomb <[email protected]>
AuthorDate: Thu Sep 21 17:41:11 2023 +0800

    [Feature] Introduce Playground (#42)
---
 paimon-web-ui-new/package.json                     |   1 +
 paimon-web-ui-new/pnpm-lock.yaml                   |   7 ++
 .../src/components/monaco-editor/index.tsx         | 124 +++++++++++++++++++++
 .../src/components/monaco-editor/type.ts           |  79 +++++++++++++
 .../layouts/content/components/toolbar/index.tsx   |   2 +-
 paimon-web-ui-new/src/locales/en/index.ts          |   6 +-
 .../{zh/index.ts => en/modules/playground.ts}      |   9 +-
 paimon-web-ui-new/src/locales/zh/index.ts          |   6 +-
 .../locales/zh/{index.ts => modules/playground.ts} |   9 +-
 paimon-web-ui-new/src/router/index.ts              |  38 ++++---
 .../zh/index.ts => router/modules/playground.ts}   |  24 ++--
 .../{views/homepage/index.tsx => router/routes.ts} |  44 ++++----
 paimon-web-ui-new/src/store/config/index.ts        |   3 +-
 .../components/catalog/index.module.scss}          |  24 +---
 .../views/playground/components/catalog/index.tsx  |  88 +++++++++++++++
 .../index.tsx => playground/index.module.scss}     |  44 +++++---
 paimon-web-ui-new/src/views/playground/index.tsx   | 101 +++++++++++++++++
 17 files changed, 514 insertions(+), 95 deletions(-)

diff --git a/paimon-web-ui-new/package.json b/paimon-web-ui-new/package.json
index c5a1f4e..e3443bb 100644
--- a/paimon-web-ui-new/package.json
+++ b/paimon-web-ui-new/package.json
@@ -13,6 +13,7 @@
   },
   "dependencies": {
     "dart-sass": "^1.25.0",
+    "monaco-editor": "^0.43.0",
     "pinia": "^2.1.6",
     "pinia-plugin-persistedstate": "^3.2.0",
     "sass": "^1.66.1",
diff --git a/paimon-web-ui-new/pnpm-lock.yaml b/paimon-web-ui-new/pnpm-lock.yaml
index 05a47af..17b654a 100644
--- a/paimon-web-ui-new/pnpm-lock.yaml
+++ b/paimon-web-ui-new/pnpm-lock.yaml
@@ -23,6 +23,9 @@ dependencies:
   dart-sass:
     specifier: ^1.25.0
     version: 1.25.0
+  monaco-editor:
+    specifier: ^0.43.0
+    version: 0.43.0
   pinia:
     specifier: ^2.1.6
     version: 2.1.6([email protected])([email protected])
@@ -2776,6 +2779,10 @@ packages:
       ufo: 1.3.0
     dev: true
 
+  /[email protected]:
+    resolution: {integrity: 
sha512-cnoqwQi/9fml2Szamv1XbSJieGJ1Dc8tENVMD26Kcfl7xGQWp7OBKMjlwKVGYFJ3/AXJjSOGvcqK7Ry/j9BM1Q==}
+    dev: false
+
   /[email protected]:
     resolution: {integrity: 
sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==}
     dev: true
diff --git a/paimon-web-ui-new/src/components/monaco-editor/index.tsx 
b/paimon-web-ui-new/src/components/monaco-editor/index.tsx
new file mode 100644
index 0000000..5bf54af
--- /dev/null
+++ b/paimon-web-ui-new/src/components/monaco-editor/index.tsx
@@ -0,0 +1,124 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import * as monaco from 'monaco-editor'
+import jsonWorker from 'monaco-editor/esm/vs/language/json/json.worker?worker'
+import cssWorker from 'monaco-editor/esm/vs/language/css/css.worker?worker'
+import htmlWorker from 'monaco-editor/esm/vs/language/html/html.worker?worker'
+import tsWorker from 
'monaco-editor/esm/vs/language/typescript/ts.worker?worker'
+import EditorWorker from 'monaco-editor/esm/vs/editor/editor.worker?worker'
+import { editorProps } from './type'
+import { useConfigStore } from '@/store/config'
+
+// @ts-ignore: worker
+self.MonacoEnvironment = {
+  getWorker(_: string, label: string) {
+    if (label === 'json') {
+      return new jsonWorker()
+    }
+    if (['css', 'scss', 'less'].includes(label)) {
+      return new cssWorker()
+    }
+    if (['html', 'handlebars', 'razor'].includes(label)) {
+      return new htmlWorker()
+    }
+    if (['typescript', 'javascript'].includes(label)) {
+      return new tsWorker()
+    }
+    return new EditorWorker()
+  }
+}
+
+export default defineComponent({
+  name: 'MonacoEditor',
+  props: editorProps,
+  emits: ['update:modelValue', 'change', 'EditorMounted'],
+  setup(props, { emit }) {
+    const configStore = useConfigStore()
+    const monacoEditorThemeRef = ref(configStore.getCurrentTheme === 'dark' ? 
'vs-dark' : 'vs')
+    let editor: monaco.editor.IStandaloneCodeEditor
+    const codeEditBox = ref()
+    const init = () => {
+      monaco.languages.typescript.javascriptDefaults.setDiagnosticsOptions({
+        noSemanticValidation: true,
+        noSyntaxValidation: false
+      })
+      monaco.languages.typescript.javascriptDefaults.setCompilerOptions({
+        target: monaco.languages.typescript.ScriptTarget.ES2020,
+        allowNonTsExtensions: true
+      })
+      editor = monaco.editor.create(codeEditBox.value, {
+        value: props.modelValue,
+        language: props.language,
+        theme: monacoEditorThemeRef.value,
+        ...props.options
+      })
+      editor.onDidChangeModelContent(() => {
+        const value = editor.getValue()
+        emit('update:modelValue', value)
+        emit('change', value)
+      })
+      emit('EditorMounted', editor)
+    }
+    watch(
+      () => props.modelValue,
+      newValue => {
+        if (editor) {
+          const value = editor.getValue()
+          if (newValue !== value) {
+            editor.setValue(newValue)
+          }
+        }
+      }
+    )
+    watch(
+      () => props.options,
+      newValue => {
+        editor.updateOptions(newValue)
+      },
+      { deep: true }
+    )
+    watch(
+      () => props.language,
+      newValue => {
+        monaco.editor.setModelLanguage(editor.getModel()!, newValue)
+      }
+    )
+    watch(
+      () => configStore.getCurrentTheme,
+      () => {
+        editor?.dispose()
+        monacoEditorThemeRef.value = configStore.getCurrentTheme === 'dark' ? 
'vs-dark' : 'vs'
+        init()
+      }
+    )
+    onBeforeUnmount(() => {
+      editor.dispose()
+    })
+    onMounted(() => {
+      init()
+    })
+    return { codeEditBox }
+  },
+  render () {
+    return (
+      <div ref='codeEditBox' style={{
+        height: '100%',
+      }}/>
+    )
+  }
+})
diff --git a/paimon-web-ui-new/src/components/monaco-editor/type.ts 
b/paimon-web-ui-new/src/components/monaco-editor/type.ts
new file mode 100644
index 0000000..a611096
--- /dev/null
+++ b/paimon-web-ui-new/src/components/monaco-editor/type.ts
@@ -0,0 +1,79 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+export type Theme = 'vs' | 'vs-dark'
+export type FoldingStrategy = 'auto' | 'indentation'
+export type RenderLineHighlight = 'all' | 'line' | 'none' | 'gutter'
+export interface Options {
+  automaticLayout?: boolean
+  foldingStrategy?: FoldingStrategy
+  renderLineHighlight?: RenderLineHighlight
+  selectOnLineNumbers?: boolean
+  minimap?: {
+    enabled: boolean
+  }
+  readOnly: boolean
+  contextmenu: boolean
+  fontSize?: number
+  scrollBeyondLastLine?: boolean
+  overviewRulerBorder?: boolean
+}
+
+export const editorProps = {
+  modelValue: {
+    type: String as PropType<string>,
+    default: null
+  },
+  width: {
+    type: [String, Number] as PropType<string | number>,
+    default: '100%'
+  },
+  height: {
+    type: [String, Number] as PropType<string | number>,
+    default: '100%'
+  },
+  language: {
+    type: String as PropType<string>,
+    default: 'javascript'
+  },
+  theme: {
+    type: String as PropType<Theme>,
+    validator(value: string): boolean {
+      return ['vs', 'vs-dark'].includes(value)
+    },
+    default: 'vs'
+  },
+  options: {
+    type: Object as PropType<Options>,
+    default() {
+      return {
+        automaticLayout: true,
+        foldingStrategy: 'indentation',
+        renderLineHighlight: 'line',
+        selectOnLineNumbers: true,
+        minimap: {
+          enabled: true
+        },
+        readOnly: false,
+        contextmenu: true,
+        fontSize: 16,
+        scrollBeyondLastLine: false,
+        overviewRulerBorder: false
+      }
+    }
+  }
+}
diff --git a/paimon-web-ui-new/src/layouts/content/components/toolbar/index.tsx 
b/paimon-web-ui-new/src/layouts/content/components/toolbar/index.tsx
index 0925a43..a436959 100644
--- a/paimon-web-ui-new/src/layouts/content/components/toolbar/index.tsx
+++ b/paimon-web-ui-new/src/layouts/content/components/toolbar/index.tsx
@@ -17,7 +17,7 @@ under the License. */
 
 import i18n from '@/locales'
 import { useConfigStore } from '@/store/config'
-import { LogoGithub, Moon, SunnyOutline, Language, PersonCircleOutline } from 
'@vicons/ionicons5'
+import { LogoGithub, Moon, SunnyOutline, Language } from '@vicons/ionicons5'
 
 export default defineComponent({
   name: 'ToolBar',
diff --git a/paimon-web-ui-new/src/locales/en/index.ts 
b/paimon-web-ui-new/src/locales/en/index.ts
index 08e479f..db4b713 100644
--- a/paimon-web-ui-new/src/locales/en/index.ts
+++ b/paimon-web-ui-new/src/locales/en/index.ts
@@ -17,8 +17,10 @@ under the License. */
 
 import layout from './modules/layout'
 import login from './modules/login'
+import playground from './modules/playground'
 
 export default {
   login,
-  layout
-}
\ No newline at end of file
+  layout,
+  playground
+}
diff --git a/paimon-web-ui-new/src/locales/zh/index.ts 
b/paimon-web-ui-new/src/locales/en/modules/playground.ts
similarity index 89%
copy from paimon-web-ui-new/src/locales/zh/index.ts
copy to paimon-web-ui-new/src/locales/en/modules/playground.ts
index 08e479f..feedda3 100644
--- a/paimon-web-ui-new/src/locales/zh/index.ts
+++ b/paimon-web-ui-new/src/locales/en/modules/playground.ts
@@ -15,10 +15,7 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import layout from './modules/layout'
-import login from './modules/login'
-
 export default {
-  login,
-  layout
-}
\ No newline at end of file
+  select_catalog: 'Select Catalog',
+  search: 'Search'
+}
diff --git a/paimon-web-ui-new/src/locales/zh/index.ts 
b/paimon-web-ui-new/src/locales/zh/index.ts
index 08e479f..db4b713 100644
--- a/paimon-web-ui-new/src/locales/zh/index.ts
+++ b/paimon-web-ui-new/src/locales/zh/index.ts
@@ -17,8 +17,10 @@ under the License. */
 
 import layout from './modules/layout'
 import login from './modules/login'
+import playground from './modules/playground'
 
 export default {
   login,
-  layout
-}
\ No newline at end of file
+  layout,
+  playground
+}
diff --git a/paimon-web-ui-new/src/locales/zh/index.ts 
b/paimon-web-ui-new/src/locales/zh/modules/playground.ts
similarity index 89%
copy from paimon-web-ui-new/src/locales/zh/index.ts
copy to paimon-web-ui-new/src/locales/zh/modules/playground.ts
index 08e479f..e9350cb 100644
--- a/paimon-web-ui-new/src/locales/zh/index.ts
+++ b/paimon-web-ui-new/src/locales/zh/modules/playground.ts
@@ -15,10 +15,7 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import layout from './modules/layout'
-import login from './modules/login'
-
 export default {
-  login,
-  layout
-}
\ No newline at end of file
+  select_catalog: '选择 Catalog',
+  search: '搜索'
+}
diff --git a/paimon-web-ui-new/src/router/index.ts 
b/paimon-web-ui-new/src/router/index.ts
index c55aaae..e2670e9 100644
--- a/paimon-web-ui-new/src/router/index.ts
+++ b/paimon-web-ui-new/src/router/index.ts
@@ -15,25 +15,31 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import { createRouter, createWebHistory } from 'vue-router'
+import {
+  createRouter,
+  createWebHistory,
+  type RouteLocationNormalized,
+  type NavigationGuardNext
+} from 'vue-router'
+import routes from './routes'
+
 
 const router = createRouter({
   history: createWebHistory(import.meta.env.BASE_URL),
-  routes: [
-    {
-      path: '/',
-      name: 'homepage',
-      // route level code-splitting
-      // this generates a separate chunk (About.[hash].js) for this route
-      // which is lazy-loaded when the route is visited.
-      component: () => import('../layouts/content')
-    },
-    {
-      path: '/login',
-      name: 'login',
-      component: () => import('../views/login')
-    }
-  ]
+  routes
 })
 
+/**
+ * Routing to intercept
+ */
+router.beforeEach(
+  async (
+    to: RouteLocationNormalized,
+    from: RouteLocationNormalized,
+    next: NavigationGuardNext
+  ) => {
+    next()
+  }
+)
+
 export default router
diff --git a/paimon-web-ui-new/src/locales/zh/index.ts 
b/paimon-web-ui-new/src/router/modules/playground.ts
similarity index 66%
copy from paimon-web-ui-new/src/locales/zh/index.ts
copy to paimon-web-ui-new/src/router/modules/playground.ts
index 08e479f..b8333c1 100644
--- a/paimon-web-ui-new/src/locales/zh/index.ts
+++ b/paimon-web-ui-new/src/router/modules/playground.ts
@@ -15,10 +15,20 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import layout from './modules/layout'
-import login from './modules/login'
-
-export default {
-  login,
-  layout
-}
\ No newline at end of file
+export default [
+  {
+    path: '/',
+    name: 'homepage',
+    meta: { title: '首页' },
+    redirect: { name: 'playground' },
+    component: () => import('@/layouts/content'),
+    children: [
+      {
+        path: '/playground',
+        name: 'playground',
+        meta: { title: '查询控制台' },
+        component: () => import('@/views/playground')
+      },
+    ]
+  }
+]
diff --git a/paimon-web-ui-new/src/views/homepage/index.tsx 
b/paimon-web-ui-new/src/router/routes.ts
similarity index 64%
copy from paimon-web-ui-new/src/views/homepage/index.tsx
copy to paimon-web-ui-new/src/router/routes.ts
index 11292eb..15339e4 100644
--- a/paimon-web-ui-new/src/views/homepage/index.tsx
+++ b/paimon-web-ui-new/src/router/routes.ts
@@ -15,22 +15,28 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import { defineComponent } from 'vue';
-
-export default defineComponent({
-  name: 'HomePage',
-  setup() {
-    const handleRequest = () => {}
-
-    return { handleRequest }
-  },
-  render() {
-    return (
-      <div>
-        <div>
-          <n-button onClick={this.handleRequest}>Request Test</n-button>
-        </div>
-      </div>
-    );
-  },
-});
+import type { RouteRecordRaw } from 'vue-router'
+import playground_routes from './modules/playground'
+
+/**
+ * Basic page
+ */
+const basePage: RouteRecordRaw[] = [
+  ...playground_routes,
+]
+
+/**
+ * Login page
+ */
+const loginPage: RouteRecordRaw[] = [
+  {
+    path: '/login',
+    name: 'login',
+    component: () => import('../views/login')
+  }
+]
+
+
+const routes: RouteRecordRaw[] = [...basePage, ...loginPage]
+
+export default routes
diff --git a/paimon-web-ui-new/src/store/config/index.ts 
b/paimon-web-ui-new/src/store/config/index.ts
index ec3e8bf..dac0a6c 100644
--- a/paimon-web-ui-new/src/store/config/index.ts
+++ b/paimon-web-ui-new/src/store/config/index.ts
@@ -24,6 +24,7 @@ export const useConfigStore = defineStore({
     theme: 'light',
     locale: 'zh'
   }),
+  persist: true,
   getters: {
     getCurrentLocale(): Locale {
       return this.locale
@@ -40,4 +41,4 @@ export const useConfigStore = defineStore({
       this.theme = theme
     }
   }
-})
\ No newline at end of file
+})
diff --git a/paimon-web-ui-new/src/views/homepage/index.tsx 
b/paimon-web-ui-new/src/views/playground/components/catalog/index.module.scss
similarity index 68%
copy from paimon-web-ui-new/src/views/homepage/index.tsx
copy to 
paimon-web-ui-new/src/views/playground/components/catalog/index.module.scss
index 11292eb..e32b957 100644
--- a/paimon-web-ui-new/src/views/homepage/index.tsx
+++ 
b/paimon-web-ui-new/src/views/playground/components/catalog/index.module.scss
@@ -15,22 +15,10 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import { defineComponent } from 'vue';
+.container {
+  width: 100%;
 
-export default defineComponent({
-  name: 'HomePage',
-  setup() {
-    const handleRequest = () => {}
-
-    return { handleRequest }
-  },
-  render() {
-    return (
-      <div>
-        <div>
-          <n-button onClick={this.handleRequest}>Request Test</n-button>
-        </div>
-      </div>
-    );
-  },
-});
+  .select-catalog {
+    padding-bottom: 10px;
+  }
+}
diff --git 
a/paimon-web-ui-new/src/views/playground/components/catalog/index.tsx 
b/paimon-web-ui-new/src/views/playground/components/catalog/index.tsx
new file mode 100644
index 0000000..ea44e8c
--- /dev/null
+++ b/paimon-web-ui-new/src/views/playground/components/catalog/index.tsx
@@ -0,0 +1,88 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import i18n from "@/locales"
+import type { TreeOption } from "naive-ui";
+import styles from './index.module.scss'
+
+export default defineComponent({
+  name: 'CataLogPage',
+  setup() {
+    const selectedValue= ref(null)
+
+    const options= [
+      {
+        label: 'catalog1',
+        value: 'catalog1'
+      },
+      {
+        label: 'catalog2',
+        value: 'catalog2'
+      }
+    ]
+
+    const searchVal = ref('')
+
+    const treeData: TreeOption[] = [
+      {
+        label: 'paimon',
+        key: 'paimon',
+        children: [
+          {
+            label: 'paimon-table-01',
+            key: 'paimon-table-01',
+            children: [
+              { label: 'id', key: 'id' },
+              { label: 'name', key: 'name' }
+            ]
+          },
+          {
+            label: 'paimon-table-02',
+            key: 'paimon-table-02',
+            children: [
+              { label: 'Osaka', key: 'Osaka' },
+            ]
+          }
+        ]
+      }
+    ]
+
+    return { selectedValue, options, searchVal, treeData }
+  },
+  render() {
+    return (
+      <div class={styles.container}>
+        <div class={styles['select-catalog']}>
+          <n-select
+            v-model:value={this.selectedValue}
+            filterable
+            placeholder={i18n.global.t('playground.select_catalog')}
+            options={this.options}
+          /> 
+        </div>
+        <n-space vertical size={12}>
+          <n-input v-model:value={this.searchVal} 
placeholder={i18n.global.t('playground.search')} />
+          <n-tree
+            pattern={this.searchVal}
+            data={this.treeData}
+            block-line
+          />
+        </n-space>
+      </div>
+    );
+  },
+});
diff --git a/paimon-web-ui-new/src/views/homepage/index.tsx 
b/paimon-web-ui-new/src/views/playground/index.module.scss
similarity index 67%
rename from paimon-web-ui-new/src/views/homepage/index.tsx
rename to paimon-web-ui-new/src/views/playground/index.module.scss
index 11292eb..839bb21 100644
--- a/paimon-web-ui-new/src/views/homepage/index.tsx
+++ b/paimon-web-ui-new/src/views/playground/index.module.scss
@@ -15,22 +15,32 @@ KIND, either express or implied.  See the License for the
 specific language governing permissions and limitations
 under the License. */
 
-import { defineComponent } from 'vue';
+.container {
+  height: 100%;
+  width: 100%;
 
-export default defineComponent({
-  name: 'HomePage',
-  setup() {
-    const handleRequest = () => {}
+  :global {
+    .n-tabs {
+      height: 100%;
+    }
+  }
 
-    return { handleRequest }
-  },
-  render() {
-    return (
-      <div>
-        <div>
-          <n-button onClick={this.handleRequest}>Request Test</n-button>
-        </div>
-      </div>
-    );
-  },
-});
+  .content {
+    display: flex;
+    height: 100%;
+
+    .catalog {
+      width: 350px;
+      height: 100%;
+      padding: 10px;
+      box-sizing: border-box;
+    }
+
+    .editor {
+      height: 100%;
+      flex: 1;
+      padding: 10px;
+      box-sizing: border-box;
+    }
+  }
+}
diff --git a/paimon-web-ui-new/src/views/playground/index.tsx 
b/paimon-web-ui-new/src/views/playground/index.tsx
new file mode 100644
index 0000000..448b0de
--- /dev/null
+++ b/paimon-web-ui-new/src/views/playground/index.tsx
@@ -0,0 +1,101 @@
+/* Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements.  See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership.  The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License.  You may obtain a copy of the License at
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied.  See the License for the
+specific language governing permissions and limitations
+under the License. */
+
+import styles from './index.module.scss';
+import type { TabsProps } from 'naive-ui';
+import { Layers, CodeSlashSharp, SyncCircleOutline } from '@vicons/ionicons5';
+import CataLog from './components/catalog';
+import * as monaco from 'monaco-editor'
+import MonacoEditor from '@/components/monaco-editor';
+
+
+export default defineComponent({
+  name: 'PlaygroundPage',
+  setup() {
+    const type = ref<TabsProps['type']>('bar')
+
+    const content = ref('')
+    const language = ref('javascript')
+    const editorMounted = (editor: monaco.editor.IStandaloneCodeEditor) => {
+      console.log('Loaded editor instance.', editor)
+    }
+
+    return {
+      type,
+      content,
+      language,
+      editorMounted
+    }
+  },
+  render() {
+    return (
+      <div class={styles.container}>
+        <n-tabs
+          type={this.type}
+          animated
+          placement="left"
+          default-value="oasis"
+        >
+          <n-tab-pane name="oasis"
+            v-slots={{
+              tab: () => (
+                <n-icon size="24">
+                  <Layers />
+                </n-icon>
+              )
+            }}
+          >
+            <div class={styles.content}>
+              <div class={styles.catalog}>
+                <CataLog />
+              </div>
+              <div class={styles.editor}>
+                <MonacoEditor
+                  v-model={this.content}
+                  language={this.language}
+                  onEditorMounted={this.editorMounted}
+                />
+              </div>
+            </div>
+          </n-tab-pane>
+          <n-tab-pane name="the beatles" tab="the Beatles"
+            v-slots={{
+              tab: () => (
+                <n-icon size="24">
+                  <CodeSlashSharp />
+                </n-icon>
+              )
+            }}
+          >
+            Saved Queries
+          </n-tab-pane>
+          <n-tab-pane name="jay chou" tab="Jay Chou"
+            v-slots={{
+              tab: () => (
+                <n-icon size="24">
+                  <SyncCircleOutline />
+                </n-icon>
+              )
+            }}
+          >
+            History
+          </n-tab-pane>
+        </n-tabs>
+      </div>
+    );
+  },
+});

Reply via email to