UNPKG

8.16 kBJavaScriptView Raw
1import Vue from 'vue/dist/vue.esm';
2import Vuex from 'vuex';
3import userConfig from 'manifest';
4import demoList from '.demoList.json';
5import router from '@/js/router.js';
6import bus from '@/js/eventbus.js';
7
8let config = userConfig;
9if (typeof config === 'function') {
10 config = config(process.env.NODE_ENV);
11}
12
13config = Object.assign(
14 {
15 name: 'DEMOSIFY',
16 version: 'v1',
17 homePage: 'https://github.com/betseyliu/demo-ground',
18 logo: '',
19 // 可选主题: active4d, allHallowsEve, amy, blackboard, brillianceBlack,
20 // brillianceDull, chromeDevtools, cloudsMidnight, clouds, cobalt,
21 // dawn, dreamweaver, eiffel, espressoLibre, github, idle, katzenmilch,
22 // kuroirTheme, lazy, magicwbAmiga, merbivoreSoft, merbivore, monokai,
23 // pastelsOnDark, slushAndPoppies, solarizedDark, solarizedLight,
24 // spacecadet, sunburst, textmateMacClassic, tomorrowNightBlue,
25 // tomorrowNightBright, tomorrowNightEighties, tomorrowNight, tomorrow,
26 // twilight, vibrantInk, zenburnesque, iplastic, idlefingers, krtheme,
27 // monoindustrial,
28 boxTheme: 'monokai',
29 globalPackages: {
30 js: [],
31 css: []
32 },
33 // tab waterfall
34 editorViewMode: 'tab'
35 },
36 config
37);
38
39import progress from 'nprogress';
40progress.configure({
41 showSpinner: false
42});
43
44Vue.use(Vuex);
45
46const demoBoxes = {};
47
48function importAllDemo(r) {
49 r.keys().forEach(key => {
50 const matched = /^\.\/((?:.+\/)*.+)\//.exec(key);
51 if (matched) {
52 demoBoxes[matched[1]] = r(key).default;
53 }
54 });
55}
56importAllDemo(require.context('demos', true, /config.js$/));
57
58const links = demoList.map(link => {
59 if (typeof link === 'string') {
60 link = { label: link, src: link };
61 }
62 // 组
63 if ('demos' in link) {
64 link.demos.map(l => ({ lable: l, src: l }));
65 }
66 return link;
67});
68
69const state = {
70 config,
71 boxes: {},
72 foldBoxes: [],
73 links,
74 iframeStatus: null,
75 isSidebarShown: true,
76 transforming: false,
77 inIframe: window !== top,
78 autoRun: true,
79 logs: [],
80 currentBox: undefined,
81 dependencies: {
82 js: [],
83 css: []
84 }
85};
86
87if (state.inIframe) {
88 state.isSidebarShown = false;
89}
90
91const mutations = {
92 CLEAR_BOXES(state) {
93 state.boxes = {};
94 },
95 UPDATE_TAB(state, { type, tabName }) {
96 if (!state.boxes[type]) state.boxes[type] = {};
97 state.boxes[type].tabName = tabName;
98 },
99 UPDATE_KEY(state, { type, key }) {
100 if (!state.boxes[type]) state.boxes[type] = {};
101 state.boxes[type].key = key;
102 },
103 UPDATE_CODE(state, { type, code }) {
104 if (!state.boxes[type]) state.boxes[type] = {};
105 state.boxes[type].code = code;
106 if (state.autoRun) bus.$emit('run');
107 },
108 UPDATE_TRANSFORM(state, { type, transform }) {
109 if (!state.boxes[type]) state.boxes[type] = {};
110 state.boxes[type].transform = transform;
111 },
112 UPDATE_TRANSFORMER(state, { type, transformer }) {
113 if (!state.boxes[type]) state.boxes[type] = {};
114 state.boxes[type].transformer = transformer;
115 },
116 UPDATE_EDITOR_HOOK(state, { type, editorHook }) {
117 if (!state.boxes[type]) state.boxes[type] = {};
118 state.boxes[type].editorHook = editorHook;
119 },
120 UPDATE_FOLD_BOXES(state, foldBoxes) {
121 state.foldBoxes = foldBoxes;
122 },
123 UPDATE_VISIBLE(state, { type, visible }) {
124 if (!state.boxes[type]) state.boxes[type] = {};
125 state.boxes[type].visible = visible;
126 },
127 TOGGLE_BOX_FOLD(state, boxName) {
128 const boxIndex = state.foldBoxes.indexOf(boxName);
129 if (boxIndex > -1) {
130 state.foldBoxes.splice(boxIndex, 1);
131 } else {
132 state.foldBoxes.push(boxName);
133 }
134 },
135 SET_IFRAME_STATUS(state, status) {
136 state.iframeStatus = status;
137 },
138 SET_TRANSFORM(state, status) {
139 state.transforming = status;
140 },
141 TOGGLE_AUTO_RUN(state) {
142 state.autoRun = !state.autoRun;
143 },
144 CLEAR_LOGS(state) {
145 state.logs = [];
146 },
147 ADD_LOG(state, log) {
148 state.logs.push(log);
149 },
150 UPDATE_DEPENDENCIES(state, dependencies = { js: [], css: [] }) {
151 state.dependencies = dependencies;
152 },
153 TOGGLE_SIDEBAR(state) {
154 state.isSidebarShown = !state.isSidebarShown;
155 },
156 UPDATE_CURRENT_BOX(state, box) {
157 state.currentBox = box;
158 }
159};
160
161const actions = {
162 clearBoxes({ commit }) {
163 commit('CLEAR_BOXES');
164 },
165 updateTab({ commit }, pl) {
166 commit('UPDATE_TAB', pl);
167 },
168 updateKey({ commit }, pl) {
169 commit('UPDATE_KEY', pl);
170 },
171 updateCode({ commit }, pl) {
172 commit('UPDATE_CODE', pl);
173 },
174 updateTransformer({ commit }, pl) {
175 commit('UPDATE_TRANSFORMER', pl);
176 },
177 updateTransform({ commit }, pl) {
178 commit('UPDATE_TRANSFORM', pl);
179 },
180 updateEditorHook({ commit }, pl) {
181 commit('UPDATE_EDITOR_HOOK', pl);
182 },
183 updateFoldBoxes({ commit }, pl) {
184 commit('UPDATE_FOLD_BOXES', pl);
185 },
186 updateVisible({ commit }, pl) {
187 commit('UPDATE_VISIBLE', pl);
188 },
189 toggleBoxFold({ commit }, pl) {
190 commit('TOGGLE_BOX_FOLD', pl);
191 },
192 toogleAutoRun({ commit }) {
193 commit('TOGGLE_AUTO_RUN');
194 },
195 updateDependencies({ commit }, pl) {
196 commit('UPDATE_DEPENDENCIES', pl);
197 },
198 updateCurrentBox({ commit }, pl) {
199 commit('UPDATE_CURRENT_BOX', pl);
200 },
201 async setBoxes({ dispatch }, demo) {
202 progress.start();
203
204 let demoID;
205 if (!demoBoxes[demo]) {
206 router.push({ path: '/404' });
207 progress.done();
208 return;
209 }
210 if (typeof demo === 'string') {
211 demoID = demo;
212 if (typeof demoBoxes[demo] === 'function') {
213 demo = await demoBoxes[demo]();
214 } else {
215 demo = await demoBoxes[demo];
216 }
217 } else {
218 demoID =
219 'demo-' +
220 Math.random()
221 .toString(16)
222 .slice(2, 14);
223 }
224
225 let { foldBoxes, packages, ...boxes } = demo;
226
227 const ac = [];
228
229 dispatch('clearBoxes');
230
231 packages = packages || { js: [], css: [] };
232
233 ['html', 'css', 'javascript', 'rawdata'].forEach(type => {
234 if (!boxes[type] || typeof boxes[type] === 'string') {
235 boxes[type] = {
236 code: boxes[type] || '',
237 visible: boxes[type] != null
238 };
239 } else if (
240 boxes[type].default &&
241 typeof boxes[type].default === 'string'
242 ) {
243 boxes[type] = {
244 code: boxes[type].default,
245 visible: true
246 };
247 } else if (typeof boxes[type].code !== 'string') {
248 boxes[type].code =
249 boxes[type].code != null ? boxes[type].code.default || '' : '';
250 }
251 boxes[type].transformer = boxes[type].transformer || type;
252 boxes[type].visible = !!boxes[type].visible;
253 });
254
255 Object.entries(boxes).forEach(
256 ([
257 type,
258 { tabName, code, transformer, visible, transform, editorHook }
259 ]) => {
260 transform =
261 transform ||
262 function(code) {
263 return code;
264 };
265 ac.push(
266 dispatch('updateTab', { type, tabName }),
267 dispatch('updateKey', { type, key: demoID }),
268 dispatch('updateCode', { type, code }),
269 dispatch('updateTransformer', { type, transformer }),
270 dispatch('updateTransform', { type, transform }),
271 dispatch('updateVisible', { type, visible: Boolean(visible) }),
272 dispatch('updateEditorHook', { type, editorHook })
273 );
274 }
275 );
276
277 const dependencies = {
278 js: [...(config.globalPackages.js || []), ...(packages.js || [])],
279 css: [...(config.globalPackages.css || []), ...(packages.css || [])]
280 };
281
282 ac.push(dispatch('updateFoldBoxes', foldBoxes || []));
283 ac.push(dispatch('updateDependencies', dependencies));
284 ac.push(
285 dispatch(
286 'updateCurrentBox',
287 Object.entries(boxes).find(([key, value]) => value.visible)[0] ||
288 undefined
289 )
290 );
291 await Promise.all(ac);
292 progress.done();
293 },
294 setIframeStatus({ commit }, status) {
295 commit('SET_IFRAME_STATUS', status);
296 },
297 transform({ commit }, status) {
298 commit('SET_TRANSFORM', status);
299 },
300 clearLogs({ commit }) {
301 commit('CLEAR_LOGS');
302 },
303 addLog({ commit }, pl) {
304 commit('ADD_LOG', pl);
305 }
306};
307
308const store = new Vuex.Store({
309 state,
310 mutations,
311 actions
312});
313
314bus.$on('setBoxes', demo => {
315 store.dispatch('setBoxes', demo);
316});
317
318export default store;