updated css/js libraries
[e-DoKo.git] / css / bootstrap / mixins.less
1 //
2 // Mixins
3 // --------------------------------------------------
4
5
6 // Utilities
7 // -------------------------
8
9 // Clearfix
10 // Source: http://nicolasgallagher.com/micro-clearfix-hack/
11 //
12 // For modern browsers
13 // 1. The space content is one way to avoid an Opera bug when the
14 //    contenteditable attribute is included anywhere else in the document.
15 //    Otherwise it causes space to appear at the top and bottom of elements
16 //    that are clearfixed.
17 // 2. The use of `table` rather than `block` is only necessary if using
18 //    `:before` to contain the top-margins of child elements.
19 .clearfix() {
20   &:before,
21   &:after {
22     content: " "; // 1
23     display: table; // 2
24   }
25   &:after {
26     clear: both;
27   }
28 }
29
30 // WebKit-style focus
31 .tab-focus() {
32   // Default
33   outline: thin dotted;
34   // WebKit
35   outline: 5px auto -webkit-focus-ring-color;
36   outline-offset: -2px;
37 }
38
39 // Center-align a block level element
40 .center-block() {
41   display: block;
42   margin-left: auto;
43   margin-right: auto;
44 }
45
46 // Sizing shortcuts
47 .size(@width; @height) {
48   width: @width;
49   height: @height;
50 }
51 .square(@size) {
52   .size(@size; @size);
53 }
54
55 // Placeholder text
56 .placeholder(@color: @input-color-placeholder) {
57   &::-moz-placeholder           { color: @color;   // Firefox
58                                   opacity: 1; } // See https://github.com/twbs/bootstrap/pull/11526
59   &:-ms-input-placeholder       { color: @color; } // Internet Explorer 10+
60   &::-webkit-input-placeholder  { color: @color; } // Safari and Chrome
61 }
62
63 // Text overflow
64 // Requires inline-block or block for proper styling
65 .text-overflow() {
66   overflow: hidden;
67   text-overflow: ellipsis;
68   white-space: nowrap;
69 }
70
71 // CSS image replacement
72 //
73 // Heads up! v3 launched with with only `.hide-text()`, but per our pattern for
74 // mixins being reused as classes with the same name, this doesn't hold up. As
75 // of v3.0.1 we have added `.text-hide()` and deprecated `.hide-text()`. Note
76 // that we cannot chain the mixins together in Less, so they are repeated.
77 //
78 // Source: https://github.com/h5bp/html5-boilerplate/commit/aa0396eae757
79
80 // Deprecated as of v3.0.1 (will be removed in v4)
81 .hide-text() {
82   font: ~"0/0" a;
83   color: transparent;
84   text-shadow: none;
85   background-color: transparent;
86   border: 0;
87 }
88 // New mixin to use as of v3.0.1
89 .text-hide() {
90   .hide-text();
91 }
92
93
94
95 // CSS3 PROPERTIES
96 // --------------------------------------------------
97
98 // Single side border-radius
99 .border-top-radius(@radius) {
100   border-top-right-radius: @radius;
101    border-top-left-radius: @radius;
102 }
103 .border-right-radius(@radius) {
104   border-bottom-right-radius: @radius;
105      border-top-right-radius: @radius;
106 }
107 .border-bottom-radius(@radius) {
108   border-bottom-right-radius: @radius;
109    border-bottom-left-radius: @radius;
110 }
111 .border-left-radius(@radius) {
112   border-bottom-left-radius: @radius;
113      border-top-left-radius: @radius;
114 }
115
116 // Drop shadows
117 //
118 // Note: Deprecated `.box-shadow()` as of v3.1.0 since all of Bootstrap's
119 //   supported browsers that have box shadow capabilities now support the
120 //   standard `box-shadow` property.
121 .box-shadow(@shadow) {
122   -webkit-box-shadow: @shadow; // iOS <4.3 & Android <4.1
123           box-shadow: @shadow;
124 }
125
126 // Transitions
127 .transition(@transition) {
128   -webkit-transition: @transition;
129           transition: @transition;
130 }
131 .transition-property(@transition-property) {
132   -webkit-transition-property: @transition-property;
133           transition-property: @transition-property;
134 }
135 .transition-delay(@transition-delay) {
136   -webkit-transition-delay: @transition-delay;
137           transition-delay: @transition-delay;
138 }
139 .transition-duration(@transition-duration) {
140   -webkit-transition-duration: @transition-duration;
141           transition-duration: @transition-duration;
142 }
143 .transition-transform(@transition) {
144   -webkit-transition: -webkit-transform @transition;
145      -moz-transition: -moz-transform @transition;
146        -o-transition: -o-transform @transition;
147           transition: transform @transition;
148 }
149
150 // Transformations
151 .rotate(@degrees) {
152   -webkit-transform: rotate(@degrees);
153       -ms-transform: rotate(@degrees); // IE9 only
154           transform: rotate(@degrees);
155 }
156 .scale(@ratio; @ratio-y...) {
157   -webkit-transform: scale(@ratio, @ratio-y);
158       -ms-transform: scale(@ratio, @ratio-y); // IE9 only
159           transform: scale(@ratio, @ratio-y);
160 }
161 .translate(@x; @y) {
162   -webkit-transform: translate(@x, @y);
163       -ms-transform: translate(@x, @y); // IE9 only
164           transform: translate(@x, @y);
165 }
166 .skew(@x; @y) {
167   -webkit-transform: skew(@x, @y);
168       -ms-transform: skewX(@x) skewY(@y); // See https://github.com/twbs/bootstrap/issues/4885; IE9+
169           transform: skew(@x, @y);
170 }
171 .translate3d(@x; @y; @z) {
172   -webkit-transform: translate3d(@x, @y, @z);
173           transform: translate3d(@x, @y, @z);
174 }
175
176 .rotateX(@degrees) {
177   -webkit-transform: rotateX(@degrees);
178       -ms-transform: rotateX(@degrees); // IE9 only
179           transform: rotateX(@degrees);
180 }
181 .rotateY(@degrees) {
182   -webkit-transform: rotateY(@degrees);
183       -ms-transform: rotateY(@degrees); // IE9 only
184           transform: rotateY(@degrees);
185 }
186 .perspective(@perspective) {
187   -webkit-perspective: @perspective;
188      -moz-perspective: @perspective;
189           perspective: @perspective;
190 }
191 .perspective-origin(@perspective) {
192   -webkit-perspective-origin: @perspective;
193      -moz-perspective-origin: @perspective;
194           perspective-origin: @perspective;
195 }
196 .transform-origin(@origin) {
197   -webkit-transform-origin: @origin;
198      -moz-transform-origin: @origin;
199       -ms-transform-origin: @origin; // IE9 only
200           transform-origin: @origin;
201 }
202
203 // Animations
204 .animation(@animation) {
205   -webkit-animation: @animation;
206           animation: @animation;
207 }
208 .animation-name(@name) {
209   -webkit-animation-name: @name;
210           animation-name: @name;
211 }
212 .animation-duration(@duration) {
213   -webkit-animation-duration: @duration;
214           animation-duration: @duration;
215 }
216 .animation-timing-function(@timing-function) {
217   -webkit-animation-timing-function: @timing-function;
218           animation-timing-function: @timing-function;
219 }
220 .animation-delay(@delay) {
221   -webkit-animation-delay: @delay;
222           animation-delay: @delay;
223 }
224 .animation-iteration-count(@iteration-count) {
225   -webkit-animation-iteration-count: @iteration-count;
226           animation-iteration-count: @iteration-count;
227 }
228 .animation-direction(@direction) {
229   -webkit-animation-direction: @direction;
230           animation-direction: @direction;
231 }
232
233 // Backface visibility
234 // Prevent browsers from flickering when using CSS 3D transforms.
235 // Default value is `visible`, but can be changed to `hidden`
236 .backface-visibility(@visibility){
237   -webkit-backface-visibility: @visibility;
238      -moz-backface-visibility: @visibility;
239           backface-visibility: @visibility;
240 }
241
242 // Box sizing
243 .box-sizing(@boxmodel) {
244   -webkit-box-sizing: @boxmodel;
245      -moz-box-sizing: @boxmodel;
246           box-sizing: @boxmodel;
247 }
248
249 // User select
250 // For selecting text on the page
251 .user-select(@select) {
252   -webkit-user-select: @select;
253      -moz-user-select: @select;
254       -ms-user-select: @select; // IE10+
255           user-select: @select;
256 }
257
258 // Resize anything
259 .resizable(@direction) {
260   resize: @direction; // Options: horizontal, vertical, both
261   overflow: auto; // Safari fix
262 }
263
264 // CSS3 Content Columns
265 .content-columns(@column-count; @column-gap: @grid-gutter-width) {
266   -webkit-column-count: @column-count;
267      -moz-column-count: @column-count;
268           column-count: @column-count;
269   -webkit-column-gap: @column-gap;
270      -moz-column-gap: @column-gap;
271           column-gap: @column-gap;
272 }
273
274 // Optional hyphenation
275 .hyphens(@mode: auto) {
276   word-wrap: break-word;
277   -webkit-hyphens: @mode;
278      -moz-hyphens: @mode;
279       -ms-hyphens: @mode; // IE10+
280        -o-hyphens: @mode;
281           hyphens: @mode;
282 }
283
284 // Opacity
285 .opacity(@opacity) {
286   opacity: @opacity;
287   // IE8 filter
288   @opacity-ie: (@opacity * 100);
289   filter: ~"alpha(opacity=@{opacity-ie})";
290 }
291
292
293
294 // GRADIENTS
295 // --------------------------------------------------
296
297 #gradient {
298
299   // Horizontal gradient, from left to right
300   //
301   // Creates two color stops, start and end, by specifying a color and position for each color stop.
302   // Color stops are not available in IE9 and below.
303   .horizontal(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {
304     background-image: -webkit-linear-gradient(left, color-stop(@start-color @start-percent), color-stop(@end-color @end-percent)); // Safari 5.1-6, Chrome 10+
305     background-image:  linear-gradient(to right, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+
306     background-repeat: repeat-x;
307     filter: e(%("progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)",argb(@start-color),argb(@end-color))); // IE9 and down
308   }
309
310   // Vertical gradient, from top to bottom
311   //
312   // Creates two color stops, start and end, by specifying a color and position for each color stop.
313   // Color stops are not available in IE9 and below.
314   .vertical(@start-color: #555; @end-color: #333; @start-percent: 0%; @end-percent: 100%) {
315     background-image: -webkit-linear-gradient(top, @start-color @start-percent, @end-color @end-percent);  // Safari 5.1-6, Chrome 10+
316     background-image: linear-gradient(to bottom, @start-color @start-percent, @end-color @end-percent); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+
317     background-repeat: repeat-x;
318     filter: e(%("progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)",argb(@start-color),argb(@end-color))); // IE9 and down
319   }
320
321   .directional(@start-color: #555; @end-color: #333; @deg: 45deg) {
322     background-repeat: repeat-x;
323     background-image: -webkit-linear-gradient(@deg, @start-color, @end-color); // Safari 5.1-6, Chrome 10+
324     background-image: linear-gradient(@deg, @start-color, @end-color); // Standard, IE10, Firefox 16+, Opera 12.10+, Safari 7+, Chrome 26+
325   }
326   .horizontal-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {
327     background-image: -webkit-linear-gradient(left, @start-color, @mid-color @color-stop, @end-color);
328     background-image: linear-gradient(to right, @start-color, @mid-color @color-stop, @end-color);
329     background-repeat: no-repeat;
330     filter: e(%("progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=1)",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback
331   }
332   .vertical-three-colors(@start-color: #00b3ee; @mid-color: #7a43b6; @color-stop: 50%; @end-color: #c3325f) {
333     background-image: -webkit-linear-gradient(@start-color, @mid-color @color-stop, @end-color);
334     background-image: linear-gradient(@start-color, @mid-color @color-stop, @end-color);
335     background-repeat: no-repeat;
336     filter: e(%("progid:DXImageTransform.Microsoft.gradient(startColorstr='%d', endColorstr='%d', GradientType=0)",argb(@start-color),argb(@end-color))); // IE9 and down, gets no color-stop at all for proper fallback
337   }
338   .radial(@inner-color: #555; @outer-color: #333) {
339     background-image: -webkit-radial-gradient(circle, @inner-color, @outer-color);
340     background-image: radial-gradient(circle, @inner-color, @outer-color);
341     background-repeat: no-repeat;
342   }
343   .striped(@color: rgba(255,255,255,.15); @angle: 45deg) {
344     background-image: -webkit-linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);
345     background-image: linear-gradient(@angle, @color 25%, transparent 25%, transparent 50%, @color 50%, @color 75%, transparent 75%, transparent);
346   }
347 }
348
349 // Reset filters for IE
350 //
351 // When you need to remove a gradient background, do not forget to use this to reset
352 // the IE filter for IE9 and below.
353 .reset-filter() {
354   filter: e(%("progid:DXImageTransform.Microsoft.gradient(enabled = false)"));
355 }
356
357
358
359 // Retina images
360 //
361 // Short retina mixin for setting background-image and -size
362
363 .img-retina(@file-1x; @file-2x; @width-1x; @height-1x) {
364   background-image: url("@{file-1x}");
365
366   @media
367   only screen and (-webkit-min-device-pixel-ratio: 2),
368   only screen and (   min--moz-device-pixel-ratio: 2),
369   only screen and (     -o-min-device-pixel-ratio: 2/1),
370   only screen and (        min-device-pixel-ratio: 2),
371   only screen and (                min-resolution: 192dpi),
372   only screen and (                min-resolution: 2dppx) {
373     background-image: url("@{file-2x}");
374     background-size: @width-1x @height-1x;
375   }
376 }
377
378
379 // Responsive image
380 //
381 // Keep images from scaling beyond the width of their parents.
382
383 .img-responsive(@display: block) {
384   display: @display;
385   max-width: 100%; // Part 1: Set a maximum relative to the parent
386   height: auto; // Part 2: Scale the height according to the width, otherwise you get stretching
387 }
388
389
390 // COMPONENT MIXINS
391 // --------------------------------------------------
392
393 // Horizontal dividers
394 // -------------------------
395 // Dividers (basically an hr) within dropdowns and nav lists
396 .nav-divider(@color: #e5e5e5) {
397   height: 1px;
398   margin: ((@line-height-computed / 2) - 1) 0;
399   overflow: hidden;
400   background-color: @color;
401 }
402
403 // Panels
404 // -------------------------
405 .panel-variant(@border; @heading-text-color; @heading-bg-color; @heading-border) {
406   border-color: @border;
407
408   & > .panel-heading {
409     color: @heading-text-color;
410     background-color: @heading-bg-color;
411     border-color: @heading-border;
412
413     + .panel-collapse .panel-body {
414       border-top-color: @border;
415     }
416   }
417   & > .panel-footer {
418     + .panel-collapse .panel-body {
419       border-bottom-color: @border;
420     }
421   }
422 }
423
424 // Alerts
425 // -------------------------
426 .alert-variant(@background; @border; @text-color) {
427   background-color: @background;
428   border-color: @border;
429   color: @text-color;
430
431   hr {
432     border-top-color: darken(@border, 5%);
433   }
434   .alert-link {
435     color: darken(@text-color, 10%);
436   }
437 }
438
439 // Tables
440 // -------------------------
441 .table-row-variant(@state; @background) {
442   // Exact selectors below required to override `.table-striped` and prevent
443   // inheritance to nested tables.
444   .table > thead > tr,
445   .table > tbody > tr,
446   .table > tfoot > tr {
447     > td.@{state},
448     > th.@{state},
449     &.@{state} > td,
450     &.@{state} > th {
451       background-color: @background;
452     }
453   }
454
455   // Hover states for `.table-hover`
456   // Note: this is not available for cells or rows within `thead` or `tfoot`.
457   .table-hover > tbody > tr {
458     > td.@{state}:hover,
459     > th.@{state}:hover,
460     &.@{state}:hover > td,
461     &.@{state}:hover > th {
462       background-color: darken(@background, 5%);
463     }
464   }
465 }
466
467 // List Groups
468 // -------------------------
469 .list-group-item-variant(@state; @background; @color) {
470   .list-group-item-@{state} {
471     color: @color;
472     background-color: @background;
473
474     a& {
475       color: @color;
476
477       .list-group-item-heading { color: inherit; }
478
479       &:hover,
480       &:focus {
481         color: @color;
482         background-color: darken(@background, 5%);
483       }
484       &.active,
485       &.active:hover,
486       &.active:focus {
487         color: #fff;
488         background-color: @color;
489         border-color: @color;
490       }
491     }
492   }
493 }
494
495 // Button variants
496 // -------------------------
497 // Easily pump out default styles, as well as :hover, :focus, :active,
498 // and disabled options for all buttons
499 .button-variant(@color; @background; @border) {
500   color: @color;
501   background-color: @background;
502   border-color: @border;
503
504   &:hover,
505   &:focus,
506   &:active,
507   &.active,
508   .open .dropdown-toggle& {
509     color: @color;
510     background-color: darken(@background, 8%);
511         border-color: darken(@border, 12%);
512   }
513   &:active,
514   &.active,
515   .open .dropdown-toggle& {
516     background-image: none;
517   }
518   &.disabled,
519   &[disabled],
520   fieldset[disabled] & {
521     &,
522     &:hover,
523     &:focus,
524     &:active,
525     &.active {
526       background-color: @background;
527           border-color: @border;
528     }
529   }
530
531   .badge {
532     color: @background;
533     background-color: @color;
534   }
535 }
536
537 // Button sizes
538 // -------------------------
539 .button-size(@padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {
540   padding: @padding-vertical @padding-horizontal;
541   font-size: @font-size;
542   line-height: @line-height;
543   border-radius: @border-radius;
544 }
545
546 // Pagination
547 // -------------------------
548 .pagination-size(@padding-vertical; @padding-horizontal; @font-size; @border-radius) {
549   > li {
550     > a,
551     > span {
552       padding: @padding-vertical @padding-horizontal;
553       font-size: @font-size;
554     }
555     &:first-child {
556       > a,
557       > span {
558         .border-left-radius(@border-radius);
559       }
560     }
561     &:last-child {
562       > a,
563       > span {
564         .border-right-radius(@border-radius);
565       }
566     }
567   }
568 }
569
570 // Labels
571 // -------------------------
572 .label-variant(@color) {
573   background-color: @color;
574   &[href] {
575     &:hover,
576     &:focus {
577       background-color: darken(@color, 10%);
578     }
579   }
580 }
581
582 // Contextual backgrounds
583 // -------------------------
584 .bg-variant(@color) {
585   background-color: @color;
586   a&:hover {
587     background-color: darken(@color, 10%);
588   }
589 }
590
591 // Typography
592 // -------------------------
593 .text-emphasis-variant(@color) {
594   color: @color;
595   a&:hover {
596     color: darken(@color, 10%);
597   }
598 }
599
600 // Navbar vertical align
601 // -------------------------
602 // Vertically center elements in the navbar.
603 // Example: an element has a height of 30px, so write out `.navbar-vertical-align(30px);` to calculate the appropriate top margin.
604 .navbar-vertical-align(@element-height) {
605   margin-top: ((@navbar-height - @element-height) / 2);
606   margin-bottom: ((@navbar-height - @element-height) / 2);
607 }
608
609 // Progress bars
610 // -------------------------
611 .progress-bar-variant(@color) {
612   background-color: @color;
613   .progress-striped & {
614     #gradient > .striped();
615   }
616 }
617
618 // Responsive utilities
619 // -------------------------
620 // More easily include all the states for responsive-utilities.less.
621 .responsive-visibility() {
622   display: block !important;
623   table&  { display: table; }
624   tr&     { display: table-row !important; }
625   th&,
626   td&     { display: table-cell !important; }
627 }
628
629 .responsive-invisibility() {
630   display: none !important;
631 }
632
633
634 // Grid System
635 // -----------
636
637 // Centered container element
638 .container-fixed() {
639   margin-right: auto;
640   margin-left: auto;
641   padding-left:  (@grid-gutter-width / 2);
642   padding-right: (@grid-gutter-width / 2);
643   &:extend(.clearfix all);
644 }
645
646 // Creates a wrapper for a series of columns
647 .make-row(@gutter: @grid-gutter-width) {
648   margin-left:  (@gutter / -2);
649   margin-right: (@gutter / -2);
650   &:extend(.clearfix all);
651 }
652
653 // Generate the extra small columns
654 .make-xs-column(@columns; @gutter: @grid-gutter-width) {
655   position: relative;
656   float: left;
657   width: percentage((@columns / @grid-columns));
658   min-height: 1px;
659   padding-left:  (@gutter / 2);
660   padding-right: (@gutter / 2);
661 }
662 .make-xs-column-offset(@columns) {
663   @media (min-width: @screen-xs-min) {
664     margin-left: percentage((@columns / @grid-columns));
665   }
666 }
667 .make-xs-column-push(@columns) {
668   @media (min-width: @screen-xs-min) {
669     left: percentage((@columns / @grid-columns));
670   }
671 }
672 .make-xs-column-pull(@columns) {
673   @media (min-width: @screen-xs-min) {
674     right: percentage((@columns / @grid-columns));
675   }
676 }
677
678
679 // Generate the small columns
680 .make-sm-column(@columns; @gutter: @grid-gutter-width) {
681   position: relative;
682   min-height: 1px;
683   padding-left:  (@gutter / 2);
684   padding-right: (@gutter / 2);
685
686   @media (min-width: @screen-sm-min) {
687     float: left;
688     width: percentage((@columns / @grid-columns));
689   }
690 }
691 .make-sm-column-offset(@columns) {
692   @media (min-width: @screen-sm-min) {
693     margin-left: percentage((@columns / @grid-columns));
694   }
695 }
696 .make-sm-column-push(@columns) {
697   @media (min-width: @screen-sm-min) {
698     left: percentage((@columns / @grid-columns));
699   }
700 }
701 .make-sm-column-pull(@columns) {
702   @media (min-width: @screen-sm-min) {
703     right: percentage((@columns / @grid-columns));
704   }
705 }
706
707
708 // Generate the medium columns
709 .make-md-column(@columns; @gutter: @grid-gutter-width) {
710   position: relative;
711   min-height: 1px;
712   padding-left:  (@gutter / 2);
713   padding-right: (@gutter / 2);
714
715   @media (min-width: @screen-md-min) {
716     float: left;
717     width: percentage((@columns / @grid-columns));
718   }
719 }
720 .make-md-column-offset(@columns) {
721   @media (min-width: @screen-md-min) {
722     margin-left: percentage((@columns / @grid-columns));
723   }
724 }
725 .make-md-column-push(@columns) {
726   @media (min-width: @screen-md-min) {
727     left: percentage((@columns / @grid-columns));
728   }
729 }
730 .make-md-column-pull(@columns) {
731   @media (min-width: @screen-md-min) {
732     right: percentage((@columns / @grid-columns));
733   }
734 }
735
736
737 // Generate the large columns
738 .make-lg-column(@columns; @gutter: @grid-gutter-width) {
739   position: relative;
740   min-height: 1px;
741   padding-left:  (@gutter / 2);
742   padding-right: (@gutter / 2);
743
744   @media (min-width: @screen-lg-min) {
745     float: left;
746     width: percentage((@columns / @grid-columns));
747   }
748 }
749 .make-lg-column-offset(@columns) {
750   @media (min-width: @screen-lg-min) {
751     margin-left: percentage((@columns / @grid-columns));
752   }
753 }
754 .make-lg-column-push(@columns) {
755   @media (min-width: @screen-lg-min) {
756     left: percentage((@columns / @grid-columns));
757   }
758 }
759 .make-lg-column-pull(@columns) {
760   @media (min-width: @screen-lg-min) {
761     right: percentage((@columns / @grid-columns));
762   }
763 }
764
765
766 // Framework grid generation
767 //
768 // Used only by Bootstrap to generate the correct number of grid classes given
769 // any value of `@grid-columns`.
770
771 .make-grid-columns() {
772   // Common styles for all sizes of grid columns, widths 1-12
773   .col(@index) when (@index = 1) { // initial
774     @item: ~".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}";
775     .col((@index + 1), @item);
776   }
777   .col(@index, @list) when (@index =< @grid-columns) { // general; "=<" isn't a typo
778     @item: ~".col-xs-@{index}, .col-sm-@{index}, .col-md-@{index}, .col-lg-@{index}";
779     .col((@index + 1), ~"@{list}, @{item}");
780   }
781   .col(@index, @list) when (@index > @grid-columns) { // terminal
782     @{list} {
783       position: relative;
784       // Prevent columns from collapsing when empty
785       min-height: 1px;
786       // Inner gutter via padding
787       padding-left:  (@grid-gutter-width / 2);
788       padding-right: (@grid-gutter-width / 2);
789     }
790   }
791   .col(1); // kickstart it
792 }
793
794 .float-grid-columns(@class) {
795   .col(@index) when (@index = 1) { // initial
796     @item: ~".col-@{class}-@{index}";
797     .col((@index + 1), @item);
798   }
799   .col(@index, @list) when (@index =< @grid-columns) { // general
800     @item: ~".col-@{class}-@{index}";
801     .col((@index + 1), ~"@{list}, @{item}");
802   }
803   .col(@index, @list) when (@index > @grid-columns) { // terminal
804     @{list} {
805       float: left;
806     }
807   }
808   .col(1); // kickstart it
809 }
810
811 .calc-grid-column(@index, @class, @type) when (@type = width) and (@index > 0) {
812   .col-@{class}-@{index} {
813     width: percentage((@index / @grid-columns));
814   }
815 }
816 .calc-grid-column(@index, @class, @type) when (@type = push) {
817   .col-@{class}-push-@{index} {
818     left: percentage((@index / @grid-columns));
819   }
820 }
821 .calc-grid-column(@index, @class, @type) when (@type = pull) {
822   .col-@{class}-pull-@{index} {
823     right: percentage((@index / @grid-columns));
824   }
825 }
826 .calc-grid-column(@index, @class, @type) when (@type = offset) {
827   .col-@{class}-offset-@{index} {
828     margin-left: percentage((@index / @grid-columns));
829   }
830 }
831
832 // Basic looping in LESS
833 .loop-grid-columns(@index, @class, @type) when (@index >= 0) {
834   .calc-grid-column(@index, @class, @type);
835   // next iteration
836   .loop-grid-columns((@index - 1), @class, @type);
837 }
838
839 // Create grid for specific class
840 .make-grid(@class) {
841   .float-grid-columns(@class);
842   .loop-grid-columns(@grid-columns, @class, width);
843   .loop-grid-columns(@grid-columns, @class, pull);
844   .loop-grid-columns(@grid-columns, @class, push);
845   .loop-grid-columns(@grid-columns, @class, offset);
846 }
847
848 // Form validation states
849 //
850 // Used in forms.less to generate the form validation CSS for warnings, errors,
851 // and successes.
852
853 .form-control-validation(@text-color: #555; @border-color: #ccc; @background-color: #f5f5f5) {
854   // Color the label and help text
855   .help-block,
856   .control-label,
857   .radio,
858   .checkbox,
859   .radio-inline,
860   .checkbox-inline  {
861     color: @text-color;
862   }
863   // Set the border and box shadow on specific inputs to match
864   .form-control {
865     border-color: @border-color;
866     .box-shadow(inset 0 1px 1px rgba(0,0,0,.075)); // Redeclare so transitions work
867     &:focus {
868       border-color: darken(@border-color, 10%);
869       @shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 6px lighten(@border-color, 20%);
870       .box-shadow(@shadow);
871     }
872   }
873   // Set validation states also for addons
874   .input-group-addon {
875     color: @text-color;
876     border-color: @border-color;
877     background-color: @background-color;
878   }
879   // Optional feedback icon
880   .form-control-feedback {
881     color: @text-color;
882   }
883 }
884
885 // Form control focus state
886 //
887 // Generate a customized focus state and for any input with the specified color,
888 // which defaults to the `@input-focus-border` variable.
889 //
890 // We highly encourage you to not customize the default value, but instead use
891 // this to tweak colors on an as-needed basis. This aesthetic change is based on
892 // WebKit's default styles, but applicable to a wider range of browsers. Its
893 // usability and accessibility should be taken into account with any change.
894 //
895 // Example usage: change the default blue border and shadow to white for better
896 // contrast against a dark gray background.
897
898 .form-control-focus(@color: @input-border-focus) {
899   @color-rgba: rgba(red(@color), green(@color), blue(@color), .6);
900   &:focus {
901     border-color: @color;
902     outline: 0;
903     .box-shadow(~"inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px @{color-rgba}");
904   }
905 }
906
907 // Form control sizing
908 //
909 // Relative text size, padding, and border-radii changes for form controls. For
910 // horizontal sizing, wrap controls in the predefined grid classes. `<select>`
911 // element gets special love because it's special, and that's a fact!
912
913 .input-size(@input-height; @padding-vertical; @padding-horizontal; @font-size; @line-height; @border-radius) {
914   height: @input-height;
915   padding: @padding-vertical @padding-horizontal;
916   font-size: @font-size;
917   line-height: @line-height;
918   border-radius: @border-radius;
919
920   select& {
921     height: @input-height;
922     line-height: @input-height;
923   }
924
925   textarea&,
926   select[multiple]& {
927     height: auto;
928   }
929 }