Add counter to filter (#14108)

See figma
https://www.figma.com/design/xt8O9mFeLl46C5InWwoMrN/Twenty?node-id=70822-35001&m=dev

<img width="75" height="61" alt="Capture d’écran 2025-08-27 à 16 57
46"
src="https://github.com/user-attachments/assets/e41290c8-3ec5-4d64-a5d2-d52bd14ccd57"
/>
<img width="75" height="61" alt="Capture d’écran 2025-08-27 à 16 57
58"
src="https://github.com/user-attachments/assets/710d5735-c256-47fc-ad2f-93e4f72b8002"
/>
<img width="121" height="89" alt="Capture d’écran 2025-08-27 à 16 16
33"
src="https://github.com/user-attachments/assets/0c8216b2-f251-4f0e-ad9f-f3a25229df40"
/>



https://github.com/user-attachments/assets/43156c0c-91b8-4386-a971-e37577e3c199
This commit is contained in:
Thomas Trompette
2025-08-27 17:25:18 +02:00
committed by GitHub
parent 58db0c9b0a
commit e449e69f4c
10 changed files with 198 additions and 24 deletions
@@ -0,0 +1,37 @@
import styled from '@emotion/styled';
const StyledFilterCounter = styled.div<{
backgroundColor: string;
textColor: string;
}>`
align-items: center;
background: ${({ backgroundColor }) => backgroundColor};
border-radius: 50%;
color: ${({ textColor }) => textColor};
display: flex;
font-size: ${({ theme }) => theme.font.size.xxs};
font-weight: ${({ theme }) => theme.font.weight.semiBold};
height: 12px;
justify-content: center;
width: 12px;
left: -3px;
position: absolute;
top: -3px;
z-index: 1;
`;
type WorkflowStepFilterCounterProps = {
backgroundColor: string;
textColor: string;
counter: number;
};
export const WorkflowStepFilterCounter = ({
backgroundColor,
textColor,
counter,
}: WorkflowStepFilterCounterProps) => (
<StyledFilterCounter backgroundColor={backgroundColor} textColor={textColor}>
{counter}
</StyledFilterCounter>
);
@@ -0,0 +1,28 @@
import { WorkflowStepFilterCounter } from '@/workflow/workflow-steps/workflow-actions/filter-action/components/WorkflowStepFilterCounter';
import { type Meta, type StoryObj } from '@storybook/react';
import { expect, within } from '@storybook/test';
import { ComponentDecorator } from 'twenty-ui/testing';
import { THEME_LIGHT } from 'twenty-ui/theme';
const meta: Meta<typeof WorkflowStepFilterCounter> = {
title: 'Modules/Workflow/Actions/Filter/WorkflowStepFilterCounter',
component: WorkflowStepFilterCounter,
decorators: [ComponentDecorator],
};
export default meta;
type Story = StoryObj<typeof WorkflowStepFilterCounter>;
export const Default: Story = {
args: {
counter: 1,
backgroundColor: THEME_LIGHT.border.color.strong,
textColor: THEME_LIGHT.font.color.inverted,
},
play: async ({ canvasElement }) => {
const canvas = within(canvasElement);
expect(await canvas.findByText('1')).toBeVisible();
},
};
@@ -0,0 +1,25 @@
import { useRecoilComponentValue } from '@/ui/utilities/state/component-state/hooks/useRecoilComponentValue';
import { createStepSelector } from '@/workflow/states/selectors/stepSelector';
import { useMemo } from 'react';
import { isDefined } from 'twenty-shared/utils';
export const useFilterCounter = ({ stepId }: { stepId: string }) => {
const stepSelector = useMemo(() => createStepSelector(stepId), [stepId]);
const step = useRecoilComponentValue(stepSelector);
if (!isDefined(step)) {
return {
filterCounter: 0,
};
}
if (step.type === 'FILTER' && isDefined(step.settings?.input?.stepFilters)) {
return {
filterCounter: step.settings.input.stepFilters.length,
};
}
return {
filterCounter: 0,
};
};