Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 (function() { | 5 (function() { |
| 6 'use strict'; | 6 'use strict'; |
| 7 | 7 |
| 8 /** | 8 /** |
| 9 * Moves |target| element above |anchor| element, in order to match the | 9 * Moves |target| element above |anchor| element, in order to match the |
| 10 * bottom lines. | 10 * bottom lines. |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 74 type: Boolean, | 74 type: Boolean, |
| 75 value: false, | 75 value: false, |
| 76 notify: true | 76 notify: true |
| 77 }, | 77 }, |
| 78 | 78 |
| 79 /** | 79 /** |
| 80 * The audio volume. 0 is silent, and 100 is maximum loud. | 80 * The audio volume. 0 is silent, and 100 is maximum loud. |
| 81 */ | 81 */ |
| 82 volume: { | 82 volume: { |
| 83 type: Number, | 83 type: Number, |
| 84 notify: true | 84 notify: true, |
| 85 reflectToAttribute: true, | |
| 86 observer: 'volumeChanged_' | |
| 85 }, | 87 }, |
| 86 | 88 |
| 87 /** | 89 /** |
| 88 * Whether the expanded button is ON. | 90 * Whether the expanded button is ON. |
| 89 */ | 91 */ |
| 90 expanded: { | 92 expanded: { |
| 91 type: Boolean, | 93 type: Boolean, |
| 92 value: false, | 94 value: false, |
| 93 notify: true | 95 notify: true |
| 94 }, | 96 }, |
| 95 | 97 |
| 96 /** | 98 /** |
| 97 * Whether the volume slider is expanded or not. | |
| 98 */ | |
| 99 volumeSliderShown: { | |
| 100 type: Boolean, | |
| 101 value: false, | |
| 102 observer: 'volumeSliderShownChanged', | |
| 103 notify: true | |
| 104 }, | |
| 105 | |
| 106 /** | |
| 107 * Whether the knob of time slider is being dragged. | 99 * Whether the knob of time slider is being dragged. |
| 108 */ | 100 */ |
| 109 dragging: { | 101 dragging: { |
| 110 type: Boolean, | 102 type: Boolean, |
| 111 value: false, | 103 value: false, |
| 112 notify: true | 104 notify: true |
| 113 }, | 105 }, |
| 114 | 106 |
| 115 /** | 107 /** |
| 116 * Dictionary which contains aria-labels for each controls. | 108 * Dictionary which contains aria-labels for each controls. |
| 117 */ | 109 */ |
| 118 ariaLabels: { | 110 ariaLabels: { |
| 119 type: Object, | 111 type: Object, |
| 120 observer: 'ariaLabelsChanged_' | 112 observer: 'ariaLabelsChanged_' |
| 121 } | 113 } |
| 122 }, | 114 }, |
| 123 | 115 |
| 124 /** | 116 /** |
| 125 * Initializes an element. This method is called automatically when the | 117 * Initializes an element. This method is called automatically when the |
| 126 * element is ready. | 118 * element is ready. |
| 127 */ | 119 */ |
| 128 ready: function() { | 120 ready: function() { |
| 129 var onFocusoutBound = this.onVolumeControllerFocusout_.bind(this); | 121 var timeSlider = /** @type {PaperSliderElement} */ (this.$.timeSlider); |
| 130 | 122 timeSlider.addEventListener('value-change', function() { |
|
yawano
2015/12/01 07:51:31
value-change -> change?
fukino
2015/12/02 04:52:03
Yes, it should be 'change'. Done.
| |
| 131 this.$.volumeSlider.addEventListener('focusout', onFocusoutBound); | |
| 132 this.$.volumeButton.addEventListener('focusout', onFocusoutBound); | |
| 133 | |
| 134 this.$.timeSlider.addEventListener('value-change', function() { | |
| 135 if (this.dragging) | 123 if (this.dragging) |
| 136 this.dragging = false; | 124 this.dragging = false; |
| 137 }.bind(this)); | 125 }.bind(this)); |
| 138 this.$.timeSlider.addEventListener('immediate-value-change', function() { | 126 timeSlider.addEventListener('immediate-value-change', function() { |
| 139 if (!this.dragging) | 127 if (!this.dragging) |
| 140 this.dragging = true; | 128 this.dragging = true; |
| 141 }.bind(this)); | 129 }.bind(this)); |
| 130 | |
| 131 // Update volume on user inputs for volume slider. | |
| 132 // During a drag operation, the volume should be updated immediately. | |
| 133 var volumeSlider = | |
| 134 /** @type {PaperSliderElement} */ (this.$.volumeSlider); | |
| 135 volumeSlider.addEventListener('change', function() { | |
| 136 this.volume = volumeSlider.value; | |
| 137 }.bind(this)); | |
| 138 volumeSlider.addEventListener('immediate-value-change', function() { | |
| 139 this.volume = volumeSlider.immediateValue; | |
| 140 }.bind(this)); | |
| 142 }, | 141 }, |
| 143 | 142 |
| 144 /** | 143 /** |
| 145 * Invoked when the next button is clicked. | 144 * Invoked when the next button is clicked. |
| 146 */ | 145 */ |
| 147 nextClick: function() { | 146 nextClick: function() { |
| 148 this.fire('next-clicked'); | 147 this.fire('next-clicked'); |
| 149 }, | 148 }, |
| 150 | 149 |
| 151 /** | 150 /** |
| 152 * Invoked when the play button is clicked. | 151 * Invoked when the play button is clicked. |
| 153 */ | 152 */ |
| 154 playClick: function() { | 153 playClick: function() { |
| 155 this.playing = !this.playing; | 154 this.playing = !this.playing; |
| 156 }, | 155 }, |
| 157 | 156 |
| 158 /** | 157 /** |
| 159 * Invoked when the previous button is clicked. | 158 * Invoked when the previous button is clicked. |
| 160 */ | 159 */ |
| 161 previousClick: function() { | 160 previousClick: function() { |
| 162 this.fire('previous-clicked'); | 161 this.fire('previous-clicked'); |
| 163 }, | 162 }, |
| 164 | 163 |
| 165 /** | 164 /** |
| 166 * Invoked when the property 'volumeSliderShown' changes. | 165 * Invoked when the volume button is clicked. |
| 167 * @param {boolean} shown | |
| 168 */ | 166 */ |
| 169 volumeSliderShownChanged: function(shown) { | 167 volumeClick: function() { |
| 170 this.showVolumeController_(shown); | 168 if (this.volume !== 0) { |
| 171 }, | 169 this.savedVolume_ = this.volume; |
| 172 | 170 this.volume = 0; |
| 173 /** | 171 } else { |
| 174 * Invoked when the focus goes out of the volume elements. | 172 this.volume = this.savedVolume_ || 50; |
| 175 * @param {!UIEvent} event The focusout event. | |
| 176 * @private | |
| 177 */ | |
| 178 onVolumeControllerFocusout_: function(event) { | |
| 179 if (this.volumeSliderShown) { | |
| 180 // If the focus goes out of the volume, hide the volume control. | |
| 181 if (!event.relatedTarget || | |
| 182 (!this.$.volumeButton.contains(event.relatedTarget) && | |
| 183 !this.$.volumeSlider.contains(event.relatedTarget))) { | |
| 184 this.volumeSliderShown = false; | |
| 185 } | |
| 186 } | 173 } |
| 187 }, | 174 }, |
| 188 | 175 |
| 189 /** | |
| 190 * Shows/hides the volume controller. | |
| 191 * @param {boolean} show True to show the controller, false to hide. | |
| 192 * @private | |
| 193 */ | |
| 194 showVolumeController_: function(show) { | |
| 195 if (show) { | |
| 196 matchBottomLine(this.$.volumeContainer, this.$.volumeButton); | |
| 197 this.$.volumeContainer.style.visibility = 'visible'; | |
| 198 } else { | |
| 199 this.$.volumeContainer.style.visibility = 'hidden'; | |
| 200 } | |
| 201 }, | |
| 202 | |
| 203 /** | 176 /** |
| 204 * Converts the time into human friendly string. | 177 * Converts the time into human friendly string. |
| 205 * @param {number} time Time to be converted. | 178 * @param {number} time Time to be converted. |
| 206 * @return {string} String representation of the given time | 179 * @return {string} String representation of the given time |
| 207 */ | 180 */ |
| 208 time2string_: function(time) { | 181 time2string_: function(time) { |
| 209 return ~~(time / 60000) + ':' + ('0' + ~~(time / 1000 % 60)).slice(-2); | 182 return ~~(time / 60000) + ':' + ('0' + ~~(time / 1000 % 60)).slice(-2); |
| 210 }, | 183 }, |
| 211 | 184 |
| 212 /** | 185 /** |
| (...skipping 12 matching lines...) Expand all Loading... | |
| 225 * @private | 198 * @private |
| 226 */ | 199 */ |
| 227 playingChanged_: function(playing) { | 200 playingChanged_: function(playing) { |
| 228 if (this.ariaLabels) { | 201 if (this.ariaLabels) { |
| 229 this.$.play.setAttribute('aria-label', | 202 this.$.play.setAttribute('aria-label', |
| 230 playing ? this.ariaLabels.pause : this.ariaLabels.play); | 203 playing ? this.ariaLabels.pause : this.ariaLabels.play); |
| 231 } | 204 } |
| 232 }, | 205 }, |
| 233 | 206 |
| 234 /** | 207 /** |
| 208 * Invoked when the volume property is changed. | |
| 209 * @param {number} volume | |
| 210 * @private | |
| 211 */ | |
| 212 volumeChanged_: function(volume) { | |
| 213 if (!this.$.volumeSlider.dragging) | |
| 214 this.$.volumeSlider.value = volume; | |
| 215 | |
| 216 if (this.ariaLabels) { | |
| 217 this.$.volumeButton.setAttribute('aria-label', | |
|
yawano
2015/12/01 07:51:31
This might be out of the scope of this CL. If you
fukino
2015/12/02 04:52:02
I'm not a big fun of tooltips when the buttons use
yawano
2015/12/02 06:11:43
Acknowledged.
| |
| 218 volume !== 0 ? this.ariaLabels.mute : this.ariaLabels.unmute); | |
| 219 } | |
| 220 }, | |
| 221 | |
| 222 /** | |
| 235 * Invoked when the ariaLabels property is changed. | 223 * Invoked when the ariaLabels property is changed. |
| 236 * @param {Object} ariaLabels | 224 * @param {Object} ariaLabels |
| 237 * @private | 225 * @private |
| 238 */ | 226 */ |
| 239 ariaLabelsChanged_: function(ariaLabels) { | 227 ariaLabelsChanged_: function(ariaLabels) { |
| 240 assert(ariaLabels); | 228 assert(ariaLabels); |
| 241 // TODO(fukino): Use data bindings. | 229 // TODO(fukino): Use data bindings. |
| 242 this.$.volumeSlider.setAttribute('aria-label', ariaLabels.volumeSlider); | 230 this.$.volumeSlider.setAttribute('aria-label', ariaLabels.volumeSlider); |
| 243 this.$.shuffle.setAttribute('aria-label', ariaLabels.shuffle); | 231 this.$.shuffle.setAttribute('aria-label', ariaLabels.shuffle); |
| 244 this.$.repeat.setAttribute('aria-label', ariaLabels.repeat); | 232 this.$.repeat.setAttribute('aria-label', ariaLabels.repeat); |
| 245 this.$.previous.setAttribute('aria-label', ariaLabels.previous); | 233 this.$.previous.setAttribute('aria-label', ariaLabels.previous); |
| 246 this.$.play.setAttribute('aria-label', | 234 this.$.play.setAttribute('aria-label', |
| 247 this.playing ? ariaLabels.pause : ariaLabels.play); | 235 this.playing ? ariaLabels.pause : ariaLabels.play); |
| 248 this.$.next.setAttribute('aria-label', ariaLabels.next); | 236 this.$.next.setAttribute('aria-label', ariaLabels.next); |
| 249 this.$.volumeButton.setAttribute('aria-label', ariaLabels.volume); | 237 this.$.volumeButton.setAttribute('aria-label', ariaLabels.volume); |
| 250 this.$.playList.setAttribute('aria-label', ariaLabels.playList); | 238 this.$.playList.setAttribute('aria-label', ariaLabels.playList); |
| 251 this.$.timeSlider.setAttribute('aria-label', ariaLabels.seekSlider); | 239 this.$.timeSlider.setAttribute('aria-label', ariaLabels.seekSlider); |
| 240 this.$.volumeButton.setAttribute('aria-label', | |
| 241 this.volume !== 0 ? ariaLabels.mute : ariaLabels.unmute); | |
| 242 this.$.volumeSlider.setAttribute('aria-label', ariaLabels.volumeSlider); | |
| 252 } | 243 } |
| 253 }); | 244 }); |
| 254 })(); // Anonymous closure | 245 })(); // Anonymous closure |
| OLD | NEW |