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

[release/1.x] Close dateinput popover #2093

Merged
merged 10 commits into from
Feb 15, 2018
27 changes: 18 additions & 9 deletions packages/datetime/src/dateInput.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -185,7 +185,7 @@ export class DateInput extends AbstractComponent<IDateInputProps, IDateInputStat

private inputRef: HTMLElement = null;
private contentRef: HTMLElement = null;
private lastPopoverElement: HTMLElement = null;
private lastElementInPopover: HTMLElement = null;

public constructor(props?: IDateInputProps, context?: any) {
super(props, context);
Expand Down Expand Up @@ -478,8 +478,13 @@ export class DateInput extends AbstractComponent<IDateInputProps, IDateInputStat
this.safeInvokeInputProp("onKeyDown", e);
};

// blur DOM event listener (not React event)
private handlePopoverBlur = () => this.handleClosePopover();
// keyboard DOM event listener (not React event)
private handlePopoverBlur = (e: KeyboardEvent) => {
if (e.which === Keys.TAB && !e.shiftKey) {
e.target.dispatchEvent(new FocusEvent("blur"));
Copy link
Contributor

Choose a reason for hiding this comment

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

why? this is suspicious. we're not in the habit of dispatching DOM events from blueprint code (except where absolutely necessary in tests).

this.handleClosePopover();
}
};

private registerPopoverBlurHandler = () => {
if (this.contentRef != null) {
Expand All @@ -488,19 +493,23 @@ export class DateInput extends AbstractComponent<IDateInputProps, IDateInputStat
const tabbableElements = this.contentRef.querySelectorAll("input, [tabindex]:not([tabindex='-1'])");
Copy link
Contributor

Choose a reason for hiding this comment

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

note to self / @giladgray: we'll need to update this for dom4 v2

Copy link
Contributor

Choose a reason for hiding this comment

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

this is already updated. queryAll was removed.

const numOfElements = tabbableElements.length;
if (numOfElements > 0) {
const lastPopoverElement = tabbableElements[numOfElements - 1] as HTMLElement;
if (this.lastPopoverElement !== lastPopoverElement) {
// Keep track of the last focusable element in popover and add
// a keydown handler, so that:
// * popover closes when the user tabs to the next element
// * or focus moves to previous element if shift+tab
Copy link
Contributor

Choose a reason for hiding this comment

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

something is wrong with the language in this comment. it doesn't parse correctly.

i think "popover closes:" belongs after "so that", but then the second bullet sounds incorrect.

const lastElement = tabbableElements[numOfElements - 1] as HTMLElement;
if (this.lastElementInPopover !== lastElement) {
this.unregisterPopoverBlurHandler();
this.lastPopoverElement = lastPopoverElement;
this.lastPopoverElement.addEventListener("blur", this.handlePopoverBlur);
this.lastElementInPopover = lastElement;
this.lastElementInPopover.addEventListener("keydown", this.handlePopoverBlur);
}
}
}
};

private unregisterPopoverBlurHandler = () => {
if (this.lastPopoverElement) {
this.lastPopoverElement.removeEventListener("blur", this.handlePopoverBlur);
if (this.lastElementInPopover != null) {
this.lastElementInPopover.removeEventListener("keydown", this.handlePopoverBlur);
}
};

Expand Down