plugin architecture
This commit is contained in:
parent
dea734ec21
commit
a0a24ebf72
@ -74,11 +74,11 @@
|
||||
"json-loader": "^0.5.4",
|
||||
"localforage": "^1.4.2",
|
||||
"lodash": "^4.13.1",
|
||||
"markup-it": "git+https://github.com/cassiozen/markup-it.git",
|
||||
"markup-it": "git+https://github.com/GitbookIO/markup-it.git",
|
||||
"pluralize": "^3.0.0",
|
||||
"prismjs": "^1.5.1",
|
||||
"react-portal": "^2.2.1",
|
||||
"selection-position": "^1.0.0",
|
||||
"slate": "^0.12.2"
|
||||
"slate": "^0.13.5"
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,5 @@
|
||||
export const SWITCH_VISUAL_MODE = 'SWITCH_VISUAL_MODE';
|
||||
export const REGISTER_COMPONENT = 'REGISTER_COMPONENT';
|
||||
|
||||
export function switchVisualMode(useVisualMode) {
|
||||
return {
|
||||
@ -6,3 +7,10 @@ export function switchVisualMode(useVisualMode) {
|
||||
payload: useVisualMode
|
||||
};
|
||||
}
|
||||
|
||||
export function registerComponent(options) {
|
||||
return {
|
||||
type: REGISTER_COMPONENT,
|
||||
payload: options
|
||||
};
|
||||
}
|
||||
|
@ -5,6 +5,7 @@ import { Router } from 'react-router';
|
||||
import configureStore from './store/configureStore';
|
||||
import routes from './routing/routes';
|
||||
import history, { syncHistory } from './routing/history';
|
||||
import { initPluginAPI } from './plugins';
|
||||
import 'file?name=index.html!../example/index.html';
|
||||
import './index.css';
|
||||
|
||||
@ -13,6 +14,8 @@ const store = configureStore();
|
||||
// Create an enhanced history that syncs navigation events with the store
|
||||
syncHistory(store);
|
||||
|
||||
initPluginAPI(store);
|
||||
|
||||
const el = document.createElement('div');
|
||||
el.id = 'root';
|
||||
document.body.appendChild(el);
|
||||
|
40
src/plugins/index.js
Normal file
40
src/plugins/index.js
Normal file
@ -0,0 +1,40 @@
|
||||
import { registerComponent } from '../actions/editor';
|
||||
|
||||
let storeRef;
|
||||
const requiredEditorComponentProperties = ['label', 'fields', 'detect', 'fromBlock', 'toBlock'];
|
||||
|
||||
const checkConfigKeys = (config, requiredProps) => {
|
||||
for (var i = requiredProps.length; i--;) {
|
||||
if (!config.hasOwnProperty(requiredProps[i])) return false;
|
||||
}
|
||||
return true;
|
||||
};
|
||||
|
||||
const wrap = (func) => function() {
|
||||
func.apply(null, arguments);
|
||||
};
|
||||
|
||||
function CMS() {
|
||||
this.registerEditorComponent = (config) => {
|
||||
if (checkConfigKeys(config, requiredEditorComponentProperties)) {
|
||||
const configObj = {
|
||||
label: config.label || 'unnamed',
|
||||
icon: config.icon || 'exclamation-triangle',
|
||||
fields: config.fields,
|
||||
detect: wrap(config.detect),
|
||||
fromBlock: wrap(config.fromBlock),
|
||||
toBlock: wrap(config.toBlock),
|
||||
toPreview: config.toPreview ? wrap(config.toPreview) : wrap(config.toBlock)
|
||||
};
|
||||
storeRef.dispatch(registerComponent(configObj));
|
||||
} else {
|
||||
const label = config.label || 'unnamed';
|
||||
window.console && console.error(`The provided component configuration for ${label} is incorrect.`);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
export const initPluginAPI = (store) => {
|
||||
storeRef = store;
|
||||
window.CMS = new CMS();
|
||||
};
|
@ -1,11 +1,12 @@
|
||||
import { Map } from 'immutable';
|
||||
import { SWITCH_VISUAL_MODE } from '../actions/editor';
|
||||
import { Map, List } from 'immutable';
|
||||
import { SWITCH_VISUAL_MODE, REGISTER_COMPONENT } from '../actions/editor';
|
||||
|
||||
const editor = (state = Map({ useVisualMode: true }), action) => {
|
||||
const editor = (state = Map({ useVisualMode: true, registeredComponents: List() }), action) => {
|
||||
switch (action.type) {
|
||||
case SWITCH_VISUAL_MODE:
|
||||
return Map({ useVisualMode: action.payload });
|
||||
|
||||
return state.setIn(['useVisualMode'], action.payload);
|
||||
case REGISTER_COMPONENT:
|
||||
return state.updateIn(['registeredComponents'], list => list.push(action.payload));
|
||||
default:
|
||||
return state;
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user