diff --git a/cypress/support/commands/navigation.js b/cypress/support/commands/navigation.js index 454f556dd..90aeca87d 100644 --- a/cypress/support/commands/navigation.js +++ b/cypress/support/commands/navigation.js @@ -24,8 +24,10 @@ Cypress.Commands.add('goToHome', () => { cy.get(`#${NAVIGATION_HOME_LINK_ID}`).click(); }); -Cypress.Commands.add('goToItemWithNavigation', (id) => { +Cypress.Commands.add('goToItemWithNavigation', (id, openHidden = false) => { cy.wait(NAVIGATE_PAUSE); - cy.get(`#${NAVIGATION_HIDDEN_PARENTS_ID}`).click(); + if (openHidden) { + cy.get(`#${NAVIGATION_HIDDEN_PARENTS_ID}`).click(); + } cy.get(`#${buildNavigationLink(id)}`).click(); }); diff --git a/package.json b/package.json index 069795d49..510fcc180 100644 --- a/package.json +++ b/package.json @@ -5,8 +5,8 @@ "license": "AGPL-3.0-only", "dependencies": { "@graasp/chatbox": "git://github.com/graasp/graasp-chatbox.git#main", - "@graasp/query-client": "git://github.com/graasp/graasp-query-client.git#82/updateDeleteItemsRoute", - "@graasp/ui": "git://github.com/graasp/graasp-ui.git#master", + "@graasp/query-client": "git://github.com/graasp/graasp-query-client.git#85/thumbnails", + "@graasp/ui": "git://github.com/graasp/graasp-ui.git", "@material-ui/core": "4.11.2", "@material-ui/icons": "5.0.0-beta.4", "@material-ui/lab": "4.0.0-alpha.57", @@ -56,6 +56,7 @@ "start:ci": "react-scripts -r @cypress/instrument-cra start", "build": "react-scripts build", "dist": "env-cmd -f ./.env.production react-scripts build", + "dist:dev": "env-cmd -f ./.env.development react-scripts build", "test": "env-cmd -f ./.env.test react-scripts test", "test:once": "env-cmd -f ./.env.test react-scripts test --watchAll=false", "eject": "react-scripts eject", diff --git a/src/components/context/LayoutContext.js b/src/components/context/LayoutContext.js index bab97a869..e740baa04 100644 --- a/src/components/context/LayoutContext.js +++ b/src/components/context/LayoutContext.js @@ -1,9 +1,6 @@ import React, { useState } from 'react'; import PropTypes from 'prop-types'; -import { - DEFAULT_ITEM_LAYOUT_MODE, - MIN_SCREEN_WIDTH, -} from '../../config/constants'; +import { DEFAULT_ITEM_LAYOUT_MODE } from '../../config/constants'; const LayoutContext = React.createContext(); @@ -22,11 +19,7 @@ const LayoutContextProvider = ({ children }) => { const [isMainMenuOpen, setIsMainMenuOpen] = useState(true); - // open item panel by default if width allows it - const isItemPanelOpen = window.innerWidth > MIN_SCREEN_WIDTH; - const [isItemMetadataMenuOpen, setIsItemMetadataMenuOpen] = useState( - isItemPanelOpen, - ); + const [isItemMetadataMenuOpen, setIsItemMetadataMenuOpen] = useState(false); const [isChatboxMenuOpen, setIsChatboxMenuOpen] = useState(false); return ( diff --git a/src/components/layout/Navigation.js b/src/components/layout/Navigation.js index 3e200701a..eb14f3b8d 100644 --- a/src/components/layout/Navigation.js +++ b/src/components/layout/Navigation.js @@ -1,4 +1,5 @@ import React, { useState } from 'react'; +import PropTypes from 'prop-types'; import Typography from '@material-ui/core/Typography'; import { useTranslation } from 'react-i18next'; import { makeStyles } from '@material-ui/core'; @@ -42,7 +43,7 @@ const Navigation = () => { const { data: parents, isLoading: parentIsLoading } = useParents({ id: itemId, path: itemPath, - enabled: parentsOpen, + enabled: true, }); if (isItemLoading) { @@ -84,6 +85,16 @@ const Navigation = () => { ); }; + const ParentLink = ({ id, name }) => ( + + {name} + + ); + ParentLink.propTypes = { + id: PropTypes.string.isRequired, + name: PropTypes.string.isRequired, + }; + const renderParents = () => { // nothing to display if no parents const p = item?.get('path'); @@ -91,29 +102,40 @@ const Navigation = () => { return null; } - // display parents only when needed - // todo: display parents if in database - if (!parentsOpen) { + if (parentIsLoading) { return ( {LOADING_CONTENT} ); } - if (parentIsLoading) { - return ; + // display parents only when needed + // always display last and first parent + if (!parentsOpen) { + return [ + parents?.size >= 1 && ( + + ), + parents?.size >= 3 && ( + + {LOADING_CONTENT} + + ), + parents?.size >= 2 && ( + + ), + ]; } - return parents?.map(({ name, id }) => ( - - {name} - - )); + return parents?.map(({ name, id }) => ); }; return ( diff --git a/src/components/main/CustomCardHeader.js b/src/components/main/CustomCardHeader.js deleted file mode 100644 index 8a97298e0..000000000 --- a/src/components/main/CustomCardHeader.js +++ /dev/null @@ -1,84 +0,0 @@ -import Avatar from '@material-ui/core/Avatar'; -import { makeStyles } from '@material-ui/core/styles'; -import Typography from '@material-ui/core/Typography'; -import PropTypes from 'prop-types'; -import React from 'react'; -import { useTranslation } from 'react-i18next'; -import { Link } from 'react-router-dom'; -import { buildItemPath } from '../../config/paths'; -import { hooks } from '../../config/queryClient'; -import { buildItemLink } from '../../config/selectors'; -import ItemMenu from './ItemMenu'; - -const { useMember } = hooks; - -const useStyles = makeStyles((theme) => ({ - root: { - display: 'flex', - justifyContent: 'space-between', - alignItems: 'center', - marginTop: theme.spacing(1), - marginBottom: theme.spacing(1), - }, - header: { - display: 'flex', - }, - avatar: { - marginLeft: theme.spacing(1), - marginRight: theme.spacing(1), - }, - title: { - fontSize: '0.9rem', - fontWeight: 'bold', - }, - link: { - textDecoration: 'none', - color: 'inherit', - }, - subtitle: { - fontSize: '0.72rem', - }, -})); - -const CustomCardHeader = ({ item, canEdit }) => { - const { id, creator, name, type } = item; - const classes = useStyles(); - const { t } = useTranslation(); - - const { data: member } = useMember(creator); - - return ( -
-
- {/* todo: add avatar for member */} - -
- - - {name} - - - - {t('Type by author', { - type, - author: member?.get('name'), - })} - -
-
- -
- ); -}; - -CustomCardHeader.propTypes = { - item: PropTypes.shape({ - id: PropTypes.string.isRequired, - creator: PropTypes.string.isRequired, - name: PropTypes.string.isRequired, - type: PropTypes.string.isRequired, - }).isRequired, - canEdit: PropTypes.bool.isRequired, -}; - -export default CustomCardHeader; diff --git a/src/components/main/Item.js b/src/components/main/Item.js index ad7b677c0..9f74a3346 100644 --- a/src/components/main/Item.js +++ b/src/components/main/Item.js @@ -1,31 +1,26 @@ import React, { useContext } from 'react'; +import truncate from 'lodash.truncate'; import PropTypes from 'prop-types'; +import { Card as GraaspCard } from '@graasp/ui'; import { makeStyles } from '@material-ui/core/styles'; -import truncate from 'lodash.truncate'; -import Card from '@material-ui/core/Card'; -import CardMedia from '@material-ui/core/CardMedia'; -import CardContent from '@material-ui/core/CardContent'; -import CardActions from '@material-ui/core/CardActions'; -import Typography from '@material-ui/core/Typography'; -import CustomCardHeader from './CustomCardHeader'; +import { Link } from 'react-router-dom'; import { DESCRIPTION_MAX_LENGTH } from '../../config/constants'; -import { buildItemCard } from '../../config/selectors'; +import { buildItemCard, buildItemLink } from '../../config/selectors'; import EditButton from '../common/EditButton'; import { isItemUpdateAllowedForUser } from '../../utils/membership'; import { getItemImage, stripHtml } from '../../utils/item'; +import ItemMenu from './ItemMenu'; import FavoriteButton from '../common/FavoriteButton'; import PinButton from '../common/PinButton'; import { CurrentUserContext } from '../context/CurrentUserContext'; +import { buildItemPath } from '../../config/paths'; -const useStyles = makeStyles(() => ({ - root: { - maxWidth: 345, - }, - media: { - height: 0, - paddingTop: '56.25%', // 16:9 +const useStyles = makeStyles({ + link: { + textDecoration: 'none', + color: 'inherit', }, -})); +}); const Item = ({ item, memberships }) => { const classes = useStyles(); @@ -39,25 +34,39 @@ const Item = ({ item, memberships }) => { memberId: member?.get('id'), }); + const Actions = ( + <> + {!member.isEmpty() && } + {enableEdition && ( + <> + + + + )} + + ); + return ( - - - - - - {truncate(stripHtml(description), { length: DESCRIPTION_MAX_LENGTH })} - - - - {!member.isEmpty() && } - {enableEdition && ( - <> - - - - )} - - + } + image={image} + cardId={buildItemCard(id)} + NameWrapper={({ children }) => ( + + {children} + + )} + /> ); }; diff --git a/src/components/main/ItemsGrid.js b/src/components/main/ItemsGrid.js index 41f7b4927..11443a303 100644 --- a/src/components/main/ItemsGrid.js +++ b/src/components/main/ItemsGrid.js @@ -90,7 +90,7 @@ const ItemsGrid = (props) => { } return itemsInPage.map((item) => ( - + -