Skip to content

Commit

Permalink
feat(public): SJIP-1104 Add page content
Browse files Browse the repository at this point in the history
  • Loading branch information
AltefrohneGaelle authored and GaelleA committed Dec 2, 2024
1 parent b93360d commit c5cd46e
Show file tree
Hide file tree
Showing 10 changed files with 367 additions and 20 deletions.
7 changes: 7 additions & 0 deletions src/locales/en.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1440,6 +1440,13 @@ const en = {
start: 'Start',
title: 'Studies',
},
publicStudies: {
title: 'Studies',
search: {
title: 'Search by study name',
placeholder: 'The Human Trisome Project',
},
},
analytics: {
title: 'Data Analysis',
subtitle: 'Quickly visualize and interpret INCLUDE Data with our user-friendly tools.',
Expand Down
13 changes: 12 additions & 1 deletion src/services/api/arranger/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,19 @@ export type Suggestion = {
};

export interface IStudiesParticipants {
data_category: string[];
description?: string;
domains?: string[];
external_ids?: string[];
family_count?: number;
file_count?: number;
guid?: string;
is_harmonized?: boolean;
participant_count: number;
program: string;
study_code: string;
study_id: string;
study_name: string;
}

export interface IDiagnosis {
Expand All @@ -47,7 +58,7 @@ export interface IStatistics {
samples: number;
sex: Record<string, number>;
studies: number;
studiesParticipants: Record<string, number>;
studiesParticipants: IStudiesParticipants[];
transcriptomes: number;
variants: number;
}
Expand Down
10 changes: 1 addition & 9 deletions src/store/global/thunks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,9 @@ const fetchStats = createAsyncThunk<IStatistics, void, { rejectValue: string; st
const { data: statistics } = await ArrangerApi.fetchStatistics();
const { data: studiesStatistics } = await ArrangerApi.fetchStudiesParticipants();

const formattedStudiesStatistics = studiesStatistics?.reduce(
(acc, { study_code, participant_count }) => {
acc[study_code] = participant_count;
return acc;
},
{} as Record<string, number>,
);

const data: IStatistics = {
...statistics!,
studiesParticipants: formattedStudiesStatistics!,
studiesParticipants: studiesStatistics!,
};

return data;
Expand Down
8 changes: 5 additions & 3 deletions src/views/Login/StudiesSection/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import BriLogo from 'components/assets/studies/study-logo-BRI.png';
import DefaultLogo from 'components/assets/studies/study-logo-default.svg';
import DsconnectLogo from 'components/assets/studies/study-logo-DSC.png';
import KfLogo from 'components/assets/studies/study-logo-KF.svg';
import { IStudiesParticipants } from 'services/api/arranger/models';

import { useGlobals } from '../../../store/global';

Expand All @@ -35,18 +36,19 @@ const studies = [
{ code: 'DS-NEXUS', formattedCode: 'dsnexus', logo: DsnexusLogo },
];

const formatStudies = (studiesParticipants: Record<string, number>) =>
const formatStudies = (studiesParticipants: IStudiesParticipants[]) =>
studies.map((study) => ({
code: study.code,
title: <img src={study.logo} alt="Study Logo" className={styles.logo} />,
subtitle: intl.get(`screen.loginPage.studies.${study.formattedCode}.name`),
description: intl.getHTML(`screen.loginPage.studies.${study.formattedCode}.description`),
participantCount: studiesParticipants[study.code],
participantCount: studiesParticipants.find((studyPart) => studyPart.study_code === study.code)
?.participant_count,
}));

const StudiesSection = () => {
const { stats } = useGlobals();
const { studiesParticipants = {}, studies: studiesCount = 0 } = stats || {};
const { studiesParticipants = [], studies: studiesCount = 0 } = stats || {};
const formattedStudies = formatStudies(studiesParticipants);
return (
<div className={styles.container}>
Expand Down
18 changes: 18 additions & 0 deletions src/views/PublicStudies/components/PageContent/index.module.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
.pageContent {
width: 100%;
}
.pageContent .tableWrapper {
width: 100%;
gap: 0 !important;
}
.pageContent .title {
margin: 0;
}
.pageContent .label {
margin-bottom: 8px;
}
.pageContent .inputContainer {
display: flex;
gap: 8px;
margin-bottom: 8px;
}
86 changes: 86 additions & 0 deletions src/views/PublicStudies/components/PageContent/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
import { useEffect, useState } from 'react';
import intl from 'react-intl-universal';
import ProLabel from '@ferlab/ui/core/components/ProLabel';
import ProTable from '@ferlab/ui/core/components/ProTable';
import GridCard from '@ferlab/ui/core/view/v2/GridCard';
import { Input, Space, Typography } from 'antd';
import { getColumns, TABLE_ID } from 'views/PublicStudies/utils';

import { useGlobals } from 'store/global';
import { getProTableDictionary } from 'utils/translation';

import styles from './index.module.css';

const { Title } = Typography;

const PageContent = () => {
const [searchValue, setSearchValue] = useState('');

const { stats, isFetchingStats } = useGlobals();
const { studiesParticipants = [] } = stats || {};

const [filteredStudies, setFilteredStudies] = useState(studiesParticipants);

useEffect(() => {
setFilteredStudies(studiesParticipants);
}, [studiesParticipants]);

const searchPrescription = (value: any) => {
if (value?.target?.value) {
const searchValue = value.target.value;
setSearchValue(searchValue);

const filteredValues = studiesParticipants.filter((study) =>
study.study_name.toLowerCase().includes(searchValue.toLowerCase()),
);
setFilteredStudies(filteredValues);
} else {
setSearchValue('');
setFilteredStudies(studiesParticipants);
}
};

const defaultColumns = getColumns();

return (
<Space direction="vertical" size={16} className={styles.pageContent}>
<Title className={styles.title} level={4}>
{intl.get('screen.publicStudies.title')}
</Title>

<div>
<ProLabel className={styles.label} title={intl.get('screen.publicStudies.search.title')} />
<div className={styles.inputContainer}>
<Input
allowClear
onChange={searchPrescription}
placeholder={intl.get('screen.publicStudies.search.placeholder')}
size="large"
value={searchValue}
/>
</div>
</div>

<GridCard
content={
<ProTable
tableId={TABLE_ID}
columns={defaultColumns}
wrapperClassName={styles.tableWrapper}
loading={isFetchingStats}
showSorterTooltip={false}
bordered
headerConfig={{
hideItemsCount: true,
}}
size="small"
dataSource={filteredStudies.map((i) => ({ ...i, key: i.study_code }))}
dictionary={getProTableDictionary()}
/>
}
/>
</Space>
);
};

export default PageContent;
20 changes: 20 additions & 0 deletions src/views/PublicStudies/index.module.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
.studiesPage {
display: flex;
}

.scrollContent {
width: 100%;
padding: var(--default-page-content-padding);
}

.descriptionCell::after {
content: '';
display: block;
}

.dbgapLink {
margin-right: 8px;
}
.dbgapLink:last-child {
margin-right: 0;
}
32 changes: 27 additions & 5 deletions src/views/PublicStudies/index.tsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,31 @@
import { useEffect } from 'react';
import { useDispatch } from 'react-redux';
import ScrollContent from '@ferlab/ui/core/layout/ScrollContent';
import PageContent from 'views/PublicStudies/components/PageContent';

import PublicLayout from 'components/PublicLayout';
import { fetchStats } from 'store/global/thunks';

import { SCROLL_WRAPPER_ID } from './utils';

import style from './index.module.css';

const PublicStudies = () => {
const dispatch = useDispatch();

useEffect(() => {
dispatch(fetchStats());
}, [dispatch]);

const PublicStudies = () => (
<PublicLayout>
<span></span>
</PublicLayout>
);
return (
<PublicLayout>
<div className={style.studiesPage}>
<ScrollContent id={SCROLL_WRAPPER_ID} className={style.scrollContent}>
<PageContent />
</ScrollContent>
</div>
</PublicLayout>
);
};

export default PublicStudies;
Loading

0 comments on commit c5cd46e

Please sign in to comment.