Skip to content

Commit df2bc2c

Browse files
Fran McDadeNoopDog
authored andcommitted
feat: add transitions to detail page status badge (#3623)
1 parent 9c0c06b commit df2bc2c

File tree

6 files changed

+130
-10
lines changed

6 files changed

+130
-10
lines changed

explorer/app/apis/azul/anvil-cmg/common/responses.ts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { AzulHit } from "../../common/entities";
1+
import { AzulHit, ResponseSource } from "../../common/entities";
22
import {
33
AggregatedActivityResponse,
44
AggregatedBioSampleResponse,
@@ -52,7 +52,8 @@ export type DatasetsResponse = AzulHit &
5252
AggregatedDonorResponse &
5353
AggregatedFileResponse &
5454
AggregatedLibraryResponse &
55-
AggregatedDiagnosisResponse;
55+
AggregatedDiagnosisResponse &
56+
ResponseSource;
5657

5758
/**
5859
* Model of response returned from the /index/donors API endpoint.

explorer/app/apis/azul/common/entities.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { RESPONSE_SOURCE } from "@clevercanary/data-explorer-ui/lib/apis/azul/common/entities";
12
import { FileEntityResponse } from "../anvil/common/entities";
23
import {
34
ActivitiesResponse,
@@ -24,3 +25,10 @@ export type AzulEntitiesResponses =
2425
| DonorsResponse
2526
| FileEntityResponse
2627
| LibrariesResponse;
28+
29+
/**
30+
* Response source.
31+
*/
32+
export interface ResponseSource {
33+
responseSource?: RESPONSE_SOURCE;
34+
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import { Fade as MFade, FadeProps as MFadeProps } from "@mui/material";
2+
import React, { ReactNode } from "react";
3+
4+
/**
5+
* Basic Fade component for rendering with component configuration.
6+
* Transition child requirements: see https://mui.com/material-ui/transitions/#child-requirement.
7+
* A wrapper element around component configuration "children" is required as the "children" do not meet the child
8+
* requirements for a transition component i.e. they are not defined as a single element.
9+
*/
10+
11+
export interface FadeProps extends Omit<MFadeProps, "children"> {
12+
children: ReactNode[]; // component configuration "children" are not defined as a single element.
13+
}
14+
15+
export const Fade = ({
16+
children,
17+
...props /* Spread props to allow for Mui Fade specific prop overrides e.g. "appear" or "style". */
18+
}: FadeProps): JSX.Element => {
19+
return (
20+
<MFade {...props}>
21+
<div>{children}</div>
22+
</MFade>
23+
);
24+
};

explorer/app/components/index.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ export { Publications } from "@clevercanary/data-explorer-ui/lib/components/Proj
5959
export { SupplementaryLinks } from "@clevercanary/data-explorer-ui/lib/components/Project/components/SupplementaryLinks/supplementaryLinks";
6060
export { TitledText } from "@clevercanary/data-explorer-ui/lib/components/Project/components/TitledText/titledText";
6161
export { ExportMethodView } from "@clevercanary/data-explorer-ui/lib/views/ExportMethodView/exportMethodView";
62+
export { Fade } from "./common/Fade/fade";
6263
export { MdxMarkdown } from "./common/MDXMarkdown/mdxMarkdown";
6364
export { ConsentCodeList } from "./Detail/components/ConsentCodeList/consentCodeList";
6465
export { ConsentTooltip } from "./Detail/components/ConsentTooltip/consentTooltip";

explorer/app/viewModelBuilders/azul/anvil-cmg/common/viewModelBuilders.ts

Lines changed: 85 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,7 @@
1-
import { LABEL } from "@clevercanary/data-explorer-ui/lib/apis/azul/common/entities";
1+
import {
2+
LABEL,
3+
RESPONSE_SOURCE,
4+
} from "@clevercanary/data-explorer-ui/lib/apis/azul/common/entities";
25
import {
36
Filters,
47
SelectedFilter,
@@ -230,14 +233,16 @@ export const buildDatasetDetails = (
230233
/**
231234
* Build props for BackPageHero component from the given datasets response.
232235
* @param datasetsResponse - Response model return from datasets API.
236+
* @param viewContext - View context.
233237
* @returns model to be used as props for the BackPageHero component.
234238
*/
235239
export const buildDatasetHero = (
236-
datasetsResponse: DatasetsResponse
240+
datasetsResponse: DatasetsResponse,
241+
viewContext: ViewContext
237242
): React.ComponentProps<typeof C.BackPageHero> => {
238243
return {
239244
breadcrumbs: getDatasetBreadcrumbs(datasetsResponse),
240-
callToAction: getDatasetCallToAction(datasetsResponse),
245+
callToAction: getDatasetCallToAction(datasetsResponse, viewContext),
241246
title: getDatasetTitle(datasetsResponse),
242247
};
243248
};
@@ -709,6 +714,23 @@ export const buildReportedEthnicities = (
709714
};
710715
};
711716

717+
/**
718+
* Returns transition relating to accessibility from the given datasets response and authorization state.
719+
* @param datasetsResponse - Response model return from datasets API.
720+
* @param viewContext - View context.
721+
* @returns model to be used as props for the Fade component.
722+
*/
723+
export function getAccessibleTransition(
724+
datasetsResponse: DatasetsResponse,
725+
viewContext: ViewContext
726+
): Partial<React.ComponentProps<typeof C.Fade>> {
727+
const isIn = isAccessibleTransitionIn(datasetsResponse, viewContext);
728+
return {
729+
in: isIn,
730+
timeout: isIn ? 0 : 300,
731+
};
732+
}
733+
712734
/**
713735
* Returns dataset related breadcrumbs.
714736
* @param datasetsResponse - Response model return from datasets API.
@@ -726,14 +748,21 @@ export function getDatasetBreadcrumbs(
726748
/**
727749
* Returns the callToAction prop for the Hero component from the given datasets response.
728750
* @param datasetsResponse - Response model return from datasets API.
751+
* @param viewContext - View context.
729752
* @returns model to be used as props for the CallToActionButton component.
730753
*/
731754
function getDatasetCallToAction(
732-
datasetsResponse: DatasetsResponse
755+
datasetsResponse: DatasetsResponse,
756+
viewContext: ViewContext
733757
): CallToAction | undefined {
758+
const isReady = isResponseReady(datasetsResponse, viewContext);
734759
const isAccessGranted = isDatasetAccessible(datasetsResponse);
735760
const registeredIdentifier = getDatasetRegisteredIdentifier(datasetsResponse);
736-
if (isAccessGranted || registeredIdentifier === LABEL.UNSPECIFIED) {
761+
if (
762+
!isReady ||
763+
isAccessGranted ||
764+
registeredIdentifier === LABEL.UNSPECIFIED
765+
) {
737766
return;
738767
}
739768
return {
@@ -816,6 +845,22 @@ export function getExportSelectedDataSummary(
816845
]);
817846
}
818847

848+
/**
849+
* Returns true if the response is accessible, or the response source is appropriate for the authorization state.
850+
* When a user is logged in, the component should only transition in when the client side request is available;
851+
* a static request will not accurately reflect the accessibility of the given response.
852+
* @param datasetsResponse - Response model return from datasets API.
853+
* @param viewContext - View context.
854+
* @returns true if the response is accessible, or the response source is appropriate for the authorization state.
855+
*/
856+
function isAccessibleTransitionIn(
857+
datasetsResponse: DatasetsResponse,
858+
viewContext: ViewContext
859+
): boolean {
860+
const isAccessible = isDatasetAccessible(datasetsResponse);
861+
return isAccessible || isResponseReady(datasetsResponse, viewContext);
862+
}
863+
819864
/**
820865
* Returns true if dataset is accessible.
821866
* @param datasetsResponse - Response model return from datasets API.
@@ -825,6 +870,26 @@ function isDatasetAccessible(datasetsResponse: DatasetsResponse): boolean {
825870
return datasetsResponse.datasets[0].accessible;
826871
}
827872

873+
/**
874+
* Returns true if the response is ready (for use) for the given authorization state.
875+
* When a user is logged in, the component should only transition in when the client side request is available;
876+
* a static request will not accurately reflect properties like "accessibility" of the given response.
877+
* @param datasetsResponse - Response model return from datasets API.
878+
* @param viewContext - View context.
879+
* @returns true if the response is ready.
880+
*/
881+
function isResponseReady(
882+
datasetsResponse: DatasetsResponse,
883+
viewContext: ViewContext
884+
): boolean {
885+
const {
886+
authState: { isAuthorized },
887+
} = viewContext;
888+
const { responseSource } = datasetsResponse;
889+
const isStatic = responseSource === RESPONSE_SOURCE.STATIC_GENERATION;
890+
return !(isAuthorized && isStatic);
891+
}
892+
828893
/**
829894
* Returns current query for the given facet.
830895
* @param filter - Selected filter.
@@ -842,6 +907,21 @@ function mapCurrentQuery(
842907
];
843908
}
844909

910+
/**
911+
* Renders entity related status badge (with transition).
912+
* @param datasetsResponse - Unused.
913+
* @param viewContext - View context.
914+
* @returns model to be used as props for the Fade component.
915+
*/
916+
export const renderDatasetStatusBadge = (
917+
datasetsResponse: DatasetsResponse,
918+
viewContext: ViewContext
919+
): Partial<React.ComponentProps<typeof C.Fade>> => {
920+
return {
921+
...getAccessibleTransition(datasetsResponse, viewContext),
922+
};
923+
};
924+
845925
/**
846926
* Renders configuration component children when the given authentication state is not authorized.
847927
* @param _ - Unused.

explorer/site-config/anvil-cmg/dev/detail/dataset/top.ts

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,15 @@ export const top: ComponentsConfig = [
1010
{
1111
children: [
1212
{
13-
component: C.StatusBadge,
14-
viewBuilder: V.buildDatasetStatus,
15-
} as ComponentConfig<typeof C.StatusBadge, DatasetsResponse>,
13+
children: [
14+
{
15+
component: C.StatusBadge,
16+
viewBuilder: V.buildDatasetStatus,
17+
} as ComponentConfig<typeof C.StatusBadge, DatasetsResponse>,
18+
],
19+
component: C.Fade,
20+
viewBuilder: V.renderDatasetStatusBadge,
21+
} as ComponentConfig<typeof C.Fade>,
1622
],
1723
component: C.BackPageHero,
1824
viewBuilder: V.buildDatasetHero,

0 commit comments

Comments
 (0)