First CardUI commit

This commit is contained in:
Cássio Zen 2016-07-11 18:57:54 -03:00
parent 9a3a013b5b
commit 1741c12bea
11 changed files with 162 additions and 47 deletions

View File

@ -17,6 +17,7 @@ collections: # A list of collections the CMS should be able to edit
meta:
- {label: "Publish Date", name: "date", widget: "datetime", format: "YYYY-MM-DD hh:mma"}
- {label: "SEO Description", name: "description", widget: "text"}
card: {type: "media", media: "image", text: "title"}
- name: "faq" # Used in routes, ie.: /admin/collections/:slug/edit
label: "FAQ" # Used in the UI, ie.: "New Post"
@ -25,6 +26,7 @@ collections: # A list of collections the CMS should be able to edit
fields: # The fields each document in this collection have
- {label: "Question", name: "title", widget: "string", tagname: "h1"}
- {label: "Answer", name: "body", widget: "markdown"}
card: {type: "alltype", text: "title"}
- name: "settings"
label: "Settings"

View File

@ -4,7 +4,7 @@
<meta charset="utf-8" />
<title>This is an example</title>
<link rel="stylesheet" href="https://facebook.github.io/draft-js/css/draft.css"/>
<link href='https://fonts.googleapis.com/css?family=Roboto:100,300,400,500,700' rel='stylesheet' type='text/css'>
<script>
window.repoFiles = {

View File

@ -65,6 +65,7 @@
"whatwg-fetch": "^1.0.0"
},
"dependencies": {
"bricks.js": "^1.7.0",
"commonmark": "^0.24.0",
"commonmark-react-renderer": "^4.1.2",
"draft-js": "^0.7.0",

11
src/components/Cards.js Normal file
View File

@ -0,0 +1,11 @@
import UnknownCard from './Cards/UnknownCard';
import MediaCard from './Cards/MediaCard';
import AlltypeCard from './Cards/AlltypeCard';
const Cards = {
_unknown: UnknownCard,
media: MediaCard,
alltype: AlltypeCard
};
export default Cards;

View File

@ -0,0 +1,14 @@
import React, { PropTypes } from 'react';
import { Card } from '../UI';
export default function AlltypeCard({ onClick, text }) {
return (
<Card onClick={onClick}>
<p>{text}</p>
</Card>
);
}
AlltypeCard.propTypes = {
text: PropTypes.string.isRequired
};

View File

@ -0,0 +1,16 @@
import React, { PropTypes } from 'react';
import { Card } from '../UI';
export default function MediaCard({ onClick, media, text }) {
return (
<Card onClick={onClick}>
<img src={media} />
<h1>{text}</h1>
</Card>
);
}
MediaCard.propTypes = {
media: PropTypes.string.isRequired,
text: PropTypes.string.isRequired
};

View File

@ -0,0 +1,15 @@
import React from 'react';
import ImmutablePropTypes from 'react-immutable-proptypes';
import { Card } from '../UI';
export default function UnknownCard({ collection }) {
return (
<Card>
<p>No card of type {collection.getIn(['card', 'type'])}.</p>
</Card>
);
}
UnknownCard.propTypes = {
collection: ImmutablePropTypes.map,
};

View File

@ -1,18 +1,81 @@
import React from 'react';
import ImmutablePropTypes from 'react-immutable-proptypes';
import { Link } from 'react-router';
import Bricks from 'bricks.js'
import { browserHistory } from 'react-router';
import Cards from './Cards';
export default function EntryListing({ collection, entries }) {
const name = collection.get('name');
return <div>
<h2>Listing entries!</h2>
{entries.map((entry) => {
const path = `/collections/${name}/entries/${entry.get('slug')}`;
return <Link key={entry.get('slug')} to={path}>
<h3>{entry.getIn(['data', 'title'])}</h3>
</Link>;
})}
</div>;
export default class EntryListing extends React.Component {
constructor(props) {
super(props);
this.bricksInstance = null;
this.bricksConfig = {
packed: 'data-packed',
sizes: [
{ columns: 2, gutter: 15 },
{ mq: '780px', columns: 3, gutter: 15 },
{ mq: '1035px', columns: 4, gutter: 15 },
{ mq: '1290px', columns: 5, gutter: 15 },
{ mq: '1545px', columns: 6, gutter: 15 },
{ mq: '1800px', columns: 7, gutter: 15 },
]
};
}
componentDidMount() {
this.bricksInstance = Bricks({
container: this._entries,
packed: this.bricksConfig.packed,
sizes: this.bricksConfig.sizes
});
this.bricksInstance.resize(true);
if (this.props.entries && this.props.entries.size > 0) {
setTimeout(() => {
this.bricksInstance.pack();
}, 0);
}
}
componentDidUpdate(prevProps) {
if ((prevProps.entries === undefined || prevProps.entries.size === 0) && this.props.entries.size === 0) {
return;
}
this.bricksInstance.pack();
}
componengWillUnmount() {
this.bricksInstance.resize(false);
}
cardFor(collection, entry, link) {
//const { entry, getMedia, onChange, onAddMedia, onRemoveMedia } = this.props;
const card = Cards[collection.getIn(['card', 'type'])] || Cards._unknown;
return React.createElement(card, {
key: entry.get('slug'),
collection: collection,
onClick: browserHistory.push.bind(this, link),
text: entry.getIn(['data', collection.getIn(['card', 'text'])]),
media: entry.getIn(['data', collection.getIn(['card', 'media'])]),
});
}
render() {
const { collection, entries } = this.props;
const name = collection.get('name');
return <div>
<h2>Listing entries!</h2>
<div ref={(c) => this._entries = c}>
{entries.map((entry) => {
const path = `/collections/${name}/entries/${entry.get('slug')}`;
return this.cardFor(collection, entry, path);
})}
</div>
</div>;
}
}
EntryListing.propTypes = {

View File

@ -4,6 +4,7 @@
composes: rounded from "../theme.css";
composes: depth from "../theme.css";
overflow: hidden;
width: 240px;
}
.card > *:not(iframe, video, img, header, footer) {

View File

@ -1,6 +1,6 @@
import React from 'react';
import styles from './Card.css';
export default function Card({ style, className = '', children }) {
return <div className={`${styles.card} ${className}`} style={style}>{children}</div>;
export default function Card({ style, className = '', onClick, children }) {
return <div className={`${styles.card} ${className}`} style={style} onClick={onClick}>{children}</div>;
}

View File

@ -3,7 +3,6 @@ import { Card } from '../UI';
import { storiesOf } from '@kadira/storybook';
const styles = {
fixedWidth: { width: 280 },
footer: {
color: '#aaa',
backgroundColor: '#555',
@ -11,40 +10,33 @@ const styles = {
marginTop: 5,
padding: 10
}
}
};
storiesOf('Card', module)
.add('Default View', () => (
<div style={styles.fixedWidth}>
<Card>
<h1>A Card</h1>
<h2>Subtitle</h2>
<p>
Margins are applied to all elements inside a card. <br/>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. lobortis vel. Nulla porttitor enim at tellus eget
malesuada eleifend. Nunc tellus turpis, tincidunt sed felis facilisis, lacinia condimentum quam. Cras quis
tortor fermentum, aliquam tortor eu, consequat ligula. Nulla eget nulla act odio varius ullamcorper turpis.
In consequat egestas nulla condimentum faucibus. Donec scelerisque convallis est nec fringila. Suspendisse
non lorem non erat congue consequat.
</p>
</Card>
</div>
<Card>
<h1>A Card</h1>
<h2>Subtitle</h2>
<p>
Margins are applied to all elements inside a card. <br/>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. lobortis vel. Nulla porttitor enim at tellus eget
malesuada eleifend. Nunc tellus turpis, tincidunt sed felis facilisis, lacinia condimentum quam. Cras quis
tortor fermentum, aliquam tortor eu, consequat ligula. Nulla eget nulla act odio varius ullamcorper turpis.
In consequat egestas nulla condimentum faucibus. Donec scelerisque convallis est nec fringila. Suspendisse
non lorem non erat congue consequat.
</p>
</Card>
)).add('Full width content', () => (
<div style={styles.fixedWidth}>
<Card>
<img src="https://i.ytimg.com/vi/tntOCGkgt98/maxresdefault.jpg" />
<h1>Card & cat</h1>
<p>Media Elements such as video, img (and iFrame for embeds) don't have margin</p>
</Card>
</div>
<Card>
<img src="https://i.ytimg.com/vi/tntOCGkgt98/maxresdefault.jpg" />
<h1>Card & cat</h1>
<p>Media Elements such as video, img (and iFrame for embeds) don't have margin</p>
</Card>
)).add('Footer', () => (
<div style={styles.fixedWidth}>
<Card>
<img src="http://www.top13.net/wp-content/uploads/2015/10/perfectly-timed-funny-cat-pictures-5.jpg" />
<h1>Now with footer.</h1>
<p>header and footer elements are also not subject to margin</p>
<footer style={styles.footer}>&copy; Thousand Cats Corp</footer>
</Card>
</div>
<Card>
<img src="http://www.top13.net/wp-content/uploads/2015/10/perfectly-timed-funny-cat-pictures-5.jpg" />
<h1>Now with footer.</h1>
<p>header and footer elements are also not subject to margin</p>
<footer style={styles.footer}>&copy; Thousand Cats Corp</footer>
</Card>
))