From 1578adfc36f1b6d2a9623f12cba2a68d09dcac62 Mon Sep 17 00:00:00 2001 From: Seth Foster Date: Fri, 5 Jul 2024 16:01:00 -0400 Subject: [PATCH] refactor(app): add and use deck map component in interventionmodal (#15570) Adds DeckMapContent to intervention modal. This is a small wrapper around one of two different kinds of deck map: - A labware-rendering map that is also capable of rendering highlights around some labware, used in some selection screens in error recovery - A deck config style block map that supports clicking on some of the blocks to select them, used in some selection screens in the drop tip wizard (and thus in error recovery) Stories for the deckmap are [on storybook](https://s3-us-west-2.amazonaws.com/opentrons-components/exec-501-deckmap-content/index.html?path=/docs/app-molecules-interventionmodal-deckmapcontent--docs), where it's rendered side-by-side with the standin since it is only destined to be used in a two-column layout. Extra fun changes: - Use the ODD text size args for _all_ slot labels in `BaseDeck`, because otherwise they are completely unreadable once the deckmap gets to small. I think this looks a lot better everywhere, and is actually readable when the deckmap is small, so let's go with it; may want to come back and make these something more specific on desktop - Error recovery has a `RecoveryMap`, a large data structure that is core to the wizard flow and defines how users move between steps and screens. Error recovery also had a `RecoveryMap`, which was a component for rendering a deckmap, and a `useRecoveryMapUtils`, a hook for getting that component's arguments. Now it uses the `DeckMapContent` component above directly, and `useDeckMapUtils`, a hook for getting that component's arguments - There's something about the deck config style map that isn't quite right and I think that it's because of this: https://opentrons.atlassian.net/browse/EXEC-513 Review requests: - i'm pretty sure what I did to drop tip will work but it might be reasonably called somewhat gross. this is all somewhat gross though, so c'est la vie - the deckmap slot labels do not render right in firefox at these sizes. if you're looking at storybook, you're going to have to use chrome - fix an issue that was preventing ER wizard from being displayed on ODD Testing, todo: - [ ] error recovery - [ ] drop tip in error recovery - [ ] drop tip outside of error recovery Closes EXEC-501 --- .../DeckMapContent.stories.tsx | 157 +++++++++++++++ .../InterventionModal/DeckMapContent.tsx | 176 +++++++++++++++++ .../InterventionModal/TwoColumn.stories.tsx | 14 +- .../molecules/InterventionModal/TwoColumn.tsx | 2 +- .../__fixtures__/deckSetup.ts | 165 ++++++++++++++++ .../InterventionModal/__fixtures__/index.ts | 1 + app/src/molecules/InterventionModal/index.tsx | 2 + .../InterventionModal/story-utils/StandIn.tsx | 14 ++ .../DropTipWizardFlows/ChooseLocation.tsx | 178 ++++++++---------- .../RecoveryOptions/FillWellAndSkip.tsx | 12 +- .../__tests__/FillWellAndSkip.test.tsx | 4 +- .../ErrorRecoveryFlows/__fixtures__/index.ts | 2 +- ...Utils.test.tsx => useDeckMapUtils.test.ts} | 24 +-- ...ecoveryMapUtils.tsx => useDeckMapUtils.ts} | 103 +++++----- .../ErrorRecoveryFlows/hooks/useERUtils.ts | 10 +- .../ErrorRecoveryFlows/shared/RecoveryMap.tsx | 74 -------- .../ErrorRecoveryFlows/shared/ReplaceTips.tsx | 6 +- .../shared/__tests__/RecoveryMap.test.tsx | 62 ------ .../ErrorRecoveryFlows/shared/index.ts | 1 - .../src/molecules/LocationIcon/index.tsx | 11 +- 20 files changed, 684 insertions(+), 334 deletions(-) create mode 100644 app/src/molecules/InterventionModal/DeckMapContent.stories.tsx create mode 100644 app/src/molecules/InterventionModal/DeckMapContent.tsx create mode 100644 app/src/molecules/InterventionModal/__fixtures__/deckSetup.ts create mode 100644 app/src/molecules/InterventionModal/__fixtures__/index.ts create mode 100644 app/src/molecules/InterventionModal/story-utils/StandIn.tsx rename app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/{useRecoveryMapUtils.test.tsx => useDeckMapUtils.test.ts} (94%) rename app/src/organisms/ErrorRecoveryFlows/hooks/{useRecoveryMapUtils.tsx => useDeckMapUtils.ts} (80%) delete mode 100644 app/src/organisms/ErrorRecoveryFlows/shared/RecoveryMap.tsx delete mode 100644 app/src/organisms/ErrorRecoveryFlows/shared/__tests__/RecoveryMap.test.tsx diff --git a/app/src/molecules/InterventionModal/DeckMapContent.stories.tsx b/app/src/molecules/InterventionModal/DeckMapContent.stories.tsx new file mode 100644 index 00000000000..56c896655e0 --- /dev/null +++ b/app/src/molecules/InterventionModal/DeckMapContent.stories.tsx @@ -0,0 +1,157 @@ +import * as React from 'react' + +import { css } from 'styled-components' +import { DeckMapContent } from '.' +import { Box, RESPONSIVENESS, BORDERS } from '@opentrons/components' +import type { Meta, StoryObj } from '@storybook/react' +import { + FLEX_ROBOT_TYPE, + OT2_ROBOT_TYPE, + fixture96Plate, + fixtureTiprack1000ul, + HEATERSHAKER_MODULE_V1, + MAGNETIC_BLOCK_V1, + TEMPERATURE_MODULE_V2, + THERMOCYCLER_MODULE_V2, +} from '@opentrons/shared-data' +import type { ModuleLocation, LabwareDefinition2 } from '@opentrons/shared-data' +import { + EXTENDED_DECK_CONFIG_FIXTURE, + STANDARD_SLOT_DECK_CONFIG_FIXTURE, + WASTE_CHUTE_DECK_CONFIG_FIXTURE, +} from './__fixtures__' +import { TwoColumn } from './TwoColumn' +import { StandInContent } from './story-utils/StandIn' + +const DEFAULT_MODULES_ON_DECK = [ + { + moduleLocation: { slotName: 'B1' }, + moduleModel: THERMOCYCLER_MODULE_V2, + nestedLabwareDef: fixture96Plate as LabwareDefinition2, + innerProps: { lidMotorState: 'open' }, + }, + { + moduleLocation: { slotName: 'D1' }, + moduleModel: TEMPERATURE_MODULE_V2, + nestedLabwareDef: fixture96Plate as LabwareDefinition2, + }, + { + moduleLocation: { slotName: 'B3' }, + moduleModel: HEATERSHAKER_MODULE_V1, + nestedLabwareDef: fixture96Plate as LabwareDefinition2, + }, + { + moduleLocation: { slotName: 'D2' }, + moduleModel: MAGNETIC_BLOCK_V1, + nestedLabwareDef: fixture96Plate as LabwareDefinition2, + }, +] + +const DEFAULT_LABWARE_ON_DECK = [ + { + labwareLocation: { slotName: 'C2' }, + definition: fixture96Plate as LabwareDefinition2, + }, + { + labwareLocation: { slotName: 'C3' }, + definition: fixtureTiprack1000ul as LabwareDefinition2, + }, +] + +const CONSOLE_LOG_ON_SELECT = (location: ModuleLocation): void => { + console.log(`selected location is ${location?.slotName}`) +} + +const meta: Meta> = { + title: 'App/Molecules/InterventionModal/DeckMapContent', + component: DeckMapContent, + argTypes: { + robotType: { + control: { + type: 'select', + }, + options: [OT2_ROBOT_TYPE, FLEX_ROBOT_TYPE], + default: FLEX_ROBOT_TYPE, + }, + kind: { + control: { + type: 'select', + }, + options: ['intervention', 'deck-config'], + }, + setSelectedLocation: { + control: { + type: 'select', + }, + options: ['print-to-console'], + mapping: { + 'print-to-console': CONSOLE_LOG_ON_SELECT, + }, + if: { arg: 'kind', eq: 'deck-config' }, + }, + deckConfig: { + control: { + type: 'select', + }, + options: ['staging-area', 'waste-chute', 'standard'], + mapping: { + 'staging-area': EXTENDED_DECK_CONFIG_FIXTURE, + 'waste-chute': WASTE_CHUTE_DECK_CONFIG_FIXTURE, + standard: STANDARD_SLOT_DECK_CONFIG_FIXTURE, + }, + if: { arg: 'kind', eq: 'intervention' }, + }, + labwareOnDeck: { + if: { arg: 'kind', eq: 'intervention' }, + }, + modulesOnDeck: { + if: { arg: 'kind', eq: 'intervention' }, + }, + highlightLabwareEventuallyIn: { + if: { arg: 'kind', eq: 'intervention' }, + }, + }, + decorators: [ + Story => ( + + + + + + + ), + ], +} + +export default meta + +type Story = StoryObj + +export const InterventionMap: Story = { + args: { + kind: 'intervention', + robotType: FLEX_ROBOT_TYPE, + deckConfig: EXTENDED_DECK_CONFIG_FIXTURE, + labwareOnDeck: DEFAULT_LABWARE_ON_DECK, + modulesOnDeck: DEFAULT_MODULES_ON_DECK, + highlightLabwareEventuallyIn: ['thermocyclerModuleV2', 'C3'], + }, +} + +export const DeckConfigMap: Story = { + args: { + kind: 'deck-config', + robotType: FLEX_ROBOT_TYPE, + setSelectedLocation: CONSOLE_LOG_ON_SELECT, + }, +} diff --git a/app/src/molecules/InterventionModal/DeckMapContent.tsx b/app/src/molecules/InterventionModal/DeckMapContent.tsx new file mode 100644 index 00000000000..a45bc920e0a --- /dev/null +++ b/app/src/molecules/InterventionModal/DeckMapContent.tsx @@ -0,0 +1,176 @@ +import * as React from 'react' +import { css } from 'styled-components' +import { + Box, + BaseDeck, + RobotCoordsForeignDiv, + COLORS, + DIRECTION_COLUMN, + DISPLAY_FLEX, + JUSTIFY_FLEX_END, + useDeckLocationSelect, +} from '@opentrons/components' + +import type { + LabwareDefinition2, + RobotType, + ModuleLocation, + LabwareLocation, +} from '@opentrons/shared-data' + +export type MapKind = 'intervention' | 'deck-config' + +export interface InterventionStyleDeckMapContentProps + extends Pick< + React.ComponentProps, + 'deckConfig' | 'robotType' | 'labwareOnDeck' | 'modulesOnDeck' + > { + kind: 'intervention' + highlightLabwareEventuallyIn: string[] +} + +export interface DeckConfigStyleDeckMapContentProps { + kind: 'deck-config' + robotType: RobotType + setSelectedLocation: (location: ModuleLocation) => void +} + +export type DeckMapContentProps = + | DeckConfigStyleDeckMapContentProps + | InterventionStyleDeckMapContentProps + +export const DeckMapContent: ( + props: DeckMapContentProps +) => JSX.Element = props => + props.kind === 'intervention' ? ( + + ) : ( + + ) + +function InterventionStyleDeckMapContent( + props: InterventionStyleDeckMapContentProps +): JSX.Element { + const labwareWithHighlights = + props.labwareOnDeck?.map(labwareOnDeck => + props.highlightLabwareEventuallyIn.reduce( + (found, locationToMatch) => + found || + getIsLabwareMatch(labwareOnDeck.labwareLocation, locationToMatch), + false + ) + ? { + ...labwareOnDeck, + labwareChildren: ( + + ), + } + : labwareOnDeck + ) ?? [] + const modulesWithHighlights = + props.modulesOnDeck?.map(module => + props.highlightLabwareEventuallyIn.reduce( + (found, locationToMatch) => + found || getIsLabwareMatch(module.moduleLocation, locationToMatch), + false + ) + ? { + ...module, + moduleChildren: + module?.nestedLabwareDef != null ? ( + + ) : undefined, + } + : module + ) ?? [] + return ( + + ) +} + +function DeckConfigStyleDeckMapContent({ + robotType, + setSelectedLocation, +}: DeckConfigStyleDeckMapContentProps): JSX.Element { + const { DeckLocationSelect, selectedLocation } = useDeckLocationSelect( + robotType, + 'default' + ) + React.useEffect(() => { + setSelectedLocation != null && setSelectedLocation(selectedLocation) + }, [selectedLocation, setSelectedLocation]) + return <>{DeckLocationSelect} +} + +export function LabwareHighlight({ + highlight, + definition, +}: { + highlight: boolean + definition: LabwareDefinition2 +}): JSX.Element { + const width = definition.dimensions.xDimension + const height = definition.dimensions.yDimension + + return ( + + + + ) +} + +const HIGHLIGHT_STYLE = css` + border-radius: 7.04px; + border: 3px solid ${COLORS.blue50}; + box-shadow: 0 0 4px 3px #74b0ff; +` + +export function getIsLabwareMatch( + locationToCheck: LabwareLocation | ModuleLocation, + deckRootLocation: string +): boolean { + if (typeof locationToCheck === 'string') { + // This is the "off deck" case, which we do not render (and therefore return false). + return false + } else if ('slotName' in locationToCheck) { + // This is if we're checking a module or a labware loaded on a slot + return locationToCheck.slotName === deckRootLocation + } else if ('addressableAreaName' in locationToCheck) { + // This is if we're loaded on an AA like a staging slot + return locationToCheck.addressableAreaName === deckRootLocation + } else { + // Defaulted cases: + // if ('moduleId' in locationToCheck), e.g. on a module: + // this should never happen because labware that is loaded on a module wouldn't be + // in onDeckLabware, and onDeckModules is for modules not labware. + // if ('labwareId' in locationToCheck), e.g. stacked labware: + // this should never happen because we don't really render it properly here + return false + } +} diff --git a/app/src/molecules/InterventionModal/TwoColumn.stories.tsx b/app/src/molecules/InterventionModal/TwoColumn.stories.tsx index 075be6acf6e..84722fbf00b 100644 --- a/app/src/molecules/InterventionModal/TwoColumn.stories.tsx +++ b/app/src/molecules/InterventionModal/TwoColumn.stories.tsx @@ -7,11 +7,11 @@ import { Flex, DIRECTION_COLUMN, Box, - BORDERS, } from '@opentrons/components' import { InlineNotification } from '../../atoms/InlineNotification' import { TwoColumn as TwoColumnComponent } from './' +import { StandInContent } from './story-utils/StandIn' import type { Meta, StoryObj } from '@storybook/react' @@ -30,18 +30,6 @@ interface StorybookArgs { rightText?: string } -function StandInContent(): JSX.Element { - return ( - - ) -} - interface NotificationProps { heading?: string message?: string diff --git a/app/src/molecules/InterventionModal/TwoColumn.tsx b/app/src/molecules/InterventionModal/TwoColumn.tsx index 634a77adb4b..8e87a2d62b5 100644 --- a/app/src/molecules/InterventionModal/TwoColumn.tsx +++ b/app/src/molecules/InterventionModal/TwoColumn.tsx @@ -14,7 +14,7 @@ export function TwoColumn({ {leftElement} - + {rightElement} diff --git a/app/src/molecules/InterventionModal/__fixtures__/deckSetup.ts b/app/src/molecules/InterventionModal/__fixtures__/deckSetup.ts new file mode 100644 index 00000000000..08c91cf53f9 --- /dev/null +++ b/app/src/molecules/InterventionModal/__fixtures__/deckSetup.ts @@ -0,0 +1,165 @@ +import { + SINGLE_LEFT_SLOT_FIXTURE, + SINGLE_CENTER_SLOT_FIXTURE, + TRASH_BIN_ADAPTER_FIXTURE, + SINGLE_RIGHT_SLOT_FIXTURE, + STAGING_AREA_RIGHT_SLOT_FIXTURE, + WASTE_CHUTE_RIGHT_ADAPTER_COVERED_FIXTURE, +} from '@opentrons/shared-data' + +import type { DeckConfiguration } from '@opentrons/shared-data' + +export const STANDARD_SLOT_DECK_CONFIG_FIXTURE: DeckConfiguration = [ + { + cutoutId: 'cutoutA1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA3', + cutoutFixtureId: TRASH_BIN_ADAPTER_FIXTURE, + }, + { + cutoutId: 'cutoutB3', + cutoutFixtureId: SINGLE_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC3', + cutoutFixtureId: SINGLE_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD3', + cutoutFixtureId: SINGLE_RIGHT_SLOT_FIXTURE, + }, +] + +// contains staging area fixtures +export const EXTENDED_DECK_CONFIG_FIXTURE: DeckConfiguration = [ + { + cutoutId: 'cutoutA1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA3', + cutoutFixtureId: TRASH_BIN_ADAPTER_FIXTURE, + }, + { + cutoutId: 'cutoutB3', + cutoutFixtureId: STAGING_AREA_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC3', + cutoutFixtureId: STAGING_AREA_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD3', + cutoutFixtureId: STAGING_AREA_RIGHT_SLOT_FIXTURE, + }, +] + +// contains waste chute fixture +export const WASTE_CHUTE_DECK_CONFIG_FIXTURE: DeckConfiguration = [ + { + cutoutId: 'cutoutA1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC1', + cutoutFixtureId: TRASH_BIN_ADAPTER_FIXTURE, + }, + { + cutoutId: 'cutoutD1', + cutoutFixtureId: SINGLE_LEFT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD2', + cutoutFixtureId: SINGLE_CENTER_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutA3', + cutoutFixtureId: SINGLE_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutB3', + cutoutFixtureId: STAGING_AREA_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutC3', + cutoutFixtureId: STAGING_AREA_RIGHT_SLOT_FIXTURE, + }, + { + cutoutId: 'cutoutD3', + cutoutFixtureId: WASTE_CHUTE_RIGHT_ADAPTER_COVERED_FIXTURE, + }, +] diff --git a/app/src/molecules/InterventionModal/__fixtures__/index.ts b/app/src/molecules/InterventionModal/__fixtures__/index.ts new file mode 100644 index 00000000000..2397001b976 --- /dev/null +++ b/app/src/molecules/InterventionModal/__fixtures__/index.ts @@ -0,0 +1 @@ +export * from './deckSetup' diff --git a/app/src/molecules/InterventionModal/index.tsx b/app/src/molecules/InterventionModal/index.tsx index 83183de6319..53e81b213a0 100644 --- a/app/src/molecules/InterventionModal/index.tsx +++ b/app/src/molecules/InterventionModal/index.tsx @@ -25,12 +25,14 @@ import { TwoColumn } from './TwoColumn' import { OneColumn } from './OneColumn' import { ModalContentMixed } from './ModalContentMixed' import { DescriptionContent } from './DescriptionContent' +import { DeckMapContent } from './DeckMapContent' export { ModalContentOneColSimpleButtons, TwoColumn, OneColumn, ModalContentMixed, DescriptionContent, + DeckMapContent, } export type ModalType = 'intervention-required' | 'error' diff --git a/app/src/molecules/InterventionModal/story-utils/StandIn.tsx b/app/src/molecules/InterventionModal/story-utils/StandIn.tsx new file mode 100644 index 00000000000..f6ac9e7dd78 --- /dev/null +++ b/app/src/molecules/InterventionModal/story-utils/StandIn.tsx @@ -0,0 +1,14 @@ +import * as React from 'react' +import { Box, BORDERS, SPACING } from '@opentrons/components' + +export function StandInContent(): JSX.Element { + return ( + + ) +} diff --git a/app/src/organisms/DropTipWizardFlows/ChooseLocation.tsx b/app/src/organisms/DropTipWizardFlows/ChooseLocation.tsx index 7eb619dc619..e1c284efc4c 100644 --- a/app/src/organisms/DropTipWizardFlows/ChooseLocation.tsx +++ b/app/src/organisms/DropTipWizardFlows/ChooseLocation.tsx @@ -1,5 +1,5 @@ import * as React from 'react' -import { css } from 'styled-components' +import styled, { css } from 'styled-components' import { useTranslation } from 'react-i18next' import { @@ -8,23 +8,25 @@ import { Btn, COLORS, DIRECTION_COLUMN, - DIRECTION_ROW, Flex, - JUSTIFY_CENTER, JUSTIFY_SPACE_BETWEEN, + JUSTIFY_FLEX_START, PrimaryButton, RESPONSIVENESS, SPACING, LegacyStyledText, TYPOGRAPHY, - useDeckLocationSelect, + DISPLAY_INLINE_BLOCK, } from '@opentrons/components' import { getDeckDefFromRobotType } from '@opentrons/shared-data' import { SmallButton } from '../../atoms/buttons' -import { TwoUpTileLayout } from '../LabwarePositionCheck/TwoUpTileLayout' +import { TwoColumn, DeckMapContent } from '../../molecules/InterventionModal' -import type { AddressableAreaName } from '@opentrons/shared-data' +import type { + AddressableAreaName, + ModuleLocation, +} from '@opentrons/shared-data' import type { DropTipWizardContainerProps } from './types' // TODO: get help link article URL @@ -36,6 +38,16 @@ type ChooseLocationProps = DropTipWizardContainerProps & { body: string | JSX.Element moveToAddressableArea: (addressableArea: AddressableAreaName) => Promise } +const Title = styled.h1` + ${TYPOGRAPHY.h1Default}; + margin-bottom: ${SPACING.spacing8}; + @media ${RESPONSIVENESS.touchscreenMediaQuerySpecs} { + ${TYPOGRAPHY.level4HeaderSemiBold}; + margin-bottom: 0; + height: ${SPACING.spacing40}; + display: ${DISPLAY_INLINE_BLOCK}; + } +` export const ChooseLocation = ( props: ChooseLocationProps @@ -47,17 +59,17 @@ export const ChooseLocation = ( body, robotType, moveToAddressableArea, - isOnDevice, } = props const { i18n, t } = useTranslation(['drop_tip_wizard', 'shared']) + const [ + selectedLocation, + setSelectedLocation, + ] = React.useState() const deckDef = getDeckDefFromRobotType(robotType) - const { DeckLocationSelect, selectedLocation } = useDeckLocationSelect( - robotType - ) const handleConfirmPosition = (): void => { const deckSlot = deckDef.locations.addressableAreas.find( - l => l.id === selectedLocation.slotName + l => l.id === selectedLocation?.slotName )?.id if (deckSlot != null) { @@ -66,97 +78,58 @@ export const ChooseLocation = ( }) } } - - if (isOnDevice) { - return ( - - - - - {title} - - {body} - - - {DeckLocationSelect} - + return ( + + + + {title} + {body} - + + + { + handleGoBack() + }} > - { - handleGoBack() - }} - > - - {t('shared:go_back')} - - - - - - ) - } else { - return ( - - - { - handleGoBack() - }} - > - - {t('shared:go_back')} - - - - {i18n.format(t('move_to_slot'), 'capitalize')} - - - } + + {t('shared:go_back')} + + + + {i18n.format(t('move_to_slot'), 'capitalize')} + + - ) - } + + ) } -const TILE_CONTAINER_STYLE = css` - flex-direction: ${DIRECTION_COLUMN}; - justify-content: ${JUSTIFY_SPACE_BETWEEN}; - height: 24.625rem; - @media ${RESPONSIVENESS.touchscreenMediaQuerySpecs} { - height: 29.5rem; - } -` const GO_BACK_BUTTON_STYLE = css` ${TYPOGRAPHY.pSemiBold}; color: ${COLORS.grey50}; @@ -182,3 +155,16 @@ const ALIGN_BUTTONS = css` align-items: ${ALIGN_CENTER}; } ` + +const CONTAINER_STYLE = css` + flex-direction: ${DIRECTION_COLUMN}; + justify-content: ${JUSTIFY_SPACE_BETWEEN}; + padding: ${SPACING.spacing32}; + height: 24.625rem; + @media ${RESPONSIVENESS.touchscreenMediaQuerySpecs} { + justify-content: ${JUSTIFY_FLEX_START}; + gap: ${SPACING.spacing32}; + padding: none; + height: 29.5rem; + } +` diff --git a/app/src/organisms/ErrorRecoveryFlows/RecoveryOptions/FillWellAndSkip.tsx b/app/src/organisms/ErrorRecoveryFlows/RecoveryOptions/FillWellAndSkip.tsx index 7b7aaf7d68e..fb21adc202a 100644 --- a/app/src/organisms/ErrorRecoveryFlows/RecoveryOptions/FillWellAndSkip.tsx +++ b/app/src/organisms/ErrorRecoveryFlows/RecoveryOptions/FillWellAndSkip.tsx @@ -14,10 +14,9 @@ import { RecoveryFooterButtons, RecoverySingleColumnContent, LeftColumnLabwareInfo, - RecoveryMap, TwoColTextAndFailedStepNextStep, } from '../shared' -import { TwoColumn } from '../../../molecules/InterventionModal' +import { TwoColumn, DeckMapContent } from '../../../molecules/InterventionModal' import { SelectRecoveryOption } from './SelectRecoveryOption' import type { RecoveryContentProps } from '../types' @@ -45,7 +44,12 @@ export function FillWellAndSkip(props: RecoveryContentProps): JSX.Element { } export function FillWell(props: RecoveryContentProps): JSX.Element | null { - const { isOnDevice, routeUpdateActions, failedLabwareUtils } = props + const { + isOnDevice, + routeUpdateActions, + failedLabwareUtils, + deckMapUtils, + } = props const { t } = useTranslation('error_recovery') const { goBackPrevStep, proceedNextStep } = routeUpdateActions @@ -63,7 +67,7 @@ export function FillWell(props: RecoveryContentProps): JSX.Element | null { /> - + { {props.title} )), - RecoveryMap: vi.fn(() =>
MOCK_RECOVERY_MAP
), } }) +vi.mock('../../../../molecules/InterventionModal/DeckMapContent', () => ({ + DeckMapContent: vi.fn(() =>
MOCK_RECOVERY_MAP
), +})) vi.mock('../CancelRun') vi.mock('../SelectRecoveryOption') vi.mock('../../../../molecules/Command') diff --git a/app/src/organisms/ErrorRecoveryFlows/__fixtures__/index.ts b/app/src/organisms/ErrorRecoveryFlows/__fixtures__/index.ts index d171ca2f91a..5af0d0d3887 100644 --- a/app/src/organisms/ErrorRecoveryFlows/__fixtures__/index.ts +++ b/app/src/organisms/ErrorRecoveryFlows/__fixtures__/index.ts @@ -68,7 +68,7 @@ export const mockRecoveryContentProps: RecoveryContentProps = { currentRecoveryOptionUtils: {} as any, failedLabwareUtils: { pickUpTipLabware: mockPickUpTipLabware } as any, failedPipetteInfo: {} as any, - recoveryMapUtils: {} as any, + deckMapUtils: { setSelectedLocation: () => {} } as any, stepCounts: {} as any, protocolAnalysis: { commands: [mockFailedCommand] } as any, trackExternalMap: () => null, diff --git a/app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useRecoveryMapUtils.test.tsx b/app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useDeckMapUtils.test.ts similarity index 94% rename from app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useRecoveryMapUtils.test.tsx rename to app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useDeckMapUtils.test.ts index 1a521443d78..4e341acda99 100644 --- a/app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useRecoveryMapUtils.test.tsx +++ b/app/src/organisms/ErrorRecoveryFlows/hooks/__tests__/useDeckMapUtils.test.ts @@ -1,4 +1,3 @@ -import * as React from 'react' import { describe, it, expect, beforeEach, vi } from 'vitest' import { @@ -17,8 +16,7 @@ import { getRunCurrentModulesInfo, getRunCurrentLabwareOnDeck, getRunCurrentModulesOnDeck, -} from '../useRecoveryMapUtils' -import { LabwareHighlight } from '../../shared' +} from '../useDeckMapUtils' import type { LabwareDefinition2 } from '@opentrons/shared-data' @@ -78,13 +76,11 @@ describe('getRunCurrentModulesOnDeck', () => { moduleLocation: { slotName: 'A1' }, innerProps: {}, nestedLabwareDef: mockLabwareDef, - moduleChildren: ( - - ), + highlight: 'MOCK_MODULE_ID', }, ]) }) - it('should set moduleChildren to null if getIsLabwareMatch returns false', () => { + it('should set highlight to null if getIsLabwareMatch returns false', () => { const result = getRunCurrentModulesOnDeck({ failedLabwareUtils: mockFailedLabwareUtils, currentModulesInfo: [ @@ -95,10 +91,10 @@ describe('getRunCurrentModulesOnDeck', () => { ], }) - expect(result[0].moduleChildren).toBeNull() + expect(result[0].highlight).toBeNull() }) - it('should set moduleChildren to null if nestedLabwareDef is null', () => { + it('should set highlight to null if nestedLabwareDef is null', () => { const result = getRunCurrentModulesOnDeck({ failedLabwareUtils: mockFailedLabwareUtils, currentModulesInfo: [ @@ -106,7 +102,7 @@ describe('getRunCurrentModulesOnDeck', () => { ], }) - expect(result[0].moduleChildren).toBeNull() + expect(result[0].highlight).toBeNull() }) }) @@ -139,14 +135,12 @@ describe('getRunCurrentLabwareOnDeck', () => { { labwareLocation: { slotName: 'A1' }, definition: mockLabwareDef, - labwareChildren: ( - - ), + highlight: 'A1', }, ]) }) - it('should set labwareChildren to null if getIsLabwareMatch returns false', () => { + it('should set highlight to null if getIsLabwareMatch returns false', () => { const result = getRunCurrentLabwareOnDeck({ failedLabwareUtils: { ...mockFailedLabwareUtils, @@ -158,7 +152,7 @@ describe('getRunCurrentLabwareOnDeck', () => { currentLabwareInfo: [mockCurrentLabwareInfo], }) - expect(result[0].labwareChildren).toBeNull() + expect(result[0].highlight).toBeNull() }) }) diff --git a/app/src/organisms/ErrorRecoveryFlows/hooks/useRecoveryMapUtils.tsx b/app/src/organisms/ErrorRecoveryFlows/hooks/useDeckMapUtils.ts similarity index 80% rename from app/src/organisms/ErrorRecoveryFlows/hooks/useRecoveryMapUtils.tsx rename to app/src/organisms/ErrorRecoveryFlows/hooks/useDeckMapUtils.ts index e0e749be0b9..3c8a45faabb 100644 --- a/app/src/organisms/ErrorRecoveryFlows/hooks/useRecoveryMapUtils.tsx +++ b/app/src/organisms/ErrorRecoveryFlows/hooks/useDeckMapUtils.ts @@ -10,8 +10,6 @@ import { THERMOCYCLER_MODULE_V1, } from '@opentrons/shared-data' -import { LabwareHighlight } from '../shared' - import type { Run } from '@opentrons/api-client' import type { DeckDefinition, @@ -21,29 +19,33 @@ import type { LabwareLocation, CutoutConfigProtocolSpec, LoadedLabware, + RobotType, } from '@opentrons/shared-data' import type { ErrorRecoveryFlowsProps } from '..' import type { UseFailedLabwareUtilsResult } from './useFailedLabwareUtils' -interface UseRecoveryMapUtilsProps { +interface UseDeckMapUtilsProps { runId: ErrorRecoveryFlowsProps['runId'] protocolAnalysis: ErrorRecoveryFlowsProps['protocolAnalysis'] failedLabwareUtils: UseFailedLabwareUtilsResult runRecord?: Run } -export interface UseRecoveryMapUtilsResult { +export interface UseDeckMapUtilsResult { deckConfig: CutoutConfigProtocolSpec[] - runCurrentModules: RunCurrentModulesOnDeck[] - runCurrentLabware: RunCurrentLabwareOnDeck[] + modulesOnDeck: RunCurrentModulesOnDeck[] + labwareOnDeck: RunCurrentLabwareOnDeck[] + highlightLabwareEventuallyIn: string[] + kind: 'intervention' + robotType: RobotType } // Returns the utilities needed by the Recovery Deck Map. -export function useRecoveryMapUtils({ +export function useDeckMapUtils({ protocolAnalysis, runRecord, runId, failedLabwareUtils, -}: UseRecoveryMapUtilsProps): UseRecoveryMapUtilsResult { +}: UseDeckMapUtilsProps): UseDeckMapUtilsResult { const robotType = protocolAnalysis?.robotType ?? OT2_ROBOT_TYPE const deckConfig = getSimplestDeckConfigForProtocol(protocolAnalysis) const deckDef = getDeckDefFromRobotType(robotType) @@ -83,8 +85,23 @@ export function useRecoveryMapUtils({ return { deckConfig, - runCurrentModules, - runCurrentLabware, + modulesOnDeck: runCurrentModules.map( + ({ moduleModel, moduleLocation, innerProps, nestedLabwareDef }) => ({ + moduleModel, + moduleLocation, + innerProps, + nestedLabwareDef, + }) + ), + labwareOnDeck: runCurrentLabware.map(({ labwareLocation, definition }) => ({ + labwareLocation, + definition, + })), + highlightLabwareEventuallyIn: [...runCurrentModules, ...runCurrentLabware] + .map(el => el.highlight) + .filter(maybeSlot => maybeSlot != null) as string[], + kind: 'intervention', + robotType, } } @@ -101,7 +118,6 @@ interface RunCurrentModulesOnDeck { lidMotorState?: undefined } nestedLabwareDef: LabwareDefinition2 | null - moduleChildren: JSX.Element | null } // Builds the necessary module object expected by BaseDeck. @@ -109,62 +125,49 @@ export function getRunCurrentModulesOnDeck({ failedLabwareUtils, currentModulesInfo, }: { - failedLabwareUtils: UseRecoveryMapUtilsProps['failedLabwareUtils'] + failedLabwareUtils: UseDeckMapUtilsProps['failedLabwareUtils'] currentModulesInfo: RunCurrentModuleInfo[] -}): RunCurrentModulesOnDeck[] { +}): Array { const { failedLabware } = failedLabwareUtils return currentModulesInfo.map( - ({ moduleDef, slotName, nestedLabwareDef, nestedLabwareSlotName }) => { - const isLabwareMatch = getIsLabwareMatch( - nestedLabwareSlotName, - failedLabware - ) - - return { - moduleModel: moduleDef.model, - moduleLocation: { slotName }, - innerProps: - moduleDef.model === THERMOCYCLER_MODULE_V1 - ? { lidMotorState: 'open' } - : {}, - - nestedLabwareDef, - moduleChildren: - isLabwareMatch && nestedLabwareDef != null ? ( - - ) : null, - } - } + ({ moduleDef, slotName, nestedLabwareDef, nestedLabwareSlotName }) => ({ + moduleModel: moduleDef.model, + moduleLocation: { slotName }, + innerProps: + moduleDef.model === THERMOCYCLER_MODULE_V1 + ? { lidMotorState: 'open' } + : {}, + + nestedLabwareDef, + highlight: getIsLabwareMatch(nestedLabwareSlotName, failedLabware) + ? nestedLabwareSlotName + : null, + }) ) } interface RunCurrentLabwareOnDeck { labwareLocation: LabwareLocation definition: LabwareDefinition2 - labwareChildren: JSX.Element | null } // Builds the necessary labware object expected by BaseDeck. export function getRunCurrentLabwareOnDeck({ currentLabwareInfo, failedLabwareUtils, }: { - failedLabwareUtils: UseRecoveryMapUtilsProps['failedLabwareUtils'] + failedLabwareUtils: UseDeckMapUtilsProps['failedLabwareUtils'] currentLabwareInfo: RunCurrentLabwareInfo[] -}): RunCurrentLabwareOnDeck[] { +}): Array { const { failedLabware } = failedLabwareUtils - return currentLabwareInfo.map(({ slotName, labwareDef, labwareLocation }) => { - const isLabwareMatch = getIsLabwareMatch(slotName, failedLabware) - - return { + return currentLabwareInfo.map( + ({ slotName, labwareDef, labwareLocation }) => ({ labwareLocation, definition: labwareDef, - labwareChildren: isLabwareMatch ? ( - - ) : null, - } - }) + highlight: getIsLabwareMatch(slotName, failedLabware) ? slotName : null, + }) + ) } interface RunCurrentModuleInfo { @@ -181,8 +184,8 @@ export const getRunCurrentModulesInfo = ({ deckDef, protocolAnalysis, }: { - protocolAnalysis: UseRecoveryMapUtilsProps['protocolAnalysis'] - runRecord: UseRecoveryMapUtilsProps['runRecord'] + protocolAnalysis: UseDeckMapUtilsProps['protocolAnalysis'] + runRecord: UseDeckMapUtilsProps['runRecord'] deckDef: DeckDefinition }): RunCurrentModuleInfo[] => { if (runRecord == null || protocolAnalysis == null) { @@ -248,8 +251,8 @@ export function getRunCurrentLabwareInfo({ runRecord, protocolAnalysis, }: { - runRecord: UseRecoveryMapUtilsProps['runRecord'] - protocolAnalysis: UseRecoveryMapUtilsProps['protocolAnalysis'] + runRecord: UseDeckMapUtilsProps['runRecord'] + protocolAnalysis: UseDeckMapUtilsProps['protocolAnalysis'] }): RunCurrentLabwareInfo[] { if (runRecord == null || protocolAnalysis == null) { return [] diff --git a/app/src/organisms/ErrorRecoveryFlows/hooks/useERUtils.ts b/app/src/organisms/ErrorRecoveryFlows/hooks/useERUtils.ts index b5f414b0546..926d4ee8ff8 100644 --- a/app/src/organisms/ErrorRecoveryFlows/hooks/useERUtils.ts +++ b/app/src/organisms/ErrorRecoveryFlows/hooks/useERUtils.ts @@ -6,7 +6,7 @@ import { useRecoveryTipStatus } from './useRecoveryTipStatus' import { useRecoveryRouting } from './useRecoveryRouting' import { useFailedLabwareUtils } from './useFailedLabwareUtils' import { getFailedCommandPipetteInfo, getNextStep } from '../utils' -import { useRecoveryMapUtils } from './useRecoveryMapUtils' +import { useDeckMapUtils } from './useDeckMapUtils' import { useNotifyAllCommandsQuery, useNotifyRunQuery, @@ -21,7 +21,7 @@ import type { UseRouteUpdateActionsResult } from './useRouteUpdateActions' import type { UseRecoveryCommandsResult } from './useRecoveryCommands' import type { RecoveryTipStatusUtils } from './useRecoveryTipStatus' import type { UseFailedLabwareUtilsResult } from './useFailedLabwareUtils' -import type { UseRecoveryMapUtilsResult } from './useRecoveryMapUtils' +import type { UseDeckMapUtilsResult } from './useDeckMapUtils' import type { CurrentRecoveryOptionUtils } from './useRecoveryRouting' import type { StepCounts } from '../../../resources/protocols/hooks' @@ -37,7 +37,7 @@ export interface ERUtilsResults { recoveryCommands: UseRecoveryCommandsResult tipStatusUtils: RecoveryTipStatusUtils failedLabwareUtils: UseFailedLabwareUtilsResult - recoveryMapUtils: UseRecoveryMapUtilsResult + deckMapUtils: UseDeckMapUtilsResult getRecoveryOptionCopy: ReturnType failedPipetteInfo: PipetteData | null hasLaunchedRecovery: boolean @@ -109,7 +109,7 @@ export function useERUtils({ routeUpdateActions, }) - const recoveryMapUtils = useRecoveryMapUtils({ + const deckMapUtils = useDeckMapUtils({ runId, runRecord, protocolAnalysis, @@ -133,7 +133,7 @@ export function useERUtils({ tipStatusUtils, failedLabwareUtils, failedPipetteInfo, - recoveryMapUtils, + deckMapUtils, getRecoveryOptionCopy, stepCounts, commandAfterFailedCommand, diff --git a/app/src/organisms/ErrorRecoveryFlows/shared/RecoveryMap.tsx b/app/src/organisms/ErrorRecoveryFlows/shared/RecoveryMap.tsx deleted file mode 100644 index 9f6c1573bb5..00000000000 --- a/app/src/organisms/ErrorRecoveryFlows/shared/RecoveryMap.tsx +++ /dev/null @@ -1,74 +0,0 @@ -import * as React from 'react' -import { css } from 'styled-components' - -import { FLEX_ROBOT_TYPE } from '@opentrons/shared-data' -import { - BaseDeck, - Box, - RobotCoordsForeignDiv, - COLORS, - DIRECTION_COLUMN, - DISPLAY_FLEX, - JUSTIFY_FLEX_END, -} from '@opentrons/components' - -import type { LabwareDefinition2 } from '@opentrons/shared-data' -import type { RecoveryContentProps } from '../types' - -export function RecoveryMap({ - isOnDevice, - recoveryMapUtils, -}: RecoveryContentProps): JSX.Element | null { - const { deckConfig, runCurrentModules, runCurrentLabware } = recoveryMapUtils - - if (isOnDevice) { - return ( - - ) - } else { - return null - } -} - -export function LabwareHighlight({ - highlight, - definition, -}: { - highlight: boolean - definition: LabwareDefinition2 -}): JSX.Element { - const width = definition.dimensions.xDimension - const height = definition.dimensions.yDimension - - return ( - - - - ) -} - -const HIGHLIGHT_STYLE = css` - border-radius: 7.04px; - border: 3px solid ${COLORS.blue50}; - box-shadow: 0 0 4px 3px #74b0ff; -` diff --git a/app/src/organisms/ErrorRecoveryFlows/shared/ReplaceTips.tsx b/app/src/organisms/ErrorRecoveryFlows/shared/ReplaceTips.tsx index 62815b403e8..cbf795778c8 100644 --- a/app/src/organisms/ErrorRecoveryFlows/shared/ReplaceTips.tsx +++ b/app/src/organisms/ErrorRecoveryFlows/shared/ReplaceTips.tsx @@ -4,10 +4,9 @@ import { Flex } from '@opentrons/components' import { useTranslation } from 'react-i18next' import { RecoverySingleColumnContent } from './RecoverySingleColumnContent' -import { TwoColumn } from '../../../molecules/InterventionModal' +import { TwoColumn, DeckMapContent } from '../../../molecules/InterventionModal' import { RecoveryFooterButtons } from './RecoveryFooterButtons' import { LeftColumnLabwareInfo } from './LeftColumnLabwareInfo' -import { RecoveryMap } from './RecoveryMap' import type { RecoveryContentProps } from '../types' @@ -17,6 +16,7 @@ export function ReplaceTips(props: RecoveryContentProps): JSX.Element | null { routeUpdateActions, failedPipetteInfo, failedLabwareUtils, + deckMapUtils, } = props const { relevantWellName } = failedLabwareUtils const { proceedNextStep } = routeUpdateActions @@ -47,7 +47,7 @@ export function ReplaceTips(props: RecoveryContentProps): JSX.Element | null { bannerText={t('replace_tips_and_select_location')} /> - + { - const actual = await importOriginal() - return { - ...actual, - BaseDeck: vi - .fn() - .mockImplementation(props =>
MOCK_BASE_DECK
), - } -}) - -const render = (props: React.ComponentProps) => { - return renderWithProviders(, { - i18nInstance: i18n, - })[0] -} - -describe('RecoveryMap', () => { - let props: React.ComponentProps - const mockDeckConfig = 'MOCK_DECK_CONFIG' - const mockRunCurrentModules = 'MOCK_RUN_MODULES' - const mockRunCurrentLw = 'MOCK_RUN_LW' - - const mockRecoveryMapUtils = { - deckConfig: mockDeckConfig, - runCurrentModules: mockRunCurrentModules, - runCurrentLabware: mockRunCurrentLw, - } as any - - beforeEach(() => { - props = { - ...mockRecoveryContentProps, - recoveryMapUtils: mockRecoveryMapUtils, - } - }) - - it('renders the BaseDeck with appropriate props when on ODD', () => { - render(props) - - screen.getByText('MOCK_BASE_DECK') - expect(vi.mocked(BaseDeck)).toHaveBeenCalledWith( - { - deckConfig: mockDeckConfig, - robotType: FLEX_ROBOT_TYPE, - modulesOnDeck: mockRunCurrentModules, - labwareOnDeck: mockRunCurrentLw, - }, - {} - ) - }) -}) diff --git a/app/src/organisms/ErrorRecoveryFlows/shared/index.ts b/app/src/organisms/ErrorRecoveryFlows/shared/index.ts index 72ca995e267..48c78d1ddd1 100644 --- a/app/src/organisms/ErrorRecoveryFlows/shared/index.ts +++ b/app/src/organisms/ErrorRecoveryFlows/shared/index.ts @@ -6,7 +6,6 @@ export { export { ReplaceTips } from './ReplaceTips' export { SelectTips } from './SelectTips' export { TwoColTextAndFailedStepNextStep } from './TwoColTextAndFailedStepNextStep' -export { RecoveryMap, LabwareHighlight } from './RecoveryMap' export { LeftColumnLabwareInfo } from './LeftColumnLabwareInfo' export { TipSelection } from './TipSelection' export { TipSelectionModal } from './TipSelectionModal' diff --git a/components/src/molecules/LocationIcon/index.tsx b/components/src/molecules/LocationIcon/index.tsx index 082833c5cd1..773efbdbbef 100644 --- a/components/src/molecules/LocationIcon/index.tsx +++ b/components/src/molecules/LocationIcon/index.tsx @@ -3,7 +3,7 @@ import { css } from 'styled-components' import { Icon } from '../../icons' import { Flex, Text } from '../../primitives' -import { ALIGN_CENTER } from '../../styles' +import { ALIGN_CENTER, JUSTIFY_CENTER } from '../../styles' import { RESPONSIVENESS, SPACING, TYPOGRAPHY } from '../../ui-style-constants' import { BORDERS, COLORS } from '../../helix-design-system' @@ -36,6 +36,7 @@ const LOCATION_ICON_STYLE = css<{ width: ${props => props.width ?? 'max-content'}; padding: ${SPACING.spacing2} ${SPACING.spacing4}; border-radius: ${BORDERS.borderRadius4}; + justify-content: ${JUSTIFY_CENTER}; height: max-content; @media ${RESPONSIVENESS.touchscreenMediaQuerySpecs} { @@ -48,13 +49,7 @@ const LOCATION_ICON_STYLE = css<{ ` const SLOT_NAME_TEXT_STYLE = css` - font-size: ${TYPOGRAPHY.fontSizeCaption}; - line-height: ${TYPOGRAPHY.lineHeightNormal}; - font-weight: ${TYPOGRAPHY.fontWeightBold}; - - @media ${RESPONSIVENESS.touchscreenMediaQuerySpecs} { - ${TYPOGRAPHY.smallBodyTextBold} - } + ${TYPOGRAPHY.smallBodyTextBold} ` export function LocationIcon({