1 |
|
2 | title: "Sliders"
|
3 | layout: detail
|
4 | section: components
|
5 | excerpt: "Sliders allow users to make selections from a range of values."
|
6 | iconId: slider
|
7 | path: /catalog/input-controls/sliders/
|
8 | -->
|
9 |
|
10 | # Slider
|
11 |
|
12 | [Sliders](https://material.io/components/sliders/) allow users to make
|
13 | selections from a range of values.
|
14 |
|
15 | The MDC Slider implementation supports both single point sliders (one thumb)
|
16 | and range sliders (two thumbs). It is backed by the browser
|
17 | `<input type="range">` element, is fully accessible, and is RTL-aware.
|
18 |
|
19 | **Contents**
|
20 |
|
21 | * [Using sliders](#using-sliders)
|
22 | * [Sliders](#sliders)
|
23 | * [Other variants](#other-variants)
|
24 | * [Additional information](#additional-information)
|
25 | * [API](#api)
|
26 |
|
27 | ## Using sliders
|
28 |
|
29 | ### Installing sliders
|
30 |
|
31 | ```
|
32 | npm install @material/slider
|
33 | ```
|
34 |
|
35 | ### Styles
|
36 |
|
37 | ```scss
|
38 | @use "@material/slider/styles";
|
39 | ```
|
40 |
|
41 | ### JavaScript instantiation
|
42 |
|
43 | ```js
|
44 | import {MDCSlider} from '@material/slider';
|
45 |
|
46 | const slider = new MDCSlider(document.querySelector('.mdc-slider'));
|
47 | ```
|
48 |
|
49 | **Note**: See [Importing the JS component](../../docs/importing-js.md) for more
|
50 | information on how to import JavaScript.
|
51 |
|
52 | ### Making sliders accessible
|
53 |
|
54 | Sliders are backed by an `<input>` element, meaning that they are fully
|
55 | accessible. Unlike the [ARIA-based slider](https://www.w3.org/TR/wai-aria-practices/#slider),
|
56 | MDC sliders are adjustable using touch-based assistive technologies such as
|
57 | TalkBack on Android.
|
58 |
|
59 | Per the spec, ensure that the following attributes are added to the
|
60 | `input` element(s):
|
61 |
|
62 | * `value`: Value representing the current value.
|
63 | * `min`: Value representing the minimum allowed value.
|
64 | * `max`: Value representing the maximum allowed value.
|
65 | * `aria-label` or `aria-labelledby`: Accessible label for the slider.
|
66 |
|
67 | If the value is not user-friendly (e.g. a number to
|
68 | represent the day of the week), also set the following:
|
69 |
|
70 | * `aria-valuetext`: Set this input attribute to a string that makes the slider
|
71 | value understandable, e.g. 'Monday'.
|
72 | * Add a function to map the slider value to `aria-valuetext` via the
|
73 | `MDCSlider#setValueToAriaValueTextFn` method.
|
74 |
|
75 | ## Sliders
|
76 |
|
77 | There are two types of sliders:
|
78 |
|
79 | 1. [Continuous slider](#continuous-slider)
|
80 | 1. [Discrete slider](#discrete-slider)
|
81 |
|
82 | ### Continuous slider
|
83 |
|
84 | Continuous sliders allow users to make meaningful selections that don’t require
|
85 | a specific value.
|
86 |
|
87 | Note: The step size for value quantization is, by default, 1. To specify
|
88 | a custom step size, provide a value for the `step` attribute on the `input`
|
89 | element.
|
90 |
|
91 | <img src="images/continuous-slider.png" alt="Continuous slider with a value of 50">
|
92 |
|
93 | ```html
|
94 | <div class="mdc-slider">
|
95 | <input class="mdc-slider__input" type="range" min="0" max="100" value="50" name="volume" aria-label="Continuous slider demo">
|
96 | <div class="mdc-slider__track">
|
97 | <div class="mdc-slider__track--inactive"></div>
|
98 | <div class="mdc-slider__track--active">
|
99 | <div class="mdc-slider__track--active_fill"></div>
|
100 | </div>
|
101 | </div>
|
102 | <div class="mdc-slider__thumb">
|
103 | <div class="mdc-slider__thumb-knob"></div>
|
104 | </div>
|
105 | </div>
|
106 | ```
|
107 |
|
108 | #### Continuous range slider
|
109 |
|
110 | Note: By default there's no minimum distance between the two thumbs. To specify
|
111 | one, provide a value for the `data-min-range` attribute on the root element and
|
112 | adjust the `min` and `max` attributes on the input elements accordingly.
|
113 |
|
114 | <img src="images/continuous-range-slider.png" alt="Continuous range slider with values of 30 and 70">
|
115 |
|
116 | ```html
|
117 | <div class="mdc-slider mdc-slider--range" data-min-range="10">
|
118 | <input class="mdc-slider__input" type="range" min="0" max="60" value="30" name="rangeStart" aria-label="Continuous range slider demo">
|
119 | <input class="mdc-slider__input" type="range" min="40" max="100" value="70" name="rangeEnd" aria-label="Continuous range slider demo">
|
120 | <div class="mdc-slider__track">
|
121 | <div class="mdc-slider__track--inactive"></div>
|
122 | <div class="mdc-slider__track--active">
|
123 | <div class="mdc-slider__track--active_fill"></div>
|
124 | </div>
|
125 | </div>
|
126 | <div class="mdc-slider__thumb">
|
127 | <div class="mdc-slider__thumb-knob"></div>
|
128 | </div>
|
129 | <div class="mdc-slider__thumb">
|
130 | <div class="mdc-slider__thumb-knob"></div>
|
131 | </div>
|
132 | </div>
|
133 | ```
|
134 |
|
135 | ### Discrete slider
|
136 |
|
137 | Discrete sliders display a numeric value label upon pressing the thumb, which
|
138 | allows a user to select an exact value.
|
139 |
|
140 | <img src="images/discrete-slider.png" alt="Discrete slider with a value of 50">
|
141 |
|
142 | To create a discrete slider, add the following:
|
143 |
|
144 | * `mdc-slider--discrete` class on the root element.
|
145 | * Value indicator element (`mdc-slider__value-indicator-container`), as shown
|
146 | below.
|
147 |
|
148 | ```html
|
149 | <div class="mdc-slider mdc-slider--discrete">
|
150 | <input class="mdc-slider__input" type="range" min="0" max="100" value="50" name="volume" step="10" aria-label="Discrete slider demo">
|
151 | <div class="mdc-slider__track">
|
152 | <div class="mdc-slider__track--inactive"></div>
|
153 | <div class="mdc-slider__track--active">
|
154 | <div class="mdc-slider__track--active_fill"></div>
|
155 | </div>
|
156 | </div>
|
157 | <div class="mdc-slider__thumb">
|
158 | <div class="mdc-slider__value-indicator-container" aria-hidden="true">
|
159 | <div class="mdc-slider__value-indicator">
|
160 | <span class="mdc-slider__value-indicator-text">
|
161 | 50
|
162 | </span>
|
163 | </div>
|
164 | </div>
|
165 | <div class="mdc-slider__thumb-knob"></div>
|
166 | </div>
|
167 | </div>
|
168 | ```
|
169 |
|
170 | #### Discrete slider with tick marks
|
171 |
|
172 | Discrete sliders can optionally display tick marks. Tick marks represent
|
173 | predetermined values to which the user can move the slider.
|
174 |
|
175 | <img src="images/discrete-slider-tick-marks.png" alt="Discrete slider (with tick marks), with a value of 50">
|
176 |
|
177 | To add tick marks to a discrete slider, add the following:
|
178 |
|
179 | * `mdc-slider--tick-marks` class on the root element
|
180 | * `mdc-slider__tick-marks` element as a child of the `mdc-slider__track`
|
181 | element
|
182 | * `mdc-slider__tick-mark--active` and `mdc-slider__tick-mark--inactive`
|
183 | elements as children of the `mdc-slider__tick-marks` element
|
184 |
|
185 | ```html
|
186 | <div class="mdc-slider mdc-slider--discrete mdc-slider--tick-marks">
|
187 | <input class="mdc-slider__input" type="range" min="0" max="100" value="50" name="volume" step="10" aria-label="Discrete slider with tick marks demo">
|
188 | <div class="mdc-slider__track">
|
189 | <div class="mdc-slider__track--inactive"></div>
|
190 | <div class="mdc-slider__track--active">
|
191 | <div class="mdc-slider__track--active_fill"></div>
|
192 | </div>
|
193 | <div class="mdc-slider__tick-marks">
|
194 | <div class="mdc-slider__tick-mark--active"></div>
|
195 | <div class="mdc-slider__tick-mark--active"></div>
|
196 | <div class="mdc-slider__tick-mark--active"></div>
|
197 | <div class="mdc-slider__tick-mark--active"></div>
|
198 | <div class="mdc-slider__tick-mark--active"></div>
|
199 | <div class="mdc-slider__tick-mark--active"></div>
|
200 | <div class="mdc-slider__tick-mark--inactive"></div>
|
201 | <div class="mdc-slider__tick-mark--inactive"></div>
|
202 | <div class="mdc-slider__tick-mark--inactive"></div>
|
203 | <div class="mdc-slider__tick-mark--inactive"></div>
|
204 | <div class="mdc-slider__tick-mark--inactive"></div>
|
205 | </div>
|
206 | </div>
|
207 | <div class="mdc-slider__thumb">
|
208 | <div class="mdc-slider__value-indicator-container" aria-hidden="true">
|
209 | <div class="mdc-slider__value-indicator">
|
210 | <span class="mdc-slider__value-indicator-text">
|
211 | 50
|
212 | </span>
|
213 | </div>
|
214 | </div>
|
215 | <div class="mdc-slider__thumb-knob"></div>
|
216 | </div>
|
217 | </div>
|
218 | ```
|
219 |
|
220 | #### Discrete range slider
|
221 |
|
222 | ```html
|
223 | <div class="mdc-slider mdc-slider--range mdc-slider--discrete">
|
224 | <input class="mdc-slider__input" type="range" min="0" max="50" value="20" step="10" name="rangeStart" aria-label="Discrete range slider demo">
|
225 | <input class="mdc-slider__input" type="range" min="20" max="100" value="50" step="10" name="rangeEnd" aria-label="Discrete range slider demo">
|
226 | <div class="mdc-slider__track">
|
227 | <div class="mdc-slider__track--inactive"></div>
|
228 | <div class="mdc-slider__track--active">
|
229 | <div class="mdc-slider__track--active_fill"></div>
|
230 | </div>
|
231 | </div>
|
232 | <div class="mdc-slider__thumb">
|
233 | <div class="mdc-slider__value-indicator-container" aria-hidden="true">
|
234 | <div class="mdc-slider__value-indicator">
|
235 | <span class="mdc-slider__value-indicator-text">
|
236 | 20
|
237 | </span>
|
238 | </div>
|
239 | </div>
|
240 | <div class="mdc-slider__thumb-knob"></div>
|
241 | </div>
|
242 | <div class="mdc-slider__thumb">
|
243 | <div class="mdc-slider__value-indicator-container" aria-hidden="true">
|
244 | <div class="mdc-slider__value-indicator">
|
245 | <span class="mdc-slider__value-indicator-text">
|
246 | 50
|
247 | </span>
|
248 | </div>
|
249 | </div>
|
250 | <div class="mdc-slider__thumb-knob"></div>
|
251 | </div>
|
252 | </div>
|
253 | ```
|
254 |
|
255 | ## Other variants
|
256 |
|
257 | ### Disabled slider
|
258 |
|
259 | To disable a slider, add the following:
|
260 |
|
261 | * `mdc-slider--disabled` class on the root element
|
262 | * `disabled` attribute on the input element
|
263 |
|
264 | ```html
|
265 | <div class="mdc-slider mdc-slider--disabled">
|
266 | <input class="mdc-slider__input" type="range" min="0" max="100" value="50" step="10" disabled name="volume" aria-label="Disabled slider demo">
|
267 | <div class="mdc-slider__track">
|
268 | <div class="mdc-slider__track--inactive"></div>
|
269 | <div class="mdc-slider__track--active">
|
270 | <div class="mdc-slider__track--active_fill"></div>
|
271 | </div>
|
272 | </div>
|
273 | <div class="mdc-slider__thumb">
|
274 | <div class="mdc-slider__thumb-knob"></div>
|
275 | </div>
|
276 | </div>
|
277 | ```
|
278 |
|
279 | ## Additional information
|
280 |
|
281 | ### Initialization with custom ranges and values
|
282 |
|
283 | When `MDCSlider` is initialized, it reads the input element's `min`,
|
284 | `max`, and `value` attributes if present, using them to set
|
285 | the component's internal `min`, `max`, and `value` properties.
|
286 |
|
287 | Use these attributes to initialize the slider with a custom range and values,
|
288 | as shown below:
|
289 |
|
290 | ```html
|
291 | <div class="mdc-slider">
|
292 | <input class="mdc-slider__input" aria-label="Slider demo" min="0" max="100" value="75">
|
293 | <!-- ... -->
|
294 | </div>
|
295 | ```
|
296 |
|
297 | ### Setting slider position before component initialization
|
298 |
|
299 | When `MDCSlider` is initialized, it updates the slider track and thumb
|
300 | positions based on the internal value(s). To set the correct track and thumb
|
301 | positions before component initialization, mark up the DOM as follows:
|
302 |
|
303 | - Calculate `rangePercentDecimal`, the active track range as a percentage of
|
304 | the entire track, i.e. `(valueEnd - valueStart) / (max - min)`.
|
305 | Set `transform:scaleX(<rangePercentDecimal>)` as an inline style on the
|
306 | `mdc-slider__track--active_fill` element.
|
307 | - Calculate `thumbEndPercent`, the initial position of the end thumb as a
|
308 | percentage of the entire track. Set `left:calc(<thumbEndPercent>% - 24px)`
|
309 | as an inline style on the end thumb (`mdc-slider__thumb`) element
|
310 | (or `right` for RTL layouts).
|
311 | - *[Range sliders only]* Calculate `thumbStartPercent`, the initial position
|
312 | of the start thumb as a percentage of the entire track. Set
|
313 | `left:calc(<thumbStartPercent>% - 24px)` as an inline style on the
|
314 | start thumb (`mdc-slider__thumb`) element (or `right` for RTL layouts).
|
315 | - *[Range sliders only]* Using the previously calculated `thumbStartPercent`,
|
316 | set `left:<thumbStartPercent>%` as an inline style on the
|
317 | `mdc-slider__track--active_fill` element (or `right` for RTL layouts).
|
318 |
|
319 | Additionally, the MDCSlider component should be initialized with
|
320 | `skipInitialUIUpdate` set to true.
|
321 |
|
322 | #### Range slider example
|
323 |
|
324 | This is an example of a range slider with internal values of
|
325 | `[min, max] = [0, 100]` and `[start, end] = [30, 70]`, and a minimum range of
|
326 | 10.
|
327 |
|
328 | ```html
|
329 | <div class="mdc-slider mdc-slider--range" data-min-range="10">
|
330 | <input class="mdc-slider__input" type="range" min="0" max="60" value="30" name="rangeStart" aria-label="Range slider demo">
|
331 | <input class="mdc-slider__input" type="range" min="40" max="100" value="70" name="rangeEnd" aria-label="Range slider demo">
|
332 | <div class="mdc-slider__track">
|
333 | <div class="mdc-slider__track--inactive"></div>
|
334 | <div class="mdc-slider__track--active">
|
335 | <div class="mdc-slider__track--active_fill"
|
336 | style="transform:scaleX(.4); left:30%"></div>
|
337 | </div>
|
338 | </div>
|
339 | <div class="mdc-slider__thumb" style="left:calc(30%-24px)">
|
340 | <div class="mdc-slider__thumb-knob"></div>
|
341 | </div>
|
342 | <div class="mdc-slider__thumb" style="left:calc(70%-24px)">
|
343 | <div class="mdc-slider__thumb-knob"></div>
|
344 | </div>
|
345 | </div>
|
346 | ```
|
347 |
|
348 | ## API
|
349 |
|
350 | ### Sass mixins
|
351 |
|
352 | Mixin | Description
|
353 | --- | ---
|
354 | `track-active-color($color)` | Sets the color of the active track.
|
355 | `track-inactive-color($color, $opacity)` | Sets the color and opacity of the inactive track.
|
356 | `thumb-color($color)` | Sets the color of the thumb.
|
357 | `thumb-ripple-color($color)` | Sets the color of the thumb ripple.
|
358 | `tick-mark-active-color($color)` | Sets the color of tick marks on the active track.
|
359 | `tick-mark-inactive-color($color)` | Sets the color of tick marks on the inactive track.
|
360 | `value-indicator-color($color, $opaicty)` | Sets the color and opacity of the value indicator.
|
361 | `value-indicator-text-color($color, $opaicty)` | Sets the color of the value indicator text.
|
362 |
|
363 | ### `MDCSlider` events
|
364 |
|
365 | Event name | `event.detail` | Description
|
366 | --- | --- | ---
|
367 | `MDCSlider:change` | `MDCSliderChangeEventDetail` | Emitted when a value has been changed and committed from a user event. Mirrors the native `change` event: https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/change_event
|
368 | `MDCSlider:input` | `MDCSliderChangeEventDetail` | Emitted when a value has been changed from a user event. Mirrors the native `input` event: https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/input_event
|
369 |
|
370 | ### `MDCSlider` methods
|
371 |
|
372 | Method Signature | Description
|
373 | --- | ---
|
374 | `getValueStart() => number` | Gets the value of the start thumb (only applicable for range sliders).
|
375 | `setValueStart(valueStart: number) => void` | Sets the value of the start thumb (only applicable for range sliders).
|
376 | `getValue() => number` | Gets the value of the thumb (for single point sliders), or the end thumb (for range sliders).
|
377 | `setValue(value: number) => void` | Sets the value of the thumb (for single point sliders), or the end thumb (for range sliders).
|
378 | `getDisabled() => boolean` | Gets the disabled state of the slider.
|
379 | `setDisabled(disabled: boolean) => void` | Sets the disabled state of the slider.
|
380 | `setValueToAriaValueTextFn((mapFn: ((value: number) => string) \| null) => void` | Sets a function that maps the slider value to value of the `aria-valuetext` attribute on the thumb element. If not set, the `aria-valuetext` attribute is unchanged when the value changes.
|
381 |
|
382 | ### Usage within frameworks
|
383 |
|
384 | If you are using a JavaScript framework such as React or Angular, you can create a slider for your framework. Depending on your needs, you can use the _Simple Approach: Wrapping MDC Web Vanilla Components_, or the _Advanced Approach: Using Foundations and Adapters_. Please follow the instructions [here](../../docs/integrating-into-frameworks.md).
|
385 |
|
386 | See [MDCSliderAdapter](./adapter.ts) and [MDCSliderFoundation](./foundation.ts) for up-to-date code documentation of slider foundation API's.
|