vp-example.vue 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123
  1. <script setup lang="ts">
  2. import { computed, unref, watchEffect } from 'vue'
  3. import { File, Repl, ReplStore } from '@vue/repl'
  4. import mainCode from './main.vue?raw'
  5. import deptCode from './dept.js?raw'
  6. import { loadKanKanThemeChalkStyle } from './dept-home'
  7. import type { SFCOptions } from '@vue/repl'
  8. const sfcOptions: SFCOptions = {
  9. script: {
  10. reactivityTransform: true,
  11. },
  12. }
  13. const props = defineProps({
  14. file: {
  15. type: String,
  16. required: true,
  17. },
  18. raw: {
  19. type: String,
  20. required: true,
  21. },
  22. demo: {
  23. type: Object,
  24. required: true,
  25. },
  26. isRepl: {
  27. type: Boolean,
  28. required: false,
  29. default: () => false,
  30. },
  31. })
  32. const isDev = computed(() => {
  33. return import.meta.env.MODE === 'development'
  34. })
  35. console.log('isDev', unref(isDev))
  36. const serverLink = computed(() => {
  37. return unref(isDev) ? '/demoServer' : 'https://test.4dkankan.com/'
  38. })
  39. // const loadSingleData = computed(() => {
  40. // const store = {
  41. // 'App.vue': decodeURIComponent(props.raw).replace('#DEMOSEVER#', unref(serverLink)),
  42. // }
  43. // return window.btoa(JSON.stringify(store))
  44. // })
  45. const store = new ReplStore({
  46. // initialize repl with previously serialized state
  47. // serializedState: unref(loadSingleData),
  48. // starts on the output pane (mobile only) if the URL has a showOutput query
  49. showOutput: true,
  50. // starts on a different tab on the output pane if the URL has a outputMode query
  51. // and default to the "preview" tab
  52. outputMode: 'preview',
  53. // specify the default URL to import Vue runtime from in the sandbox
  54. // default is the CDN link from unpkg.com with version matching Vue's version
  55. // from peerDependency
  56. defaultVueRuntimeURL: 'https://cdn.jsdelivr.net/npm/@vue/runtime-dom@latest/dist/runtime-dom.esm-browser.js',
  57. })
  58. watchEffect(async () => {
  59. if (!unref(props.isRepl)) {
  60. await loadKanKanThemeChalkStyle()
  61. } else {
  62. if (unref(props.raw)) {
  63. store.setImportMap({
  64. imports: {
  65. vue: 'https://cdn.jsdelivr.net/npm/@vue/runtime-dom@latest/dist/runtime-dom.esm-browser.js',
  66. '@vue/shared': 'https://cdn.jsdelivr.net/npm/@vue/shared@latest/dist/shared.esm-bundler.js',
  67. 'kankan-components': 'https://4dkk.4dage.com/npm_test/kankan-components/dist/index.full.min.mjs',
  68. },
  69. })
  70. const mainFile = new File('PlaygroundMain.vue', mainCode)
  71. const deptFile = new File('dept.js', deptCode)
  72. const appFile = new File('App.vue', decodeURIComponent(props.raw).replace('#DEMOSEVER#', unref(serverLink)))
  73. store.addFile(mainFile)
  74. store.addFile(appFile)
  75. store.addFile(deptFile)
  76. store.state.mainFile = 'PlaygroundMain.vue'
  77. store.state.activeFile = appFile
  78. store.init()
  79. }
  80. }
  81. })
  82. </script>
  83. <template>
  84. <div class="example-showcase" antialiased>
  85. <ClientOnly>
  86. <template v-if="demo">
  87. <component :is="demo" v-if="!isRepl" v-bind="$attrs" />
  88. <Repl v-else ref="repl" :store="store" v-bind="$attrs" :sfc-options="sfcOptions" :clear-console="false" :show-compile-output="true" auto-resize />
  89. </template>
  90. </ClientOnly>
  91. </div>
  92. </template>
  93. <style lang="scss" scoped>
  94. .example-showcase {
  95. padding: 1.5rem;
  96. margin: 0.5px;
  97. background-color: var(--bg-color);
  98. }
  99. </style>
  100. <style lang="scss">
  101. .vue-repl {
  102. height: 650px;
  103. .left {
  104. display: none;
  105. }
  106. .right {
  107. width: 100% !important;
  108. }
  109. // .tab-buttons {
  110. // display: none;
  111. // }
  112. }
  113. </style>