Skip to content

Commit

Permalink
feat(icon-button): Implement isRTL helper library, and refactor icon-…
Browse files Browse the repository at this point in the history
…button to use it.

PiperOrigin-RevId: 471352106
  • Loading branch information
dfreedm authored and copybara-github committed Aug 31, 2022
1 parent ce24805 commit 5dd43fa
Show file tree
Hide file tree
Showing 4 changed files with 62 additions and 13 deletions.
18 changes: 18 additions & 0 deletions controller/is-rtl.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
/**
* @license
* Copyright 2022 Google LLC
* SPDX-License-Identifier: Apache-2.0
*/

/**
* Returns `true` if the given element is in a right-to-left direction.
*
* @param el Element to determine direction from
* @param shouldCheck Optional. If `false`, return `false` without checking
* direction. Determining the direction of `el` is somewhat expensive, so
* this parameter can be used as a conditional guard. Defaults to `true`.
*/
export function isRtl(el: HTMLElement, shouldCheck = true) {
return shouldCheck &&
getComputedStyle(el).getPropertyValue('direction').trim() === 'rtl';
}
34 changes: 34 additions & 0 deletions controller/is-rtl_test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import 'jasmine';

import {isRtl} from './is-rtl.js';

function setDirection(node: HTMLElement, rtl: boolean) {
node.dir = rtl ? 'rtl' : 'ltr';
}

describe('isRtl', () => {
let testDiv: HTMLElement;

beforeEach(() => {
// reset document direction
setDirection(document.documentElement, false);
testDiv = document.createElement('div');
document.body.appendChild(testDiv);
});

afterEach(() => {
document.body.removeChild(testDiv);
});

it('returns the direction of a given node', () => {
expect(isRtl(testDiv)).toEqual(false);
setDirection(testDiv, true);
expect(isRtl(testDiv)).toEqual(true);
});

it('does not check direction if `shouldCheck` is false', () => {
expect(isRtl(testDiv, false)).toEqual(false);
setDirection(testDiv, true);
expect(isRtl(testDiv, false)).toEqual(false);
});
});
9 changes: 7 additions & 2 deletions iconbutton/icon-button_test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,10 @@ const ICON_BUTTON_TOGGLE_TEMPLATE = html`
</md-standard-icon-button-toggle>
`;

interface IconButtonInternals {
flipIcon: boolean;
}

describe('icon button tests', () => {
const env = new Environment();

Expand Down Expand Up @@ -166,7 +170,7 @@ describe('icon button tests', () => {
env.render(template).querySelector('md-standard-icon-button')!;
await env.waitForStability();

expect(element.flipIcon).toBeTrue();
expect((element as unknown as IconButtonInternals).flipIcon).toBeTrue();
});

it('if `flipsIconInRtl=true`, does not flip icon in an LTR context',
Expand All @@ -181,7 +185,8 @@ describe('icon button tests', () => {
env.render(template).querySelector('md-standard-icon-button')!;
await env.waitForStability();

expect(element.flipIcon).toBeFalse();
expect((element as unknown as IconButtonInternals).flipIcon)
.toBeFalse();
});
});

Expand Down
14 changes: 3 additions & 11 deletions iconbutton/lib/icon-button.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import '@material/web/focus/focus-ring.js';
import '@material/web/icon/icon.js';

import {ActionElement, BeginPressConfig, EndPressConfig} from '@material/web/actionelement/action-element.js';
import {isRtl} from '@material/web/controller/is-rtl.js';
import {ariaProperty} from '@material/web/decorators/aria-property.js';
import {pointerPress, shouldShowStrongFocus} from '@material/web/focus/strong-focus.js';
import {MdRipple} from '@material/web/ripple/ripple.js';
Expand All @@ -26,7 +27,7 @@ export abstract class IconButton extends ActionElement {

@property({type: Boolean}) flipIconInRtl = false;

@property({type: Boolean}) flipIcon = false;
@state() protected flipIcon: boolean = isRtl(this, this.flipIconInRtl);

/** @soyPrefixAttribute */
@ariaProperty // tslint:disable-line:no-new-decorators
Expand Down Expand Up @@ -106,19 +107,10 @@ export abstract class IconButton extends ActionElement {
}

override connectedCallback() {
this.maybeFlipIconInRtl();

this.flipIcon = isRtl(this, this.flipIconInRtl);
super.connectedCallback();
}

private maybeFlipIconInRtl() {
if (!this.flipIconInRtl) return;

const isRtl =
getComputedStyle(this).getPropertyValue('direction') === 'rtl';
this.flipIcon = isRtl;
}

override beginPress({positionEvent}: BeginPressConfig) {
this.ripple.beginPress(positionEvent);
}
Expand Down

0 comments on commit 5dd43fa

Please sign in to comment.