From ad13684fe341736b1044c0a9ce7fe8cdca4cfb85 Mon Sep 17 00:00:00 2001 From: Andrew Nicolaou Date: Sun, 10 Nov 2019 17:08:00 +0100 Subject: [PATCH] New simplified sketch list when adding from Collection view --- .../IDE/components/AddToCollectionList.jsx | 18 +-- .../components/AddToCollectionSketchList.jsx | 130 ++++++++++++++++++ .../components/QuickAddList/QuickAddList.jsx | 33 +++-- client/modules/User/components/Collection.jsx | 4 +- client/styles/components/_collection.scss | 1 - client/styles/components/_quick-add.scss | 3 +- 6 files changed, 161 insertions(+), 28 deletions(-) create mode 100644 client/modules/IDE/components/AddToCollectionSketchList.jsx diff --git a/client/modules/IDE/components/AddToCollectionList.jsx b/client/modules/IDE/components/AddToCollectionList.jsx index 12af01d3..74aa2011 100644 --- a/client/modules/IDE/components/AddToCollectionList.jsx +++ b/client/modules/IDE/components/AddToCollectionList.jsx @@ -1,10 +1,8 @@ import PropTypes from 'prop-types'; import React from 'react'; import { Helmet } from 'react-helmet'; -import InlineSVG from 'react-inlinesvg'; import { connect } from 'react-redux'; import { bindActionCreators } from 'redux'; -import classNames from 'classnames'; import * as ProjectActions from '../actions/project'; import * as ProjectsActions from '../actions/projects'; @@ -13,7 +11,7 @@ import * as ToastActions from '../actions/toast'; import * as SortingActions from '../actions/sorting'; import getSortedCollections from '../selectors/collections'; import Loader from '../../App/components/loader'; -import QuickAddList from './QuickAddList/QuickAddList'; +import QuickAddList from './QuickAddList'; const projectInCollection = (project, collection) => collection.items.find(item => item.project.id === project.id) != null; @@ -56,14 +54,6 @@ class CollectionList extends React.Component { this.props.removeFromCollection(collection.id, this.props.project.id); } - handleAddRemove = (collection) => { - if (projectInCollection(this.props.project, collection)) { - this.handleCollectionRemove(collection); - } else { - this.handleCollectionAdd(collection); - } - } - render() { const username = this.props.username !== undefined ? this.props.username : this.props.user.username; const { collections, project } = this.props; @@ -79,13 +69,13 @@ class CollectionList extends React.Component { if (this.props.loading && !this.state.hasLoadedData) { content = ; } else if (hasCollections) { - content = ; + content = ; } else { content = 'No collections'; } return ( -
+
{this.getTitle()} @@ -154,7 +144,7 @@ function mapStateToProps(state, ownProps) { collections: getSortedCollections(state), sorting: state.sorting, loading: state.loading, - project: state.project, + project: ownProps.project || state.project, projectId: ownProps && ownProps.params ? ownProps.prams.project_id : null, }; } diff --git a/client/modules/IDE/components/AddToCollectionSketchList.jsx b/client/modules/IDE/components/AddToCollectionSketchList.jsx new file mode 100644 index 00000000..632cf676 --- /dev/null +++ b/client/modules/IDE/components/AddToCollectionSketchList.jsx @@ -0,0 +1,130 @@ +import PropTypes from 'prop-types'; +import React from 'react'; +import { Helmet } from 'react-helmet'; +import { connect } from 'react-redux'; +import { bindActionCreators } from 'redux'; +// import find from 'lodash/find'; +import * as ProjectsActions from '../actions/projects'; +import * as CollectionsActions from '../actions/collections'; +import * as ToastActions from '../actions/toast'; +import * as SortingActions from '../actions/sorting'; +import getSortedSketches from '../selectors/projects'; +import Loader from '../../App/components/loader'; +import QuickAddList from './QuickAddList'; + +class SketchList extends React.Component { + constructor(props) { + super(props); + this.props.getProjects(this.props.username); + + this.state = { + isInitialDataLoad: true, + }; + } + + componentWillReceiveProps(nextProps) { + if (this.props.sketches !== nextProps.sketches && Array.isArray(nextProps.sketches)) { + this.setState({ + isInitialDataLoad: false, + }); + } + } + + getSketchesTitle() { + if (this.props.username === this.props.user.username) { + return 'p5.js Web Editor | My sketches'; + } + return `p5.js Web Editor | ${this.props.username}'s sketches`; + } + + handleCollectionAdd = (sketch) => { + this.props.addToCollection(this.props.collection.id, sketch.id); + } + + handleCollectionRemove = (sketch) => { + this.props.removeFromCollection(this.props.collection.id, sketch.id); + } + + inCollection = sketch => this.props.collection.items.find(item => item.project.id === sketch.id) != null + + render() { + const hasSketches = this.props.sketches.length > 0; + const sketchesWithAddedStatus = this.props.sketches.map(sketch => ({ + ...sketch, + isAdded: this.inCollection(sketch), + })); + + let content = null; + + if (this.props.loading && this.state.isInitialDataLoad) { + content = ; + } else if (hasSketches) { + content = ; + } else { + content = 'No collections'; + } + + return ( +
+ + {this.getSketchesTitle()} + + {content} +
+ ); + } +} + +SketchList.propTypes = { + user: PropTypes.shape({ + username: PropTypes.string, + authenticated: PropTypes.bool.isRequired + }).isRequired, + getProjects: PropTypes.func.isRequired, + sketches: PropTypes.arrayOf(PropTypes.shape({ + id: PropTypes.string.isRequired, + name: PropTypes.string.isRequired, + createdAt: PropTypes.string.isRequired, + updatedAt: PropTypes.string.isRequired + })).isRequired, + collection: PropTypes.shape({ + id: PropTypes.string.isRequired, + name: PropTypes.string.isRequired, + items: PropTypes.arrayOf(PropTypes.shape({ + project: PropTypes.shape({ + id: PropTypes.string.isRequired, + }), + })), + }).isRequired, + username: PropTypes.string, + loading: PropTypes.bool.isRequired, + sorting: PropTypes.shape({ + field: PropTypes.string.isRequired, + direction: PropTypes.string.isRequired + }).isRequired, + addToCollection: PropTypes.func.isRequired, + removeFromCollection: PropTypes.func.isRequired, +}; + +SketchList.defaultProps = { + username: undefined +}; + +function mapStateToProps(state) { + return { + user: state.user, + sketches: getSortedSketches(state), + sorting: state.sorting, + loading: state.loading, + project: state.project + }; +} + +function mapDispatchToProps(dispatch) { + return bindActionCreators( + Object.assign({}, ProjectsActions, CollectionsActions, ToastActions, SortingActions), + dispatch + ); +} + +export default connect(mapStateToProps, mapDispatchToProps)(SketchList); diff --git a/client/modules/IDE/components/QuickAddList/QuickAddList.jsx b/client/modules/IDE/components/QuickAddList/QuickAddList.jsx index d1e88ac8..3d566654 100644 --- a/client/modules/IDE/components/QuickAddList/QuickAddList.jsx +++ b/client/modules/IDE/components/QuickAddList/QuickAddList.jsx @@ -27,20 +27,33 @@ Item.propTypes = { onSelect: PropTypes.func.isRequired, }; -const QuickAddList = ({ items, onSelect }) => ( -
    {items.map(item => ( onSelect(item) +const QuickAddList = ({ + items, onAdd, onRemove +}) => { + const handleAction = (item) => { + if (item.isAdded) { + onRemove(item); + } else { + onAdd(item); } - />))} -
-); + }; + + return ( +
    {items.map(item => ( handleAction(item) + } + />))} +
+ ); +}; QuickAddList.propTypes = { items: PropTypes.arrayOf(ItemType).isRequired, - onSelect: PropTypes.func.isRequired, + onAdd: PropTypes.func.isRequired, + onRemove: PropTypes.func.isRequired, }; export default QuickAddList; diff --git a/client/modules/User/components/Collection.jsx b/client/modules/User/components/Collection.jsx index 41fbf13e..68b99f30 100644 --- a/client/modules/User/components/Collection.jsx +++ b/client/modules/User/components/Collection.jsx @@ -17,7 +17,7 @@ import { getCollection } from '../../IDE/selectors/collections'; import Loader from '../../App/components/loader'; import EditableInput from '../../IDE/components/EditableInput'; import Overlay from '../../App/components/Overlay'; -import SketchList from '../../IDE/components/SketchList'; +import SketchList from '../../IDE/components/AddToCollectionSketchList'; import CopyableInput from '../../IDE/components/CopyableInput'; import SketchSearchbar from '../../IDE/components/Searchbar'; @@ -470,7 +470,7 @@ class Collection extends React.Component { this.state.isAddingSketches && ( } closeOverlay={this.hideAddSketches}>
- +
) diff --git a/client/styles/components/_collection.scss b/client/styles/components/_collection.scss index b0f122f2..88e1fa53 100644 --- a/client/styles/components/_collection.scss +++ b/client/styles/components/_collection.scss @@ -84,7 +84,6 @@ .collection-add-sketch { min-width: #{800 / $base-font-size}rem; - padding: #{24 / $base-font-size}rem; overflow: scroll; } diff --git a/client/styles/components/_quick-add.scss b/client/styles/components/_quick-add.scss index e3658b50..1775ba3e 100644 --- a/client/styles/components/_quick-add.scss +++ b/client/styles/components/_quick-add.scss @@ -1,6 +1,7 @@ .quick-add { + width: auto; + min-width: #{600 / $base-font-size}rem; padding: #{24 / $base-font-size}rem; - width: #{600 / $base-font-size}rem; } .quick-add__item {