Skip to content

Commit

Permalink
Fixed an issue with focus management after opening a livechat.
Browse files Browse the repository at this point in the history
  • Loading branch information
tonyanziano committed Aug 28, 2019
1 parent 82dd1c6 commit 488daad
Show file tree
Hide file tree
Showing 5 changed files with 52 additions and 3 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- [1781](https://github.com/microsoft/BotFramework-Emulator/pull/1781)
- [1782](https://github.com/microsoft/BotFramework-Emulator/pull/1782)
- [1783](https://github.com/microsoft/BotFramework-Emulator/pull/1783)
- [1784](https://github.com/microsoft/BotFramework-Emulator/pull/1784)

## v4.5.2 - 2019 - 07 - 17
## Fixed
Expand Down
7 changes: 7 additions & 0 deletions packages/app/client/src/ui/editor/emulator/emulator.spec.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -552,4 +552,11 @@ describe('<EmulatorContainer/>', () => {
expect(mockRemoteCallsMade[2].args).toEqual(['someConvoId', 'someBotId', 'someUserId', 'someDocId']);
expect(mockDispatch).toHaveBeenCalledWith(updateDocument('someDocId', { meta: 'some file info' }));
});

it('should set a restart button ref', () => {
const mockButtonRef: any = {};
instance.setRestartButtonRef(mockButtonRef);

expect(instance.restartButtonRef).toBe(mockButtonRef);
});
});
12 changes: 12 additions & 0 deletions packages/app/client/src/ui/editor/emulator/emulator.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ export class Emulator extends React.Component<EmulatorProps, {}> {
@CommandServiceInstance()
private commandService: CommandServiceImpl;
private conversationInitRequested: boolean;
private restartButtonRef: HTMLButtonElement;

private readonly onVerticalSizeChange = debounce((sizes: SplitterSize[]) => {
this.props.document.ui = {
Expand All @@ -110,6 +111,12 @@ export class Emulator extends React.Component<EmulatorProps, {}> {
return !props.directLine || props.document.conversationId !== (props.directLine as any).conversationId;
}

componentDidMount() {
if (this.restartButtonRef) {
this.restartButtonRef.focus();
}
}

componentWillMount() {
window.addEventListener('keydown', this.keyboardEventListener);
if (this.shouldStartNewConversation()) {
Expand Down Expand Up @@ -292,6 +299,7 @@ export class Emulator extends React.Component<EmulatorProps, {}> {
buttonClass={styles.restartIcon}
options={[NewUserId, SameUserId]}
onClick={this.onStartOverClick}
buttonRef={this.setRestartButtonRef}
/>
<button
className={`${styles.saveIcon} ${styles.toolbarIcon || ''}`}
Expand Down Expand Up @@ -418,6 +426,10 @@ export class Emulator extends React.Component<EmulatorProps, {}> {
this.props.restartDebugSession(conversationId, document.documentId);
};

private setRestartButtonRef = (ref: HTMLButtonElement): void => {
this.restartButtonRef = ref;
};

private readonly keyboardEventListener: EventListener = async (event: KeyboardEvent): Promise<void> => {
// Meta corresponds to 'Command' on Mac
const ctrlOrCmdPressed = event.getModifierState('Control') || event.getModifierState('Meta');
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,13 @@ describe('<SplitButton>', () => {
expect(node.html()).not.toBe(null);
});

it('should pass the primary button ref to the buttonRef prop', () => {
const mockButtonRef = jest.fn(() => null);
wrapper = mount(<SplitButton buttonRef={mockButtonRef} />);

expect(mockButtonRef).toHaveBeenCalledWith(jasmine.any(HTMLButtonElement));
});

it('should set a caret button ref', () => {
const mockCaretRef = "I'm a caret button!";
instance.setCaretRef(mockCaretRef);
Expand Down
28 changes: 25 additions & 3 deletions packages/sdk/ui-react/src/widget/splitButton/splitButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ export interface SplitButtonProps {
onChange?: (newValue: string) => any;
onClick?: (value: string) => any;
options?: string[];
buttonRef?: (ref: HTMLButtonElement) => void;
selected?: number;
}

Expand All @@ -66,13 +67,27 @@ export class SplitButton extends React.Component<SplitButtonProps, SplitButtonSt
public render(): JSX.Element {
const { buttonClass = '', defaultLabel = '', disabled = false, options = [] } = this.props;
const { expanded, selected } = this.state;
const { caretRef, hidePanel, onClickOption, onClickDefault, onClickCaret, onKeyDown, setCaretRef } = this;
const {
caretRef,
hidePanel,
onClickOption,
onClickDefault,
onClickCaret,
onKeyDown,
setButtonRef,
setCaretRef,
} = this;
const expandedClass = expanded ? ` ${styles.expanded}` : '';

return (
<>
<div className={styles.container}>
<button className={`${styles.defaultButton} ${buttonClass}`} disabled={disabled} onClick={onClickDefault}>
<button
className={`${styles.defaultButton} ${buttonClass}`}
disabled={disabled}
onClick={onClickDefault}
ref={setButtonRef}
>
<span>{defaultLabel}</span>
</button>
<div className={styles.separator} />
Expand All @@ -97,6 +112,13 @@ export class SplitButton extends React.Component<SplitButtonProps, SplitButtonSt
);
}

private setButtonRef = (ref: HTMLButtonElement): void => {
const { buttonRef } = this.props;
if (buttonRef && ref) {
buttonRef(ref);
}
};

private setCaretRef = (ref: HTMLButtonElement): void => {
this.caretRef = ref;
};
Expand All @@ -107,7 +129,7 @@ export class SplitButton extends React.Component<SplitButtonProps, SplitButtonSt
this.setState({ expanded: !expanded, selected: 0 });
};

private onClickDefault = (e: React.SyntheticEvent<HTMLButtonElement>): void => {
private onClickDefault = (_e: React.SyntheticEvent<HTMLButtonElement>): void => {
const { onClick, options = [] } = this.props;
if (onClick && options.length) {
onClick(options[0]);
Expand Down

0 comments on commit 488daad

Please sign in to comment.