Conversation
|
|
||
| export default Ember.Component.extend(MDCComponent, { | ||
| //region Attributes | ||
| /** |
There was a problem hiding this comment.
What does the @private signify, given that it's within Attributes which are usually public?
There was a problem hiding this comment.
The attribute scrolling only ever gets used inside mdc-tab-bar-scroller.hbs, where it gets passed into {{mdc-tab-bar}} as true. In that sense yes it's an attribute, but I marked it as private because this isn't something the user should ever be passing on their own into the {{mdc-tab-bar}}, it's handled internally by the code.
| }, | ||
| didInsertElement() { | ||
| this._super(...arguments); | ||
| if (get(this, 'scrolling')) { |
There was a problem hiding this comment.
It seems like you might want to gate this based on the presence of the action instead of scrolling.
There was a problem hiding this comment.
Yeah that's a good idea. If I do this then I no longer need the scrolling attribute also.
| }, | ||
| willDestroyElement() { | ||
| this._super(...arguments); | ||
| if (get(this, 'scrolling')) { |
There was a problem hiding this comment.
It seems like you might want to gate this based on the presence of the action instead of scrolling.
| }, | ||
| didInsertElement() { | ||
| this._super(...arguments); | ||
| set(this, 'scrollFrameElement', getElementProperty(this, 'querySelector')(strings.FRAME_SELECTOR)); |
There was a problem hiding this comment.
Please be sure to have a fallback for getElementProperty when it's supposed to return a function. Example:
getElementProperty(this, 'querySelector', () => null)(strings.FRAME_SELECTOR)| CLASS_NAMES: cssClasses, | ||
|
|
||
| /** | ||
| * @type {Object} |
There was a problem hiding this comment.
I believe these should be @property not @type, and should be HTMLElement instead of Object.
There was a problem hiding this comment.
I can make this change but just to double-check, was this also supposed to apply to mdc-menu.js as well? We have a property there that uses @type {HTMLElement} instead of @property.
There was a problem hiding this comment.
Whoops! Those should eventually be fixed, but they shouldn't block this PR.
| removeClassFromForwardIndicator: (className) => run(() => get(this, 'forwardIndicatorClasses').removeObject(className)), | ||
| addClassToBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').addObject(className)), | ||
| removeClassFromBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').removeObject(className)), | ||
| isRTL: () => getElementProperty(this, 'direction') === 'rtl', |
There was a problem hiding this comment.
I believe you want to get dir, not direction. Alternatively, you can do getComputedStyle for the CSS direction.
| addClassToBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').addObject(className)), | ||
| removeClassFromBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').removeObject(className)), | ||
| isRTL: () => getElementProperty(this, 'direction') === 'rtl', | ||
| registerBackIndicatorClickHandler: (handler) => get(this, 'backIndicatorElement').addEventListener('click', handler), |
There was a problem hiding this comment.
I'm not sure if this will happen or not, but I have a concern:
If the back indicator element is un-rendered and re-rendered as a different DOM element by Ember after the click handler was registered, then it will no longer have a click event listener attached. This is bad, and should be avoided.
If this is a problem, I see two ways to avoid it:
- Store the back indicator element click handlers in the component JS, and re-attach them every time on
didRender - Store the back indicator element click handlers in the component JS, and use the
clickEmber hook for the whole component, firing off each back indicator element click handler if the event'stargetwas the back indicator element.
I think I'd prefer the latter of those two, and I'm not sure that list is exhaustive.
There was a problem hiding this comment.
This applies to the other register/deregisterHandler methods that apply listeners directly to the elements, too.
There was a problem hiding this comment.
I'm not sure I understand-- why would the back indicator element ever be un-rendered without the entire component itself being un-rendered?
There was a problem hiding this comment.
You're completely right, it wouldn't be. This was only a risk if there was a boolean around the indicators or something, which there's clearly not.
| removeClassFromForwardIndicator: (className) => run(() => get(this, 'forwardIndicatorClasses').removeObject(className)), | ||
| addClassToBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').addObject(className)), | ||
| removeClassFromBackIndicator: (className) => run(() => get(this, 'backIndicatorClasses').removeObject(className)), | ||
| isRTL: () => getComputedStyle(get(this, 'element')).getPropertyValue('direction') === 'rtl', |
There was a problem hiding this comment.
It seems like this might run the risk of this.element being missing because the component has been destroyed -- probably safest to change it to something like:
!!this && !get(this, 'isDestroyed') && !!get(this, 'element') && getComputedStyle(get(this, 'element')).getPropertyValue('direction') === 'rtl'| }, | ||
| willDestroyElement() { | ||
| this._super(...arguments); | ||
| if (get(this, 'deregister-tab-bar')) { |
There was a problem hiding this comment.
You won't have to wrap this or the other in an if if you add a default for deregister-tab-bar in the Attributes region.
|
Thank you so much for the PR! This will ship out soon with v0.0.35 👍 |
Material Design Tab Bar Scroller component is now available for use in Ember Material Components Web. This component acts as a parent container for
mdc-tab-barby invoking an instance of it inside its Handlebars.Example implementation: