├── license.txt ├── demo ├── pink-batman-1.html ├── wheres-bruce-wayne.html └── pink-batman-2.html ├── readme.md └── code └── batman-comic.css /license.txt: -------------------------------------------------------------------------------- 1 | `batman-comic.css` is copyright 2024 by Alvaro Montoro. 2 | 3 | The library is provided as-is. The author makes no representations or warranties of any kind, expressed or implied, as to the operation 4 | of the library, and is not responsible for any damage/side effect that the use of this library may cause. 5 | 6 | Feel free to use the `batman-comic.css` library to create non-commercial comics. If you create a comic strip with this, please share 7 | it with me, you can find me on [Twitter](https://twitter.com/alvaro_montoro) or [Mastodon](https://front-end.social/@alvaromontoro). 8 | 9 | Attribution is required (a comment in source code is fine). -------------------------------------------------------------------------------- /demo/pink-batman-1.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | Batman-Comic.CSS 11 | 12 | 13 | 14 |
15 | 23 |
24 |
Robin!! Did you wash your red shirt with my suit again?!?!
25 |
26 |
27 |
28 | 29 | -------------------------------------------------------------------------------- /demo/wheres-bruce-wayne.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | Batman-Comic.CSS 11 | 12 | 13 | 14 | 32 | 33 | -------------------------------------------------------------------------------- /demo/pink-batman-2.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | Batman-Comic.CSS 11 | 12 | 13 | 14 | 40 | 41 | -------------------------------------------------------------------------------- /readme.md: -------------------------------------------------------------------------------- 1 | # Batman-Comic.CSS 2 | 3 | `batman-comic.css` is a CSS utility-class library that allows to easily create Batman comics strips. Each character is 4 | a `
` that has the appropriate classes to show the character and their facial expressions. 5 | 6 | ## Characters 7 | 8 | - Batman 9 | - Robin 10 | 11 | ### Batman 12 | 13 | Custom properties for colors: 14 | 15 | - `--skin-color`: #fca (pink-ish) 16 | - `--mouth-color`: #700 (dark red) 17 | - `--suit-color`: #333 (gray) 18 | - `--suit-color-dark`: #222 (dark gray) 19 | - `--logo-color`: #ff5 (yellow) 20 | - `--logo-color-dark`: #dd2 (dark yellow) 21 | - `--eye-color`: #fff (white) 22 | 23 | ### Robin 24 | 25 | Custom properties for colors: 26 | 27 | - `--skin-color`: #fca (pink-ish) 28 | - `--skin-color-dark`: #da8 (dark pink-ish) 29 | - `--mouth-color`: #fff (white) 30 | - `--suit-color`: #f00 (red) 31 | - `--shirt-color`: #080 (green) 32 | - `--cape-color`: #ff5 (yellow-ish) 33 | - `--logo-color`: #ff5 (yellow-ish) 34 | - `--logo-color-dark`: #000 (black) 35 | - `--eye-color`: #fff (white) 36 | - `--mask-color`: #000 (black) 37 | - `--hair-color`: #000 (black) 38 | 39 | --- 40 | 41 | ## Character Expressions 42 | 43 | All characters have these expressions available, add the classes and see how their faces change. 44 | 45 | ### Eyes 46 | 47 | - `eyes-no`: No eyes. 48 | - `eyes-think`: Eyes slightly closed from the top. 49 | - `eyes-doubt`: Eyes slightly closed from top to bottom. 50 | - `eyes-sad`: Eyes skewed to look sad (towards the inside). 51 | - `eyes-angry`: Eyes skewed to look angry (towards the outside). 52 | - `eyes-suspicious`: left eye think, right eye angry. 53 | - `eyes-surprise` (combinable): larger eyes. 54 | - `eyes-shock` (combinable): left eye smaller, right eye larger. 55 | 56 | ### Mouth 57 | 58 | - `mouth-no`: No mouth. 59 | - `mouth-sad`: Frawned mouth. 60 | - `mouth-angry`: see mouth-sad. 61 | - `mouth-talk`: Mouth with the character talking. 62 | - `mouth-round`: a circle 63 | - `mouth-whisper`: a small oval 64 | - `mouth-right` (combinable): moves the mouth slightly to the right side. 65 | - `mouth-left` (combinable): moves the mouth slightly to the left side. 66 | - `mouth-to-right` (combinable): skews the mouth towards the right. 67 | - `mouth-to-left` (combinable): skews the outh towards the left. 68 | 69 | ### Others 70 | 71 | - `blush`: a redish glow in the visible part of the face. 72 | - `scare`: a blueish glow in the visible part of the face. 73 | - `shame`: a (lighter?) redish glow in the visible part of the face. 74 | 75 | --- 76 | 77 | ## Sizes and Positions 78 | 79 | There are a series of classes that will apply to any element. These classes determine position and size of the element. 80 | 81 | ### Sizes 82 | 83 | At this moment, you can only specify the width and an element, and it only applies to speech bubbles (you can use them on 84 | characters, but results may be disastrous). The class names will follow the pattern `.width-[AMOUNT]` where `[AMOUNT]` 85 | is a multiple of 5: 86 | 87 | - `.width-0`: a width of 0% of the container. 88 | - `.width-5`: a width of 5% of the container. 89 | - `.width-10`: a width of 10% of the container. 90 | - ... 91 | - `.width-100`: a width of 100% of the container. 92 | 93 | ### Positions 94 | 95 | Positon must be specified using horitonzally and vertically with a series of classes that follow the pattern `.pos-[DIRECTION]-[AMOUNT]`: 96 | 97 | - `[DIRECTION]` will be x or y for horizontal and vertical positioning respectively. 98 | - `[AMOUNT]` will be a multiple of five that indicates the percentage to apply to the element (from the left of the panel). 99 | 100 | By default, characters are positioned at the bottom part of the panel, so you won't need to specify the vertical position for them. 101 | 102 | For example, if we want to place Batman at the center of the panel, we'll have to use the following code (50 being the center as it is 50%): 103 | 104 | ``` 105 |
106 | ``` 107 | 108 | ### Rotations 109 | 110 | You can use a set of generic classes to rotate elements withn certain limits (the rotations will apply to characters and props, too): 111 | 112 | - `.rotate-0`: does not rotate the element (not really needed). 113 | - `.rotate-5`: rotates the element 5 degrees clockwise. 114 | - `.rotate-10`: rotates the element 10 degrees clockwise. 115 | - `.rotate-15`: rotates the element 15 degrees clockwise. 116 | - `.rotate-20`: rotates the element 20 degrees clockwise. 117 | - `.rotate-25`: rotates the element 25 degrees clockwise. 118 | - `.rotate-30`: rotates the element 30 degrees clockwise. 119 | - `.rotate--5`: rotates the element 5 degrees counter-clockwise. 120 | - `.rotate--10`: rotates the element 10 degrees counter-clockwise. 121 | - `.rotate--15`: rotates the element 15 degrees counter-clockwise. 122 | - `.rotate--20`: rotates the element 20 degrees counter-clockwise. 123 | - `.rotate--25`: rotates the element 25 degrees counter-clockwise. 124 | - `.rotate--30`: rotates the element 30 degrees counter-clockwise. 125 | 126 | --- 127 | 128 | ## Speech Bubbles 129 | 130 | Speech bubbles are sections to write what the characters are saying or thinking. In this version, they are quite simple, 131 | they are some text and a line connecting the text to the speaking chracter. 132 | 133 | ``` 134 |
Holy Interplanetary Yardstick, Batman!
135 | ``` 136 | 137 | ### Size 138 | 139 | For speech bubbles sizes, check the previous section. 140 | 141 | For the size of the line connecting the text with the character, there are a couple of classes that you could use to customize it: 142 | 143 | - `short`: shorter line 144 | - `tall`: longer/taller line 145 | 146 | ### Position 147 | 148 | For speech bubbles positioning, check the previous section. 149 | 150 | The line connecting text and character will be right-to-left by default. If you want to change direction and make it left-to-right, 151 | just add the `left` class... easy, no? 152 | 153 | To move the line from one side to the other, we will use a class system similar to the one for horizontal positioning described on 154 | the previous section, but indicating it is for hte line. For example, `pos-line-30` will place the line at a 30% from the beginning 155 | of the speech bubble. 156 | 157 | ### Off-panel Bubbles 158 | 159 | Sometimes, we may want to have a speech bubble coming from a character located outside of the panel, that is not visible. In that 160 | case, add the off-panel class. 161 | 162 | --- 163 | 164 | ## Props 165 | 166 | No props added yet. 167 | 168 | --- 169 | 170 | ## Panels 171 | 172 | By default the comic strip is designed to have 3 panels per row, each panel taking a column within the row. But you can add classes 173 | to the section so they occupy different sizes. 174 | 175 | Add the classes `two`, `three`, or `four` to each panel so it spans two, three, or four columns respectively. 176 | 177 | ...But you can add the class `four-panels` to the comic strip so it will have four panels per row (they will be smaller, and the figures 178 | will be slightly scaled down.) 179 | 180 | --- 181 | 182 | ## "Best Practices" 183 | 184 | To be determined. Something something "best practices don't work" something something. Just have fun for now. That should definitely 185 | be a best practice for this type of projects. 186 | 187 | But if you want a set of best practices; here are some: 188 | 189 | - Don't overlap elements/characters. It gets confusing. 190 | - Add a role="img" and a hidden text description to your comics so they are slightly more accessible. 191 | 192 | --- 193 | 194 | ## Examples 195 | 196 | ### Example 1 197 | 198 | ``` 199 | 217 | ``` 218 | 219 | ### Example 2 220 | 221 | ``` 222 | 243 | ``` 244 | 245 | --- 246 | 247 | ## Collaborations 248 | 249 | Feel free to use the `batman-comic.css` library to create non-commercial comics. If you create a comic strip with this, please share 250 | it with me, you can find me on [Twitter](https://twitter.com/alvaro_montoro) or [Mastodon](https://front-end.social/@alvaromontoro). 251 | 252 | Attribution is required (a comment in source code is fine). 253 | 254 | --- 255 | 256 | ## License 257 | 258 | `batman-comic.css` is copyright 2024 by Alvaro Montoro. 259 | 260 | The library is provided as-is. The author makes no representations or warranties of any kind, expressed or implied, as to the operation 261 | of the library, and is not responsible for any damage/side effect that the use of this library may cause. 262 | 263 | -------------------------------------------------------------------------------- /code/batman-comic.css: -------------------------------------------------------------------------------- 1 | /** 2 | ** Batman-Comic.CSS 3 | ** Copyright 2024 Alvaro Montoro (alvaromontoro@gmail.com) 4 | **/ 5 | 6 | @import url('https://fonts.googleapis.com/css2?family=Comic+Neue:wght@400;700'); 7 | 8 | :where(.batman-comic) { 9 | --size: 1vmin; 10 | font-size: var(--size); 11 | position: relative; 12 | display: grid; 13 | grid-template-columns: repeat(3, 1fr); 14 | gap: 1vmin; 15 | width: 98vmin; 16 | margin-bottom: 1em; 17 | 18 | .comic-description { 19 | position: absolute; 20 | width: 1px; 21 | height: 1px; 22 | overflow: hidden; 23 | clip-path: rect(0,0,0,0); 24 | } 25 | 26 | &.four-panels { 27 | font-size: calc(var(--size) * 0.8); 28 | width: 98vmin; 29 | grid-template-columns: repeat(4, 1fr); 30 | 31 | & > section { 32 | border: 0.4em solid; 33 | } 34 | } 35 | 36 | & > .panel, 37 | & > section { 38 | position: relative; 39 | border: 0.5em solid; 40 | border-radius: 0.5em; 41 | height: 32em; 42 | box-sizing: border-box; 43 | background: linear-gradient(#c9c6, #c9c0 80%); 44 | overflow: hidden; 45 | 46 | &.two { 47 | grid-column-end: span 2; 48 | } 49 | 50 | &.three { 51 | grid-column-end: span 3; 52 | } 53 | 54 | &.four { 55 | grid-column-end: span 4; 56 | } 57 | 58 | & *, 59 | & *::before, 60 | & *::after { 61 | position: absolute; 62 | box-sizing: border-box; 63 | } 64 | } 65 | 66 | .bubble { 67 | transform: translateX(-50%); 68 | font-size: 1.6em; 69 | font-family: 'Comic Neue', 'Comic Sans', 'Comic Sans MS', Helvetica, Arial, sans-serif; 70 | text-align: center; 71 | text-wrap: balance; 72 | 73 | &::before { 74 | --pos: 50%; 75 | content: ""; 76 | width: 2em; 77 | height: 3em; 78 | border-radius: 0 0 100% 0; 79 | border: 0.15em solid; 80 | border-top: 0; 81 | clip-path: polygon(0.2em 0.2em, 100% 0.2em, 100% 100%, 0.2em 100%); 82 | transform: translate(-50%, -0.2em); 83 | left: var(--pos); 84 | top: 100%; 85 | } 86 | 87 | &.short { 88 | &::before { 89 | height: 2em; 90 | } 91 | } 92 | 93 | &.tall { 94 | &::before { 95 | height: 4em; 96 | } 97 | } 98 | 99 | &.left { 100 | &::before { 101 | transform: translate(-50%) scaleX(-1); 102 | } 103 | } 104 | 105 | &.off-panel { 106 | &::before { 107 | width: 100%; 108 | transform: translate(-100%); 109 | } 110 | 111 | &.left { 112 | &::before { 113 | transform: translate(0%) scaleX(-1); 114 | } 115 | } 116 | } 117 | } 118 | 119 | .batman { 120 | /* colors */ 121 | --skin-color: #fca; 122 | --mouth-color: #700; 123 | --suit-color: #333; 124 | --suit-color-dark: #222; 125 | --logo-color: #ff5; 126 | --logo-color-dark: #dd2; 127 | --eye-color: #fff; 128 | /* others */ 129 | --mouth: radial-gradient(farthest-side at 50% 0, var(--mouth-color) 99%, #0000) 50% 90% / 13% 8% no-repeat; 130 | --mouth-position: 50%; 131 | --mouth-direction: linear-gradient(#0000 0 0); 132 | --arms-position: 50%; 133 | --arms-width: 54%; 134 | --arms-height: 115%; 135 | --eye1-size: 8%; 136 | --eye2-size: 8%; 137 | --eyelids: linear-gradient(#0000 0 0); 138 | --extra: linear-gradient(#0000 0 0); 139 | --extra-under-mask: linear-gradient(#0000 0 0); 140 | --ears: 141 | radial-gradient(150% 150% at 10% 36%, var(--suit-color-dark) 5%, #0000 5.25%), 142 | radial-gradient(150% 150% at 90% 36%, var(--suit-color-dark) 5%, #0000 5.25%) 143 | ; 144 | /* modifiers */ 145 | --rotation: 0deg; 146 | width: 19em; 147 | height: 22em; 148 | background: 149 | /* ears */ 150 | var(--ears), 151 | /* cuello */ 152 | radial-gradient(var(--suit-color-dark) 20%, #0000 21%), 153 | /* logo */ 154 | linear-gradient(to top right, var(--suit-color) 50%, #0000 0) 50.5% 74% / 4% 4% no-repeat, 155 | linear-gradient(to top left, var(--suit-color) 50%, #0000 0) 49.5% 74% / 4% 4% no-repeat, 156 | conic-gradient(from 340deg, var(--suit-color) 40deg, #0000 41deg) 50% 80% / 10% 7% no-repeat, 157 | conic-gradient(from 340deg, var(--suit-color) 40deg, #0000 41deg) 47.5% 79% / 10% 5% no-repeat, 158 | conic-gradient(from 340deg, var(--suit-color) 40deg, #0000 41deg) 52.5% 79% / 10% 5% no-repeat, 159 | radial-gradient(14% 5% at 50% 75%, var(--logo-color) 36% 49%, #0000 50%) 50% 69% / 60% 60% no-repeat, 160 | radial-gradient(14% 5% at 50% 75%, var(--logo-color) 36% 49%, #0000 50%) 50% 81.1% / 60% 60% no-repeat, 161 | radial-gradient(20% 10% at 50% 75%, var(--suit-color) 35%, var(--logo-color) 36% 49%, #0000 50%), 162 | /* cuerpo */ 163 | linear-gradient(var(--logo-color-dark) 0 0) 50% 100% / 8% 6% no-repeat, 164 | linear-gradient(var(--logo-color-dark) 0 0) 37% 100% / 3% 6% no-repeat, 165 | linear-gradient(var(--logo-color-dark) 0 0) 63% 100% / 3% 6% no-repeat, 166 | linear-gradient(var(--logo-color) 0 0) 50% 100% / 40% 5% no-repeat, 167 | conic-gradient(at 50% -20%, #0000 170deg, var(--suit-color) 170.33deg 189.66deg, #0000 190deg) 50% 100% / 80% 80% no-repeat, 168 | /* brazos */ 169 | radial-gradient(var(--arms-width) 115% at var(--arms-position) 118%, var(--suit-color-dark) 55%, #0000 55.2%); 170 | bottom: 0; 171 | left: 50%; 172 | transform: translate(-50%, 0) rotate(var(--rotation)); 173 | transform-origin: 50% 100%; 174 | box-shadow: 175 | 0 10em 0 -5.5em var(--suit-color), 176 | 0 10em 0 -4.1em var(--suit-color-dark); 177 | 178 | &::before { 179 | content: ""; 180 | --rotation: 0deg; 181 | width: 17em; 182 | height: 12em; 183 | background: 184 | var(--extra), 185 | /* eyes */ 186 | var(--eyelids), 187 | radial-gradient(circle at 35% 53%, var(--eye-color) var(--eye1-size), #0000 calc(var(--eye1-size) + 0.6%)), 188 | radial-gradient(circle at 65% 53%, var(--eye-color) var(--eye2-size), #0000 calc(var(--eye2-size) + 0.6%)), 189 | /* mask */ 190 | linear-gradient(100deg, var(--suit-color) 30%, #0000 30.25%), 191 | linear-gradient(-100deg, var(--suit-color) 30%, #0000 30.25%), 192 | linear-gradient(-181deg, var(--suit-color) 69%, #0000 69.25%), 193 | conic-gradient(from -50deg at 50% 76%, #0000, var(--suit-color) 1deg 99deg, #0000 100deg), 194 | /* extra under mask */ 195 | var(--extra-under-mask), 196 | /* mouth */ 197 | var(--mouth-direction), 198 | var(--mouth), 199 | var(--skin-color); 200 | border-radius: 50% / 20%; 201 | top: 5%; 202 | left: 50%; 203 | transform: translateX(-50%) rotate(var(--rotation)); 204 | transform-origin: 50% 100%; 205 | clip-path: polygon(10% 0, 90% 0, 100% 80%, 100% 100%, 0 100%, 0 80%) 206 | } 207 | 208 | &::after { 209 | --rotation: 0deg; 210 | content: ""; 211 | width: 17em; 212 | height: 25%; 213 | left: 50%; 214 | top: -8%; 215 | transform: translateX(-50%) rotate(var(--rotation)); 216 | transform-origin: 50% 100%; 217 | background: 218 | /* linear-gradient(-120deg, #0000 87%, var(--gray) 88%), 219 | linear-gradient(120deg, #0000 87%, var(--gray) 88%), */ 220 | conic-gradient(from 160deg at 11% 0, var(--suit-color) 26deg, #0000 27deg) no-repeat, 221 | conic-gradient(from 174deg at 89% 0, #0000, var(--suit-color) 1deg 26deg, #0000 27deg) no-repeat 222 | ; 223 | } 224 | 225 | &.rotate-head-right { 226 | --ears: 227 | radial-gradient(150% 150% at 16% 32%, var(--suit-color-dark) 5%, #0000 5.25%), 228 | radial-gradient(150% 150% at 92.5% 43%, var(--suit-color-dark) 5%, #0000 5.25%) 229 | ; 230 | 231 | &::before { 232 | --rotation: 10deg; 233 | top: 7%; 234 | } 235 | 236 | &::after { 237 | --rotation: 10deg; 238 | left: 59%; 239 | top: -6%; 240 | } 241 | } 242 | 243 | &.rotate-head-left { 244 | --ears: 245 | radial-gradient(150% 150% at 7.5% 45%, var(--suit-color-dark) 5%, #0000 5.25%), 246 | radial-gradient(150% 150% at 83% 33%, var(--suit-color-dark) 5%, #0000 5.25%) 247 | ; 248 | 249 | &::before { 250 | --rotation: -10deg; 251 | top: 7%; 252 | } 253 | 254 | &::after { 255 | --rotation: -10deg; 256 | left: 41.5%; 257 | top: -6%; 258 | } 259 | } 260 | 261 | /* general cara */ 262 | &.blush { 263 | --extra-under-mask: 264 | radial-gradient(40% 40% at 30% 50%, #f006, #0000), 265 | radial-gradient(40% 40% at 70% 50%, #f006, #0000); 266 | } 267 | &.scare { 268 | --extra-under-mask: 269 | radial-gradient(40% 40% at 30% 50%, #00f3, #0000), 270 | radial-gradient(40% 40% at 70% 50%, #00f3, #0000); 271 | } 272 | &.shame { 273 | --extra-under-mask: 274 | radial-gradient(40% 40% at 30% 50%, #f006, #0000), 275 | radial-gradient(40% 40% at 70% 50%, #f006, #0000); 276 | } 277 | 278 | /* boca */ 279 | &.mouth-no { 280 | --mouth: linear-gradient(#0000 0 0); 281 | } 282 | 283 | &.mouth-angry, 284 | &.mouth-sad { 285 | --mouth: radial-gradient(farthest-side at 50% 100%, var(--mouth-color) 99%, #0000) var(--mouth-position) 90% / 13% 8% no-repeat; 286 | } 287 | 288 | &.mouth-talk { 289 | --mouth: radial-gradient(farthest-side at 50% 100%, var(--mouth-color) 99%, #0000) var(--mouth-position) 88% / 15% 5% no-repeat; 290 | } 291 | 292 | &.mouth-round { 293 | --mouth: radial-gradient(circle at var(--mouth-position) 86%, var(--mouth-color) 3%, #0000 4%); 294 | } 295 | 296 | &.mouth-whisper { 297 | --mouth: radial-gradient(55% 100% at var(--mouth-position) 86%, var(--mouth-color) 3%, #0000 4%); 298 | } 299 | 300 | &.mouth-to-right { 301 | --mouth-direction: linear-gradient(186deg, #0000 86%, var(--skin-color) 86.5%) var(--mouth-position) 50% / 30% 100% no-repeat; 302 | } 303 | 304 | &.mouth-to-left { 305 | --mouth-direction: linear-gradient(174deg, #0000 86%, var(--skin-color) 86.5%) var(--mouth-position) 50% / 30% 100% no-repeat; 306 | } 307 | 308 | &.mouth-left { 309 | --mouth-position: 45%; 310 | } 311 | 312 | &.mouth-right { 313 | --mouth-position: 55%; 314 | } 315 | 316 | 317 | /* eyes */ 318 | &.eyes-no { 319 | --eye-color: #0000; 320 | } 321 | 322 | &.eyes-think { 323 | --eyelids: linear-gradient(var(--suit-color) 48%, #0000 0); 324 | } 325 | 326 | &.eyes-doubt { 327 | --eyelids: linear-gradient(var(--suit-color) 47%, #0000 0 60%, var(--suit-color) 0 70%, #0000 0); 328 | } 329 | 330 | &.eyes-sad { 331 | --eyelids: conic-gradient(at 50% 45%, var(--suit-color) 105deg, #0000 0 255deg, var(--suit-color) 0); 332 | } 333 | 334 | &.eyes-angry { 335 | --eyelids: conic-gradient(at 50% 55%, var(--suit-color) 80deg, #0000 0 280deg, var(--suit-color) 0); 336 | } 337 | 338 | &.eyes-suspicious { 339 | --eyelids: conic-gradient(at 52% 55%, var(--suit-color) 83deg, #0000 0 285deg, var(--suit-color) 0); 340 | } 341 | 342 | &.eyes-surprise { 343 | --eye1-size: 12%; 344 | --eye2-size: 12%; 345 | } 346 | 347 | &.eyes-shock { 348 | --eye1-size: 9%; 349 | --eye2-size: 11%; 350 | } 351 | } 352 | 353 | 354 | 355 | .robin { 356 | /* colores */ 357 | --skin-color: #fca; 358 | --skin-color-dark: #da8; 359 | --mouth-color: #fff; 360 | --suit-color: #f00; 361 | --shirt-color: #080; 362 | --cape-color: #ff5; 363 | --logo-color: #ff5; 364 | --logo-color-dark: #000; 365 | --eye-color: #fff; 366 | --mask-color: #000; 367 | --hair-color: #000; 368 | /* otros */ 369 | --mouth: 370 | radial-gradient(100% 140% at 50% 0%, var(--mouth-color) 30%, #0000 30.5%) 50% 100% / 30% 22% no-repeat; 371 | --mouth-position: 50%; 372 | --mouth-direction: linear-gradient(#0000 0 0); 373 | --arms-position: 50%; 374 | --arms-width: 54%; 375 | --arms-height: 115%; 376 | --eye1-size: 8%; 377 | --eye2-size: 8%; 378 | --eyelids: linear-gradient(#0000 0 0); 379 | --extra: linear-gradient(#0000 0 0); 380 | --extra-under-mask: linear-gradient(#0000 0 0); 381 | --ears: 382 | radial-gradient(circle at 6% 35%, var(--skin-color-dark) 5%, #0000 5.25%), 383 | radial-gradient(circle at 94% 35%, var(--skin-color-dark) 5%, #0000 5.25%); 384 | /* modifiers */ 385 | --rotation: 0deg; 386 | --dir: 50%; 387 | width: 19em; 388 | height: 20em; 389 | background: 390 | /* ears */ 391 | var(--ears), 392 | /* cuello */ 393 | conic-gradient(at 50% 100%, var(--skin-color-dark) 40deg, #0000 42deg 318deg, var(--skin-color-dark) 320deg) var(--dir) 55% / 80% 20% no-repeat, 394 | radial-gradient(var(--cape-color) 21%, #0000 21.5%), 395 | /* botones */ 396 | linear-gradient(90deg, #0000 47%, var(--cape-color) 0 53%, #0000 0) var(--dir) 75% / 80% 2% no-repeat, 397 | linear-gradient(90deg, #0000 47%, var(--cape-color) 0 53%, #0000 0) var(--dir) 85% / 80% 2% no-repeat, 398 | linear-gradient(90deg, #0000 47%, var(--cape-color) 0 53%, #0000 0) var(--dir) 95% / 80% 2% no-repeat, 399 | /* robin logo */ 400 | linear-gradient(var(--logo-color) 0 0) 56.75% 77% / 1.5% 7% no-repeat, 401 | radial-gradient(farthest-side at 0 50%, #0000 70%, var(--logo-color) 72% 98%, #0000 99.9%) 59.75% 74.75% / 4% 4.5% no-repeat, 402 | linear-gradient(45deg, #0000 45%, var(--logo-color) 47% 68%, #0000 70%) 60% 78% / 3% 3% no-repeat, 403 | radial-gradient(circle at 58% 75%, var(--logo-color-dark) 4%, #0000 4.5%), 404 | /* cuerpo */ 405 | conic-gradient(at 50% -20%, #0000 170deg, var(--suit-color) 170.33deg 189.66deg, #0000 190deg) 50% 100% / 80% 80% no-repeat, 406 | /* mangas y brazos */ 407 | conic-gradient(at 50% 5%, #0000 155deg, var(--shirt-color) 155.5deg 204.75deg, #0000 205deg) 50% 60% / 80% 50% no-repeat, 408 | radial-gradient(50% 50% at 50.125% 0, var(--shirt-color) 99%, #0000 99%) 50% 84% / 45% 5% no-repeat, 409 | conic-gradient(at 55% -250%, #0000 170deg, var(--skin-color-dark) 170.25deg 193.75deg, #0000 194deg) 50% 100% / 70% 30% no-repeat 410 | ; 411 | bottom: 0; 412 | left: 50%; 413 | transform: translate(-50%, 0) rotate(var(--rotation)); 414 | transform-origin: 50% 100%; 415 | box-shadow: 416 | 0 7em 0 -6.2em var(--suit-color), 417 | 0 10em 0 -6.2em var(--suit-color), 418 | 0 10em 0 -5em var(--skin-color-dark); 419 | 420 | &::before { 421 | --rotation: 0deg; 422 | content: ""; 423 | width: 16em; 424 | height: 11em; 425 | border-radius: 50% / 20%; 426 | top: 5%; 427 | left: 50%; 428 | transform: translateX(-50%) rotate(var(--rotation)); 429 | background: 430 | var(--extra), 431 | /* eyes + mascara */ 432 | var(--eyelids), 433 | radial-gradient(circle at 35% 47%, var(--eye-color) var(--eye1-size), #0000 calc(var(--eye1-size) + 0.5%)), 434 | radial-gradient(circle at 65% 47%, var(--eye-color) var(--eye2-size), #0000 calc(var(--eye2-size) + 0.5%)), 435 | radial-gradient(75% 70% at 30% 45%, var(--mask-color) 30%, #0000 31%), 436 | radial-gradient(75% 70% at 70% 45%, var(--mask-color) 30%, #0000 31%), 437 | /* nariz */ 438 | conic-gradient(at 50% 100%, var(--skin-color-dark) 34deg, #0000 36deg 324deg, var(--skin-color-dark) 326deg) 50% 65% / 20% 20% no-repeat, 439 | /* boca */ 440 | var(--mouth-direction), 441 | var(--mouth), 442 | /* base */ 443 | var(--extra-under-mask), 444 | var(--skin-color); 445 | } 446 | 447 | &::after { 448 | --rotation: 0deg; 449 | content: ""; 450 | width: 80%; 451 | height: 20%; 452 | left: 50%; 453 | top: 0.4%; 454 | transform: translate(-50%, -50%) rotate(var(--rotation)); 455 | background: 456 | conic-gradient(at 50% 20%, #0000 100deg, var(--hair-color) 101deg 140deg, #0000 142deg), 457 | radial-gradient(100% 100% at 60% 100%, var(--hair-color) 45%, #0000 46%) 458 | ; 459 | border-radius: 100%; 460 | box-shadow: inset -5em -0.5em var(--hair-color); 461 | } 462 | 463 | &.rotate-head-right { 464 | --ears: 465 | radial-gradient(circle at 12% 25%, var(--skin-color-dark) 5%, #0000 5.25%), 466 | radial-gradient(circle at 94.5% 41%, var(--skin-color-dark) 5%, #0000 5.25%); 467 | 468 | &::before { 469 | --rotation: 10deg; 470 | top: 4%; 471 | left: 55%; 472 | } 473 | 474 | &::after { 475 | --rotation: 10deg; 476 | left: 59%; 477 | top: 0%; 478 | } 479 | } 480 | 481 | &.rotate-head-left { 482 | --ears: 483 | radial-gradient(150% 150% at 8% 40%, var(--skin-color-dark) 5%, #0000 5.25%), 484 | radial-gradient(150% 150% at 91% 26%, var(--skin-color-dark) 5%, #0000 5.25%) 485 | ; 486 | 487 | &::before { 488 | --rotation: -10deg; 489 | top: 4%; 490 | } 491 | 492 | &::after { 493 | --rotation: -10deg; 494 | left: 49%; 495 | top: -2%; 496 | } 497 | } 498 | 499 | /* general cara */ 500 | &.blush { 501 | --extra-under-mask: 502 | radial-gradient(40% 40% at 30% 60%, #f002, #f000), 503 | radial-gradient(40% 40% at 70% 60%, #f002, #f000); 504 | } 505 | 506 | &.scare { 507 | --extra-under-mask: 508 | linear-gradient(#00f3, #f000 40%); 509 | } 510 | 511 | &.shame { 512 | --extra-under-mask: 513 | radial-gradient(40% 40% at 30% 50%, #f003, #0000), 514 | radial-gradient(40% 40% at 70% 50%, #f006, #0000); 515 | } 516 | 517 | /* boca */ 518 | &.mouth-no { 519 | --mouth: linear-gradient(#0000 0 0); 520 | } 521 | 522 | &.mouth-angry, 523 | &.mouth-sad { 524 | --mouth: radial-gradient(farthest-side at 50% 100%, var(--mouth-color) 99%, #0000) var(--mouth-position) 87% / 13% 8% no-repeat; 525 | } 526 | 527 | &.mouth-talk { 528 | --mouth: radial-gradient(farthest-side at 50% 100%, var(--mouth-color) 99%, #0000) var(--mouth-position) 86% / 14% 6% no-repeat; 529 | } 530 | 531 | &.mouth-round { 532 | --mouth: radial-gradient(circle at var(--mouth-position) 85%, var(--mouth-color) 3%, #0000 4%); 533 | } 534 | 535 | &.mouth-whisper { 536 | --mouth: radial-gradient(55% 100% at var(--mouth-position) 84%, var(--mouth-color) 3%, #0000 4%); 537 | } 538 | 539 | &.mouth-to-right { 540 | --mouth-direction: linear-gradient(186deg, #0000 83%, var(--skin-color) 83.5%) var(--mouth-position) 50% / 30% 100% no-repeat; 541 | } 542 | 543 | &.mouth-to-left { 544 | --mouth-direction: linear-gradient(174deg, #0000 83%, var(--skin-color) 83.5%) var(--mouth-position) 100% / 30% 90% no-repeat; 545 | } 546 | 547 | &.mouth-left { 548 | --mouth-position: 45%; 549 | } 550 | 551 | &.mouth-right { 552 | --mouth-position: 55%; 553 | } 554 | 555 | 556 | /* eyes */ 557 | &.eyes-no { 558 | --eye-color: #0000; 559 | } 560 | 561 | &.eyes-think { 562 | --eyelids: linear-gradient(var(--mask-color) 48%, #0000 0) 50% 45% / 50% 15% no-repeat; 563 | } 564 | 565 | &.eyes-doubt { 566 | --eyelids: 567 | linear-gradient(var(--mask-color) 25%, #0000 0 60%, var(--mask-color) 0 70%, #0000 0) 30% 50% / 25% 35% no-repeat, 568 | linear-gradient(var(--mask-color) 25%, #0000 0 60%, var(--mask-color) 0 70%, #0000 0) 70% 50% / 25% 35% no-repeat; 569 | } 570 | 571 | &.eyes-sad { 572 | --eyelids: 573 | linear-gradient(170deg, var(--mask-color) 35%, #0000 36%) 30% 50% / 25% 35% no-repeat, 574 | linear-gradient(190deg, var(--mask-color) 35%, #0000 36%) 70% 50% / 25% 35% no-repeat; 575 | } 576 | 577 | &.eyes-angry { 578 | --eyelids: 579 | linear-gradient(190deg, var(--mask-color) 35%, #0000 36%) 30% 50% / 25% 35% no-repeat, 580 | linear-gradient(170deg, var(--mask-color) 35%, #0000 36%) 70% 50% / 25% 35% no-repeat; 581 | } 582 | 583 | &.eyes-suspicious { 584 | --eyelids: 585 | linear-gradient(185deg, var(--mask-color) 38%, #0000 39%) 30% 50% / 25% 35% no-repeat, 586 | linear-gradient(165deg, var(--mask-color) 32%, #0000 33%) 70% 50% / 25% 35% no-repeat; 587 | } 588 | 589 | &.eyes-surprise { 590 | --eye1-size: 12%; 591 | --eye2-size: 12%; 592 | } 593 | 594 | &.eyes-shock { 595 | --eye1-size: 9%; 596 | --eye2-size: 11%; 597 | } 598 | } 599 | 600 | 601 | /* posiciones personajes */ 602 | .pos-x-0 { left: 0%; } 603 | .pos-x-5 { left: 5%; } 604 | .pos-x-10 { left: 10%; } 605 | .pos-x-15 { left: 15%; } 606 | .pos-x-20 { left: 20%; } 607 | .pos-x-25 { left: 25%; } 608 | .pos-x-30 { left: 30%; } 609 | .pos-x-35 { left: 35%; } 610 | .pos-x-40 { left: 40%; } 611 | .pos-x-45 { left: 45%; } 612 | .pos-x-50 { left: 50%; } 613 | .pos-x-55 { left: 55%; } 614 | .pos-x-60 { left: 60%; } 615 | .pos-x-65 { left: 65%; } 616 | .pos-x-70 { left: 70%; } 617 | .pos-x-75 { left: 75%; } 618 | .pos-x-80 { left: 80%; } 619 | .pos-x-85 { left: 85%; } 620 | .pos-x-90 { left: 90%; } 621 | .pos-x-95 { left: 95%; } 622 | .pos-x-100 { left: 100%; } 623 | 624 | .pos-line-0 { &::before { left: 0%; } } 625 | .pos-line-5 { &::before { left: 5%; } } 626 | .pos-line-10 { &::before { left: 10%; } } 627 | .pos-line-15 { &::before { left: 15%; } } 628 | .pos-line-20 { &::before { left: 20%; } } 629 | .pos-line-25 { &::before { left: 25%; } } 630 | .pos-line-30 { &::before { left: 30%; } } 631 | .pos-line-35 { &::before { left: 35%; } } 632 | .pos-line-40 { &::before { left: 40%; } } 633 | .pos-line-45 { &::before { left: 45%; } } 634 | .pos-line-50 { &::before { left: 50%; } } 635 | .pos-line-55 { &::before { left: 55%; } } 636 | .pos-line-60 { &::before { left: 60%; } } 637 | .pos-line-65 { &::before { left: 65%; } } 638 | .pos-line-70 { &::before { left: 70%; } } 639 | .pos-line-75 { &::before { left: 75%; } } 640 | .pos-line-80 { &::before { left: 80%; } } 641 | .pos-line-85 { &::before { left: 85%; } } 642 | .pos-line-90 { &::before { left: 90%; } } 643 | .pos-line-95 { &::before { left: 95%; } } 644 | .pos-line-100 { &::before { left: 100%; } } 645 | 646 | .pos-y-0 { top: 0%; } 647 | .pos-y-5 { top: 5%; } 648 | .pos-y-10 { top: 10%; } 649 | .pos-y-15 { top: 15%; } 650 | .pos-y-20 { top: 20%; } 651 | .pos-y-25 { top: 25%; } 652 | .pos-y-30 { top: 30%; } 653 | .pos-y-35 { top: 35%; } 654 | .pos-y-40 { top: 40%; } 655 | .pos-y-45 { top: 45%; } 656 | .pos-y-50 { top: 50%; } 657 | .pos-y-55 { top: 55%; } 658 | .pos-y-60 { top: 60%; } 659 | .pos-y-65 { top: 65%; } 660 | .pos-y-70 { top: 70%; } 661 | .pos-y-75 { top: 75%; } 662 | .pos-y-80 { top: 80%; } 663 | .pos-y-85 { top: 85%; } 664 | .pos-y-90 { top: 90%; } 665 | .pos-y-95 { top: 95%; } 666 | .pos-y-100 { top: 100%; } 667 | 668 | .width-0 { width: 0%; } 669 | .width-5 { width: 5%; } 670 | .width-10 { width: 10%; } 671 | .width-15 { width: 15%; } 672 | .width-20 { width: 20%; } 673 | .width-25 { width: 25%; } 674 | .width-30 { width: 30%; } 675 | .width-35 { width: 35%; } 676 | .width-40 { width: 40%; } 677 | .width-45 { width: 45%; } 678 | .width-50 { width: 50%; } 679 | .width-55 { width: 55%; } 680 | .width-60 { width: 60%; } 681 | .width-65 { width: 65%; } 682 | .width-70 { width: 70%; } 683 | .width-75 { width: 75%; } 684 | .width-80 { width: 80%; } 685 | .width-85 { width: 85%; } 686 | .width-90 { width: 90%; } 687 | .width-95 { width: 95%; } 688 | .width-100 { width: 100%; } 689 | 690 | .rotate-0 { --rotation: 0deg; } 691 | .rotate-5 { --rotation: 5deg; } 692 | .rotate-10 { --rotation: 10deg; } 693 | .rotate-15 { --rotation: 15deg; } 694 | .rotate-20 { --rotation: 20deg; } 695 | .rotate-25 { --rotation: 25deg; } 696 | .rotate-30 { --rotation: 30deg; } 697 | .rotate--5 { --rotation: -5deg; } 698 | .rotate--10 { --rotation: -10deg; } 699 | .rotate--15 { --rotation: -15deg; } 700 | .rotate--20 { --rotation: -20deg; } 701 | .rotate--25 { --rotation: -25deg; } 702 | .rotate--30 { --rotation: -30deg; } 703 | } --------------------------------------------------------------------------------