Demo setup (#266)
This commit is contained in:
parent
f50cba56ea
commit
e7d67e84e9
@ -94,18 +94,10 @@ module.exports = {
|
|||||||
].filter(Boolean),
|
].filter(Boolean),
|
||||||
output: {
|
output: {
|
||||||
path: path.resolve(__dirname, 'dist'),
|
path: path.resolve(__dirname, 'dist'),
|
||||||
filename: 'static-cms-core.js',
|
filename: 'static-cms-app.js',
|
||||||
library: {
|
library: {
|
||||||
name: 'StaticCmsCore',
|
name: 'StaticCmsApp',
|
||||||
type: 'umd',
|
type: 'umd',
|
||||||
},
|
},
|
||||||
},
|
}
|
||||||
devServer: {
|
|
||||||
static: {
|
|
||||||
directory: './dev-test',
|
|
||||||
},
|
|
||||||
host: '0.0.0.0',
|
|
||||||
port: devServerPort,
|
|
||||||
hot: true,
|
|
||||||
},
|
|
||||||
};
|
};
|
||||||
|
1162
packages/demo/config.yml
Normal file
1162
packages/demo/config.yml
Normal file
File diff suppressed because it is too large
Load Diff
21
packages/demo/example.css
Normal file
21
packages/demo/example.css
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
html,
|
||||||
|
body {
|
||||||
|
color: #444;
|
||||||
|
font-size: 14px;
|
||||||
|
font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
padding: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
h1 {
|
||||||
|
margin-top: 20px;
|
||||||
|
color: #666;
|
||||||
|
font-weight: bold;
|
||||||
|
font-size: 32px;
|
||||||
|
}
|
||||||
|
|
||||||
|
img {
|
||||||
|
max-width: 100%;
|
||||||
|
}
|
248
packages/demo/index.html
Normal file
248
packages/demo/index.html
Normal file
File diff suppressed because one or more lines are too long
173
packages/demo/index.js
Normal file
173
packages/demo/index.js
Normal file
@ -0,0 +1,173 @@
|
|||||||
|
// Register all the things
|
||||||
|
CMS.init();
|
||||||
|
|
||||||
|
const PostPreview = ({ entry, widgetFor, widgetsFor }) => {
|
||||||
|
return h(
|
||||||
|
'div',
|
||||||
|
{},
|
||||||
|
h('div', { className: 'cover' }, h('h1', {}, entry.data.title), widgetFor('image')),
|
||||||
|
h('p', {}, h('small', {}, 'Written ' + entry.data.date)),
|
||||||
|
h('div', { className: 'text' }, widgetFor('body')),
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const GeneralPreview = ({ widgetsFor, getAsset, entry }) => {
|
||||||
|
const title = entry.data.site_title;
|
||||||
|
const posts = entry.data.posts;
|
||||||
|
const thumb = posts && posts.thumb;
|
||||||
|
|
||||||
|
const [thumbUrl, setThumbUrl] = useState('');
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
let alive = true;
|
||||||
|
|
||||||
|
const loadThumb = async () => {
|
||||||
|
const thumbAsset = await getAsset(thumb);
|
||||||
|
if (alive) {
|
||||||
|
setThumbUrl(thumbAsset.toString());
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
loadThumb();
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
alive = false;
|
||||||
|
};
|
||||||
|
}, [thumb]);
|
||||||
|
|
||||||
|
return h(
|
||||||
|
'div',
|
||||||
|
{},
|
||||||
|
h('h1', {}, title),
|
||||||
|
h(
|
||||||
|
'dl',
|
||||||
|
{},
|
||||||
|
h('dt', {}, 'Posts on Frontpage'),
|
||||||
|
h('dd', {}, widgetsFor('posts').widgets.front_limit ?? 0),
|
||||||
|
|
||||||
|
h('dt', {}, 'Default Author'),
|
||||||
|
h('dd', {}, widgetsFor('posts').data?.author ?? 'None'),
|
||||||
|
|
||||||
|
h('dt', {}, 'Default Thumbnail'),
|
||||||
|
h('dd', {}, thumb && h('img', { src: thumbUrl })),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const AuthorsPreview = ({ widgetsFor }) => {
|
||||||
|
return h(
|
||||||
|
'div',
|
||||||
|
{},
|
||||||
|
h('h1', {}, 'Authors'),
|
||||||
|
widgetsFor('authors').map(function (author, index) {
|
||||||
|
return h(
|
||||||
|
'div',
|
||||||
|
{ key: index },
|
||||||
|
h('hr', {}),
|
||||||
|
h('strong', {}, author.data.name),
|
||||||
|
author.widgets.description,
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const RelationKitchenSinkPostPreview = ({ fieldsMetaData }) => {
|
||||||
|
// When a post is selected from the relation field, all of it's data
|
||||||
|
// will be available in the field's metadata nested under the collection
|
||||||
|
// name, and then further nested under the value specified in `value_field`.
|
||||||
|
// In this case, the post would be nested under "posts" and then under
|
||||||
|
// the title of the selected post, since our `value_field` in the config
|
||||||
|
// is "title".
|
||||||
|
const post = fieldsMetaData && fieldsMetaData.posts.value;
|
||||||
|
const style = { border: '2px solid #ccc', borderRadius: '8px', padding: '20px' };
|
||||||
|
return post
|
||||||
|
? h(
|
||||||
|
'div',
|
||||||
|
{ style: style },
|
||||||
|
h('h2', {}, 'Related Post'),
|
||||||
|
h('h3', {}, post.title),
|
||||||
|
h('img', { src: post.image }),
|
||||||
|
h('p', {}, (post.body ?? '').slice(0, 100) + '...'),
|
||||||
|
)
|
||||||
|
: null;
|
||||||
|
};
|
||||||
|
|
||||||
|
const CustomPage = () => {
|
||||||
|
return h('div', {}, 'I am a custom page!');
|
||||||
|
};
|
||||||
|
|
||||||
|
CMS.registerPreviewStyle('.toastui-editor-contents h1 { color: blue }', { raw: true });
|
||||||
|
CMS.registerPreviewTemplate('posts', PostPreview);
|
||||||
|
CMS.registerPreviewTemplate('general', GeneralPreview);
|
||||||
|
CMS.registerPreviewTemplate('authors', AuthorsPreview);
|
||||||
|
// Pass the name of a registered control to reuse with a new widget preview.
|
||||||
|
CMS.registerWidget('relationKitchenSinkPost', 'relation', RelationKitchenSinkPostPreview);
|
||||||
|
CMS.registerAdditionalLink({
|
||||||
|
id: 'example',
|
||||||
|
title: 'Example.com',
|
||||||
|
data: 'https://example.com',
|
||||||
|
options: {
|
||||||
|
icon: 'page',
|
||||||
|
},
|
||||||
|
});
|
||||||
|
CMS.registerAdditionalLink({
|
||||||
|
id: 'custom-page',
|
||||||
|
title: 'Custom Page',
|
||||||
|
data: CustomPage,
|
||||||
|
options: {
|
||||||
|
icon: 'page',
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
CMS.registerShortcode('youtube', {
|
||||||
|
label: 'YouTube',
|
||||||
|
openTag: '[',
|
||||||
|
closeTag: ']',
|
||||||
|
separator: '|',
|
||||||
|
toProps: args => {
|
||||||
|
if (args.length > 0) {
|
||||||
|
return { src: args[0] };
|
||||||
|
}
|
||||||
|
|
||||||
|
return { src: '' };
|
||||||
|
},
|
||||||
|
toArgs: ({ src }) => {
|
||||||
|
return [src];
|
||||||
|
},
|
||||||
|
control: ({ src, onChange }) => {
|
||||||
|
return h('span', {}, [
|
||||||
|
h('input', {
|
||||||
|
key: 'control-input',
|
||||||
|
value: src,
|
||||||
|
onChange: event => {
|
||||||
|
onChange({ src: event.target.value });
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
h(
|
||||||
|
'iframe',
|
||||||
|
{
|
||||||
|
key: 'control-preview',
|
||||||
|
width: '420',
|
||||||
|
height: '315',
|
||||||
|
src: `https://www.youtube.com/embed/${src}`,
|
||||||
|
},
|
||||||
|
'',
|
||||||
|
),
|
||||||
|
]);
|
||||||
|
},
|
||||||
|
preview: ({ src }) => {
|
||||||
|
return h(
|
||||||
|
'span',
|
||||||
|
{},
|
||||||
|
h(
|
||||||
|
'iframe',
|
||||||
|
{
|
||||||
|
width: '420',
|
||||||
|
height: '315',
|
||||||
|
src: `https://www.youtube.com/embed/${src}`,
|
||||||
|
},
|
||||||
|
'',
|
||||||
|
),
|
||||||
|
);
|
||||||
|
},
|
||||||
|
});
|
30
yarn.lock
30
yarn.lock
@ -3393,10 +3393,10 @@
|
|||||||
redux-thunk "^2.4.2"
|
redux-thunk "^2.4.2"
|
||||||
reselect "^4.1.7"
|
reselect "^4.1.7"
|
||||||
|
|
||||||
"@remix-run/router@1.1.0":
|
"@remix-run/router@1.2.0":
|
||||||
version "1.1.0"
|
version "1.2.0"
|
||||||
resolved "https://registry.yarnpkg.com/@remix-run/router/-/router-1.1.0.tgz#b48db8148c8a888e50580a8152b6f68161c49406"
|
resolved "https://registry.yarnpkg.com/@remix-run/router/-/router-1.2.0.tgz#54eff8306938b64c521f4a9ed313d33a91ef019a"
|
||||||
integrity sha512-rGl+jH/7x1KBCQScz9p54p0dtPLNeKGb3e0wD2H5/oZj41bwQUnXdzbj2TbUAFhvD7cp9EyEQA4dEgpUFa1O7Q==
|
integrity sha512-GO82KYYTWPRCgdNtnheaZG3LcViUlxRFlHM7ykh7N+ufoXi6PVIHoP+9RUG/vuzl2hr9i/h6EA1Eq+2HpqJ0gQ==
|
||||||
|
|
||||||
"@rollup/plugin-babel@^5.2.0":
|
"@rollup/plugin-babel@^5.2.0":
|
||||||
version "5.3.1"
|
version "5.3.1"
|
||||||
@ -13151,20 +13151,20 @@ react-refresh@0.14.0:
|
|||||||
resolved "https://registry.yarnpkg.com/react-refresh/-/react-refresh-0.14.0.tgz#4e02825378a5f227079554d4284889354e5f553e"
|
resolved "https://registry.yarnpkg.com/react-refresh/-/react-refresh-0.14.0.tgz#4e02825378a5f227079554d4284889354e5f553e"
|
||||||
integrity sha512-wViHqhAd8OHeLS/IRMJjTSDHF3U9eWi62F/MledQGPdJGDhodXJ9PBLNGr6WWL7qlH12Mt3TyTpbS+hGXMjCzQ==
|
integrity sha512-wViHqhAd8OHeLS/IRMJjTSDHF3U9eWi62F/MledQGPdJGDhodXJ9PBLNGr6WWL7qlH12Mt3TyTpbS+hGXMjCzQ==
|
||||||
|
|
||||||
react-router-dom@6.5.0:
|
react-router-dom@6.6.0:
|
||||||
version "6.5.0"
|
version "6.6.0"
|
||||||
resolved "https://registry.yarnpkg.com/react-router-dom/-/react-router-dom-6.5.0.tgz#3970bdcaa7c710a6e0b478a833ba0b4b8ae61a6f"
|
resolved "https://registry.yarnpkg.com/react-router-dom/-/react-router-dom-6.6.0.tgz#ad20b37b69e9fe7c6389663a0767ba40a19f71fe"
|
||||||
integrity sha512-/XzRc5fq80gW1ctiIGilyKFZC/j4kfe75uivMsTChFbkvrK4ZrF3P3cGIc1f/SSkQ4JiJozPrf+AwUHHWVehVg==
|
integrity sha512-qC4jnvpfCPKVle1mKLD75IvZLcbVJyFMlSn16WY9ZiOed3dgSmqhslCf/u3tmSccWOujkdsT/OwGq12bELmvjg==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@remix-run/router" "1.1.0"
|
"@remix-run/router" "1.2.0"
|
||||||
react-router "6.5.0"
|
react-router "6.6.0"
|
||||||
|
|
||||||
react-router@6.5.0:
|
react-router@6.6.0:
|
||||||
version "6.5.0"
|
version "6.6.0"
|
||||||
resolved "https://registry.yarnpkg.com/react-router/-/react-router-6.5.0.tgz#b53f15543a60750c925609d2e38037ac5aed6dd3"
|
resolved "https://registry.yarnpkg.com/react-router/-/react-router-6.6.0.tgz#9ae27cfc6bf7f2b28e1f028fe01fdbec96a3a41d"
|
||||||
integrity sha512-fqqUSU0NC0tSX0sZbyuxzuAzvGqbjiZItBQnyicWlOUmzhAU8YuLgRbaCL2hf3sJdtRy4LP/WBrWtARkMvdGPQ==
|
integrity sha512-+VPfCIaFbkW7BAiB/2oeprxKAt1KLbl+zXZ10CXOYezKWgBmTKyh8XjI53eLqY5kd7uY+V4rh3UW44FclwUU+Q==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@remix-run/router" "1.1.0"
|
"@remix-run/router" "1.2.0"
|
||||||
|
|
||||||
react-schemaorg@2.0.0:
|
react-schemaorg@2.0.0:
|
||||||
version "2.0.0"
|
version "2.0.0"
|
||||||
|
Loading…
x
Reference in New Issue
Block a user