Skip to content

Commit 003cf69

Browse files
Giancarlo Mariotmartijnrusschen
Giancarlo Mariot
authored andcommitted
Adding clickable week number feature. (Hacker0x01#936)
* Added optional 'onWeekSelect' prop method that allows for a click action to take place in the week number. * Improving test expectation.
1 parent 63533e5 commit 003cf69

File tree

7 files changed

+74
-4
lines changed

7 files changed

+74
-4
lines changed

src/calendar.jsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ export default class Calendar extends React.Component {
4444
forceShowMonthNavigation: PropTypes.bool,
4545
onDropdownFocus: PropTypes.func,
4646
onSelect: PropTypes.func.isRequired,
47+
onWeekSelect: PropTypes.func,
4748
openToDate: PropTypes.object,
4849
peekNextMonth: PropTypes.bool,
4950
scrollableYearDropdown: PropTypes.bool,
@@ -282,6 +283,7 @@ export default class Calendar extends React.Component {
282283
onDayClick={this.handleDayClick}
283284
onDayMouseEnter={this.handleDayMouseEnter}
284285
onMouseLeave={this.handleMonthMouseLeave}
286+
onWeekSelect={this.props.onWeekSelect}
285287
formatWeekNumber={this.props.formatWeekNumber}
286288
minDate={this.props.minDate}
287289
maxDate={this.props.maxDate}

src/datepicker.jsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ export default class DatePicker extends React.Component {
5050
onBlur: PropTypes.func,
5151
onChange: PropTypes.func.isRequired,
5252
onSelect: PropTypes.func,
53+
onWeekSelect: PropTypes.func,
5354
onClickOutside: PropTypes.func,
5455
onChangeRaw: PropTypes.func,
5556
onFocus: PropTypes.func,
@@ -339,6 +340,7 @@ export default class DatePicker extends React.Component {
339340
selected={this.props.selected}
340341
preSelection={this.state.preSelection}
341342
onSelect={this.handleSelect}
343+
onWeekSelect={this.props.onWeekSelect}
342344
openToDate={this.props.openToDate}
343345
minDate={this.props.minDate}
344346
maxDate={this.props.maxDate}

src/month.jsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ export default class Month extends React.Component {
2222
onDayClick: PropTypes.func,
2323
onDayMouseEnter: PropTypes.func,
2424
onMouseLeave: PropTypes.func,
25+
onWeekSelect: PropTypes.func,
2526
peekNextMonth: PropTypes.bool,
2627
preSelection: PropTypes.object,
2728
selected: PropTypes.object,
@@ -71,6 +72,7 @@ export default class Month extends React.Component {
7172
month={this.props.day.month()}
7273
onDayClick={this.handleDayClick}
7374
onDayMouseEnter={this.handleDayMouseEnter}
75+
onWeekSelect={this.props.onWeekSelect}
7476
formatWeekNumber={this.props.formatWeekNumber}
7577
minDate={this.props.minDate}
7678
maxDate={this.props.maxDate}

src/stylesheets/datepicker.scss

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -148,6 +148,13 @@
148148
line-height: $datepicker__item-size;
149149
text-align: center;
150150
margin: $datepicker__day-margin;
151+
&.react-datepicker__week-number--clickable {
152+
cursor: pointer;
153+
&:hover {
154+
border-radius: $datepicker__border-radius;
155+
background-color: $datepicker__background-color;
156+
}
157+
}
151158
}
152159

153160
.react-datepicker__day-name,

src/week.jsx

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ export default class Week extends React.Component {
1919
month: PropTypes.number,
2020
onDayClick: PropTypes.func,
2121
onDayMouseEnter: PropTypes.func,
22+
onWeekSelect: PropTypes.func,
2223
preSelection: PropTypes.object,
2324
selected: PropTypes.object,
2425
selectingDate: PropTypes.object,
@@ -41,6 +42,12 @@ export default class Week extends React.Component {
4142
}
4243
}
4344

45+
handleWeekClick = (day, weekNumber, event) => {
46+
if (typeof this.props.onWeekSelect === 'function') {
47+
this.props.onWeekSelect(day, weekNumber, event)
48+
}
49+
}
50+
4451
formatWeekNumber = (startOfWeek) => {
4552
if (this.props.formatWeekNumber) {
4653
return this.props.formatWeekNumber(startOfWeek)
@@ -51,8 +58,12 @@ export default class Week extends React.Component {
5158
renderDays = () => {
5259
const startOfWeek = this.props.day.clone().startOf('week')
5360
const days = []
61+
const weekNumber = this.formatWeekNumber(startOfWeek)
5462
if (this.props.showWeekNumber) {
55-
days.push(<WeekNumber key="W" weekNumber={this.formatWeekNumber(startOfWeek)} />)
63+
const onClickAction = this.props.onWeekSelect
64+
? this.handleWeekClick.bind(this, startOfWeek, weekNumber)
65+
: undefined
66+
days.push(<WeekNumber key="W" weekNumber={weekNumber} onClick={onClickAction} />)
5667
}
5768
return days.concat([0, 1, 2, 3, 4, 5, 6].map(offset => {
5869
const day = startOfWeek.clone().add(offset, 'days')

src/week_number.jsx

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,29 @@
11
import React from 'react'
22
import PropTypes from 'prop-types'
3+
import classnames from 'classnames'
34

45
export default class WeekNumber extends React.Component {
56
static propTypes = {
6-
weekNumber: PropTypes.number.isRequired
7+
weekNumber: PropTypes.number.isRequired,
8+
onClick: PropTypes.func
9+
}
10+
11+
handleClick = (event) => {
12+
if (this.props.onClick) {
13+
this.props.onClick(event)
14+
}
715
}
816

917
render () {
18+
const weekNumberClasses = {
19+
'react-datepicker__week-number': true,
20+
'react-datepicker__week-number--clickable': !!this.props.onClick
21+
}
1022
return (
1123
<div
12-
className="react-datepicker__week-number"
13-
aria-label={`week-${this.props.weekNumber}`}>
24+
className={classnames(weekNumberClasses)}
25+
aria-label={`week-${this.props.weekNumber}`}
26+
onClick={this.handleClick}>
1427
{this.props.weekNumber}
1528
</div>
1629
)

test/week_test.js

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,39 @@ describe('Week', () => {
5757
assert(day.prop('day').isSame(dayClicked, 'day'))
5858
})
5959

60+
it('should call the provided onWeekSelect function and pass the first day of the week', () => {
61+
let firstDayReceived = null
62+
63+
function onWeekClick (newFirstWeekDay) {
64+
firstDayReceived = newFirstWeekDay
65+
}
66+
67+
const weekStart = moment('2015-12-20')
68+
const week = shallow(
69+
<Week day={weekStart} showWeekNumber onWeekSelect={onWeekClick} />
70+
)
71+
const weekNumberElement = week.find(WeekNumber)
72+
weekNumberElement.simulate('click')
73+
expect(firstDayReceived.isSame(weekStart)).to.be.true
74+
})
75+
76+
it('should call the provided onWeekSelect function and pass the week number', () => {
77+
let weekNumberReceived = null
78+
79+
function onWeekClick (unused, newWeekNumber) {
80+
weekNumberReceived = newWeekNumber
81+
}
82+
83+
const weekStart = moment('2015-12-20')
84+
const realWeekNumber = parseInt(weekStart.format('w'), 10)
85+
const week = shallow(
86+
<Week day={weekStart} showWeekNumber onWeekSelect={onWeekClick} />
87+
)
88+
const weekNumberElement = week.find(WeekNumber)
89+
weekNumberElement.simulate('click')
90+
expect(weekNumberReceived).to.equal(realWeekNumber)
91+
})
92+
6093
it('should set the week number with the provided formatWeekNumber function', () => {
6194
let firstDayReceived = null
6295

0 commit comments

Comments
 (0)