|
| 1 | +@import "variables"; |
| 2 | +@import "default-theme"; |
| 3 | + |
| 4 | +$md-progress-bar-height: 5px !default; |
| 5 | +$md-progress-bar-full-animation-duration: 2s !default; |
| 6 | +$md-progress-bar-piece-animation-duration: 250ms !default; |
| 7 | + |
| 8 | +// TODO(josephperrott): Find better way to inline svgs. |
| 9 | +/** In buffer mode a repeated SVG object is used as a background. Each of the following defines the SVG object for each |
| 10 | + of the class defined colors. |
| 11 | +
|
| 12 | + Each string is a URL encoded version of: |
| 13 | +
|
| 14 | + <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" |
| 15 | + version="1.1" x="0px" y="0px" enable-background="new 0 0 5 2" |
| 16 | + xml:space="preserve" viewBox="0 0 5 2" preserveAspectRatio="none slice"> |
| 17 | + <circle cx="1" cy="1" r="1" fill="{INJECTED_COLOR}"/> |
| 18 | + </svg> |
| 19 | +
|
| 20 | + */ |
| 21 | +$md-buffer-bubbles-primary: ( |
| 22 | + "data:image/svg+xml;charset=UTF-8,%3Csvg%20version%3D%271.1%27%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27" + |
| 23 | + "%20xmlns%3Axlink%3D%27http%3A%2F%2Fwww.w3.org%2F1999%2Fxlink%27%20x%3D%270px%27%20y%3D%270px%27%20enable-backgroun" + |
| 24 | + "d%3D%27new%200%200%205%202%27%20xml%3Aspace%3D%27preserve%27%20viewBox%3D%270%200%205%202%27%20preserveAspectRatio" + |
| 25 | + "%3D%27none%20slice%27%3E%3Ccircle%20cx%3D%271%27%20cy%3D%271%27%20r%3D%271%27%20fill%3D%27" + |
| 26 | + md-color($md-primary, 100) + "%27%2F%3E%3C%2Fsvg%3E") !default; |
| 27 | +$md-buffer-bubbles-accent: ( |
| 28 | + "data:image/svg+xml;charset=UTF-8,%3Csvg%20version%3D%271.1%27%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27" + |
| 29 | + "%20xmlns%3Axlink%3D%27http%3A%2F%2Fwww.w3.org%2F1999%2Fxlink%27%20x%3D%270px%27%20y%3D%270px%27%20enable-backgroun" + |
| 30 | + "d%3D%27new%200%200%205%202%27%20xml%3Aspace%3D%27preserve%27%20viewBox%3D%270%200%205%202%27%20preserveAspectRatio" + |
| 31 | + "%3D%27none%20slice%27%3E%3Ccircle%20cx%3D%271%27%20cy%3D%271%27%20r%3D%271%27%20fill%3D%27" + |
| 32 | + md-color($md-accent, 100) + "%27%2F%3E%3C%2Fsvg%3E") !default; |
| 33 | +$md-buffer-bubbles-warn: ( |
| 34 | + "data:image/svg+xml;charset=UTF-8,%3Csvg%20version%3D%271.1%27%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27" + |
| 35 | + "%20xmlns%3Axlink%3D%27http%3A%2F%2Fwww.w3.org%2F1999%2Fxlink%27%20x%3D%270px%27%20y%3D%270px%27%20enable-backgroun" + |
| 36 | + "d%3D%27new%200%200%205%202%27%20xml%3Aspace%3D%27preserve%27%20viewBox%3D%270%200%205%202%27%20preserveAspectRatio" + |
| 37 | + "%3D%27none%20slice%27%3E%3Ccircle%20cx%3D%271%27%20cy%3D%271%27%20r%3D%271%27%20fill%3D%27" + |
| 38 | + md-color($md-warn, 100) + "%27%2F%3E%3C%2Fsvg%3E") !default; |
| 39 | + |
| 40 | +:host { |
| 41 | + display: block; |
| 42 | + // Height is provided for md-progress-bar to act as a default. |
| 43 | + height: $md-progress-bar-height; |
| 44 | + overflow: hidden; |
| 45 | + position: relative; |
| 46 | + // translateZ is added to force the md-progress-bar into its own GPU layer. |
| 47 | + transform: translateZ(0); |
| 48 | + transition: opacity $md-progress-bar-piece-animation-duration linear; |
| 49 | + width: 100%; |
| 50 | + |
| 51 | + // The progress bar background is used to show the bubble animation scrolling behind a buffering progress bar. |
| 52 | + .md-progress-bar-background { |
| 53 | + background: url($md-buffer-bubbles-primary); |
| 54 | + background-repeat: repeat-x; |
| 55 | + background-size: 10px 4px; |
| 56 | + height: 100%; |
| 57 | + position: absolute; |
| 58 | + visibility: hidden; |
| 59 | + width: 100%; |
| 60 | + } |
| 61 | + |
| 62 | + /** |
| 63 | + * The progress bar buffer is the bar indicator showing the buffer value and is only visible beyond the current value |
| 64 | + * of the primary progress bar. |
| 65 | + */ |
| 66 | + .md-progress-bar-buffer { |
| 67 | + background-color: md-color($md-primary, 100); |
| 68 | + height: 100%; |
| 69 | + position: absolute; |
| 70 | + transform-origin: top left; |
| 71 | + transition: transform $md-progress-bar-piece-animation-duration ease; |
| 72 | + width: 100%; |
| 73 | + } |
| 74 | + |
| 75 | + /** |
| 76 | + * The secondary progress bar is only used in the indeterminate animation, because of this it is hidden in other uses. |
| 77 | + */ |
| 78 | + .md-progress-bar-secondary { |
| 79 | + visibility: hidden; |
| 80 | + } |
| 81 | + |
| 82 | + /** |
| 83 | + * The progress bar fill fills the progress bar with the indicator color. |
| 84 | + */ |
| 85 | + .md-progress-bar-fill { |
| 86 | + animation: none; |
| 87 | + height: 100%; |
| 88 | + position: absolute; |
| 89 | + transform-origin: top left; |
| 90 | + transition: transform $md-progress-bar-piece-animation-duration ease; |
| 91 | + width: 100%; |
| 92 | + } |
| 93 | + |
| 94 | + /** |
| 95 | + * A pseudo element is created for each progress bar bar that fills with the indicator color. |
| 96 | + */ |
| 97 | + .md-progress-bar-fill::after { |
| 98 | + animation: none; |
| 99 | + background-color: md-color($md-primary, 600); |
| 100 | + content: ''; |
| 101 | + display: inline-block; |
| 102 | + height: 100%; |
| 103 | + position: absolute; |
| 104 | + width: 100%; |
| 105 | + } |
| 106 | + |
| 107 | + &[color="accent"] { |
| 108 | + .md-progress-bar-background { |
| 109 | + background: url($md-buffer-bubbles-accent); |
| 110 | + background-repeat: repeat-x; |
| 111 | + background-size: 10px 4px; |
| 112 | + } |
| 113 | + .md-progress-bar-buffer { |
| 114 | + background-color: md-color($md-accent, 100); |
| 115 | + } |
| 116 | + .md-progress-bar-fill::after { |
| 117 | + background-color: md-color($md-accent, 600); |
| 118 | + } |
| 119 | + } |
| 120 | + |
| 121 | + &[color="warn"] { |
| 122 | + .md-progress-bar-background { |
| 123 | + background: url($md-buffer-bubbles-warn); |
| 124 | + background-repeat: repeat-x; |
| 125 | + background-size: 10px 4px; |
| 126 | + } |
| 127 | + .md-progress-bar-buffer { |
| 128 | + background-color: md-color($md-warn, 100); |
| 129 | + } |
| 130 | + .md-progress-bar-fill::after { |
| 131 | + background-color: md-color($md-warn, 600); |
| 132 | + } |
| 133 | + } |
| 134 | + |
| 135 | + &[mode="query"] { |
| 136 | + transform: rotateZ(180deg); |
| 137 | + } |
| 138 | + |
| 139 | + &[mode="indeterminate"], |
| 140 | + &[mode="query"] { |
| 141 | + .md-progress-bar-fill { |
| 142 | + transition: none; |
| 143 | + } |
| 144 | + .md-progress-bar-primary { |
| 145 | + animation: md-progress-bar-primary-indeterminate-translate $md-progress-bar-full-animation-duration infinite linear; |
| 146 | + left: -145.166611%; |
| 147 | + } |
| 148 | + .md-progress-bar-primary.md-progress-bar-fill::after { |
| 149 | + animation: md-progress-bar-primary-indeterminate-scale $md-progress-bar-full-animation-duration infinite linear; |
| 150 | + } |
| 151 | + .md-progress-bar-secondary { |
| 152 | + animation: md-progress-bar-secondary-indeterminate-translate $md-progress-bar-full-animation-duration infinite linear; |
| 153 | + left: -54.888891%; |
| 154 | + visibility: visible; |
| 155 | + } |
| 156 | + .md-progress-bar-secondary.md-progress-bar-fill::after { |
| 157 | + animation: md-progress-bar-secondary-indeterminate-scale $md-progress-bar-full-animation-duration infinite linear; |
| 158 | + } |
| 159 | + } |
| 160 | + |
| 161 | + &[mode="buffer"] { |
| 162 | + .md-progress-bar-background { |
| 163 | + animation: md-progress-bar-background-scroll $md-progress-bar-piece-animation-duration infinite linear; |
| 164 | + visibility: visible; |
| 165 | + } |
| 166 | + } |
| 167 | +} |
| 168 | + |
| 169 | + |
| 170 | +// Reverse the apparent directionality of progress vars for rtl. |
| 171 | +:host-context([dir="rtl"]) { |
| 172 | + transform: rotateY(180deg); |
| 173 | +} |
| 174 | + |
| 175 | + |
| 176 | +/** The values used for animations in md-progress-bar, both timing and transformation, can be considered magic values. |
| 177 | + They are sourced from the Material Design example spec and duplicate the values of the original designers |
| 178 | + definitions. |
| 179 | +
|
| 180 | +
|
| 181 | + The indeterminate state is essentially made up of two progress bars, one primary (the one that is shown in both the |
| 182 | + determinate and indeterminate states) and one secondary, which essentially mirrors the primary progress bar in |
| 183 | + appearance but is only shown to assist with the indeterminate animations. |
| 184 | +
|
| 185 | +
|
| 186 | + KEYFRAME BLOCK DESCRIPTION |
| 187 | + primary-indeterminate-translate Translation of the primary progressbar across the screen |
| 188 | + primary-indeterminate-scale Scaling of the primary progressbar as it's being translated across the screen |
| 189 | + secondary-indeterminate-translate Translation of the secondary progressbar across the screen |
| 190 | + secondary-indeterminate-scale Scaling of the secondary progressbar as it's being translated across the screen |
| 191 | +
|
| 192 | + Because two different transform animations need to be applied at once, the translation is applied to the outer |
| 193 | + element and the scaling is applied to the inner element, which provides the illusion necessary to make the animation |
| 194 | + work. |
| 195 | +*/ |
| 196 | + |
| 197 | +// Progress Bar Timing functions: |
| 198 | +// $md-progress-bar-primary-indeterminate-translate-step-1 has no timing function. |
| 199 | +$md-progress-bar-primary-indeterminate-translate-step-2: cubic-bezier(.5, 0, .701732, .495819) !default; |
| 200 | +$md-progress-bar-primary-indeterminate-translate-step-3: cubic-bezier(.302435, .381352, .55, .956352) !default; |
| 201 | +// $md-progress-bar-primary-indeterminate-translate-step-4 has no timing function. |
| 202 | + |
| 203 | +// $md-progress-bar-primary-indeterminate-scale-step-1 has no timing function |
| 204 | +$md-progress-bar-primary-indeterminate-scale-step-2: cubic-bezier(.334731, .124820, .785844, 1) !default; |
| 205 | +$md-progress-bar-primary-indeterminate-scale-step-3: cubic-bezier(.06, .11, .6, 1) !default; |
| 206 | +// $md-progress-bar-primary-indeterminate-scale-step-4 has no timing function |
| 207 | + |
| 208 | +$md-progress-bar-secondary-indeterminate-translate-step-1: cubic-bezier(.15, 0, .515058, .409685) !default; |
| 209 | +$md-progress-bar-secondary-indeterminate-translate-step-2: cubic-bezier(.310330, .284058, .8, .733712) !default; |
| 210 | +$md-progress-bar-secondary-indeterminate-translate-step-3: cubic-bezier(.4, .627035, .6, .902026) !default; |
| 211 | +// $md-progress-bar-secondary-indeterminate-translate-step-4 has no timing function |
| 212 | + |
| 213 | +$md-progress-bar-secondary-indeterminate-scale-step-1: cubic-bezier(.15, 0, .515058, .409685) !default; |
| 214 | +$md-progress-bar-secondary-indeterminate-scale-step-2: cubic-bezier(.310330, .284058, .8, .733712) !default; |
| 215 | +$md-progress-bar-secondary-indeterminate-scale-step-3: cubic-bezier(.4, .627035, .6, .902026) !default; |
| 216 | +// $md-progress-bar-secondary-indeterminate-scale-step-4 has no timing function |
| 217 | + |
| 218 | +/** Animations for indeterminate and query mode. */ |
| 219 | +// Primary indicator. |
| 220 | +@keyframes md-progress-bar-primary-indeterminate-translate { |
| 221 | + 0% { |
| 222 | + transform: translateX(0px); |
| 223 | + } |
| 224 | + 20% { |
| 225 | + animation-timing-function: $md-progress-bar-primary-indeterminate-translate-step-2; |
| 226 | + transform: translateX(0px); |
| 227 | + } |
| 228 | + 59.15% { |
| 229 | + animation-timing-function: $md-progress-bar-primary-indeterminate-translate-step-3; |
| 230 | + transform: translateX(83.67142%); |
| 231 | + } |
| 232 | + 100% { |
| 233 | + transform: translateX(200.611057%); |
| 234 | + } |
| 235 | +} |
| 236 | + |
| 237 | +@keyframes md-progress-bar-primary-indeterminate-scale { |
| 238 | + 0% { |
| 239 | + transform: scaleX(.08); |
| 240 | + } |
| 241 | + 36.65% { |
| 242 | + animation-timing-function: $md-progress-bar-primary-indeterminate-scale-step-2; |
| 243 | + transform: scaleX(.08); |
| 244 | + } |
| 245 | + 69.15% { |
| 246 | + animation-timing-function: $md-progress-bar-primary-indeterminate-scale-step-3; |
| 247 | + transform: scaleX(.661479); |
| 248 | + } |
| 249 | + 100% { |
| 250 | + transform: scaleX(.08); |
| 251 | + } |
| 252 | +} |
| 253 | + |
| 254 | +// Secondary indicator. |
| 255 | +@keyframes md-progress-bar-secondary-indeterminate-translate { |
| 256 | + 0% { |
| 257 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-translate-step-1; |
| 258 | + transform: translateX(0px); |
| 259 | + } |
| 260 | + 25% { |
| 261 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-translate-step-2; |
| 262 | + |
| 263 | + transform: translateX(37.651913%); |
| 264 | + } |
| 265 | + 48.35% { |
| 266 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-translate-step-3; |
| 267 | + transform: translateX(84.386165%); |
| 268 | + } |
| 269 | + 100% { |
| 270 | + transform: translateX(160.277782%); |
| 271 | + } |
| 272 | +} |
| 273 | + |
| 274 | +@keyframes md-progress-bar-secondary-indeterminate-scale { |
| 275 | + 0% { |
| 276 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-scale-step-1; |
| 277 | + transform: scaleX(.08); |
| 278 | + } |
| 279 | + 19.15% { |
| 280 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-scale-step-2; |
| 281 | + transform: scaleX(.457104); |
| 282 | + } |
| 283 | + 44.15% { |
| 284 | + animation-timing-function: $md-progress-bar-secondary-indeterminate-scale-step-3; |
| 285 | + transform: scaleX(.727960); |
| 286 | + } |
| 287 | + 100% { |
| 288 | + transform: scaleX(.08); |
| 289 | + } |
| 290 | +} |
| 291 | + |
| 292 | +/** Animation for buffer mode. */ |
| 293 | +@keyframes md-progress-bar-background-scroll { |
| 294 | + to { |
| 295 | + transform: translateX(-10px); |
| 296 | + } |
| 297 | +} |
0 commit comments