feat: Display last updates in About modal

This commit is contained in:
Maksim Eltyshev
2025-12-17 15:49:33 +01:00
parent 27fd10ba3f
commit 4f5f5ddad4
50 changed files with 220 additions and 48 deletions
@@ -13,7 +13,9 @@ import { useClosableModal } from '../../../hooks';
import TermsPane from './TermsPane';
import AboutPane from './AboutPane';
const InformationModal = React.memo(() => {
import styles from './AboutModal.module.scss';
const AboutModal = React.memo(() => {
const dispatch = useDispatch();
const [t] = useTranslation();
@@ -39,7 +41,14 @@ const InformationModal = React.memo(() => {
];
return (
<ClosableModal open closeIcon size="small" centered={false} onClose={handleClose}>
<ClosableModal
open
closeIcon
size="small"
centered={false}
className={styles.wrapper}
onClose={handleClose}
>
<ClosableModal.Content>
<Tab
menu={{
@@ -53,4 +62,4 @@ const InformationModal = React.memo(() => {
);
});
export default InformationModal;
export default AboutModal;
@@ -0,0 +1,14 @@
/*!
* Copyright (c) 2024 PLANKA Software GmbH
* Licensed under the Fair Use License: https://github.com/plankanban/planka/blob/master/LICENSE.md
*/
:global(#app) {
.wrapper {
margin: 2rem auto;
@media (width < 926px) {
margin: 1rem auto;
}
}
}
@@ -0,0 +1,60 @@
/*!
* Copyright (c) 2024 PLANKA Software GmbH
* Licensed under the Fair Use License: https://github.com/plankanban/planka/blob/master/LICENSE.md
*/
import React, { useEffect, useState } from 'react';
import { useTranslation } from 'react-i18next';
import { Divider, Header, Image, Loader, Tab } from 'semantic-ui-react';
import version from '../../../version';
import Markdown from '../Markdown';
import aboutLogo from '../../../assets/images/about-logo.png';
import whatsNewUrl from '../../../assets/docs/whats-new.md?url';
import styles from './AboutPane.module.scss';
const AboutPane = React.memo(() => {
const [t] = useTranslation();
const [whatsNew, setWhatsNew] = useState(null);
useEffect(() => {
async function fetchWhatsNew() {
let response;
try {
response = await fetch(whatsNewUrl);
} catch {
return;
}
const text = await response.text();
setWhatsNew(text);
}
fetchWhatsNew();
}, []);
return (
<Tab.Pane attached={false} className={styles.wrapper}>
<a href="https://github.com/plankanban/planka" target="_blank" rel="noreferrer">
<Image centered src={aboutLogo} size="large" />
</a>
<div className={styles.version}>{version}</div>
<Divider horizontal>
<Header as="h4">
{t('common.whatsNew', {
context: 'title',
})}
</Header>
</Divider>
{whatsNew ? (
<Markdown>{whatsNew}</Markdown>
) : (
<Loader active inverted inline="centered" size="small" />
)}
</Tab.Pane>
);
});
export default AboutPane;
@@ -6,6 +6,7 @@
:global(#app) {
.version {
font-weight: bold;
margin-bottom: 40px;
text-align: center;
}
@@ -3,6 +3,6 @@
* Licensed under the Fair Use License: https://github.com/plankanban/planka/blob/master/LICENSE.md
*/
import InformationModal from './InformationModal';
import AboutModal from './AboutModal';
export default InformationModal;
export default AboutModal;
+3 -3
View File
@@ -16,7 +16,7 @@ import Toaster from '../Toaster';
import Fixed from '../Fixed';
import Static from '../Static';
import AdministrationModal from '../AdministrationModal';
import InformationModal from '../InformationModal';
import AboutModal from '../AboutModal';
import UserSettingsModal from '../../users/UserSettingsModal';
import ProjectBackground from '../../projects/ProjectBackground';
import AddProjectModal from '../../projects/AddProjectModal';
@@ -63,8 +63,8 @@ const Core = React.memo(() => {
modalNode = <AdministrationModal />;
break;
case ModalTypes.INFORMATION:
modalNode = <InformationModal />;
case ModalTypes.ABOUT:
modalNode = <AboutModal />;
break;
case ModalTypes.USER_SETTINGS:
@@ -1,24 +0,0 @@
/*!
* Copyright (c) 2024 PLANKA Software GmbH
* Licensed under the Fair Use License: https://github.com/plankanban/planka/blob/master/LICENSE.md
*/
import React from 'react';
import { Image, Tab } from 'semantic-ui-react';
import version from '../../../version';
import aboutLogo from '../../../assets/images/about-logo.png';
import styles from './AboutPane.module.scss';
const AboutPane = React.memo(() => (
<Tab.Pane attached={false} className={styles.wrapper}>
<a href="https://github.com/plankanban/planka" target="_blank" rel="noreferrer">
<Image centered src={aboutLogo} size="large" />
</a>
<div className={styles.version}>{version}</div>
</Tab.Pane>
));
export default AboutPane;
@@ -40,8 +40,8 @@ const UserActionsStep = React.memo(({ onClose }) => {
onClose();
}, [onClose, dispatch]);
const handleInformationClick = useCallback(() => {
dispatch(entryActions.openInformationModal());
const handleAboutClick = useCallback(() => {
dispatch(entryActions.openAboutModal());
onClose();
}, [onClose, dispatch]);
@@ -98,7 +98,7 @@ const UserActionsStep = React.memo(({ onClose }) => {
)}
</>
)}
<Menu.Item className={styles.menuItem} onClick={handleInformationClick}>
<Menu.Item className={styles.menuItem} onClick={handleAboutClick}>
<Icon name="info circle" className={styles.menuItemIcon} />
{t('common.aboutApp', {
context: 'title',