// Foundation for Sites by ZURB // foundation.zurb.com // Licensed under MIT Open Source //// /// @group flex-grid //// $-zf-flex-justify: ( 'left': flex-start, 'right': flex-end, 'center': center, 'justify': space-between, 'spaced': space-around, ); $-zf-flex-align: ( 'top': flex-start, 'bottom': flex-end, 'middle': center, 'stretch': stretch, ); /// Creates a container for a flex grid row. /// /// @param {Keyword|List} $behavior [null] /// Modifications to the default grid styles. `nest` indicates the row will be placed inside another row. `collapse` indicates that the columns inside this row will not have padding. `nest collapse` combines both behaviors. /// @param {Number} $width [$grid-row-width] - Maximum width of the row. /// @param {Number} $columns [null] - Number of columns to use for this row. If set to `null` (the default), the global column count will be used. /// @param {Boolean} $base [true] - Set to `false` to prevent basic styles from being output. Useful if you're calling this mixin on the same element twice, as it prevents duplicate CSS output. /// @param {Number} $gutter [$grid-column-gutter] - Gutter to use when inverting margins, in case the row is nested. @mixin flex-grid-row( $behavior: null, $width: $grid-row-width, $columns: null, $base: true, $gutter: $grid-column-gutter ) { $behavior: -zf-get-options($behavior, nest collapse); $margin: auto; @if map-get($behavior, nest) { @include grid-row-nest($gutter); @if map-get($behavior, collapse) { margin-left: 0; margin-right: 0; } } @else { max-width: $width; margin-left: auto; margin-right: auto; } @if $base { display: flex; flex-flow: row wrap; } @if $columns != null { @include grid-context($columns, $base) { @content; } } } /// Calculates the `flex` property for a flex grid column. It accepts all of the same values as the basic `grid-column()` function, along with two extras: /// - `null` (the default) will make the column expand to fill space. /// - `shrink` will make the column contract, so it only takes up the horizontal space it needs. /// /// @param {Mixed} $columns [null] - Width of the column. @function flex-grid-column($columns: null) { // scss-lint:disable ZeroUnit $flex: 1 1 0px; @if $columns == shrink { $flex: 0 0 auto; } @else if $columns != null { $flex: 0 0 grid-column($columns); } @return $flex; } /// Creates a column for a flex grid. By default, the column will stretch to the full width of its container, but this can be overridden with sizing classes, or by using the `unstack` class on the parent flex row. /// /// @param {Mixed} $columns [null] - Width of the column. Refer to the `flex-grid-column()` function to see possible values. /// @param {Number} $gutter [$grid-column-gutter] - Space between columns, added as a left and right padding. @mixin flex-grid-column( $columns: null, $gutter: $grid-column-gutter ) { @if $gutter != null { $gutter: rem-calc($gutter) / 2; } @else { @each $breakpoint, $gutter in $grid-column-responsive-gutter { $padding: rem-calc($gutter) / 2; @include breakpoint($breakpoint) { padding-left: $padding; padding-right: $padding; } } } flex: flex-grid-column($columns); padding-left: $gutter; padding-right: $gutter; // max-width fixes IE 10/11 not respecting the flex-basis property @if $columns != null and $columns != shrink { max-width: grid-column($columns); } } /// Changes the source order of a flex grid column. Columns with lower numbers appear first in the layout. /// @param {Number} $order [0] - Order number to apply. @mixin flex-grid-order($order: 0) { order: $order; } /// Horizontally or vertically aligns the columns within a flex row. Apply this mixin to a flex row. /// /// @param {Keyword} $x [null] - Horizontal alignment to use. Can be `left`, `right`, `center`, `justify`, or `spaced`. Or, set it to `null` (the default) to not set horizontal alignment. /// @param {Keyword} $y [null] - Vertical alignment to use. Can be `top`, `bottom`, `middle`, or `stretch`. Or, set it to `null` (the default) to not set vertical alignment. @mixin flex-grid-row-align($x: null, $y: null) { @if $x { @if map-has-key($-zf-flex-justify, $x) { $x: map-get($-zf-flex-justify, $x); } @else { @warn 'flex-grid-row-align(): #{$x} is not a valid value for horizontal alignment. Use left, right, center, justify, or spaced.' } } @if $y { @if map-has-key($-zf-flex-align, $y) { $y: map-get($-zf-flex-align, $y); } @else { @warn 'flex-grid-row-align(): #{$y} is not a valid value for vertical alignment. Use top, bottom, middle, or stretch.' } } justify-content: $x; align-items: $y; } /// Vertically align a single column within a flex row. Apply this mixin to a flex column. /// /// @param {Keyword} $y [null] - Vertical alignment to use. Can be `top`, `bottom`, `middle`, or `stretch`. Or, set it to `null` (the default) to not set vertical alignment. @mixin flex-grid-column-align($y: null) { @if $y { @if map-has-key($-zf-flex-align, $y) { $y: map-get($-zf-flex-align, $y); } @else { @warn 'flex-grid-column-align(): #{$y} is not a valid value for alignment. Use top, bottom, middle, or stretch.' } } align-self: $y; } @mixin foundation-flex-grid { // Row .row { @include flex-grid-row; // Nesting behavior & & { @include flex-grid-row(nest, $base: false); } // Expanded row &.expanded { max-width: none; } &.collapse { > .column { @include grid-col-collapse; } } } // Column .column { @include flex-grid-column; } // Column row // The double .row class is needed to bump up the specificity .column.row.row { float: none; // To properly nest a column row, padding and margin is removed .row & { padding-left: 0; padding-right: 0; margin-left: 0; margin-right: 0; } } @include -zf-each-breakpoint { @for $i from 1 through $grid-column-count { // Sizing (percentage) .#{$-zf-size}-#{$i} { flex: flex-grid-column($i); max-width: grid-column($i); } // Offsets $o: $i - 1; .#{$-zf-size}-offset-#{$o} { @include grid-column-offset($o); } } @for $i from 1 through 6 { // Source ordering .#{$-zf-size}-order-#{$i} { @include flex-grid-order($i); } } @if $-zf-size != small { // Sizing (expand) @include breakpoint($-zf-size) { .#{$-zf-size}-expand { flex: flex-grid-column(); } } // Auto-stacking/unstacking @at-root (without: media) { .row.#{$-zf-size}-unstack { .column { flex: flex-grid-column(100%); @include breakpoint($-zf-size) { flex: flex-grid-column(); } } } } } // Responsive collapsing .#{$-zf-size}-collapse { > .column { @include grid-col-collapse; } } .#{$-zf-size}-uncollapse { $gutter: null; @if $grid-column-gutter { $gutter: $grid-column-gutter; } @else { $gutter: -zf-get-bp-val($grid-column-responsive-gutter, $-zf-size); } > .column { @include grid-col-uncollapse($gutter); } } } // Sizing (shrink) .shrink { flex: flex-grid-column(shrink); max-width: 100%; } // Horizontal alignment using justify-content @each $hdir, $prop in map-remove($-zf-flex-justify, left) { .row.align-#{$hdir} { @include flex-grid-row-align($x: $hdir); } } // Vertical alignment using align-items and align-self @each $vdir, $prop in $-zf-flex-align { .row.align-#{$vdir} { @include flex-grid-row-align($y: $vdir); } .column.align-#{$vdir} { @include flex-grid-column-align($vdir); } } .columns { // scss-lint:disable PlaceholderInExtend @extend .column; } }