1

I want to show year component only in a NSDatePicker.

I tried set/add NSDateFormatter to NSDatePicker, but with no luck. (By dragging a NSDateFormatter to NSDatePicker in nib)

Is there any way to achieve this without subclassing NSDatePicker or NSTextField? Thank you!

rmaddy
  • 314,917
  • 42
  • 532
  • 579
Zhigang An
  • 296
  • 2
  • 13
  • 2
    If it's just a column of year numbers, in what sense is this about "dates" at all? You're just picking an integer from a list of integers. There is no need of a date picker for that. – matt Dec 21 '16 at 01:17
  • I think this [Show year in NSDatePicker](http://stackoverflow.com/questions/12017791/uidatepicker-to-show-year-only) link will helpful for you checked it. – amit_donga Dec 21 '16 at 05:52

3 Answers3

2

After diving into Apple's Documentation, I found the solution and want to post it here, in case it is useful for someone else.

No need to subclass NSDatePicker, there is a method - (void)setDatePickerElements:(NSDatePickerElementFlags)elementFlags which specifies which element the date picker would display. elementFlags is a constant, defined by a enum as:

enum {
   NSHourMinuteDatePickerElementFlag       = 0x000c,
   NSHourMinuteSecondDatePickerElementFlag = 0x000e,
   NSTimeZoneDatePickerElementFlag         = 0x0010,
   NSYearMonthDatePickerElementFlag        = 0x00c0,
   NSYearMonthDayDatePickerElementFlag     = 0x00e0,
   NSEraDatePickerElementFlag              = 0x0100,
};
typedef NSUInteger NSDatePickerElementFlags;

When looking at those constants, I find it is just a bit mask. Bit place and the corresponding calendar elements is as follows:

15 - 9 bit: Unknown. Maybe unused.

8 bit: Era. (Would not display anything if has a 4-digit year format.)

7 bit: Year.

6 bit: Month.

5 bit: Day.

4 bit: Time zone.

3 bit: Hour.

2 bit: Minute.

1 bit: second.

0 bit: Unknown. Maybe millisecond, or unused.

So, the following line would give me a year only date picker:

[_yearOnlyDatePicker setDatePickerElements:0x0080];

_yearOnlyPicker is an instance of NSDatePicker.


Here is the result:

How yearOnlyDatePicker looks like in Interface Builder:

In interface builder.

How yearOnlyDatePicker looks like when running the app:

When running the app.

Zhigang An
  • 296
  • 2
  • 13
  • This does not work in OS X 10.11 or later. OS X 10.10 not tested. But it does work for OS X 10.9 or earlier. – Zhigang An Dec 26 '16 at 05:44
1

It is easy you don't need to use NSDatePicker. All you have to do is create a range of years you want and use it as datasource for normal picker.

for (int i=1900; i<=currentYear; i++) {
  [_yourDataSourceArr addObject:[NSString stringWithFormat:@"%d",i]];
}
GeneCode
  • 7,545
  • 8
  • 50
  • 85
1

-[NSDatePicker setDatePickerElements:] can no longer be tricked into showing year only.

A year-only NSDatePicker can be obtained by configuring a year-month picker and subclassing NSDatePickerCell to prevent it from creating the month and separator fields:

- (void)_addSubfieldForElement:(int)arg1 withDateFormat:(id)arg2 referenceStrings:(id)arg3
{
    if ((arg1 == 6) || (arg1 == 100)) {
        return;
    }

    [super _addSubfieldForElement:arg1 withDateFormat:arg2 referenceStrings:arg3]; // Private API
}

Please file bug reports with Apple to request a year-only variant of NSDatePicker. I also requested a week-of-year picker.

Pierre Bernard
  • 3,148
  • 2
  • 23
  • 31
  • I'm considering file a bug with Apple. But I guess Apple just want us do it by subclassing either NSDatePicker or NSTextField + stepper button. – Zhigang An Jul 17 '18 at 16:44