diff --git a/projects/plugins/protect/src/js/components/admin-section-hero/index.tsx b/projects/plugins/protect/src/js/components/admin-section-hero/index.tsx index 5ccf607698084..7638936db5139 100644 --- a/projects/plugins/protect/src/js/components/admin-section-hero/index.tsx +++ b/projects/plugins/protect/src/js/components/admin-section-hero/index.tsx @@ -2,67 +2,73 @@ import { AdminSectionHero as JetpackAdminSectionHero, H3, ShieldIcon, + Container, + Col, } from '@automattic/jetpack-components'; -import SeventyFiveLayout from '../seventy-five-layout'; +import clsx from 'clsx'; import AdminSectionHeroNotices from './admin-section-hero-notices'; import styles from './styles.module.scss'; -interface AdminSectionHeroProps { - main: React.ReactNode; - secondary?: React.ReactNode; - preserveSecondaryOnMobile?: boolean; - spacing?: number; -} - -interface AdminSectionHeroComponent extends React.FC< AdminSectionHeroProps > { - Heading: React.FC< { - children: React.ReactNode; - showIcon?: boolean; - variant?: 'default' | 'success' | 'error'; - outline?: boolean; - } >; - Subheading: React.FC< { children: React.ReactNode } >; -} - -const AdminSectionHero: AdminSectionHeroComponent = ( { - main, - secondary, - preserveSecondaryOnMobile = true, - spacing = 7, -} ) => { +const AdminSectionHero = ( { + children, + ...props +}: React.ComponentProps< typeof JetpackAdminSectionHero > ) => { return ( - + - + + +
{ children }
+ +
); }; -AdminSectionHero.Heading = ( { +AdminSectionHero.Main = ( { children, - variant = 'default', - showIcon = false, + className, + ...props }: { children: React.ReactNode; - variant?: 'default' | 'success' | 'error'; - showIcon?: boolean; + className?: string; + [ key: string ]: unknown; +} ) => { + return ( +
+ { children } +
+ ); +}; + +AdminSectionHero.Aside = ( { + children, + className, + ...props +}: React.ComponentProps< 'div' > & { + className?: string; } ) => { return ( -

+
{ children } - { showIcon && ( +
+ ); +}; + +AdminSectionHero.Heading = ( { + children, + icon, + ...props +}: React.ComponentProps< typeof H3 > & { + icon?: 'default' | 'success' | 'error'; +} ) => { + return ( +

+ { children } + { !! icon && ( { - return
{ children }
; -}; - export default AdminSectionHero; diff --git a/projects/plugins/protect/src/js/components/admin-section-hero/stories/index.stories.jsx b/projects/plugins/protect/src/js/components/admin-section-hero/stories/index.stories.jsx index ca2dfda7fc98e..59ed9086d6317 100644 --- a/projects/plugins/protect/src/js/components/admin-section-hero/stories/index.stories.jsx +++ b/projects/plugins/protect/src/js/components/admin-section-hero/stories/index.stories.jsx @@ -9,16 +9,16 @@ export default { export const Default = args => ; Default.args = { - main: ( + children: ( <> - - - { 'No threats found' } - - + + + { 'No threats found' } { 'Most recent results' } - + + + + ), - secondary: , }; diff --git a/projects/plugins/protect/src/js/components/admin-section-hero/styles.module.scss b/projects/plugins/protect/src/js/components/admin-section-hero/styles.module.scss index a414aa9216f5c..74cfe29aaaded 100644 --- a/projects/plugins/protect/src/js/components/admin-section-hero/styles.module.scss +++ b/projects/plugins/protect/src/js/components/admin-section-hero/styles.module.scss @@ -1,15 +1,39 @@ -.header-main { +.admin-section-hero { display: flex; flex-direction: column; - justify-content: center; - align-items: flex-start; + gap: calc( var( --spacing-base ) * 6 ); // 48px + + max-width: var(--max-container-width); + padding: calc( var( --spacing-base ) * 6 ) 0; // 48px 0 + margin: 0 auto; + + @media (min-width: 600px) { + padding: calc( var( --spacing-base ) * 7 ) 0; // 56px 0 + } + + @media (min-width: 600px) { + padding: calc( var( --spacing-base ) * 7 ) 0; // 56px 0 + } + + @media ( min-width: 1100px ) { + flex-direction: row; + align-items: center; + gap: calc( var( --spacing-base ) * 3 ); // 24px + } } -.header-secondary { - display: flex; - flex-direction: column; - justify-content: center; - align-items: flex-end; +.admin-section-hero__main { + flex: 2; +} + +.admin-section-hero__aside { + flex: 1; + flex-shrink: 0; + + @media ( min-width: 1200px ) { + display: flex; + justify-content: flex-end; + } } .heading-icon { @@ -17,10 +41,6 @@ margin-bottom: calc( var( --spacing-base ) / 2 * -1 ); // -4px } -.subheading { - width: fit-content; -} - .connection-error-col { margin-top: calc( var( --spacing-base ) * 3 + 1px ); // 25px } diff --git a/projects/plugins/protect/src/js/components/error-admin-section-hero/index.tsx b/projects/plugins/protect/src/js/components/error-admin-section-hero/index.tsx index 1a9bc87387fa9..536d8f50de7d1 100644 --- a/projects/plugins/protect/src/js/components/error-admin-section-hero/index.tsx +++ b/projects/plugins/protect/src/js/components/error-admin-section-hero/index.tsx @@ -1,6 +1,5 @@ -import { Text } from '@automattic/jetpack-components'; +import { ShieldIcon, Text } from '@automattic/jetpack-components'; import { __ } from '@wordpress/i18n'; -import { Icon, warning } from '@wordpress/icons'; import AdminSectionHero from '../admin-section-hero'; import styles from './styles.module.scss'; @@ -19,22 +18,17 @@ const ErrorAdminSectionHero: React.FC< ErrorAdminSectionHeroProps > = ( { displayErrorMessage += ' ' + __( 'Try again in a few minutes.', 'jetpack-protect' ); return ( - - -
- - { __( 'An error occurred', 'jetpack-protect' ) } -
-
- - { displayErrorMessage } - - - } - preserveSecondaryOnMobile={ false } - /> + + + +
+ { __( 'An error occurred', 'jetpack-protect' ) } + +
+
+ { displayErrorMessage } +
+
); }; diff --git a/projects/plugins/protect/src/js/components/error-admin-section-hero/styles.module.scss b/projects/plugins/protect/src/js/components/error-admin-section-hero/styles.module.scss index 6f0750abd02f8..1c89377d4b4b5 100644 --- a/projects/plugins/protect/src/js/components/error-admin-section-hero/styles.module.scss +++ b/projects/plugins/protect/src/js/components/error-admin-section-hero/styles.module.scss @@ -4,11 +4,7 @@ } .warning { - width: 54px; - height: 54px; - fill: var( --jp-red ); - margin-left: -8px; - margin-right: var( --spacing-base ); // 8px + margin-left: calc( var( --spacing-base ) * 1.5 ); // 12px } .scan-navigation { diff --git a/projects/plugins/protect/src/js/routes/firewall/firewall-admin-section-hero.tsx b/projects/plugins/protect/src/js/routes/firewall/firewall-admin-section-hero.tsx index 3f70a75509b76..837f649c67f16 100644 --- a/projects/plugins/protect/src/js/routes/firewall/firewall-admin-section-hero.tsx +++ b/projects/plugins/protect/src/js/routes/firewall/firewall-admin-section-hero.tsx @@ -5,6 +5,7 @@ import AdminSectionHero from '../../components/admin-section-hero'; import useWafData from '../../hooks/use-waf-data'; import FirewallStatCards from './firewall-statcards'; import FirewallSubheading from './firewall-subheading'; +import styles from './styles.module.scss'; const FirewallAdminSectionHero = () => { const { @@ -84,16 +85,22 @@ const FirewallAdminSectionHero = () => { }, [ status ] ); return ( - - - { heading } - { subheading } - - } - secondary={ wafSupported && } - /> + + + + { heading } + { subheading } + + { wafSupported && ( + + + + ) } + ); }; diff --git a/projects/plugins/protect/src/js/routes/firewall/firewall-statcards.jsx b/projects/plugins/protect/src/js/routes/firewall/firewall-statcards.jsx index 15c80df763c18..1eebd67cb60d7 100644 --- a/projects/plugins/protect/src/js/routes/firewall/firewall-statcards.jsx +++ b/projects/plugins/protect/src/js/routes/firewall/firewall-statcards.jsx @@ -93,7 +93,7 @@ const FirewallStatCards = () => { ); return ( -
+
diff --git a/projects/plugins/protect/src/js/routes/firewall/styles.module.scss b/projects/plugins/protect/src/js/routes/firewall/styles.module.scss index c0350ff100e6b..06c41c479d172 100644 --- a/projects/plugins/protect/src/js/routes/firewall/styles.module.scss +++ b/projects/plugins/protect/src/js/routes/firewall/styles.module.scss @@ -3,6 +3,10 @@ max-width: calc( 744px + ( var( --spacing-base ) * 6 ) ); // 744px + 48px (desired inner width + horizontal padding) } +.status { + margin-bottom: calc( var( --spacing-base ) * 2 ); // 16px +} + .toggle-section { display: flex; @@ -145,14 +149,10 @@ align-items: center; } -.stat-card-wrapper { +.stat-cards-wrapper { display: flex; - margin-left: auto; - flex-wrap: wrap; - - >:first-child { - margin-right: calc( var( --spacing-base ) * 3 ); // 24px - } + justify-content: flex-end; + gap: calc( var( --spacing-base ) * 3 ); // 24px .disabled { opacity: 0.5; @@ -171,27 +171,6 @@ white-space: nowrap; } -@media ( max-width: 1115px ) { - .stat-card-wrapper { - margin-top: calc( var( --spacing-base ) * 3 ); // 24px - } -} - -@media ( max-width: 599px ) { - .stat-card-wrapper { - margin-top: calc( var( --spacing-base ) * 3 ); // 24px - - >:first-child { - margin-right: 0; - margin-bottom: var( --spacing-base ); // 8px - } - } - - .stat-card-icon { - margin-bottom: 0; - } -} - .footer-checkbox { display: flex; align-items: center; @@ -231,7 +210,21 @@ } } +@media ( max-width: 1200px ) { + .stat-cards-wrapper { + justify-content: flex-start; + } +} + @media ( max-width: 599px ) { + .stat-cards-wrapper { + flex-direction: column; + gap: var( --spacing-base ); // 8px + } + + .stat-card-icon { + margin-bottom: 0; + } .share-data-section { margin-top: 0; diff --git a/projects/plugins/protect/src/js/routes/scan/scan-admin-section-hero.tsx b/projects/plugins/protect/src/js/routes/scan/scan-admin-section-hero.tsx index db76bac1b15b0..4257c585351eb 100644 --- a/projects/plugins/protect/src/js/routes/scan/scan-admin-section-hero.tsx +++ b/projects/plugins/protect/src/js/routes/scan/scan-admin-section-hero.tsx @@ -59,6 +59,28 @@ const ScanAdminSectionHero: React.FC = () => { lastCheckedLocalTimestamp = new Date( status.lastChecked + ' UTC' ).getTime(); } + let heading = __( "Don't worry about a thing", 'jetpack-protect' ); + if ( numThreats > 0 ) { + if ( hasPlan ) { + heading = sprintf( + /* translators: %s: Total number of threats */ + _n( '%1$s active threat', '%1$s active threats', numThreats, 'jetpack-protect' ), + numThreats + ); + } else { + heading = sprintf( + /* translators: %s: Total number of vulnerabilities */ + _n( + '%1$s active vulnerability', + '%1$s active vulnerabilities', + numThreats, + 'jetpack-protect' + ), + numThreats + ); + } + } + const handleShowAutoFixersClick = threatList => { return event => { event.preventDefault(); @@ -84,94 +106,79 @@ const ScanAdminSectionHero: React.FC = () => { } return ( - - - { lastCheckedLocalTimestamp - ? sprintf( - // translators: %s: date and time of the last scan - __( '%s results', 'jetpack-protect' ), - dateI18n( 'F jS g:i A', lastCheckedLocalTimestamp, false ) - ) - : __( 'Most recent results', 'jetpack-protect' ) } + + + + { lastCheckedLocalTimestamp + ? sprintf( + // translators: %s: date and time of the last scan + __( '%s results', 'jetpack-protect' ), + dateI18n( 'F jS, g:i A', lastCheckedLocalTimestamp, false ) + ) + : __( 'Most recent results', 'jetpack-protect' ) } + + + 0 ? 'error' : 'success' }> + { heading } + + { hasPlan ? ( + + { __( + "We actively review your site's files line-by-line to identify threats and vulnerabilities.", + 'jetpack-protect' + ) } - - 0 ? 'error' : 'success' }> - { numThreats > 0 - ? sprintf( - /* translators: %s: Total number of threats/vulnerabilities */ - __( '%1$s active %2$s', 'jetpack-protect' ), - numThreats, - hasPlan - ? _n( 'threat', 'threats', numThreats, 'jetpack-protect' ) - : _n( 'vulnerability', 'vulnerabilities', numThreats, 'jetpack-protect' ) - ) - : __( "Don't worry about a thing", 'jetpack-protect' ) } - - - <> - { hasPlan ? ( - - { __( - "We actively review your site's files line-by-line to identify threats and vulnerabilities.", - 'jetpack-protect' - ) } - - ) : ( - <> - - { sprintf( - // translators: placeholder is the number of total vulnerabilities i.e. "22,000". - __( - 'Every day we check your plugins, themes, and WordPress version against our %s listed vulnerabilities powered by WPScan, an Automattic brand.', - 'jetpack-protect' - ), - totalVulnerabilitiesFormatted - ) } - - - - - + ) : ( + <> + + { sprintf( + // translators: placeholder is the number of total vulnerabilities i.e. "22,000". + __( + 'Every day we check your plugins, themes, and WordPress version against our %s listed vulnerabilities powered by WPScan, an Automattic brand.', + 'jetpack-protect' + ), + totalVulnerabilitiesFormatted ) } - { fixableList.length > 0 && ( - <> -
- -
-
+ -
- - } - /> + > + + + + ) } + { fixableList.length > 0 && ( + <> +
+ +
+
+
); }; diff --git a/projects/plugins/protect/src/js/routes/scan/scanning-admin-section-hero.tsx b/projects/plugins/protect/src/js/routes/scan/scanning-admin-section-hero.tsx index 4db4449b60119..ac9e0137cd170 100644 --- a/projects/plugins/protect/src/js/routes/scan/scanning-admin-section-hero.tsx +++ b/projects/plugins/protect/src/js/routes/scan/scanning-admin-section-hero.tsx @@ -18,44 +18,38 @@ const ScanningAdminSectionHero: React.FC = () => { : totalVulnerabilities.toLocaleString(); return ( - - - { __( 'Your results will be ready soon', 'jetpack-protect' ) } - - - <> - { hasPlan && ( - - ) } - - { hasPlan - ? __( - "Jetpack is actively scanning your site's files line-by-line to identify threats and vulnerabilities. This could take a minute or two.", - 'jetpack-protect' - ) - : sprintf( - // translators: placeholder is the number of total vulnerabilities i.e. "22,000". - __( - 'We are scanning for security threats from our more than %s listed vulnerabilities, powered by WPScan. This could take a minute or two.', - 'jetpack-protect' - ), - totalVulnerabilitiesFormatted - ) } - - - - - } - secondary={ } - preserveSecondaryOnMobile={ false } - spacing={ 4 } - /> + + + + { __( 'Your results will be ready soon', 'jetpack-protect' ) } + + { hasPlan && ( + + ) } + + { hasPlan + ? __( + "Jetpack is actively scanning your site's files line-by-line to identify threats and vulnerabilities. This could take a minute or two.", + 'jetpack-protect' + ) + : sprintf( + // translators: placeholder is the number of total vulnerabilities i.e. "22,000". + __( + 'We are scanning for security threats from our more than %s listed vulnerabilities, powered by WPScan. This could take a minute or two.', + 'jetpack-protect' + ), + totalVulnerabilitiesFormatted + ) } + + + + + + ); }; diff --git a/projects/plugins/protect/src/js/routes/scan/styles.module.scss b/projects/plugins/protect/src/js/routes/scan/styles.module.scss index 163fd23248aaa..5806ca5353863 100644 --- a/projects/plugins/protect/src/js/routes/scan/styles.module.scss +++ b/projects/plugins/protect/src/js/routes/scan/styles.module.scss @@ -1,3 +1,7 @@ +.scanning-main { + max-width: 512px; +} + .auto-fixers { margin-top: calc( var( --spacing-base ) * 4 ); // 32px } @@ -12,3 +16,9 @@ margin-right: calc( var( --spacing-base ) * -3 ); // -24px } } + +.progress-animation { + @media (max-width: 1099px) { + display: none; + } +}