Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SHIBA-2119] Added Optional Height Prop for Scrollable Calendar #3057

Merged
merged 10 commits into from
Nov 7, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions examples/bpk-component-scrollable-calendar/examples.js
Original file line number Diff line number Diff line change
Expand Up @@ -136,6 +136,24 @@ const DefaultExample = () => (
/>
);

const DefaultExampleWithCustomHeight = () => (
<ScrollableCal
weekStartsOn={1}
daysOfWeek={weekDays}
formatMonth={formatMonth}
formatDateFull={formatDateFull}
DateComponent={BpkScrollableCalendarDate}
minDate={new Date(2020, 3, 1)}
maxDate={new Date(2020, 6, 1)}
selectionConfiguration={{
type: CALENDAR_SELECTION_TYPE.single,
date: new Date(2020, 3, 15),
}}
customRowHeight={3}
/>
);


const RangeExample = () => (
<ScrollableCal
weekStartsOn={1}
Expand Down Expand Up @@ -349,6 +367,7 @@ const PastCalendarExample = () => (

export {
DefaultExample,
DefaultExampleWithCustomHeight,
RangeExample,
SplitWeekRangeExample,
WeekStartsOnSixExample,
Expand Down
7 changes: 7 additions & 0 deletions examples/bpk-component-scrollable-calendar/stories.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ import {
PastCalendarExample,
RangeExample,
SplitWeekRangeExample,
DefaultExampleWithCustomHeight,
} from './examples';

export default {
Expand Down Expand Up @@ -92,6 +93,12 @@ VisualTestWithZoom.args = {
zoomEnabled: true
};

export const VisualTestWithCustomHeight = DefaultExampleWithCustomHeight;
export const VisualTestWithCustomHeightWithZoom = VisualTestWithCustomHeight.bind({});
VisualTestWithCustomHeightWithZoom.args = {
zoomEnabled: true
};

export const VisualTestRange = RangeExample;
export const VisualTestRangeWithZoom = VisualTestRange.bind({});
VisualTestRangeWithZoom.args = {
Expand Down
3 changes: 3 additions & 0 deletions packages/bpk-component-calendar/src/BpkCalendarContainer.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ export type Props = {
initiallyFocusedDate?: Date | null;
markToday?: boolean;
markOutsideDays?: boolean;
customRowHeight?: number;
};
type InjectedProps = {
onDateClick: ((date: Date) => void) | null;
Expand Down Expand Up @@ -105,6 +106,7 @@ declare const withCalendarState: <P extends object>(Calendar: ComponentType<P>)
initiallyFocusedDate: null;
markToday: boolean;
markOutsideDays: boolean;
customRowHeight?: number;
};
contextType?: import("react").Context<any> | undefined;
};
Expand Down Expand Up @@ -157,6 +159,7 @@ declare const _default: {
initiallyFocusedDate: null;
markToday: boolean;
markOutsideDays: boolean;
customRowHeight?: number;
};
contextType?: import("react").Context<any> | undefined;
};
Expand Down
4 changes: 4 additions & 0 deletions packages/bpk-component-calendar/src/BpkCalendarContainer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,10 @@ export type Props = {
initiallyFocusedDate?: Date | null;
markToday?: boolean;
markOutsideDays?: boolean;
/**
* Sets the height of month rows in 'rem' units. If not specified, the default value of `2.75rem` will be used.
*/
customRowHeight?: number;
};

type InjectedProps = {
Expand Down
1 change: 1 addition & 0 deletions packages/bpk-component-calendar/src/composeCalendar.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ export type Props = {
preventKeyboardFocus?: boolean;
selectionConfiguration?: SelectionConfiguration;
gridClassName?: string | null;
customRowHeight?: number;
/**
* Key to be used to pick the desired weekDay format from the `daysOfWeek` object, for example: `nameAbbr` or `nameNarrow`.
*/
Expand Down
6 changes: 6 additions & 0 deletions packages/bpk-component-calendar/src/composeCalendar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,10 @@ export type Props = {
preventKeyboardFocus?: boolean;
selectionConfiguration?: SelectionConfiguration;
gridClassName?: string | null;
/**
* Sets the height of month rows in 'rem' units. If not specified, the default value of `2.75rem` will be used.
*/
customRowHeight?: number;
/**
* Key to be used to pick the desired weekDay format from the `daysOfWeek` object, for example: `nameAbbr` or `nameNarrow`.
*/
Expand Down Expand Up @@ -116,6 +120,7 @@ const composeCalendar = (
const BpkCalendar = ({
changeMonthLabel = null,
className = null,
customRowHeight,
dateModifiers = {},
dateProps = {},
daysOfWeek,
Expand Down Expand Up @@ -216,6 +221,7 @@ const composeCalendar = (
className={gridClasses.join(' ')}
dateProps={dateProps}
selectionConfiguration={selectionConfiguration}
customRowHeight={customRowHeight}
{...gridProps}
/>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,22 @@ describe('BpkCalendarScrollGridList', () => {
expect(asFragment()).toMatchSnapshot();
});

it('should render correctly with a custom "customRowHeight" attribute', () => {
const { asFragment } = render(
<BpkScrollableCalendarGridList
minDate={DateUtils.addDays(testDate, -1)}
maxDate={DateUtils.addMonths(testDate, 12)}
month={testDate}
formatMonth={formatMonth}
formatDateFull={formatDateFull}
DateComponent={BpkCalendarScrollDate}
weekStartsOn={0}
customRowHeight={3}
/>,
);
expect(asFragment()).toMatchSnapshot();
});

it('should render correctly with a custom date component', () => {
const MyCustomDate = (props: any) => {
const cx = {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ type Props = Partial<BpkCalendarGridProps> & {
focusedDate?: Date | null;
selectionConfiguration?: SelectionConfiguration;
className?: string | null;
customRowHeight?: number;
};
declare const BpkScrollableCalendarGridList: (props: Props) => JSX.Element;
export default BpkScrollableCalendarGridList;
Original file line number Diff line number Diff line change
Expand Up @@ -36,16 +36,11 @@ import { getMonthsArray, getMonthItemHeights } from './utils';
const getClassName = cssModules(STYLES);

// These constants are here to facilitate calculating the height
// Row and month item heights are defined in rem to support text scaling
const ROW_HEIGHT = 2.75;
// This is the additional height of each grid without any rows.
const BASE_MONTH_ITEM_HEIGHT = 8.125;
const COLUMN_COUNT = 7;
// Most browsers have by default 16px root font size
const DEFAULT_ROOT_FONT_SIZE = 16;
// Most calendar grids have 5 rows. Calculate height in px as this is what react-window expects.
const ESTIMATED_MONTH_ITEM_HEIGHT =
(BASE_MONTH_ITEM_HEIGHT + 5 * ROW_HEIGHT) * DEFAULT_ROOT_FONT_SIZE;
// Minimum month item width (useful for server-side rendering. This value will be overridden with an accurate width after mounting)
const ESTIMATED_MONTH_ITEM_WIDTH = BASE_MONTH_ITEM_HEIGHT * 7 * DEFAULT_ROOT_FONT_SIZE;

Expand All @@ -60,11 +55,16 @@ type Props = Partial<BpkCalendarGridProps> & {
focusedDate?: Date | null;
selectionConfiguration?: SelectionConfiguration;
className?: string | null;
/**
* Sets the height of month rows in 'rem' units. If not specified, the default value of `2.75rem` will be used.
*/
customRowHeight?: number;
Copy link
Contributor

@anambl anambl Nov 7, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might be worth adding a JSDOC comment to specify this value should be in rem - and same with the other components where this is part of the API. That's gonna reflect in the Storybook API docs then too automatically!

Copy link
Contributor Author

@AsimAM AsimAM Nov 7, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks - I opted for regular comments instead of JSDOC comments due to consistency (a lot of the other props are being specified by regular comments) and it would look odd to have JSDoc for a singular prop. But happy to change it if it is still the preference.

Screenshot 2023-11-07 at 12 38 56

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

no, that's totally fine!

};

const BpkScrollableCalendarGridList = (props: Props) => {
const {
className = null,
customRowHeight = 2.75,
focusedDate = null,
minDate,
selectionConfiguration,
Expand All @@ -75,6 +75,12 @@ const BpkScrollableCalendarGridList = (props: Props) => {
const endDate = startOfDay(startOfMonth(rest.maxDate));
const monthsCount = DateUtils.differenceInCalendarMonths(endDate, startDate);

// Row and month item heights are defined in rem to support text scaling
const rowHeight = customRowHeight;
// Most calendar grids have 5 rows. Calculate height in px as this is what react-window expects.
const estimatedMonthItemHeight =
(BASE_MONTH_ITEM_HEIGHT + 5 * rowHeight) * DEFAULT_ROOT_FONT_SIZE;

const getInitialRootFontSize = () =>
parseFloat(getComputedStyle(document.documentElement).fontSize) ||
DEFAULT_ROOT_FONT_SIZE;
Expand All @@ -94,7 +100,7 @@ const BpkScrollableCalendarGridList = (props: Props) => {
months,
rest.weekStartsOn,
COLUMN_COUNT,
ROW_HEIGHT * rootFontSize,
rowHeight * rootFontSize,
BASE_MONTH_ITEM_HEIGHT * rootFontSize,
),
[rootFontSize, months, rest.weekStartsOn],
Expand All @@ -111,7 +117,7 @@ const BpkScrollableCalendarGridList = (props: Props) => {
typeof document !== 'undefined' ? document.querySelector('html') : {};

const getItemSize = (index: number) =>
monthItemHeights[index] || ESTIMATED_MONTH_ITEM_HEIGHT;
monthItemHeights[index] || estimatedMonthItemHeight;

const rowRenderer = ({ index, style }: { index: number; style: {} }) => (
<div style={style}>
Expand Down Expand Up @@ -158,7 +164,7 @@ const BpkScrollableCalendarGridList = (props: Props) => {
>
<AutoSizer
onResize={onResize}
defaultHeight={ESTIMATED_MONTH_ITEM_HEIGHT}
defaultHeight={estimatedMonthItemHeight}
defaultWidth={ESTIMATED_MONTH_ITEM_WIDTH}
>
{({ height, width }: { height: number | string, width: number | string}) => (
Expand All @@ -170,7 +176,7 @@ const BpkScrollableCalendarGridList = (props: Props) => {
}
width={width}
height={height}
estimatedItemSize={ESTIMATED_MONTH_ITEM_HEIGHT}
estimatedItemSize={estimatedMonthItemHeight}
itemSize={getItemSize}
itemCount={months.length}
overscanCount={1}
Expand Down
Loading
Loading