From 6e89b695f15534c743b4b3e2d8eef295d1dfccdd Mon Sep 17 00:00:00 2001 From: stanislavh Date: Fri, 22 Nov 2024 11:12:52 +0100 Subject: [PATCH] SONAR-22309 Fix a11y issues on Activity page --- .../apps/projectActivity/components/Event.tsx | 60 +++--- .../ProjectActivityAnalysesList.tsx | 178 +++++++++--------- .../components/ProjectActivityDateInput.tsx | 7 +- .../components/ProjectActivityPageFilters.tsx | 33 ++-- .../__tests__/ProjectActivityApp-it.tsx | 22 ++- .../components/activity-graph/EventInner.tsx | 2 +- .../activity-graph/GraphHistory.tsx | 151 ++++++++------- .../activity-graph/GraphsHistory.tsx | 107 +++++------ .../__tests__/ActivityGraph-it.tsx | 15 +- .../DatePickerCustomCalendarNavigation.tsx | 3 +- .../resources/org/sonar/l10n/core.properties | 11 +- 11 files changed, 310 insertions(+), 279 deletions(-) diff --git a/server/sonar-web/src/main/js/apps/projectActivity/components/Event.tsx b/server/sonar-web/src/main/js/apps/projectActivity/components/Event.tsx index 06d19395a9b..124763d4a57 100644 --- a/server/sonar-web/src/main/js/apps/projectActivity/components/Event.tsx +++ b/server/sonar-web/src/main/js/apps/projectActivity/components/Event.tsx @@ -18,10 +18,16 @@ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ +import { + ButtonIcon, + ButtonSize, + ButtonVariety, + IconDelete, + IconEdit, +} from '@sonarsource/echoes-react'; import * as React from 'react'; -import { DestructiveIcon, InteractiveIcon, PencilIcon, TrashIcon } from '~design-system'; +import { useIntl } from 'react-intl'; import EventInner from '../../../components/activity-graph/EventInner'; -import Tooltip from '../../../components/controls/Tooltip'; import { translate } from '../../../helpers/l10n'; import { AnalysisEvent, ProjectAnalysisEventCategory } from '../../../types/project-activity'; import ChangeEventForm from './forms/ChangeEventForm'; @@ -36,6 +42,7 @@ export interface EventProps { function Event(props: Readonly) { const { analysisKey, event, canAdmin, isFirst } = props; + const intl = useIntl(); const [changing, setChanging] = React.useState(false); const [deleting, setDeleting] = React.useState(false); @@ -46,6 +53,15 @@ function Event(props: Readonly) { const canDelete = isOther || (isVersion && !isFirst); const showActions = canAdmin && (canChange || canDelete); + const editEventLabel = intl.formatMessage( + { id: 'project_activity.events.tooltip.edit' }, + { event: `${event.category} ${event.name}` }, + ); + const deleteEventLabel = intl.formatMessage( + { id: 'project_activity.events.tooltip.delete' }, + { event: `${event.category} ${event.name}` }, + ); + return (
@@ -53,28 +69,28 @@ function Event(props: Readonly) { {showActions && (
{canChange && ( - - setChanging(true)} - stopPropagation - size="small" - /> - + setChanging(true)} + /> )} {canDelete && ( - - setDeleting(true)} - stopPropagation - size="small" - /> - + setDeleting(true)} + /> )}
)} diff --git a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityAnalysesList.tsx b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityAnalysesList.tsx index c55aec00f8a..e155e6d07ae 100644 --- a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityAnalysesList.tsx +++ b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityAnalysesList.tsx @@ -19,10 +19,11 @@ */ import styled from '@emotion/styled'; +import { Spinner, Text } from '@sonarsource/echoes-react'; import classNames from 'classnames'; import { isEqual } from 'date-fns'; import * as React from 'react'; -import { Badge, HelperHintIcon, LightLabel, Spinner, themeColor } from '~design-system'; +import { Badge, HelperHintIcon, themeColor } from '~design-system'; import Tooltip from '../../../components/controls/Tooltip'; import DateFormatter from '../../../components/intl/DateFormatter'; import { toShortISO8601String } from '../../../helpers/dates'; @@ -120,106 +121,107 @@ export default class ProjectActivityAnalysesList extends React.PureComponent 1 || (byVersionByDay.length === 1 && Object.keys(byVersionByDay[0].byDay).length > 0); - if (this.props.analyses.length === 0 || !hasFilteredData) { - return ( -
- {this.props.initializing ? ( -
- -
- ) : ( -
- {translate('no_results')} -
- )} -
- ); - } + const hasData = analyses.length > 0 && hasFilteredData; return ( -
    (this.scrollContainer = element)} - style={{ - height: 'calc(100vh - 250px)', - marginTop: - this.props.project.qualifier === ComponentQualifier.Project - ? LIST_MARGIN_TOP - : undefined, - }} - > - {newCodePeriod.baselineAnalysisKey !== undefined && - newCodePeriod.firstNewCodeAnalysisKey === undefined && ( - - - {translate('project_activity.new_code_period_start')} - - - - - - )} - - {byVersionByDay.map((version, idx) => { - const days = Object.keys(version.byDay); - if (days.length <= 0) { - return null; - } + <> +
    + + {!hasData && ( +
    + {translate('no_results')} +
    + )} +
    +
    - return ( -
  • - {version.version && ( - + {hasData && ( +
      (this.scrollContainer = element)} + style={{ + height: 'calc(100vh - 250px)', + marginTop: + this.props.project.qualifier === ComponentQualifier.Project + ? LIST_MARGIN_TOP + : undefined, + }} + > + {newCodePeriod.baselineAnalysisKey !== undefined && + newCodePeriod.firstNewCodeAnalysisKey === undefined && ( + + + {translate('project_activity.new_code_period_start')} + - {version.version} + - + )} -
        - {days.map((day) => ( -
      • -
        - -
        -
          - {version.byDay[day]?.map((analysis) => - this.renderAnalysis(analysis, newCodePeriod.firstNewCodeAnalysisKey), + + {byVersionByDay.map((version, idx) => { + const days = Object.keys(version.byDay); + if (days.length <= 0) { + return null; + } + + return ( +
        • + {version.version && ( + -
        • - ))} -
        -
      • - ); - })} - {this.props.analysesLoading && ( -
      • - -
      • + > + + {version.version} + + + )} +
          + {days.map((day) => ( +
        • +
          + +
          +
            + {version.byDay[day]?.map((analysis) => + this.renderAnalysis(analysis, newCodePeriod.firstNewCodeAnalysisKey), + )} +
          +
        • + ))} +
        + + ); + })} + {this.props.analysesLoading && ( +
      • + +
      • + )} +
      )} -
    + ); } } diff --git a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityDateInput.tsx b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityDateInput.tsx index 51b7db8fee5..bef9e20b434 100644 --- a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityDateInput.tsx +++ b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityDateInput.tsx @@ -18,7 +18,7 @@ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ -import { Button } from '@sonarsource/echoes-react'; +import { Button, ButtonGroup, Label } from '@sonarsource/echoes-react'; import * as React from 'react'; import { DateRangePicker, PopupZLevel } from '~design-system'; import { translate } from '../../../helpers/l10n'; @@ -41,7 +41,8 @@ export default class ProjectActivityDateInput extends React.PureComponent render() { return ( -
    + + > {translate('project_activity.reset_dates')} -
    + ); } } diff --git a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityPageFilters.tsx b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityPageFilters.tsx index 0ee0d13708c..08a344243ab 100644 --- a/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityPageFilters.tsx +++ b/server/sonar-web/src/main/js/apps/projectActivity/components/ProjectActivityPageFilters.tsx @@ -18,8 +18,9 @@ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ +import { ButtonGroup, InputSize, Label, Select } from '@sonarsource/echoes-react'; import * as React from 'react'; -import { InputSelect, LabelValueSelectOption } from '~design-system'; +import { LabelValueSelectOption } from '~design-system'; import { isPortfolioLike } from '~sonar-aligned/helpers/component'; import { ComponentQualifier } from '~sonar-aligned/types/component'; import { translate } from '../../../helpers/l10n'; @@ -52,8 +53,8 @@ export default function ProjectActivityPageFilters(props: ProjectActivityPageFil })); const handleCategoryChange = React.useCallback( - (option: { value: string } | null) => { - updateQuery({ category: option ? option.value : '' }); + (option: string | null) => { + updateQuery({ category: option ?? '' }); }, [updateQuery], ); @@ -61,19 +62,19 @@ export default function ProjectActivityPageFilters(props: ProjectActivityPageFil return (
    {!isPortfolioLike(project.qualifier) && ( - handleCategoryChange(data)} - options={options} - placeholder={translate('project_activity.filter_events')} - size="full" - value={options.find((o) => o.value === category)} - classNames={{ - menu: () => 'sw-z-dropdown-menu-page', - }} - /> + + +