From 0badf690a6234f2283fded6cc376bfab5cc2a3b8 Mon Sep 17 00:00:00 2001 From: leangseu-edx <83240113+leangseu-edx@users.noreply.github.com> Date: Mon, 31 Oct 2022 13:29:24 -0400 Subject: [PATCH] Lk/update responsive view (#58) --- src/containers/CourseCard/CourseCard.scss | 7 + .../CourseCardBanners/CertificateBanner.jsx | 2 +- .../CertificateBanner.test.jsx.snap | 1 - .../components/CourseCardContent.jsx | 2 +- .../__snapshots__/index.test.jsx.snap | 34 +- .../components/CourseCardMenu/index.jsx | 23 +- .../CourseCardContent.test.jsx.snap | 6 +- .../__snapshots__/index.test.jsx.snap | 70 +++- src/containers/CourseList/hooks.js | 7 +- src/containers/CourseList/index.jsx | 11 +- src/containers/CourseList/index.scss | 35 +- src/containers/CourseList/index.test.jsx | 13 +- src/containers/Dashboard/LoadedView.jsx | 20 +- .../__snapshots__/LoadedView.test.jsx.snap | 102 ++++-- src/containers/Dashboard/index.scss | 22 ++ .../__snapshots__/index.test.jsx.snap | 6 - .../LearnerDashboardHeader/index.jsx | 1 - .../__snapshots__/index.test.jsx.snap | 316 ++++++++++-------- src/containers/MasqueradeBar/index.jsx | 93 +++--- src/containers/MasqueradeBar/index.scss | 9 + src/containers/MasqueradeBar/messages.js | 2 +- .../__snapshots__/index.test.jsx.snap | 2 +- src/containers/WidgetSidebar/index.jsx | 2 +- 23 files changed, 485 insertions(+), 301 deletions(-) diff --git a/src/containers/CourseCard/CourseCard.scss b/src/containers/CourseCard/CourseCard.scss index bdaa71b..0c42580 100644 --- a/src/containers/CourseCard/CourseCard.scss +++ b/src/containers/CourseCard/CourseCard.scss @@ -2,6 +2,10 @@ .course-card { .card { + .pgn__card-wrapper-image-cap.vertical { + display: flex; + min-height: $card-image-vertical-max-height; + } .pgn__card-image-cap { border-bottom-left-radius: 0 !important; } @@ -11,6 +15,9 @@ .pgn__card-header-content { margin-top: 1.5rem; } + .pgn__card-footer .pgn__action-row { + white-space: nowrap; + } .course-card-verify-ribbon-container { width: 100%; diff --git a/src/containers/CourseCard/components/CourseCardBanners/CertificateBanner.jsx b/src/containers/CourseCard/components/CourseCardBanners/CertificateBanner.jsx index 7d409bc..0ee054f 100644 --- a/src/containers/CourseCard/components/CourseCardBanners/CertificateBanner.jsx +++ b/src/containers/CourseCard/components/CourseCardBanners/CertificateBanner.jsx @@ -50,7 +50,7 @@ export const CertificateBanner = ({ cardId }) => { if (isArchived) { return ( - {formatMessage(messages.notEligibleForCert)}. + {formatMessage(messages.notEligibleForCert)} {' '} {formatMessage(messages.viewGrades)} diff --git a/src/containers/CourseCard/components/CourseCardBanners/__snapshots__/CertificateBanner.test.jsx.snap b/src/containers/CourseCard/components/CourseCardBanners/__snapshots__/CertificateBanner.test.jsx.snap index 2ca3674..8bf1652 100644 --- a/src/containers/CourseCard/components/CourseCardBanners/__snapshots__/CertificateBanner.test.jsx.snap +++ b/src/containers/CourseCard/components/CourseCardBanners/__snapshots__/CertificateBanner.test.jsx.snap @@ -101,7 +101,6 @@ exports[`CertificateBanner snapshot not passing and has finished 1`] = ` variant="warning" > You are not eligible for a certificate. - . { const { isVerified } = appHooks.useCardEnrollmentData(cardId); return ( <> - + Email settings - - - Share to Twitter - - + + Share to Twitter + Email settings - - - Share to Twitter - - + + Share to Twitter + { )} */} {twitter.isEnabled && ( - - - {formatMessage(messages.shareToTwitter)} - - + + {formatMessage(messages.shareToTwitter)} + )} diff --git a/src/containers/CourseCard/components/__snapshots__/CourseCardContent.test.jsx.snap b/src/containers/CourseCard/components/__snapshots__/CourseCardContent.test.jsx.snap index d091162..610125f 100644 --- a/src/containers/CourseCard/components/__snapshots__/CourseCardContent.test.jsx.snap +++ b/src/containers/CourseCard/components/__snapshots__/CourseCardContent.test.jsx.snap @@ -3,7 +3,7 @@ exports[`CourseCardContent snapshot not verified 1`] = ` +
+

+ My Courses +

+
+ +
+
+
+ +
+
+ + + + +
+ +`; + exports[`CourseList snapshots with filters 1`] = `

My Courses

My Courses

@@ -84,16 +131,15 @@ exports[`CourseList snapshots with no filters 1`] = ` className="course-list-container" >

My Courses

diff --git a/src/containers/CourseList/hooks.js b/src/containers/CourseList/hooks.js index 1fb1a73..ebbe74b 100644 --- a/src/containers/CourseList/hooks.js +++ b/src/containers/CourseList/hooks.js @@ -1,7 +1,7 @@ import React from 'react'; import { useDispatch } from 'react-redux'; -import { useCheckboxSetValues } from '@edx/paragon'; +import { useCheckboxSetValues, useWindowSize, breakpoints } from '@edx/paragon'; import { StrictDict } from 'utils'; import { actions, hooks as appHooks } from 'data/redux'; @@ -9,6 +9,11 @@ import { ListPageSize, SortKeys } from 'data/constants/app'; import * as module from './hooks'; +export const useIsCollapsed = () => { + const { width } = useWindowSize(); + return width < breakpoints.medium.maxWidth; +}; + export const state = StrictDict({ sortBy: (val) => React.useState(val), // eslint-disable-line }); diff --git a/src/containers/CourseList/index.jsx b/src/containers/CourseList/index.jsx index 1760a60..a5d357f 100644 --- a/src/containers/CourseList/index.jsx +++ b/src/containers/CourseList/index.jsx @@ -9,7 +9,7 @@ import { } from 'containers/CourseFilterControls'; import CourseCard from 'containers/CourseCard'; -import { useCourseListData } from './hooks'; +import { useCourseListData, useIsCollapsed } from './hooks'; import messages from './messages'; @@ -24,11 +24,12 @@ export const CourseList = () => { showFilters, visibleList, } = useCourseListData(); + const isCollapsed = useIsCollapsed(); return (
-
-

{formatMessage(messages.myCourses)}

-
+
+

{formatMessage(messages.myCourses)}

+
@@ -43,7 +44,7 @@ export const CourseList = () => { ))} {numPages > 1 && ( ({ useCourseListData: jest.fn(), + useIsCollapsed: jest.fn(), })); jest.mock('containers/CourseCard', () => 'CourseCard'); @@ -21,6 +22,7 @@ describe('CourseList', () => { showFilters: false, visibleList: [], }; + useIsCollapsed.mockReturnValue(false); const createWrapper = (courseListData) => { useCourseListData.mockReturnValueOnce({ ...defaultCourseListData, @@ -50,5 +52,14 @@ describe('CourseList', () => { }); expect(wrapper).toMatchSnapshot(); }); + test('collapsed with multiple courses and pages', () => { + useIsCollapsed.mockReturnValueOnce(true); + const wrapper = createWrapper({ + visibleList: [{ cardId: 'foo' }, { cardId: 'bar' }, { cardId: 'baz' }], + numPages: 3, + showFilters: true, + }); + expect(wrapper).toMatchSnapshot(); + }); }); }); diff --git a/src/containers/Dashboard/LoadedView.jsx b/src/containers/Dashboard/LoadedView.jsx index d3e0b996c..3663dae 100644 --- a/src/containers/Dashboard/LoadedView.jsx +++ b/src/containers/Dashboard/LoadedView.jsx @@ -7,13 +7,17 @@ import hooks from './hooks'; export const columnConfig = { courseList: { - xs: { span: 12, offset: 0 }, - sm: { span: 8, offset: 2 }, - md: { span: 12, offset: 0 }, - lg: { span: 10, offset: 1 }, + sm: { span: 12, offset: 0 }, + md: { span: 10, offset: 1 }, + lg: { span: 12, offset: 0 }, xl: { span: 8, offset: 0 }, }, - sidebar: { md: 12, xl: 4 }, + sidebar: { + sm: { span: 12, offset: 0 }, + md: { span: 10, offset: 1 }, + lg: { span: 12, offset: 0 }, + xl: { span: 4, offset: 0 }, + }, }; export const LoadedView = () => { @@ -22,11 +26,11 @@ export const LoadedView = () => { return ( - + - - {!isCollapsed && (

 

)} + + {!isCollapsed && (

 

)}
diff --git a/src/containers/Dashboard/__snapshots__/LoadedView.test.jsx.snap b/src/containers/Dashboard/__snapshots__/LoadedView.test.jsx.snap index bb4efbd..df69a87 100644 --- a/src/containers/Dashboard/__snapshots__/LoadedView.test.jsx.snap +++ b/src/containers/Dashboard/__snapshots__/LoadedView.test.jsx.snap @@ -7,23 +7,23 @@ exports[`LoadedView collapsed snapshot 1`] = ` > + + + - - - @@ -59,23 +75,23 @@ exports[`LoadedView not collapsed snapshot 1`] = ` > + + + - - -

 

diff --git a/src/containers/Dashboard/index.scss b/src/containers/Dashboard/index.scss index e69de29..3241781 100644 --- a/src/containers/Dashboard/index.scss +++ b/src/containers/Dashboard/index.scss @@ -0,0 +1,22 @@ +@import "@edx/paragon/scss/core/core"; + +.course-list-column { + padding: 0 map-get($spacers, 4); + margin: auto; +} + +.sidebar-column { + padding: 0 map-get($spacers, 3) 0 map-get($spacers, 1); +} + +@include media-breakpoint-down(lg) { + .sidebar-column { + // grid are inheriting dir="ltr" from the body, so we need to override it + [dir=ltr] & { + padding: 0 map-get($spacers, 3); + } + [dir=rtl] & { + padding: 0 map-get($spacers, 3); + } + } +} \ No newline at end of file diff --git a/src/containers/LearnerDashboardHeader/__snapshots__/index.test.jsx.snap b/src/containers/LearnerDashboardHeader/__snapshots__/index.test.jsx.snap index 92abd92..6fee45f 100644 --- a/src/containers/LearnerDashboardHeader/__snapshots__/index.test.jsx.snap +++ b/src/containers/LearnerDashboardHeader/__snapshots__/index.test.jsx.snap @@ -36,9 +36,6 @@ exports[`LearnerDashboardHeader snapshots with collapsed 1`] = `
-
`; @@ -77,8 +74,5 @@ exports[`LearnerDashboardHeader snapshots without collapsed 1`] = ` />
-
`; diff --git a/src/containers/LearnerDashboardHeader/index.jsx b/src/containers/LearnerDashboardHeader/index.jsx index e17702d..c7d2273 100644 --- a/src/containers/LearnerDashboardHeader/index.jsx +++ b/src/containers/LearnerDashboardHeader/index.jsx @@ -53,7 +53,6 @@ export const LearnerDashboardHeader = () => { {!isCollapsed && }
-
); }; diff --git a/src/containers/MasqueradeBar/__snapshots__/index.test.jsx.snap b/src/containers/MasqueradeBar/__snapshots__/index.test.jsx.snap index 224435c..42af13c 100644 --- a/src/containers/MasqueradeBar/__snapshots__/index.test.jsx.snap +++ b/src/containers/MasqueradeBar/__snapshots__/index.test.jsx.snap @@ -1,178 +1,202 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP exports[`MasqueradeBar snapshot can masquerade 1`] = ` -
- - - View as: - - - - - + + View as: + + + + + - + state="default" + type="submit" + variant="brand" + /> + +
`; exports[`MasqueradeBar snapshot can masquerade with input 1`] = ` -
- - - View as: - - - - - + + View as: + + + + + - + state="default" + type="submit" + variant="brand" + /> + +
`; exports[`MasqueradeBar snapshot cannot masquerade 1`] = `""`; exports[`MasqueradeBar snapshot is masquerading failed with error 1`] = ` -
- - - View as: - - - - - - + + View as: + + + + + + - + state="default" + type="submit" + variant="brand" + /> + +
`; exports[`MasqueradeBar snapshot is masquerading pending 1`] = ` -
- - - View as: - - - - - + + View as: + + + + + - + state="pending" + type="submit" + variant="brand" + /> + +
`; exports[`MasqueradeBar snapshot is masquerading with input 1`] = ` -
- - - Viewing as: - - - test - -
+ + + Viewing as: + + + test + + +
`; diff --git a/src/containers/MasqueradeBar/index.jsx b/src/containers/MasqueradeBar/index.jsx index ce411bc..a3b9873 100644 --- a/src/containers/MasqueradeBar/index.jsx +++ b/src/containers/MasqueradeBar/index.jsx @@ -36,52 +36,55 @@ export const MasqueradeBar = () => { if (!canMasquerade) { return null; } return ( -
- {isMasquerading ? ( - <> - - - {formatMessage(messages.ViewingAs)} - - - {masqueradeInput} - - - ) : ( - <> - - - {formatMessage(messages.ViewAs)} - - - + + {isMasquerading ? ( + <> + + + {formatMessage(messages.ViewingAs)} + + + {masqueradeInput} + + + ) : ( + <> + + + {formatMessage(messages.ViewAs)} + + + + {isMasqueradingFailed && ( + + {formatMessage(masqueradeErrorMessage)} + + )} + + - {isMasqueradingFailed && ( - - {formatMessage(masqueradeErrorMessage)} - - )} - - - - )} - + + )} + + ); }; diff --git a/src/containers/MasqueradeBar/index.scss b/src/containers/MasqueradeBar/index.scss index a3b1ca6..5cba8de 100644 --- a/src/containers/MasqueradeBar/index.scss +++ b/src/containers/MasqueradeBar/index.scss @@ -4,12 +4,14 @@ display: flex; align-items: flex-start; padding: map-get($spacers, 3); + margin-bottom: map-get($spacers, 2); .masquerade-form-label { padding: map-get($spacers, 2) map-get($spacers, 3); display: flex; align-items: center; margin-bottom: 0; + white-space: nowrap; &>.pgn__icon { margin-right: map-get($spacers, 3); @@ -26,4 +28,11 @@ padding: map-get($spacers, 2) map-get($spacers, 3); font-size: $font-size-base; } +} + +@include media-breakpoint-down(md) { + .masquerade-bar { + margin: auto; + padding: map-get($spacers, 3) map-get($spacers, 4); + } } \ No newline at end of file diff --git a/src/containers/MasqueradeBar/messages.js b/src/containers/MasqueradeBar/messages.js index 1257218..a6b721d 100644 --- a/src/containers/MasqueradeBar/messages.js +++ b/src/containers/MasqueradeBar/messages.js @@ -18,7 +18,7 @@ const messages = defineMessages({ }, StudentNameInput: { id: 'MasqueradeBar.StudentNameInput', - defaultMessage: 'Student username or email', + defaultMessage: 'Username or email', description: 'Label for the Student Name or email input', }, NoStudentFound: { diff --git a/src/containers/WidgetSidebar/__snapshots__/index.test.jsx.snap b/src/containers/WidgetSidebar/__snapshots__/index.test.jsx.snap index 2ce6ed3..d7a5c5a 100644 --- a/src/containers/WidgetSidebar/__snapshots__/index.test.jsx.snap +++ b/src/containers/WidgetSidebar/__snapshots__/index.test.jsx.snap @@ -2,7 +2,7 @@ exports[`WidgetSidebar snapshots default 1`] = `
( -
+