54 changed files with 4073 additions and 0 deletions
@ -0,0 +1,4 @@
|
||||
// Susy |
||||
// ==== |
||||
|
||||
@import 'susy/language/susyone'; |
@ -0,0 +1,7 @@
|
||||
// Su |
||||
// == |
||||
|
||||
@import "su/utilities"; |
||||
@import "su/settings"; |
||||
@import "su/validation"; |
||||
@import "su/grid"; |
@ -0,0 +1,24 @@
|
||||
// Susy Next Syntax |
||||
// ================ |
||||
|
||||
$susy-version: 2.1; |
||||
|
||||
@import "../su"; |
||||
@import "../output/float"; |
||||
|
||||
@import "susy/settings"; |
||||
@import "susy/validation"; |
||||
@import "susy/grids"; |
||||
@import "susy/box-sizing"; |
||||
@import "susy/context"; |
||||
@import "susy/background"; |
||||
@import "susy/container"; |
||||
@import "susy/span"; |
||||
@import "susy/gutters"; |
||||
@import "susy/isolate"; |
||||
@import "susy/gallery"; |
||||
@import "susy/rows"; |
||||
@import "susy/margins"; |
||||
@import "susy/padding"; |
||||
@import "susy/bleed"; |
||||
@import "susy/breakpoint-plugin"; |
@ -0,0 +1,13 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Partials |
||||
|
||||
$susy-version: 1.5; |
||||
|
||||
@import "susyone/settings"; |
||||
@import "susyone/functions"; |
||||
@import "susyone/grid"; |
||||
@import "susyone/isolation"; |
||||
@import "susyone/padding"; |
||||
@import "susyone/margin"; |
||||
@import "susyone/media"; |
||||
@import "susyone/background"; |
@ -0,0 +1,385 @@
|
||||
// Background Grid Syntax |
||||
// ====================== |
||||
|
||||
$susy-overlay-grid-head-exists: false; |
||||
|
||||
|
||||
// Show Grid/s |
||||
// ----------- |
||||
// Show grid on any element using either background or overlay. |
||||
// - [$grid] : <settings> |
||||
@mixin show-grid( |
||||
$grid: $susy |
||||
) { |
||||
$inspect: $grid; |
||||
$_output: debug-get(output, $grid); |
||||
|
||||
@include susy-inspect(show-grid, $inspect); |
||||
@if $_output == overlay and susy-get(debug image, $grid) != hide { |
||||
@include overlay-grid($grid); |
||||
} @else { |
||||
@include background-grid($grid); |
||||
} |
||||
} |
||||
|
||||
@mixin show-grids( |
||||
$grid: $susy |
||||
) { |
||||
@include show-grid($grid); |
||||
} |
||||
|
||||
// Background Grid |
||||
// --------------- |
||||
// Show a grid background on any element. |
||||
// - [$grid] : <settings> |
||||
@mixin background-grid( |
||||
$grid: $susy |
||||
) { |
||||
$inspect : $grid; |
||||
$_output : get-background($grid); |
||||
|
||||
@if length($_output) > 0 { |
||||
$_flow: susy-get(flow, $grid); |
||||
|
||||
$_image: (); |
||||
@each $name, $layer in map-get($_output, image) { |
||||
$_direction: if($name == baseline, to bottom, to to($_flow)); |
||||
$_image: append($_image, linear-gradient($_direction, $layer), comma); |
||||
} |
||||
$_output: map-merge($_output, (image: $_image)); |
||||
|
||||
@include background-grid-output($_output...); |
||||
@include susy-inspect(background-grid, $inspect); |
||||
} |
||||
} |
||||
|
||||
|
||||
// Overlay Grid |
||||
// ------------ |
||||
// Generate an icon to trigger grid-overlays on any given elements. |
||||
// $grids... : <selector> [<settings>] [, <selector>]* |
||||
@mixin overlay-grid ( |
||||
$grid: $susy |
||||
) { |
||||
@if not($susy-overlay-grid-head-exists) { |
||||
@at-root head { @include overlay-head($grid); } |
||||
@at-root head:before { @include overlay-trigger; } |
||||
@at-root head:hover { @include overlay-trigger-hover; } |
||||
$susy-overlay-grid-head-exists: true !global; |
||||
} |
||||
|
||||
head:hover ~ &, |
||||
head:hover ~ body & { |
||||
position: relative; |
||||
&:before { |
||||
@include grid-overlay-base; |
||||
@include background-grid($grid); |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
// [Private] Overlay Trigger |
||||
// ------------------------- |
||||
@mixin overlay-trigger { |
||||
content: "|||"; |
||||
display: block; |
||||
padding: 5px 10px; |
||||
font: { |
||||
family: sans-serif; |
||||
size: 16px; |
||||
weight: bold; |
||||
} |
||||
} |
||||
|
||||
|
||||
// [Private] Overlay Trigger Hover |
||||
// ------------------------------- |
||||
@mixin overlay-trigger-hover { |
||||
background: rgba(white, .5); |
||||
color: red; |
||||
} |
||||
|
||||
|
||||
// [Private] Overlay Head |
||||
// ---------------------- |
||||
// <head> styles to create grid overlay toggle |
||||
@mixin overlay-head ( |
||||
$grid: $susy |
||||
) { |
||||
$_toggle: debug-get(toggle, $grid); |
||||
$_horz: null; |
||||
$_vert: null; |
||||
|
||||
@each $side in $_toggle { |
||||
$_horz: if($side == left or $side == right, $side, $_horz); |
||||
$_vert: if($side == top or $side == bottom, $side, $_vert); |
||||
} |
||||
|
||||
display: block; |
||||
position: fixed; |
||||
#{$_horz}: 10px; |
||||
#{$_vert}: 10px; |
||||
z-index: 999; |
||||
color: #333; |
||||
background: rgba(white, .25); |
||||
} |
||||
|
||||
|
||||
// [Private] Grid Overlay Base |
||||
// --------------------------- |
||||
// Base styles for generating a grid overlay |
||||
@mixin grid-overlay-base() { |
||||
position: absolute; |
||||
top: 0; |
||||
left: 0; |
||||
bottom: 0; |
||||
right: 0; |
||||
content: " "; |
||||
z-index: 998; |
||||
} |
||||
|
||||
|
||||
// Get Symmetrical Background |
||||
// -------------------------- |
||||
// - $grid: <map> |
||||
@function get-background-sym( |
||||
$grid |
||||
) { |
||||
$grid : parse-grid($grid); |
||||
$_gutters : susy-get(gutters, $grid); |
||||
$_column-width : susy-get(column-width, $grid); |
||||
$_math : susy-get(math, $grid); |
||||
|
||||
$_color : debug-get(color); |
||||
$_trans : transparent; |
||||
$_light : lighten($_color, 15%); |
||||
|
||||
$_end : 1 + $_gutters; |
||||
$_after : percentage(1/$_end); |
||||
$_stops : (); |
||||
$_size : span(1 $grid wide); |
||||
|
||||
@if is-inside($grid) { |
||||
$_stops: $_color, $_light; |
||||
} @else if is-split($grid) { |
||||
$_split: $_gutters/2; |
||||
$_before: percentage($_split/$_end); |
||||
$_after: percentage((1 + $_split)/$_end); |
||||
$_stops: $_trans $_before, $_color $_before, $_light $_after, $_trans $_after; |
||||
} @else { |
||||
$_stops: $_color, $_light $_after, $_trans $_after; |
||||
} |
||||
|
||||
@if $_math == static { |
||||
$_size: valid-column-math($_math, $_column-width) * $_end; |
||||
} |
||||
|
||||
$_output: ( |
||||
image: (columns: $_stops), |
||||
size: $_size, |
||||
); |
||||
|
||||
@return $_output; |
||||
} |
||||
|
||||
|
||||
// Get Asymmetrical Inside |
||||
// ----------------------- |
||||
// - $grid: <settings> |
||||
@function get-asym-inside( |
||||
$grid |
||||
) { |
||||
$grid : parse-grid($grid); |
||||
$_columns : susy-get(columns, $grid); |
||||
|
||||
$_color : debug-get(color); |
||||
$_light : lighten($_color, 15%); |
||||
$_stops : (); |
||||
|
||||
@for $location from 1 through susy-count($_columns) { |
||||
$this-stop: (); |
||||
|
||||
@if $location == 1 { |
||||
$this-stop: append($this-stop, $_color, comma); |
||||
} @else { |
||||
$start: parse-span(1 at $location $grid); |
||||
$start: get-isolation($start); |
||||
$this-stop: append($this-stop, $_color $start, comma); |
||||
} |
||||
|
||||
@if $location == susy-count($_columns) { |
||||
$this-stop: append($this-stop, $_light, comma); |
||||
} @else { |
||||
$_end: parse-span(1 at ($location + 1) $grid); |
||||
$_end: get-isolation($_end); |
||||
$this-stop: append($this-stop, $_light $_end, comma); |
||||
} |
||||
|
||||
$_stops: join($_stops, $this-stop, comma); |
||||
} |
||||
|
||||
@return $_stops; |
||||
} |
||||
|
||||
|
||||
// Get Asymmetrical Split |
||||
// ---------------------- |
||||
// - $grid: <settings> |
||||
@function get-asym-split( |
||||
$grid |
||||
) { |
||||
$grid : parse-grid($grid); |
||||
$_columns : susy-get(columns, $grid); |
||||
|
||||
$_color : debug-get(color); |
||||
$_light : lighten($_color, 15%); |
||||
$_stops : (); |
||||
|
||||
@for $location from 1 through susy-count($_columns) { |
||||
$this-stop: (); |
||||
|
||||
$start: parse-span(1 at $location $grid); |
||||
$start: get-isolation($start); |
||||
$this-stop: append($this-stop, transparent $start, comma); |
||||
$this-stop: append($this-stop, $_color $start, comma); |
||||
|
||||
$_end: $start + span(1 at $location $grid); |
||||
$this-stop: append($this-stop, $_light $_end, comma); |
||||
$this-stop: append($this-stop, transparent $_end, comma); |
||||
|
||||
$_stops: join($_stops, $this-stop, comma); |
||||
} |
||||
|
||||
@return $_stops; |
||||
} |
||||
|
||||
|
||||
// Get Asymmetrical Outside |
||||
// ------------------------ |
||||
// - $grid: <settings> |
||||
@function get-asym-outside( |
||||
$grid |
||||
) { |
||||
$grid : parse-grid($grid); |
||||
$_columns : susy-get(columns, $grid); |
||||
|
||||
$_color : debug-get(color); |
||||
$_light : lighten($_color, 15%); |
||||
$_trans : transparent; |
||||
$_stops : (); |
||||
|
||||
@for $location from 1 through susy-count($_columns) { |
||||
$this-stop: (); |
||||
|
||||
@if $location == 1 { |
||||
$this-stop: append($this-stop, $_color, comma); |
||||
} @else { |
||||
$start: parse-span(1 at $location $grid); |
||||
$start: get-isolation($start); |
||||
$this-stop: append($this-stop, $_color $start, comma); |
||||
} |
||||
|
||||
@if $location == susy-count($_columns) { |
||||
$this-stop: append($this-stop, $_light, comma); |
||||
} @else { |
||||
$gutter: get-span-width(first $location $grid); |
||||
|
||||
$_end: parse-span(1 at ($location + 1) $grid); |
||||
$_end: get-isolation($_end); |
||||
|
||||
$gutter: $_light $gutter, $_trans $gutter, $_trans $_end; |
||||
$this-stop: join($this-stop, $gutter, comma); |
||||
} |
||||
|
||||
$_stops: join($_stops, $this-stop, comma); |
||||
} |
||||
|
||||
@return $_stops; |
||||
} |
||||
|
||||
|
||||
// Get Asymmetrical Background |
||||
// --------------------------- |
||||
// - $grid: <settings> |
||||
@function get-background-asym( |
||||
$grid |
||||
) { |
||||
$_stops: (); |
||||
|
||||
@if is-inside($grid) { |
||||
$_stops: get-asym-inside($grid); |
||||
} @else if is-split($grid) { |
||||
$_stops: get-asym-split($grid); |
||||
} @else { |
||||
$_stops: get-asym-outside($grid); |
||||
} |
||||
|
||||
@return (image: (columns: $_stops)); |
||||
} |
||||
|
||||
|
||||
// Get Background |
||||
// -------------- |
||||
// - $grid: <settings> |
||||
@function get-background( |
||||
$grid |
||||
) { |
||||
$grid : parse-grid($grid); |
||||
$_show : susy-get(debug image, $grid); |
||||
$_return : (); |
||||
|
||||
@if $_show and $_show != 'hide' { |
||||
$_columns: susy-get(columns, $grid); |
||||
|
||||
@if $_show != 'show-baseline' { |
||||
$_sym: is-symmetrical($_columns); |
||||
$_return: if($_sym, get-background-sym($grid), get-background-asym($grid)); |
||||
$_return: map-merge($_return, (clip: content-box)); |
||||
} |
||||
|
||||
@if $_show != 'show-columns' |
||||
and global-variable-exists(base-line-height) |
||||
and type-of($base-line-height) == 'number' |
||||
and not unitless($base-line-height) { |
||||
$_color: variable-exists('grid-background-baseline-color'); |
||||
$_color: if($_color, $grid-background-baseline-color, #000); |
||||
|
||||
$_image: map-get($_return, image); |
||||
$_size: map-get($_return, size); |
||||
$_baseline: (baseline: ($_color 1px, transparent 1px)); |
||||
$_baseline-size: 100% $base-line-height; |
||||
|
||||
$_return: map-merge($_return, ( |
||||
image: if($_image, map-merge($_image, $_baseline), $_baseline), |
||||
size: if($_size, ($_size, $_baseline-size), $_baseline-size), |
||||
)); |
||||
|
||||
@if $_show == 'show' { |
||||
$_clip: map-get($_return, clip); |
||||
$_return: map-merge($_return, (clip: join($_clip, border-box, comma))); |
||||
} |
||||
} @else if $_show == 'show-baseline' { |
||||
@warn 'Please provide a $base-line-height with the desired height and units'; |
||||
} |
||||
} |
||||
|
||||
@if map-get($_return, image) { |
||||
$_return: map-merge($_return, (flow: susy-get(flow, $grid))); |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Get Debug |
||||
// --------- |
||||
// Return the value of a debug setting |
||||
// - $key: <setting> |
||||
@function debug-get( |
||||
$key, |
||||
$grid: $susy |
||||
) { |
||||
$key: join(debug, $key, space); |
||||
@return susy-get($key, $grid); |
||||
} |
@ -0,0 +1,200 @@
|
||||
// Bleed Syntax |
||||
// ============ |
||||
|
||||
// Bleed |
||||
// ----- |
||||
// Add negative margins, and equal positive padding to create bleed. |
||||
// - $bleed : <span> |
||||
@mixin bleed( |
||||
$bleed: 0 gutter() |
||||
) { |
||||
$inspect : $bleed; |
||||
$output : get-bleed($bleed); |
||||
|
||||
@if susy-get(global-box-sizing) != content-box { |
||||
$output: map-merge((box-sizing: content-box), $output); |
||||
} |
||||
|
||||
@include susy-inspect(bleed, $inspect); |
||||
@include output($output); |
||||
} |
||||
|
||||
|
||||
// Bleed-x |
||||
// ------- |
||||
// Shortcut for horizontal bleed. |
||||
// - $bleed : <span> |
||||
@mixin bleed-x( |
||||
$bleed: gutter() |
||||
) { |
||||
$bleed : parse-span($bleed); |
||||
$trbl : susy-get(span, $bleed); |
||||
|
||||
@if length($trbl) == 1 { |
||||
$bleed: map-merge($bleed, (span: 0 nth($trbl, 1))); |
||||
} @else if length($trbl) == 2 { |
||||
$bleed: map-merge($bleed, (span: 0 nth($trbl, 2) 0 nth($trbl, 1))); |
||||
} @else { |
||||
@warn 'bleed-x only takes 2 lengths, but #{length($trbl)} were passed.'; |
||||
} |
||||
|
||||
@include bleed($bleed); |
||||
} |
||||
|
||||
|
||||
// Bleed-y |
||||
// ------- |
||||
// Shortcut for vertical bleed. |
||||
// - $bleed : <span> |
||||
@mixin bleed-y( |
||||
$bleed: if(function-exists(rhythm), rhythm(1), 1em) |
||||
) { |
||||
$bleed : parse-span($bleed); |
||||
$trbl : susy-get(span, $bleed); |
||||
|
||||
@if length($trbl) == 1 { |
||||
$bleed: map-merge($bleed, (span: nth($trbl, 1) 0)); |
||||
} @else if length($trbl) == 2 { |
||||
$bleed: map-merge($bleed, (span: nth($trbl, 1) 0 nth($trbl, 2) 0)); |
||||
} @else { |
||||
@warn 'bleed-y only takes 2 lengths, but #{length($trbl)} were passed.'; |
||||
} |
||||
|
||||
@include bleed($bleed); |
||||
} |
||||
|
||||
|
||||
// Get Bleed |
||||
// --------- |
||||
// Return bleed output values |
||||
// - $bleed: <span> |
||||
@function get-bleed( |
||||
$bleed |
||||
) { |
||||
$bleed : map-merge((spread: wide), parse-span($bleed)); |
||||
$trbl : susy-get(span, $bleed); |
||||
$short : null; |
||||
$output : (); |
||||
|
||||
@for $i from 1 through length($trbl) { |
||||
$this: nth($trbl, $i); |
||||
$new: (); |
||||
$margin: null; |
||||
$padding: null; |
||||
$padding-x: null; |
||||
|
||||
@if $this > 0 { |
||||
$this: map-merge($bleed, (span: $this)); |
||||
$margin: span($this); |
||||
$padding: $margin; |
||||
$padding-x: $padding; |
||||
} |
||||
|
||||
@if $margin and $margin > 0 { |
||||
$margin: - $margin; |
||||
|
||||
@if is-inside($this) { |
||||
$gutter: gutter($this); |
||||
$join: if($gutter and comparable($padding, $gutter), true, false); |
||||
$padding-x: if($join and $padding > 0, $padding + $gutter, $padding); |
||||
} |
||||
} |
||||
|
||||
@if $i == 1 { |
||||
$new: ( |
||||
margin-top: $margin, |
||||
padding-top: $padding, |
||||
margin-right: $margin, |
||||
padding-right: $padding-x, |
||||
margin-bottom: $margin, |
||||
padding-bottom: $padding, |
||||
margin-left: $margin, |
||||
padding-left: $padding-x, |
||||
); |
||||
} @else if $i == 2 { |
||||
$new: ( |
||||
margin-right: $margin, |
||||
padding-right: $padding-x, |
||||
margin-left: $margin, |
||||
padding-left: $padding-x, |
||||
); |
||||
} @else if $i == 3 { |
||||
$new: ( |
||||
margin-bottom: $margin, |
||||
padding-bottom: $padding, |
||||
); |
||||
} @else if $i == 4 { |
||||
$new: ( |
||||
margin-left: $margin, |
||||
padding-left: $padding-x, |
||||
); |
||||
} |
||||
|
||||
$output: map-merge($output, $new); |
||||
} |
||||
|
||||
@each $prop, $value in $output { |
||||
$output: if($value == 0, map-merge($output, ($prop: null)), $output); |
||||
} |
||||
|
||||
@return bleed-shorthand($output); |
||||
} |
||||
|
||||
// Bleed Shorthand |
||||
// --------------- |
||||
// Convert bleed output into shorthand when possible. |
||||
// - $bleed: <output map> |
||||
@function bleed-shorthand( |
||||
$bleed |
||||
) { |
||||
$margin: (); |
||||
$padding: (); |
||||
$return: (); |
||||
|
||||
@each $key, $value in $bleed { |
||||
@if str-index($key, margin) { |
||||
$margin: map-merge($margin, ($key: $value)); |
||||
} @else if str-index($key, padding) > 0 { |
||||
$padding: map-merge($padding, ($key: $value)); |
||||
} |
||||
} |
||||
|
||||
$props: ( |
||||
margin: $margin, |
||||
padding: $padding, |
||||
); |
||||
|
||||
@each $name, $map in $props { |
||||
$four: if(length(map-keys($map)) == 4, true, false); |
||||
$null: if(index(map-values($map), null), true, false); |
||||
|
||||
@if $four and not($null) { |
||||
$top: map-get($map, '#{$name}-top'); |
||||
$right: map-get($map, '#{$name}-right'); |
||||
$bottom: map-get($map, '#{$name}-bottom'); |
||||
$left: map-get($map, '#{$name}-left'); |
||||
|
||||
$tb: if($top == $bottom, $top, null); |
||||
$rl: if($right == $left, $right, null); |
||||
$all: if($tb == $rl, $tb, null); |
||||
|
||||
$new: if($all, $all, null); |
||||
|
||||
@if not($new) { |
||||
@if $tb and $rl { |
||||
$new: $tb $rl; |
||||
} @else if $rl { |
||||
$new: $top $rl $bottom; |
||||
} @else { |
||||
$new: $top $right $bottom $left; |
||||
} |
||||
} |
||||
|
||||
$return: map-merge($return, ($name: $new)); |
||||
} @else { |
||||
$return: map-merge($return, $map); |
||||
} |
||||
} |
||||
|
||||
@return $return; |
||||
} |
@ -0,0 +1,47 @@
|
||||
// Susy Box Sizing |
||||
// ================= |
||||
|
||||
// Global Box Sizing |
||||
// ----------------- |
||||
// Set a box model globally on all elements. |
||||
// - [$box]: border-box | content-box |
||||
// - [$inherit]: true | false |
||||
@mixin global-box-sizing( |
||||
$box: susy-get(global-box-sizing), |
||||
$inherit: false |
||||
) { |
||||
$inspect: $box; |
||||
|
||||
@if $inherit { |
||||
@at-root { |
||||
html { @include output((box-sizing: $box)); } |
||||
*, *:before, *:after { box-sizing: inherit; } |
||||
} |
||||
} @else { |
||||
*, *:before, *:after { @include output((box-sizing: $box)); } |
||||
} |
||||
|
||||
@include susy-inspect(global-box-sizing, $inspect); |
||||
@include update-box-model($box); |
||||
} |
||||
|
||||
// Border Box Sizing |
||||
// ----------------- |
||||
// A legacy shortcut... |
||||
// - [$inherit]: true | false |
||||
@mixin border-box-sizing( |
||||
$inherit: false |
||||
) { |
||||
@include global-box-sizing(border-box, $inherit); |
||||
} |
||||
|
||||
// Update Box Model |
||||
// ---------------- |
||||
// PRIVATE: Updates global box model setting |
||||
@mixin update-box-model( |
||||
$box |
||||
) { |
||||
@if $box != susy-get(global-box-sizing) { |
||||
@include susy-set(global-box-sizing, $box); |
||||
} |
||||
} |
@ -0,0 +1,185 @@
|
||||
// Breakpoint Integration |
||||
// ====================== |
||||
|
||||
$susy-media: () !default; |
||||
$susy-media-fallback: false !default; |
||||
|
||||
$_susy-media-context: (); |
||||
|
||||
|
||||
// Susy Breakpoint |
||||
// --------------- |
||||
// Change grids at different media query breakpoints. |
||||
// - $query : <min-width> [<max-width>] | <property> <value> | <map> |
||||
// - $layout : <settings> |
||||
// - $no-query : <boolean> | <selector> |
||||
@mixin susy-breakpoint( |
||||
$query, |
||||
$layout: false, |
||||
$no-query: $susy-media-fallback |
||||
) { |
||||
@include susy-media-router($query, $no-query) { |
||||
@if $layout { |
||||
@include with-layout($layout) { |
||||
@content; |
||||
} |
||||
} @else { |
||||
@content; |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
// Susy Media |
||||
// ---------- |
||||
// - $query: <min-width> [<max-width>] | <property> <value> |
||||
// - $no-query: <boolean> | <selector> |
||||
@mixin susy-media( |
||||
$query, |
||||
$no-query: $susy-media-fallback |
||||
) { |
||||
$old-context: $_susy-media-context; |
||||
$name: if(map-has-key($susy-media, $query), $query, null); |
||||
$query: susy-get-media($query); |
||||
$query: susy-parse-media($query); |
||||
|
||||
@include susy-media-context($query, $name); |
||||
|
||||
@if $no-query and type-of($no-query) != string { |
||||
@content; |
||||
} @else { |
||||
@media #{susy-render-media($query)} { |
||||
@content; |
||||
} |
||||
|
||||
@if type-of($no-query) == string { |
||||
#{$no-query} & { |
||||
@content; |
||||
} |
||||
} |
||||
} |
||||
|
||||
@include susy-media-context($old-context, $clean: true); |
||||
} |
||||
|
||||
|
||||
// Media Router |
||||
// ------------ |
||||
// Rout media arguments to the correct mixin. |
||||
@mixin susy-media-router( |
||||
$query, |
||||
$no-query: $susy-media-fallback |
||||
) { |
||||
@if susy-support(breakpoint, (mixin: breakpoint), $warn: false) { |
||||
@include breakpoint($query, $no-query) { |
||||
@content; |
||||
} |
||||
} @else { |
||||
@include susy-media($query, $no-query) { |
||||
@content; |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
// Update Context |
||||
// ------------- |
||||
// Set the new media context |
||||
@mixin susy-media-context( |
||||
$query, |
||||
$name: null, |
||||
$clean: false |
||||
) { |
||||
$query: map-merge((name: $name), $query); |
||||
|
||||
@if $clean { |
||||
$_susy-media-context: $query !global; |
||||
} @else { |
||||
$_susy-media-context: map-merge($_susy-media-context, $query) !global; |
||||
} |
||||
} |
||||
|
||||
|
||||
// Media Context |
||||
// ------------- |
||||
// Return the full media context, or a single media property (e.g. min-width) |
||||
@function susy-media-context( |
||||
$property: false |
||||
) { |
||||
@if $property { |
||||
@return map-get($_susy-media-context, $property); |
||||
} @else { |
||||
@return $_susy-media-context; |
||||
} |
||||
} |
||||
|
||||
|
||||
// Get Media |
||||
// --------- |
||||
// Return a named media-query from $susy-media. |
||||
// - $name: <key> |
||||
@function susy-get-media( |
||||
$name |
||||
) { |
||||
@if map-has-key($susy-media, $name) { |
||||
$map-value: map-get($susy-media, $name); |
||||
@if ($name == $map-value) { |
||||
$name: $map-value; |
||||
} @else { |
||||
$name: susy-get-media($map-value); |
||||
} |
||||
} |
||||
|
||||
@return $name; |
||||
} |
||||
|
||||
|
||||
// Render Media |
||||
// ------------ |
||||
// Build a media-query string from various media settings |
||||
@function susy-render-media( |
||||
$query |
||||
) { |
||||
$output: null; |
||||
@each $property, $value in $query { |
||||
$string: null; |
||||
|
||||
@if $property == media { |
||||
$string: $value; |
||||
} @else { |
||||
$string: '(#{$property}: #{$value})'; |
||||
} |
||||
|
||||
$output: if($output, '#{$output} and #{$string}', $string); |
||||
} |
||||
|
||||
@return $output; |
||||
} |
||||
|
||||
|
||||
// Parse Media |
||||
// ----------- |
||||
// Return parsed media-query settings based on shorthand |
||||
@function susy-parse-media( |
||||
$query |
||||
) { |
||||
$mq: null; |
||||
@if type-of($query) == map { |
||||
$mq: $query; |
||||
} @else if type-of($query) == number { |
||||
$mq: (min-width: $query); |
||||
} @else if type-of($query) == list and length($query) == 2 { |
||||
@if type-of(nth($query, 1)) == number { |
||||
$mq: ( |
||||
min-width: min($query...), |
||||
max-width: max($query...), |
||||
); |
||||
} @else { |
||||
$mq: (nth($query, 1): nth($query, 2)); |
||||
} |
||||
} @else { |
||||
$mq: (media: '#{$query}'); |
||||
} |
||||
|
||||
@return $mq; |
||||
} |
@ -0,0 +1,81 @@
|
||||
// Container Syntax |
||||
// ================ |
||||
|
||||
// Container [mixin] |
||||
// ----------------- |
||||
// Set a container element |
||||
// - [$layout] : <settings> |
||||
@mixin container( |
||||
$layout: $susy |
||||
) { |
||||
$inspect : $layout; |
||||
$layout : parse-grid($layout); |
||||
|
||||
$_width : get-container-width($layout); |
||||
$_justify : parse-container-position(susy-get(container-position, $layout)); |
||||
$_property : if(susy-get(math, $layout) == static, width, max-width); |
||||
|
||||
$_box : susy-get(box-sizing, $layout); |
||||
|
||||
@if $_box { |
||||
@include output((box-sizing: $_box)); |
||||
} |
||||
|
||||
@include susy-inspect(container, $inspect); |
||||
@include float-container($_width, $_justify, $_property); |
||||
@include show-grid($layout); |
||||
} |
||||
|
||||
// Container [function] |
||||
// -------------------- |
||||
// Return container width |
||||
// - [$layout] : <settings> |
||||
@function container( |
||||
$layout: $susy |
||||
) { |
||||
$layout: parse-grid($layout); |
||||
@return get-container-width($layout); |
||||
} |
||||
|
||||
// Get Container Width |
||||
// ------------------- |
||||
// Calculate the container width |
||||
// - [$layout]: <settings> |
||||
@function get-container-width( |
||||
$layout: $susy |
||||
) { |
||||
$layout : parse-grid($layout); |
||||
$_width : susy-get(container, $layout); |
||||
$_column-width : susy-get(column-width, $layout); |
||||
$_math : susy-get(math, $layout); |
||||
|
||||
@if not($_width) or $_width == auto { |
||||
@if valid-column-math($_math, $_column-width) { |
||||
$_columns : susy-get(columns, $layout); |
||||
$_gutters : susy-get(gutters, $layout); |
||||
$_spread : if(is-split($layout), wide, narrow); |
||||
$_width : susy-sum($_columns, $_gutters, $_spread) * $_column-width; |
||||
} @else { |
||||
$_width: 100%; |
||||
} |
||||
} |
||||
|
||||
@return $_width; |
||||
} |
||||
|
||||
// Parse Container Position |
||||
// ------------------------ |
||||
// Parse the $container-position into margin values. |
||||
// - [$justify] : left | center | right | <length> [<length>] |
||||
@function parse-container-position( |
||||
$justify: map-get($susy-defaults, container-position) |
||||
) { |
||||
$_return: if($justify == left, 0, auto) if($justify == right, 0, auto); |
||||
|
||||
@if not(index(left right center, $justify)) { |
||||
$_return: nth($justify, 1); |
||||
$_return: $_return if(length($justify) > 1, nth($justify, 2), $_return); |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
@ -0,0 +1,36 @@
|
||||
// Context Syntax |
||||
// ============== |
||||
|
||||
// Nested [function] |
||||
// ----------------- |
||||
// Return a subset grid for nested context. |
||||
// - $context : <span> |
||||
@function nested( |
||||
$context |
||||
) { |
||||
$context : parse-span($context); |
||||
$span : susy-get(span, $context); |
||||
$location : get-location($context); |
||||
$columns : susy-get(columns, $context); |
||||
|
||||
@return susy-slice($span, $location, $columns); |
||||
} |
||||
|
||||
// Nested [mixin] |
||||
// -------------- |
||||
// Use a subset grid for a nested context |
||||
// - $context : <span> |
||||
// - @content : <content> |
||||
@mixin nested( |
||||
$context |
||||
) { |
||||
$inspect : $context; |
||||
$context : parse-span($context); |
||||
$old : susy-get(columns); |
||||
$susy : map-merge($susy, (columns: nested($context))) !global; |
||||
|
||||
@include susy-inspect(nested, $inspect); |
||||
@content; |
||||
|
||||
$susy : map-merge($susy, (columns: $old)) !global; |
||||
} |
@ -0,0 +1,94 @@
|
||||
// Gallery Syntax |
||||
// ============== |
||||
|
||||
// Gallery |
||||
// ------- |
||||
// Create an isolated gallery |
||||
// - $span : <span> |
||||
// - [$selector] : child | of-type |
||||
@mixin gallery( |
||||
$span, |
||||
$selector: child |
||||
) { |
||||
$inspect : $span; |
||||
$span : parse-span($span); |
||||
$span : map-merge($span, (location: 1)); |
||||
|
||||
$n : susy-get(span, $span); |
||||
$columns : susy-get(columns, $span); |
||||
$context : susy-count($columns); |
||||
$flow : susy-get(flow, $span); |
||||
|
||||
$inside : is-inside($span); |
||||
$from : from($flow); |
||||
$line : floor($context / $n); |
||||
$symmetrical : is-symmetrical($columns); |
||||
|
||||
$output: ( |
||||
width : null, |
||||
float : from, |
||||
margin-before : null, |
||||
margin-after : null, |
||||
padding-before : null, |
||||
padding-after : null, |
||||
flow : $flow, |
||||
); |
||||
|
||||
@if $inside { |
||||
$gutters: get-gutters($span); |
||||
$output: map-merge($output, ( |
||||
padding-before: map-get($gutters, before), |
||||
padding-after: map-get($gutters, after), |
||||
)); |
||||
} |
||||
|
||||
@if $symmetrical { |
||||
$output: map-merge($output, (width: get-span-width($span))); |
||||
} |
||||
|
||||
$box : susy-get(box-sizing, $span); |
||||
$global-box : if(susy-get(global-box-sizing) == 'border-box', true, false); |
||||
|
||||
@include susy-inspect(gallery, $inspect); |
||||
|
||||
// Collective Output |
||||
@if $box == border-box or ($inside and not($box) and not($global-box)) { |
||||
@include output((box-sizing: border-box)); |
||||
} @else if $box == content-box { |
||||
@include output((box-sizing: content-box)); |
||||
} |
||||
|
||||
@include float-span-output($output...); |
||||
|
||||
// Individual Loop |
||||
@for $item from 1 through $line { |
||||
$nth: '#{$line}n + #{$item}'; |
||||
&:nth-#{$selector}(#{$nth}) { |
||||
// Individual Prep |
||||
$output: ( |
||||
width : if($symmetrical, null, get-span-width($span)), |
||||
float : null, |
||||
margin-before : get-isolation($span), |
||||
margin-after : -100%, |
||||
padding-before : null, |
||||
padding-after : null, |
||||
flow : $flow, |
||||
); |
||||
|
||||
// Individual Output |
||||
@include float-span-output($output...); |
||||
|
||||
@if get-edge($span) == first { |
||||
@include break; |
||||
@include first($span); |
||||
} @else { |
||||
@include nobreak; |
||||
} |
||||
|
||||
// Individual Location Increment |
||||
$location: get-location($span) + $n; |
||||
$location: if($location > $context, 1, $location); |
||||
$span: map-merge($span, (location: $location)); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,64 @@
|
||||
// Grid Syntax |
||||
// =========== |
||||
|
||||
|
||||
// Layout |
||||
// ------ |
||||
// Set a new layout using a shorthand |
||||
// - $layout: <settings> |
||||
// - $clean: boolean |
||||
@mixin layout( |
||||
$layout, |
||||
$clean: false |
||||
) { |
||||
$inspect : $layout; |
||||
$susy : _get-layout($layout, $clean) !global; |
||||
|
||||
@include susy-inspect(layout, $inspect); |
||||
} |
||||
|
||||
|
||||
// Use Grid |
||||
// -------- |
||||
// Use an arbitrary layout for a section of code |
||||
// - $layout: <settings> |
||||
// - $clean: boolean |
||||
@mixin with-layout( |
||||
$layout, |
||||
$clean: false |
||||
) { |
||||
$inspect : $layout; |
||||
$old : $susy; |
||||
$susy : _get-layout($layout, $clean) !global; |
||||
|
||||
@include susy-inspect(with-layout, $inspect); |
||||
|
||||
@content; |
||||
|
||||
$susy: $old !global; |
||||
} |
||||
|
||||
|
||||
// Layout |
||||
// ------ |
||||
// Return a parsed layout map based on shorthand syntax |
||||
// - $layout: <settings> |
||||
@function layout( |
||||
$layout: $susy |
||||
) { |
||||
@return parse-grid($layout); |
||||
} |
||||
|
||||
|
||||
// Get Layout |
||||
// ---------- |
||||
// Return a new layout based on current and given settings |
||||
// - $layout: <settings> |
||||
// - $clean: boolean |
||||
@function _get-layout( |
||||
$layout, |
||||
$clean: false |
||||
) { |
||||
$layout: layout($layout); |
||||
@return if($clean, $layout, _susy-deep-merge($susy, $layout)); |
||||
} |
@ -0,0 +1,154 @@
|
||||
// Gutter Syntax |
||||
// ============= |
||||
|
||||
|
||||
// Gutters |
||||
// ------- |
||||
// Set gutters on an element. |
||||
// - [$span] : <settings> |
||||
@mixin gutters( |
||||
$span: $susy |
||||
) { |
||||
$inspect : $span; |
||||
$span : parse-gutters($span); |
||||
$_gutters : get-gutters($span); |
||||
|
||||
$_output: ( |
||||
before: map-get($_gutters, before), |
||||
after: map-get($_gutters, after), |
||||
flow: susy-get(flow, $span), |
||||
); |
||||
|
||||
@include susy-inspect(gutters, $inspect); |
||||
|
||||
@if is-inside($span) { |
||||
@include padding-output($_output...); |
||||
} @else { |
||||
@include margin-output($_output...); |
||||
} |
||||
} |
||||
|
||||
@mixin gutter( |
||||
$span: $susy |
||||
) { |
||||
@include gutters($span); |
||||
} |
||||
|
||||
|
||||
// Gutter |
||||
// ------ |
||||
// Return the width of a gutter. |
||||
// - [$span] : <settings> |
||||
@function gutter( |
||||
$span: $susy |
||||
) { |
||||
$span: parse-gutters($span); |
||||
|
||||
$_gutters: get-gutters($span); |
||||
$_gutters: map-get($_gutters, before) or map-get($_gutters, after); |
||||
|
||||
@return $_gutters; |
||||
} |
||||
|
||||
@function gutters( |
||||
$span: $susy |
||||
) { |
||||
@return gutter($span); |
||||
} |
||||
|
||||
|
||||
// Get Gutter Width |
||||
// ---------------- |
||||
// Return gutter width. |
||||
// - [$context]: <context> |
||||
@function get-gutter-width( |
||||
$context: $susy |
||||
) { |
||||
$context : parse-gutters($context); |
||||
|
||||
$_gutters : susy-get(gutters, $context); |
||||
$_gutter : susy-get(gutter-override, $context); |
||||
|
||||
@if $_gutters and ($_gutters > 0) and not($_gutter) { |
||||
$_column-width: susy-get(column-width, $context); |
||||
$_math: gutter-math($context); |
||||
@if $_math == static { |
||||
$_gutter: $_gutters * valid-column-math($_math, $_column-width); |
||||
} @else { |
||||
$_columns : susy-get(columns, $context); |
||||
$_spread : if(is-split($context), wide, susy-get(spread, $context)); |
||||
$_gutter : percentage($_gutters / susy-sum($_columns, $_gutters, $_spread)); |
||||
} |
||||
} |
||||
|
||||
$_gutter: if($_gutter == 'no-gutters' or $_gutter == 'no-gutter', null, $_gutter); |
||||
|
||||
@return $_gutter; |
||||
} |
||||
|
||||
|
||||
// Get Gutters |
||||
// ----------- |
||||
// Return before and after gutter values. |
||||
// - [$context]: <context> |
||||
@function get-gutters( |
||||
$context: $susy |
||||
) { |
||||
$context : parse-gutters($context); |
||||
|
||||
$_gutter-position : susy-get(gutter-position, $context); |
||||
$_gutter : get-gutter-width($context); |
||||
|
||||
$_return : (before: null, after: null); |
||||
|
||||
@if is-split($context) and $_gutter { |
||||
$_gutter: $_gutter / 2; |
||||
$_return: map-merge($_return, (before: $_gutter, after: $_gutter)); |
||||
} @else { |
||||
$_return: map-merge($_return, ($_gutter-position: $_gutter)); |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Is Inside |
||||
// --------- |
||||
// Returns true if gutters are inside. |
||||
// $context: <context> |
||||
@function is-inside( |
||||
$context |
||||
) { |
||||
$_inside: inside inside-static; |
||||
$_gutter-position: susy-get(gutter-position, $context); |
||||
|
||||
@return if(index($_inside, $_gutter-position), true, false); |
||||
} |
||||
|
||||
|
||||
// Is Split |
||||
// -------- |
||||
// Returns true if gutters are split. |
||||
// $context: <context> |
||||
@function is-split( |
||||
$context |
||||
) { |
||||
$_split: split inside inside-static; |
||||
$_gutter-position: susy-get(gutter-position, $context); |
||||
|
||||
@return if(index($_split, $_gutter-position), true, false); |
||||
} |
||||
|
||||
|
||||
// Gutter Math |
||||
// ----------- |
||||
// Return the math to use for gutter calculations |
||||
// $context: <context> |
||||
@function gutter-math( |
||||
$context: $susy |
||||
) { |
||||
$_return : susy-get(math, $context); |
||||
$_return : if(susy-get(gutter-position, $context) == inside-static, static, $_return); |
||||
|
||||
@return $_return; |
||||
} |
@ -0,0 +1,77 @@
|
||||
// Isolation Syntax |
||||
// ================ |
||||
|
||||
|
||||
// Isolate [Mixin] |
||||
// --------------- |
||||
// Set isolation as an override. |
||||
// - $location: <span> |
||||
@mixin isolate( |
||||
$isolate: 1 |
||||
) { |
||||
$inspect: $isolate; |
||||
|
||||
$output: ( |
||||
push: isolate($isolate), |
||||
flow: susy-get(flow, $isolate), |
||||
); |
||||
|
||||
@include susy-inspect(isolate, $inspect); |
||||
@include isolate-output($output...); |
||||
} |
||||
|
||||
|
||||
// Isolate [function] |
||||
// ------------------ |
||||
// Return an isolation offset width. |
||||
// - $location: <span> |
||||
@function isolate( |
||||
$isolate: 1 |
||||
) { |
||||
$isolate: parse-span($isolate); |
||||
$isolation: susy-get(span, $isolate); |
||||
|
||||
@if $isolation and not(get-location($isolate)) { |
||||
$new: ( |
||||
span: null, |
||||
location: $isolation, |
||||
); |
||||
$isolate: map-merge($isolate, $new); |
||||
} |
||||
|
||||
@return get-isolation($isolate); |
||||
} |
||||
|
||||
|
||||
// Get Isolation |
||||
// ------------- |
||||
// Return the isolation offset width |
||||
// - $input: <map> |
||||
@function get-isolation( |
||||
$input |
||||
) { |
||||
$location : get-location($input); |
||||
$columns : susy-get(columns, $input); |
||||
$width : null; |
||||
|
||||
@if type-of($location) == number and not(unitless($location)) { |
||||
$width: $location; |
||||
} @else if $location { |
||||
$push: $location - 1; |
||||
@if $push > 0 { |
||||
$push: map-merge($input, ( |
||||
span: $push, |
||||
location: 1, |
||||
spread: wide, |
||||
)); |
||||
$width: get-span-width($push); |
||||
} |
||||
} |
||||
|
||||
@if susy-get(gutter-position, $input) == split |
||||
and susy-get(gutters, $input) > 0 { |
||||
$width: if($width == null, gutters($input), $width + gutters($input)); |
||||
} |
||||
|
||||
@return $width or 0; |
||||
} |
@ -0,0 +1,94 @@
|
||||
// Margin Syntax |
||||
// ============= |
||||
|
||||
// Pre |
||||
// --- |
||||
// Add spanning-margins before an element. |
||||
// - $span : <span> |
||||
@mixin pre( |
||||
$span |
||||
) { |
||||
$inspect: $span; |
||||
$span : map-merge((spread: wide), parse-span($span)); |
||||
$flow : susy-get(flow, $span); |
||||
$split : if(susy-get(gutter-position, $span) == split, true, false); |
||||
$gutter : gutter($span); |
||||
$span : span($span); |
||||
$width : if($split and $gutter, $span + $gutter, $span); |
||||
|
||||
@include susy-inspect(pre, $inspect); |
||||
@include margin-output($width, null, $flow); |
||||
} |
||||
|
||||
// Post |
||||
// ---- |
||||
// Add spanning-margins after an element. |
||||
// - $span : <span> |
||||
@mixin post( |
||||
$span |
||||
) { |
||||
$inspect : $span; |
||||
$span : map-merge((spread: wide), parse-span($span)); |
||||
$flow : susy-get(flow, $span); |
||||
$split : if(susy-get(gutter-position, $span) == split, true, false); |
||||
$width : if($split, span($span) + gutter($span), span($span)); |
||||
|
||||
@include susy-inspect(post, $inspect); |
||||
@include margin-output(null, $width, $flow); |
||||
} |
||||
|
||||
// Push |
||||
// ---- |
||||
// Simple synonymn for pre. |
||||
// - $span : <span> |
||||
@mixin push( |
||||
$span |
||||
) { |
||||
@include pre($span); |
||||
} |
||||
|
||||
// Pull |
||||
// ---- |
||||
// Add negative spanning-margins before an element. |
||||
// - $span : <span> |
||||
@mixin pull( |
||||
$span |
||||
) { |
||||
$inspect : $span; |
||||
$span : map-merge((spread: wide), parse-span($span)); |
||||
$flow : susy-get(flow, $span); |
||||
$split : if(susy-get(gutter-position, $span) == split, true, false); |
||||
$width : if($split, 0 - span($span) + gutter($span), 0 - span($span)); |
||||
|
||||
@include susy-inspect(pull, $inspect); |
||||
@include margin-output($width, null, $flow); |
||||
} |
||||
|
||||
// Squish |
||||
// ------ |
||||
// Add spanning-margins before and after an element. |
||||
// - $pre : <span> |
||||
// - [$post] : <span> |
||||
@mixin squish( |
||||
$pre, |
||||
$post: false |
||||
) { |
||||
$inspect : ($pre, $post); |
||||
$pre : map-merge((spread: wide), parse-span($pre)); |
||||
|
||||
@if $post { |
||||
$post: map-merge((spread: wide), parse-span($post)); |
||||
} @else { |
||||
$span: susy-get(span, $pre); |
||||
@if length($span) > 1 { |
||||
$pre: map-merge($pre, (span: nth($span, 1))); |
||||
$post: map-merge($pre, (span: nth($span, 2))); |
||||
} @else { |
||||
$post: $pre; |
||||
} |
||||
} |
||||
|
||||
@include susy-inspect(squish, $inspect); |
||||
@include pre($pre); |
||||
@include post($post); |
||||
} |
@ -0,0 +1,74 @@
|
||||
// Padding Syntax |
||||
// ============== |
||||
|
||||
// Prefix |
||||
// ------ |
||||
// Add spanning-padding before an element. |
||||
// - $span : <span> |
||||
@mixin prefix( |
||||
$span |
||||
) { |
||||
$inspect : $span; |
||||
$span : map-merge((spread: wide), parse-span($span)); |
||||
$flow : susy-get(flow, $span); |
||||
$width : span($span); |
||||
|
||||
@if is-inside($span) { |
||||
$gutter: gutter($span); |
||||
$width: if($gutter and comparable($width, $gutter), $width + $gutter, $width); |
||||
} |
||||
|
||||
@include susy-inspect(prefix, $inspect); |
||||
@include padding-output($width, null, $flow); |
||||
} |
||||
|
||||
// Suffix |
||||
// ------ |
||||
// Add spanning-padding after an element. |
||||
// - $span : <span> |
||||
@mixin suffix( |
||||
$span |
||||
) { |
||||
$inspect : $span; |
||||
$span : map-merge((spread: wide), parse-span($span)); |
||||
$flow : susy-get(flow, $span); |
||||
$width : span($span); |
||||
|
||||
@if is-inside($span) { |
||||
$gutter: gutter($span); |
||||
$width: if($gutter and comparable($width, $gutter), $width + $gutter, $width); |
||||
} |
||||
|
||||
@include susy-inspect(suffix, $inspect); |
||||
@include padding-output(null, $width, $flow); |
||||
} |
||||
|
||||
// Pad |
||||
// --- |
||||
// Add spanning-padding before and after an element. |
||||
// - $pre : <span> |
||||
// - [$post] : <span> |
||||
@mixin pad( |
||||
$pre, |
||||
$post: false |
||||
) { |
||||
$inspect : ($pre, $post); |
||||
$pre : map-merge((spread: wide), parse-span($pre)); |
||||
|
||||
@if $post { |
||||
$post: map-merge((spread: wide), parse-span($post)); |
||||
} @else { |
||||
$span: susy-get(span, $pre); |
||||
@if length($span) > 1 { |
||||
$pre: map-merge($pre, (span: nth($span, 1))); |
||||
$post: map-merge($pre, (span: nth($span, 2))); |
||||
} @else { |
||||
$post: $pre; |
||||
} |
||||
} |
||||
|
||||
@include susy-inspect(pad, $inspect); |
||||
@include prefix($pre); |
||||
@include suffix($post); |
||||
|
||||
} |
@ -0,0 +1,138 @@
|
||||
// Row Start & End |
||||
// =============== |
||||
|
||||
// Break |
||||
// ----- |
||||
// Apply to any element that should force a line break. |
||||
@mixin break { |
||||
@include output((clear: both)); |
||||
} |
||||
|
||||
|
||||
// NoBreak |
||||
// ------- |
||||
// Cancel the break() effect, e.g. when using media queries. |
||||
@mixin nobreak { |
||||
@include output((clear: none)); |
||||
} |
||||
|
||||
|
||||
// Full |
||||
// ---- |
||||
// - [$context]: <layout shorthand> |
||||
@mixin full( |
||||
$context: $susy |
||||
) { |
||||
$inspect : $context; |
||||
@include susy-inspect(full, $inspect); |
||||
@include span(full of parse-grid($context) break); |
||||
} |
||||
|
||||
|
||||
// First |
||||
// ----- |
||||
// - [$context]: <settings> |
||||
@mixin first( |
||||
$context: $susy |
||||
) { |
||||
$inspect : $context; |
||||
$context : parse-grid($context); |
||||
$flow : susy-get(flow, $context); |
||||
|
||||
@include susy-inspect(first, $inspect); |
||||
@if not(is-split($context)) { |
||||
@include float-first($flow); |
||||
} |
||||
} |
||||
|
||||
@mixin alpha( |
||||
$context: $susy |
||||
) { |
||||
@include first($context); |
||||
} |
||||
|
||||
|
||||
// Last |
||||
// ---- |
||||
// - [$context]: <settings> |
||||
@mixin last( |
||||
$context: $susy |
||||
) { |
||||
$inspect : $context; |
||||
$context : parse-grid($context); |
||||
|
||||
@include susy-inspect(last, $inspect); |
||||
|
||||
$output: ( |
||||
flow: susy-get(flow, $context), |
||||
last-flow: susy-get(last-flow, $context), |
||||
margin: if(is-split($context), null, 0), |
||||
); |
||||
|
||||
@include float-last($output...); |
||||
} |
||||
|
||||
@mixin omega( |
||||
$context: $susy |
||||
) { |
||||
@include last($context); |
||||
} |
||||
|
||||
|
||||
// Get Edge |
||||
// -------- |
||||
// Calculate edge value based on location, if possible |
||||
@function get-edge( |
||||
$span |
||||
) { |
||||
$span : parse-span($span); |
||||
$edge : susy-get(edge, $span); |
||||
|
||||
@if not($edge) { |
||||
$count: susy-count(susy-get(columns, $span)); |
||||
$location: susy-get(location, $span); |
||||
$n: susy-get(span, $span); |
||||
|
||||
$number: if(type-of($location) == number, true, false); |
||||
$index: if($number and unitless($location), true, false); |
||||
|
||||
@if $n == $count { |
||||
$edge: full; |
||||
} @else if $location and $n and $index { |
||||
@if $location == 1 { |
||||
$edge: if($n == $count, full, first); |
||||
} @else if $location + $n - 1 == $count { |
||||
$edge: last; |
||||
} |
||||
} |
||||
} |
||||
|
||||
@if $edge == alpha or $edge == omega { |
||||
$edge: if($edge == alpha, first, last); |
||||
} |
||||
|
||||
@return $edge; |
||||
} |
||||
|
||||
|
||||
// Get Location |
||||
// ------------ |
||||
// Calculate location value based on edge, if possible |
||||
@function get-location( |
||||
$span |
||||
) { |
||||
$span : parse-span($span); |
||||
$location : susy-get(location, $span); |
||||
$edge : get-edge($span); |
||||
$n : susy-get(span, $span); |
||||
|
||||
@if $edge and not($location) and type-of($n) == number and unitless($n) { |
||||
@if $edge == first { |
||||
$location: 1; |
||||
} @else if $edge == last { |
||||
$location: susy-count(susy-get(columns, $span)) - $n + 1; |
||||
} |
||||
} |
||||
|
||||
@return $location |
||||
} |
@ -0,0 +1,216 @@
|
||||
// Susy Settings |
||||
// ============= |
||||
|
||||
// Susy Language Defaults |
||||
// ---------------------- |
||||
// - PRIVATE |
||||
@include susy-defaults(( |
||||
container: auto, |
||||
math: fluid, |
||||
output: float, |
||||
container-position: center, |
||||
gutter-position: after, |
||||
global-box-sizing: content-box, |
||||
debug: ( |
||||
image: hide, |
||||
color: rgba(#66f, .25), |
||||
output: background, |
||||
toggle: top right, |
||||
), |
||||
)); |
||||
|
||||
|
||||
// Valid Keyword Values |
||||
// -------------------- |
||||
// - PRIVATE: DONT'T TOUCH |
||||
$susy-keywords: ( |
||||
container: auto, |
||||
math: static fluid, |
||||
output: isolate float, |
||||
container-position: left center right, |
||||
flow: ltr rtl, |
||||
gutter-position: before after split inside inside-static, |
||||
box-sizing: border-box content-box, |
||||
span: full, |
||||
edge: first alpha last omega full, |
||||
spread: narrow wide wider, |
||||
gutter-override: no-gutters no-gutter, |
||||
role: nest, |
||||
clear: break nobreak, |
||||
debug image: show hide show-columns show-baseline, |
||||
debug output: background overlay, |
||||
); |
||||
|
||||
|
||||
// Parse Susy Keywords and Maps |
||||
// ---------------------------- |
||||
@function parse-settings( |
||||
$short: $susy |
||||
) { |
||||
$_return: (); |
||||
|
||||
@if type-of($short) == map { |
||||
$_return: $short; |
||||
} @else { |
||||
@each $item in $short { |
||||
// strings |
||||
@if type-of($item) == string { |
||||
@each $key, $value in $susy-keywords { |
||||
@if index($value, $item) { |
||||
$_key-value: append($key, $item); |
||||
$_return: _susy-deep-set($_return, $_key-value...); |
||||
} |
||||
} |
||||
// maps |
||||
} @else if type-of($item) == map { |
||||
$_return: map-merge($_return, $item); |
||||
} |
||||
} |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Parse Columns & Gutters |
||||
// ----------------------- |
||||
@function parse-layout( |
||||
$short |
||||
) { |
||||
$_return: (); |
||||
$_columns: (); |
||||
$_gutters: null; |
||||
|
||||
@if not(unitless(nth(nth($short, 1), 1))) { |
||||
$_gutters: nth($short, 1); |
||||
} @else { |
||||
$_columns: (columns: nth($short, 1)); |
||||
$_gutters: if(length($short) > 1, nth($short, 2), $_gutters); |
||||
} |
||||
|
||||
@if type-of($_gutters) == list and length($_gutters) > 0 { |
||||
$_gutters: ( |
||||
gutters: nth($_gutters, 2) / nth($_gutters, 1), |
||||
column-width: nth($_gutters, 1), |
||||
); |
||||
} @else { |
||||
$_gutters: if($_gutters, (gutters: $_gutters), ()); |
||||
} |
||||
|
||||
$_return: map-merge($_return, $_columns); |
||||
$_return: map-merge($_return, $_gutters); |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Parse Grid/Context |
||||
// ------------------ |
||||
@function parse-grid( |
||||
$short: $susy |
||||
) { |
||||
$_return: parse-settings($short); |
||||
$_layout: (); |
||||
|
||||
@if type-of($short) == map { |
||||
$_return: $short; |
||||
} @else { |
||||
@each $item in $short { |
||||
// number or list |
||||
@if type-of($item) == number or type-of($item) == list { |
||||
@if type-of($item) == list or unitless($item) { |
||||
$_layout: append($_layout, $item); |
||||
} @else { |
||||
$_return: map-merge($_return, (container: $item)); |
||||
} |
||||
} |
||||
} |
||||
|
||||
$_layout: if(length($_layout) > 0, parse-layout($_layout), $_layout); |
||||
} |
||||
|
||||
@return map-merge($_return, $_layout); |
||||
} |
||||
|
||||
|
||||
// Parse Span |
||||
// ---------- |
||||
@function parse-span( |
||||
$short, |
||||
$key: span |
||||
) { |
||||
$_return: (); |
||||
|
||||
@if type-of($short) == map { |
||||
$_return: $short; |
||||
} @else { |
||||
$_at: index($short, at); |
||||
|
||||
@if $_at { |
||||
$_loci: $_at + 1; |
||||
$_location: nth($short, $_loci); |
||||
$_return: map-merge($_return, (location: $_location)); |
||||
$short: set-nth($short, $_at, null); |
||||
$short: set-nth($short, $_loci, null); |
||||
} |
||||
|
||||
$_i: 1; |
||||
$_span: (); |
||||
|
||||
@while $_i <= length($short) { |
||||
$_this: nth($short, $_i); |
||||
|
||||
@if type-of($_this) == number { |
||||
$_span: append($_span, $_this); |
||||
$short: set-nth($short, $_i, null); |
||||
} @else if $_this == of { |
||||
$short: set-nth($short, $_i, null); |
||||
$_i: length($short) + 1; |
||||
} |
||||
|
||||
$_i: $_i + 1; |
||||
} |
||||
|
||||
@if length($_span) > 0 { |
||||
$_span: if(length($_span) == 1, nth($_span, 1), $_span); |
||||
$_return: map-merge($_return, ($key: $_span)); |
||||
} |
||||
|
||||
$_return: map-merge($_return, parse-grid($short)); |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Parse Gutters |
||||
// ------------- |
||||
@function parse-gutters( |
||||
$short: $susy |
||||
) { |
||||
$_gutters: parse-span($short, gutter-override); |
||||
$_span: susy-get(gutter-override, $_gutters); |
||||
|
||||
@if $_span and not(map-get($_gutters, columns)) { |
||||
$_context: (); |
||||
$_new: (); |
||||
|
||||
@each $item in $_span { |
||||
@if type-of($item) == number and unitless($item) { |
||||
$_context: append($_context, $item); |
||||
} @else { |
||||
$_new: append($_new, $item); |
||||
} |
||||
} |
||||
|
||||
$_context: parse-grid($_context); |
||||
$_new: if(length($_new) == 0, null, $_new); |
||||
$_new: if(length($_new) == 1, nth($_new, 1), $_new); |
||||
$_new: (gutter-override: if($_new != $_span, $_new, $_span)); |
||||
|
||||
$_gutters: map-merge($_gutters, $_new); |
||||
$_gutters: map-merge($_gutters, $_context); |
||||
} |
||||
|
||||
@return $_gutters; |
||||
} |
@ -0,0 +1,163 @@
|
||||
// Span Syntax |
||||
// =========== |
||||
|
||||
// Span [mixin] |
||||
// ------------ |
||||
// Set a spanning element using shorthand syntax. |
||||
// - $span : <span> |
||||
@mixin span( |
||||
$span |
||||
) { |
||||
$inspect: $span; |
||||
$span: parse-span($span); |
||||
$output: span-math($span); |
||||
$nesting: susy-get(span, $span); |
||||
$clear: susy-get(clear, $span); |
||||
|
||||
$box: susy-get(box-sizing, $span); |
||||
$content-box: if(susy-get(global-box-sizing) != 'border-box', true, false); |
||||
$box: $box or if(is-inside($span) and $content-box, border-box, null); |
||||
|
||||
@if $clear == break { |
||||
@include break; |
||||
} @else if $clear == nobreak { |
||||
@include nobreak; |
||||
} |
||||
|
||||
@include susy-inspect(span, $inspect); |
||||
@include output((box-sizing: $box)); |
||||
@include float-span-output($output...); |
||||
|
||||
@if valid-columns($nesting, silent) { |
||||
@include nested($span) { @content; } |
||||
} @else { |
||||
@content; |
||||
} |
||||
} |
||||
|
||||
// Span [function] |
||||
// --------------- |
||||
// Return the width of a span. |
||||
// - $span : <span> |
||||
@function span( |
||||
$span |
||||
) { |
||||
@return get-span-width($span); |
||||
} |
||||
|
||||
// Span Math |
||||
// --------- |
||||
// Get all the span results. |
||||
// - $span: <map> |
||||
@function span-math( |
||||
$span |
||||
) { |
||||
$nest : if(susy-get(role, $span) == nest, true, false); |
||||
$split-nest : if(is-split($span) and $nest, true, false); |
||||
$edge : get-edge($span); |
||||
$location : get-location($span); |
||||
|
||||
$float : from; |
||||
$padding-before : null; |
||||
$padding-after : null; |
||||
$margin-before : null; |
||||
$margin-after : null; |
||||
|
||||
// calculate widths |
||||
$spread: index(map-values($span), spread); |
||||
$span: if($split-nest and not($spread), map-merge($span, (spread: wide)), $span); |
||||
$width: get-span-width($span); |
||||
$gutters: get-gutters($span); |
||||
|
||||
// apply gutters |
||||
@if is-inside($span) { |
||||
@if not(susy-get(role, $span)) { |
||||
$padding-before: map-get($gutters, before); |
||||
$padding-after: map-get($gutters, after); |
||||
} |
||||
} @else { |
||||
@if not($split-nest) { |
||||
$margin-before: map-get($gutters, before); |
||||
$margin-after: map-get($gutters, after); |
||||
} |
||||
} |
||||
|
||||
// special margin handling |
||||
@if susy-get(output, $span) == isolate and $location { |
||||
$margin-before: get-isolation($span); |
||||
$margin-after: -100%; |
||||
} @else if $edge { |
||||
$is-split: is-split($span); |
||||
$pos: susy-get(gutter-position, $span); |
||||
|
||||
@if $edge == last { |
||||
$float: susy-get(last-flow, $span); |
||||
} |
||||
|
||||
@if not($is-split) { |
||||
@if $edge == full or ($edge == first and $pos == before) { |
||||
$margin-before: 0; |
||||
} |
||||
@if $edge == full or ($edge == last and $pos == after) { |
||||
$margin-after: 0; |
||||
} |
||||
} |
||||
|
||||
} |
||||
|
||||
@return ( |
||||
width : $width, |
||||
float : $float, |
||||
margin-before : $margin-before, |
||||
margin-after : $margin-after, |
||||
padding-before : $padding-before, |
||||
padding-after : $padding-after, |
||||
flow : susy-get(flow, $span), |
||||
); |
||||
} |
||||
|
||||
// Get Span Width |
||||
// -------------- |
||||
// Return span width. |
||||
// - $span: <map> |
||||
@function get-span-width( |
||||
$span |
||||
) { |
||||
$span : parse-span($span); |
||||
|
||||
$n : susy-get(span, $span); |
||||
$location : get-location($span); |
||||
$columns : susy-get(columns, $span); |
||||
$gutters : susy-get(gutters, $span); |
||||
$spread : susy-get(spread, $span); |
||||
|
||||
$context : null; |
||||
$span-sum : null; |
||||
$width : null; |
||||
|
||||
@if $n == 'full' { |
||||
$pos: susy-get(gutter-position, $span); |
||||
$role: susy-get(role, $span); |
||||
$n: if($pos == split and $role != nest, susy-count($columns), 100%); |
||||
} |
||||
|
||||
@if type-of($n) != number { |
||||
@warn "(#{type-of($n)}) #{$n} is not a valid span."; |
||||
} @else if unitless($n) { |
||||
$context: susy-sum($columns, $gutters, if(is-split($span), wide, narrow)); |
||||
$spread: if(is-inside($span), $spread or wide, $spread); |
||||
$span-sum: susy($n, $location, $columns, $gutters, $spread); |
||||
|
||||
$_math: susy-get(math, $span); |
||||
$_column-width: susy-get(column-width, $span); |
||||
@if $_math == static { |
||||
$width: $span-sum * valid-column-math($_math, $_column-width); |
||||
} @else { |
||||
$width: percentage($span-sum / $context); |
||||
} |
||||
} @else { |
||||
$width: $n; |
||||
} |
||||
|
||||
@return $width; |
||||
} |
@ -0,0 +1,16 @@
|
||||
// Validation |
||||
// ========== |
||||
|
||||
|
||||
// Validate Column Math |
||||
// -------------------- |
||||
@function valid-column-math( |
||||
$math, |
||||
$column-width |
||||
) { |
||||
@if $math == static and not($column-width) { |
||||
@error 'Static math requires a valid column-width setting.'; |
||||
} |
||||
|
||||
@return $column-width; |
||||
} |
@ -0,0 +1,18 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Imports |
||||
|
||||
@import "compass/layout/grid-background"; |
||||
@import "compass/css3/background-origin"; |
||||
@import "compass/css3/background-clip"; |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Susy Grid Background |
||||
// |
||||
// A wrapper for the compass "column-grid-background" mixin |
||||
// Uses all your settings to create a grid background for a container element. |
||||
// Note: Sub-pixel rounding can lead to several pixels of variation between browsers. |
||||
@mixin susy-grid-background(){ |
||||
@include column-grid-background($total-columns, column(), gutter(), 0); |
||||
@include background-origin(content-box); |
||||
@include background-clip(content-box); |
||||
} |
@ -0,0 +1,377 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Imports |
||||
|
||||
// We need access to some basic font settings for handling media-queries. |
||||
@import "compass/typography/vertical_rhythm"; |
||||
|
||||
// For now, we also need this... |
||||
$browser-default-font-size-px : 16px; |
||||
$browser-default-font-size-percent : 100%; |
||||
$browser-default-font-size-pt : 12pt; |
||||
|
||||
$rem-with-px-fallback : true !default; |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Sass list Functions |
||||
|
||||
// Return a list with specific items removed |
||||
// |
||||
// filter($list, $target) |
||||
// - $list : The list to filter. |
||||
// - $target : An item to be removed from the list. |
||||
@function filter($list, $target) { |
||||
$clean: compact(); |
||||
@if index($list, $target) { |
||||
@each $item in $list { |
||||
$clean: if($item == $target, $clean, append($clean, $item)); |
||||
} |
||||
} @else { $clean: $list; } |
||||
@return $clean; |
||||
} |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Don't use static output when it will break things |
||||
|
||||
// Switch element-level output to fluid, when container-width is wrong for static |
||||
// |
||||
// fix-static-misalignment([$style, $width]) |
||||
// - $style: $container-style. |
||||
// - $width: $container-width. |
||||
@function fix-static-misalignment( |
||||
$style: $container-style, |
||||
$width: $container-width |
||||
) { |
||||
@if $container-width and $container-width != container-outer-width($width: false) { |
||||
$style: fluid; |
||||
} |
||||
@return $style; |
||||
} |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Grid Functions |
||||
|
||||
// Returns the full width of a grid based on your grid settings. |
||||
// |
||||
// $columns : The number of columns to get width for. |
||||
@function columns-width( |
||||
$columns : $total-columns |
||||
) { |
||||
@if round($columns) != $columns { |
||||
@warn "Susy works best with integer column-spans." + |
||||
"For partial-columns, you may need to finesse the math by hand using functions directly."; |
||||
} |
||||
@return ($columns * $column-width) + (if($columns >= 1, ceil($columns - 1), 0) * $gutter-width); |
||||
} |
||||
|
||||
// Return the grid width after adding or subtracting grid padding |
||||
// |
||||
// $width : the width of the grid without padding; |
||||
// $operation : ( add | subtract ) if padding should be added or subtracted; |
||||
@function handle-grid-padding( |
||||
$width, |
||||
$operation : subtract |
||||
) { |
||||
$pad: $grid-padding*2; |
||||
|
||||
@if comparable($width, $grid-padding) { |
||||
$width: if($operation == subtract, $width - $pad, $width + $pad); |
||||
} @else { |
||||
@warn "$grid-padding must be set in units comparable to the container width."; |
||||
} |
||||
|
||||
@return $width; |
||||
} |
||||
|
||||
// Return the full outer width of a Container element. |
||||
// |
||||
// $columns : The number of columns in the Grid Layout. |
||||
@function container-outer-width( |
||||
$columns : $total-columns, |
||||
$width : $container-width |
||||
) { |
||||
$outerwidth: if($width, $width, columns-width($columns)); |
||||
|
||||
@if $width { |
||||
@if not($border-box-sizing) { $outerwidth: handle-grid-padding($outerwidth, subtract); } |
||||
} @else { |
||||
@if $border-box-sizing { $outerwidth: handle-grid-padding($outerwidth, add); } |
||||
} |
||||
|
||||
@return $outerwidth; |
||||
} |
||||
|
||||
// Return the percentage width of a single column in a given 'context'. |
||||
// |
||||
// $context : The grid context in columns, if nested. |
||||
// $style : The container style to use. |
||||
@function column( |
||||
$context : $total-columns, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
@return if($style == static, $column-width, relative-width($column-width, $context)); |
||||
} |
||||
|
||||
// Return the percentage width of multiple 'columns' in a given 'context'. |
||||
// |
||||
// $columns : The number of columns to get relative width for. |
||||
// $context : The grid context in columns, if nested. |
||||
// $style : The container style to use. |
||||
@function columns( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
@return if($style == static, columns-width($columns), relative-width(columns-width($columns), $context)); |
||||
} |
||||
|
||||
// Return the percentage width of a single gutter in a given 'context'. |
||||
// |
||||
// $context : The grid context in columns, if nested. |
||||
// $style : The container style to use. |
||||
@function gutter( |
||||
$context : $total-columns, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
@return if($style == static, $gutter-width, relative-width($gutter-width, $context)); |
||||
} |
||||
|
||||
// Return the percentage width of a given value in a given 'context'. |
||||
// |
||||
// $width : Any given width value. |
||||
// $context : The grid context in columns, if nested. |
||||
@function relative-width( |
||||
$width, |
||||
$context : $total-columns |
||||
) { |
||||
@return percentage($width / columns-width($context)); |
||||
} |
||||
|
||||
// Return the total space occupied by multiple columns and associated gutters. |
||||
// Useful for adding padding or margins (prefix, suffix, push, pull, etc.) |
||||
// |
||||
// $columns : The number of columns to get relative space for. |
||||
// $context : The grid context in columns, if nested. |
||||
// $style : The container style to use. |
||||
@function space( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
@return columns($columns, $context, $style) + if($columns >= 1, gutter($context, $style), 0); |
||||
} |
||||
|
||||
// Accept a list including column-count and (optional) position. |
||||
// Return either the column count or the position alone. |
||||
// |
||||
// $columns : the list to split and interprate. |
||||
// $request : The value to return, either 'columns' or 'position'. |
||||
@function split-columns-value( |
||||
$columns, |
||||
$request : columns |
||||
) { |
||||
$pos : false; |
||||
$cols : false; |
||||
|
||||
@each $var in $columns { |
||||
@if (type-of($var) == 'string') { |
||||
$pos: $var; |
||||
} @else { |
||||
@if (type-of($var) == 'number') and (unitless($var)) { |
||||
$cols: $var; |
||||
} @else { |
||||
@warn '"#{$var}" is not a valid part of "$columns: #{$columns}" in the columns() mixin.'; |
||||
} |
||||
} |
||||
} |
||||
|
||||
@if $request == 'columns' { |
||||
@return $cols; |
||||
} @else { |
||||
@if $request == 'position' { |
||||
@return $pos; |
||||
} @else { |
||||
@warn '"#{$request}" is not a valid value for $request'; |
||||
} |
||||
} |
||||
} |
||||
|
||||
// Accept nth-selector variables, and format them as a valid CSS3 selector. |
||||
// |
||||
// $n : [first | only | last | <equation>] |
||||
// $selector : [child | last-child | of-type | last-of-type ] |
||||
@function format-nth( |
||||
$n : last, |
||||
$selector : child |
||||
) { |
||||
@if ($n == 'last') or ($n =='first') or ($n =='only') { |
||||
$selector: '#{$n}-#{$selector}'; |
||||
} @else { |
||||
$selector: 'nth-#{$selector}(#{$n})'; |
||||
} |
||||
@return $selector; |
||||
} |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Media Functions |
||||
|
||||
// Return an em value adjusted to match the browser default font size. |
||||
// Note: This only works if actual sizes are set relative to browser defaults. |
||||
// |
||||
// $ems : The initial value to be converted. |
||||
// $font-size : The current font-size in. |
||||
@function base-ems( |
||||
$ems, |
||||
$font-size: $base-font-size |
||||
){ |
||||
$font-size : if(unit($ems) == 'rem', $base-font-size, $font-size); |
||||
$unit : unit($font-size); |
||||
$mult : $ems / ($ems * 0 + 1); |
||||
|
||||
@if $unit == 'px' { |
||||
@return $font-size / $browser-default-font-size-px * $mult * 1em; |
||||
} |
||||
@else if $unit == '%' { |
||||
@return $font-size / $browser-default-font-size-percent * $mult * 1em; |
||||
} |
||||
@else if $unit == 'em' { |
||||
@return $font-size / 1em * $mult * 1em; |
||||
} |
||||
@else if $unit == 'pt' { |
||||
@return $font-size / $browser-default-font-size-pt * $mult * 1em; |
||||
} |
||||
@else { |
||||
@warn 'Variable $base-font-size does not have a valid font unit. Valid units for fonts in CSS are px, pt, em, and %.'; |
||||
} |
||||
} |
||||
|
||||
// This name will be deprecated... |
||||
@function absolute-ems( |
||||
$ems, |
||||
$font-size: $base-font-size |
||||
){ |
||||
@return base-ems( $ems, $font-size); |
||||
} |
||||
|
||||
// Return a length, after any em-values have been sent through absolute-ems(). |
||||
// |
||||
// $length : The length value to be checked and adjusted if necessary. |
||||
// $font-size : The current font-size in px. |
||||
@function fix-ems( |
||||
$length, |
||||
$font-size: $base-font-size |
||||
){ |
||||
@if $length { |
||||
@if (unit($length) == 'em') or (unit($length) == 'rem') { |
||||
$length: absolute-ems($length,$font-size); |
||||
} |
||||
} |
||||
@return $length; |
||||
} |
||||
|
||||
// Sort a list of arguments into "$min $layout $max $ie" order, and return the list. |
||||
// |
||||
// $media-layout : a list of values [$min $layout $max $ie] including... |
||||
// : - one unitless number (columns in a layout) |
||||
// : - two optional lengths (min and max-width media-query breakpoints). |
||||
// : - one optional boolean or string to trigger fallback support for IE. |
||||
// $font-size : [optional] The base font-size of your layout, if you are using ems. |
||||
// : - defaults to $base-font-size |
||||
@function medialayout( |
||||
$media-layout, |
||||
$font-size: $base-font-size |
||||
) { |
||||
$media : false; |
||||
$min : false; |
||||
$layout : false; |
||||
$max : false; |
||||
$ie : false; |
||||
$has-layout : false; |
||||
|
||||
@each $val in $media-layout { |
||||
@if (type-of($val) == "number") { |
||||
@if unitless($val) { |
||||
$layout : $val; |
||||
$has-layout : true; |
||||
} @else { |
||||
@if ($has-layout) and not($media) { |
||||
$max: $val; |
||||
} @else { |
||||
@if $media { |
||||
$media: join($media,$val); |
||||
} @else { |
||||
$media: $val; |
||||
} |
||||
} |
||||
} |
||||
} @else { |
||||
$ie: $val; |
||||
} |
||||
} |
||||
@if (length($media) > 0) { |
||||
@if (length($media) == 1) { |
||||
$min: nth($media,1); |
||||
} @else { |
||||
$min: nth($media,1); |
||||
$max: nth($media,2); |
||||
@if comparable($min, $max) { |
||||
@if ($min > $max) { |
||||
$max: nth($media,1); |
||||
$min: nth($media,2); |
||||
} |
||||
} @else { |
||||
@warn "Can't compare incompatible units." + |
||||
"Using #{$min} for min-width, and #{$max} for max-width"; |
||||
} |
||||
@if (length($media) > 2) { |
||||
@warn "You can only send two lengths: a min-width and an (optional) max-width." + |
||||
"You sent #{length($media)}: #{$media}"; |
||||
} |
||||
} |
||||
} |
||||
|
||||
// media-queries must be set in ems relative to the browser default |
||||
// rather than the font-size set in CSS. |
||||
$min: fix-ems($min,$font-size); |
||||
$max: fix-ems($max,$font-size); |
||||
|
||||
@return $min $layout $max $ie; |
||||
} |
||||
|
||||
// Return the nearest layout (column-count) above a given breakpoint. |
||||
// |
||||
// $min : The min-width media-query breakpoint above which to establish a new layout. |
||||
@function get-layout( |
||||
$min |
||||
) { |
||||
$min : fix-ems($min); |
||||
$return : false; |
||||
|
||||
@if comparable($min, $column-width) { |
||||
$return : ceil(($min + $gutter-width) / ($column-width + $gutter-width)); |
||||
} @else { |
||||
@warn "Can't determine a layout, becuse #{$min} and #{$column-width} are not comparable."; |
||||
} |
||||
|
||||
@return $return; |
||||
} |
||||
|
||||
// Check to see if a given $media-layout list is simply the default. |
||||
// |
||||
// $media-layout : a list of values including - |
||||
// : One unitless number (columns in a layout) |
||||
// : Two optional lengths (min and max-width media-query breakpoints). |
||||
// : One optional boolean or string to trigger fallback support for IE. |
||||
@function is-default-layout( |
||||
$media-layout |
||||
) { |
||||
$media-layout : medialayout($media-layout); |
||||
$min : nth($media-layout,1); |
||||
$layout-cols : nth($media-layout,2); |
||||
$max : nth($media-layout,3); |
||||
|
||||
@if $min or $max { |
||||
@return false; |
||||
} @else { |
||||
@return if($layout-cols == $total-columns,true,false); |
||||
} |
||||
} |
@ -0,0 +1,312 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Imports |
||||
|
||||
@import "compass/utilities/general/clearfix"; |
||||
@import "compass/css3/box-sizing"; |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Border-Box Sizing |
||||
|
||||
// Apply the border-box sizing model to all elements |
||||
// and adjust the grid math appropriately. |
||||
@mixin border-box-sizing { |
||||
$border-box-sizing: true !global; |
||||
* { @include box-sizing(border-box); } |
||||
} |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Container |
||||
|
||||
// Set the width of a container |
||||
// |
||||
// $columns : The number of columns in the Grid Layout. |
||||
@mixin set-container-width( |
||||
$columns : $total-columns, |
||||
$style : $container-style, |
||||
$px-vals : $pixel-values-only |
||||
){ |
||||
$width: container-outer-width($columns); |
||||
|
||||
@if $style == 'static' { |
||||
@if $px-vals == true { |
||||
width: round(convert-length($width, px)); |
||||
} @else { |
||||
@include rem(width, $width); |
||||
} |
||||
} @else { |
||||
@if $style == 'fluid' { |
||||
@if unit($width) == '%' { |
||||
@if $px-vals == true { |
||||
width: round(convert-length($width, px)); |
||||
} @else { |
||||
@include rem(width, $width); |
||||
} |
||||
} |
||||
} @else { |
||||
@if $px-vals == true { |
||||
max-width: round(convert-length($width, px)); |
||||
} @else { |
||||
@include rem(max-width, $width); |
||||
} |
||||
|
||||
@include for-legacy-browser(ie,"6") { |
||||
@if unit($width) == 'rem' { |
||||
_width: round(convert-length($width, px)); |
||||
} @else { |
||||
_width: $width; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
// Set the outer grid-containing element(s). |
||||
// |
||||
// $columns : The number of columns in the container. |
||||
@mixin apply-container( |
||||
$columns : $total-columns, |
||||
$px-vals : $pixel-values-only |
||||
){ |
||||
@include pie-clearfix; |
||||
@include set-container-width($columns); |
||||
@if $px-vals == true { |
||||
padding-left: round(convert-length($grid-padding, px)); |
||||
padding-right: round(convert-length($grid-padding, px)); |
||||
} @else { |
||||
@include rem(padding-left, $grid-padding); |
||||
@include rem(padding-right, $grid-padding); |
||||
} |
||||
margin: { left: auto; right: auto; } |
||||
} |
||||
|
||||
// Set one or more layouts on a grid-containing element at any number of media-query breakpoints. |
||||
// |
||||
// $media-layout-1 : [default:$total-columns] A list of values including - |
||||
// : One unitless number (representing columns in a layout) |
||||
// : Two optional lengths (representing min and max-width media-query breakpoints). |
||||
// $media-layout-2 ...-10 : [optional] Same as $media-layout-1 |
||||
@mixin container( |
||||
$media-layouts... |
||||
){ |
||||
$media-layouts: if(length($media-layouts) > 0, $media-layouts, $total-columns); |
||||
|
||||
@each $ml in $media-layouts { |
||||
@if is-default-layout($ml) { |
||||
@include apply-container; |
||||
} @else { |
||||
@include at-breakpoint($ml) { |
||||
@include apply-container; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Columns |
||||
|
||||
// Create a grid element spanning any number of 'columns' in a grid 'context'. |
||||
// $columns : The number of columns to span. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $padding : [optional] Padding applied to the inside of individual grid columns. |
||||
// : Padding is only output if one or two values are specified (e.g. 1em or 10px 20px) |
||||
// : Padding values are applied only on the horizontal axis in from-to order |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin span-columns( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$padding : false, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
$pos : split-columns-value($columns,position); |
||||
$cols : split-columns-value($columns,columns); |
||||
$pad-from : if($style == static, 0 * $gutter-width, relative-width(0 * $gutter-width, $context)); |
||||
$pad-to : if($style == static, 0 * $gutter-width, relative-width(0 * $gutter-width, $context)); |
||||
|
||||
@if $padding != false { |
||||
$pad-from : nth($padding, 1); |
||||
|
||||
@if length($padding) > 1 { |
||||
$pad-to: nth($padding, 2); |
||||
} @else { |
||||
$pad-to: $pad-from; |
||||
} |
||||
|
||||
$pad-from : if($style == static, $pad-from, relative-width($pad-from, $context)); |
||||
$pad-to : if($style == static, $pad-to, relative-width($pad-to, $context)); |
||||
|
||||
padding-#{$from}: $pad-from; |
||||
padding-#{$to}: $pad-to; |
||||
} |
||||
|
||||
width: columns($cols, $context, $style) - if($border-box-sizing, 0, $pad-to + $pad-from); |
||||
|
||||
@if ($pos == 'omega') { |
||||
@include omega($from); |
||||
} @else { |
||||
float: $from; |
||||
margin-#{$to}: gutter($context, $style); |
||||
@include for-legacy-browser(ie, "6") { |
||||
display: inline; |
||||
} |
||||
} |
||||
} |
||||
|
||||
// Apply to elements spanning the last column, to account for the page edge. |
||||
// Only needed as an override. Normally 'omega' can just be called by `columns`. |
||||
// |
||||
// $from : The start-direction for your document. |
||||
@mixin omega( |
||||
$from : $from-direction |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
$hack : opposite-position($omega-float); |
||||
|
||||
float: $omega-float; |
||||
margin-#{$to}: 0; |
||||
|
||||
@include for-legacy-browser(ie, "6", "7") { |
||||
*margin-#{$hack}: - $gutter-width; |
||||
@include for-legacy-browser(ie, "6") { |
||||
display: inline; |
||||
} |
||||
} |
||||
} |
||||
|
||||
// Shortcut to apply omega to a specific subset of elements. |
||||
// |
||||
// $n : [first | only | last | <equation>] |
||||
// $selector : [child | last-child | of-type | last-of-type ] |
||||
// $from : The start-direction for your document. |
||||
@mixin nth-omega( |
||||
$n : last, |
||||
$selector : child, |
||||
$from : $from-direction |
||||
) { |
||||
$from : unquote($from); |
||||
|
||||
&:#{format-nth($n,$selector)} { |
||||
@if $n == "first" { |
||||
@include omega($from); |
||||
} @else { |
||||
@include with-browser-ranges(css-sel3) { |
||||
@include omega($from); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Resets |
||||
|
||||
// Reset a '+columns' grid element to default block behavior |
||||
// |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
@mixin reset-columns( |
||||
$from: $from-direction |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
$hack : opposite-position($omega-float); |
||||
|
||||
float: none; |
||||
width: auto; |
||||
margin-#{$to}: auto; |
||||
|
||||
@include for-legacy-browser(ie, "6", "7") { |
||||
*margin-#{$hack}: auto; |
||||
@include for-legacy-browser(ie, "6") { |
||||
display: block; |
||||
} |
||||
} |
||||
} |
||||
|
||||
// Apply to elements previously set as omega. |
||||
// This will return floats and margins back to non-omega settigns. |
||||
// |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// $from : The start-direction for your document. |
||||
// $style : The container style to use. |
||||
@mixin remove-omega( |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
$hack : opposite-position($omega-float); |
||||
|
||||
float: $from; |
||||
margin-#{$to}: gutter($context, $style); |
||||
|
||||
@include for-legacy-browser(ie, "6", "7") { |
||||
*margin-#{$hack}: auto; |
||||
} |
||||
} |
||||
|
||||
// Shortcut to apply remove-omega to a specific subset of elements. |
||||
// |
||||
// $n : [first | only | last | <equation>] |
||||
// $selector : [child | last-child | of-type | last-of-type ] |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// $from : The start-direction for your document. |
||||
// $style : The container style to use. |
||||
@mixin remove-nth-omega( |
||||
$n : last, |
||||
$selector : child, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
|
||||
&:#{format-nth($n,$selector)} { |
||||
@if $n == "first" { |
||||
@include remove-omega($context, $from, $style); |
||||
} @else { |
||||
@include with-browser-ranges(css-sel3) { |
||||
@include remove-omega($context, $from, $style); |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Change Settings |
||||
|
||||
@mixin with-grid-settings( |
||||
$columns: $total-columns, |
||||
$width: $column-width, |
||||
$gutter: $gutter-width, |
||||
$padding: $grid-padding |
||||
) { |
||||
// keep the defaults around |
||||
$default-columns: $total-columns; |
||||
$default-width: $column-width; |
||||
$default-gutter: $gutter-width; |
||||
$default-padding: $grid-padding; |
||||
|
||||
// use the new settings |
||||
$total-columns: $columns !global; |
||||
$column-width: $width !global; |
||||
$gutter-width: $gutter !global; |
||||
$grid-padding: $padding !global; |
||||
|
||||
// apply to contents |
||||
@content; |
||||
|
||||
// re-instate the defaults |
||||
$total-columns: $default-columns !global; |
||||
$column-width: $default-width !global; |
||||
$gutter-width: $default-gutter !global; |
||||
$grid-padding: $default-padding !global; |
||||
} |
@ -0,0 +1,51 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Isolation |
||||
|
||||
// Isolate the position of a grid element (use in addition to span-columns) |
||||
// |
||||
// $location : The grid column to isolate in, relative to the container; |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
@mixin isolate( |
||||
$location, |
||||
$context: $total-columns, |
||||
$from: $from-direction, |
||||
$style: fix-static-misalignment() |
||||
) { |
||||
$to: opposite-position($from); |
||||
margin-#{$to}: -100%; |
||||
margin-#{$from}: space($location - 1, $context, $style); |
||||
} |
||||
|
||||
// Isolate a group of elements in a grid, using nth-child selectors |
||||
// |
||||
// $columns : The column-width of each item on the grid; |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// $selector : [child | of-type | last-of-type ] (default is 'child') |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
@mixin isolate-grid( |
||||
$columns, |
||||
$context: $total-columns, |
||||
$selector: 'child', |
||||
$from: $from-direction, |
||||
$style: fix-static-misalignment() |
||||
) { |
||||
$to: opposite-position($from); |
||||
$location: 1; |
||||
$line: floor($context / $columns); |
||||
|
||||
@include span-columns($columns, $context, $from: $from, $style: $style); |
||||
margin-#{$to}: -100%; |
||||
|
||||
@for $item from 1 through $line { |
||||
$nth: '#{$line}n + #{$item}'; |
||||
&:#{format-nth($nth,$selector)} { |
||||
margin-#{$from}: space($location - 1, $context, $style); |
||||
@if $location == 1 { clear: $from; } |
||||
@else { clear: none; } |
||||
|
||||
$location: $location + $columns; |
||||
@if $location > $context { $location: 1; } |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,93 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Margin Mixins |
||||
|
||||
// Apply 'columns' margin before an element to push it along the grid. |
||||
// |
||||
// $columns : The number of columns to span. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin pre( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
margin-#{$from}: space($columns, $context, $style); |
||||
} |
||||
|
||||
// 'push' is a synonymn for 'pre' |
||||
@mixin push( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
@include pre($columns, $context, $from, $style); |
||||
} |
||||
|
||||
// Apply negative 'columns' margin before an element to pull it along the grid. |
||||
// |
||||
// $columns : The number of columns to span. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin pull( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
margin-#{$from}: 0 - space($columns, $context, $style); |
||||
} |
||||
|
||||
// Apply 'columns' margin after an element to contain it in a grid. |
||||
// |
||||
// $columns : The number of columns to span. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin post( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
margin-#{$to}: space($columns, $context, $style); |
||||
} |
||||
|
||||
// Apply 'columns' before and/or after an element to contain it on a grid. |
||||
// |
||||
// $pre : The number of columns to add as margin before. |
||||
// $post : The number of columns to add as margin after. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin squish( |
||||
$pre : false, |
||||
$post : false, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
@if $pre { |
||||
@include pre($pre, $context, $from, $style) |
||||
} |
||||
@if $post { |
||||
@include post($post, $context, $from, $style) |
||||
} |
||||
} |
@ -0,0 +1,105 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Media Mixins |
||||
|
||||
// Create a new layout context for (@content) descendants. |
||||
// |
||||
// $layout-cols : a (unitless) number of columns to use for this layout. |
||||
@mixin layout( |
||||
$layout-cols |
||||
) { |
||||
// store default $total-columns setting for later, then change it. |
||||
$default-layout : $total-columns; |
||||
$total-columns : $layout-cols !global; |
||||
|
||||
// apply children in this new layout context. |
||||
@content; |
||||
|
||||
// return to default $total-columns setting. |
||||
$total-columns : $default-layout !global; |
||||
} |
||||
|
||||
// Nest a block of code inside a new media-query and layout context. |
||||
// |
||||
// $media-layout : a list of values [$min $layout $max $ie] including... |
||||
// : - one unitless number (columns in a layout) |
||||
// : - two optional lengths (min and max-width media-query breakpoints). |
||||
// : - one optional boolean or string to trigger fallback support for IE. |
||||
// $font-size : [optional] The base font-size of your layout, if you are using ems. |
||||
// : - defaults to $base-font-size |
||||
@mixin at-breakpoint( |
||||
$media-layout, |
||||
$font-size: $base-font-size |
||||
) { |
||||
$media-layout : medialayout($media-layout,$font-size); |
||||
$min : nth($media-layout,1); |
||||
$layout : nth($media-layout,2); |
||||
$max : nth($media-layout,3); |
||||
$ie : nth($media-layout,4); |
||||
|
||||
@if not($breakpoint-media-output) and not($breakpoint-ie-output) and not($breakpoint-raw-output) { |
||||
@warn "Either $breakpoint-media-output, $breakpoint-ie-output, or $breakpoint-raw-output must be true for at-breakpoint to work."; |
||||
} |
||||
|
||||
// We need to have either a min-width breakpoint or a layout in order to proceed. |
||||
@if $min or $layout or $max { |
||||
|
||||
// If we don't have a layout, we create one based on the min-width. |
||||
@if not($layout) { |
||||
$layout: get-layout($min); |
||||
} |
||||
|
||||
// If we still don't have a layout, we have a problem. |
||||
@if $layout { |
||||
// Set our new layout context. |
||||
@include layout($layout) { |
||||
@if $breakpoint-media-output { |
||||
@include with-browser-ranges(css-mediaqueries) { |
||||
@if $min and $max { |
||||
// Both $min and $max |
||||
@media (min-width: $min) and (max-width: $max) { |
||||
@content; |
||||
} |
||||
} @else { |
||||
@if not($min) and not($max) { |
||||
// Neither $min nor $max: |
||||
// We can create a breakpoint based on the number of columns in the layout. |
||||
$min: fix-ems(container-outer-width($width: false)); |
||||
} |
||||
@if $min { |
||||
// Min only: |
||||
@media (min-width: $min) { |
||||
@content; |
||||
} |
||||
} @else { |
||||
// Max only: |
||||
@media (max-width: $max) { |
||||
@content; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
} |
||||
// Set an IE fallback |
||||
@if $ie and $breakpoint-ie-output { |
||||
@if (type-of($ie) == 'bool') { |
||||
$ie: 'lt-ie9'; |
||||
} |
||||
.#{$ie} & { |
||||
@content; |
||||
} |
||||
} |
||||
|
||||
@if $breakpoint-raw-output { |
||||
@content; |
||||
} |
||||
} |
||||
} @else { |
||||
@warn "We were unable to determine a layout for your breakpoint."; |
||||
} |
||||
|
||||
} @else { |
||||
@warn "You need to provide either a valid layout (number of columns)" |
||||
+ "or a valid media-query min-width breakpoint (length)."; |
||||
} |
||||
|
||||
} |
@ -0,0 +1,92 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Padding Mixins |
||||
|
||||
// add empty colums as padding before an element. |
||||
// $columns : The number of columns to prefix. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin prefix( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
padding-#{$from}: space($columns, $context, $style); |
||||
} |
||||
|
||||
// add empty colums as padding after an element. |
||||
// $columns : The number of columns to suffix. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin suffix( |
||||
$columns, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
$to : opposite-position($from); |
||||
padding-#{$to}: space($columns, $context, $style); |
||||
} |
||||
|
||||
// add empty colums as padding before and after an element. |
||||
// $columns : The number of columns to pad. |
||||
// $context : [optional] The context (columns spanned by parent). |
||||
// : Context is required on any nested elements. |
||||
// : Context MUST NOT be declared on a root element. |
||||
// $from : The start direction of your layout (e.g. 'left' for ltr languages) |
||||
// $style : The container style to use. |
||||
@mixin pad( |
||||
$prefix : false, |
||||
$suffix : false, |
||||
$context : $total-columns, |
||||
$from : $from-direction, |
||||
$style : fix-static-misalignment() |
||||
) { |
||||
$from : unquote($from); |
||||
@if $prefix { |
||||
@include prefix($prefix, $context, $from, $style); |
||||
} |
||||
@if $suffix { |
||||
@include suffix($suffix, $context, $from, $style); |
||||
} |
||||
} |
||||
|
||||
// Bleed into colums with margin/padding on any side of an element. |
||||
// $width : The side of the bleed. |
||||
// : Any unit-length will be used directly. |
||||
// : Any unitless number will be used as a column-count. |
||||
// : Use "2 of 6" format to represent 2 cals in a 6-col nested context. |
||||
// $sides : One or more sides to bleed [ top | right | bottom | left | all ]. |
||||
// $style : The container style to use. |
||||
@mixin bleed( |
||||
$width: $grid-padding, |
||||
$sides: left right, |
||||
$style: fix-static-misalignment() |
||||
) { |
||||
@if $border-box-sizing { @include box-sizing(content-box) } |
||||
|
||||
@if type-of($width) == 'list' { |
||||
$width: filter($width, of); |
||||
$width: space(nth($width,1), nth($width,2), $style); |
||||
} @else if unitless($width) { |
||||
$width: space($width, $style: $style); |
||||
} |
||||
|
||||
@if $sides == 'all' { |
||||
margin: - $width; |
||||
padding: $width; |
||||
} @else { |
||||
@each $side in $sides { |
||||
margin-#{$side}: - $width; |
||||
padding-#{$side}: $width; |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,60 @@
|
||||
// --------------------------------------------------------------------------- |
||||
// Susy Settings |
||||
|
||||
// The total number of columns in the grid |
||||
$total-columns : 12 !default; |
||||
|
||||
// The width of columns and gutters. |
||||
// These must all be set with the comparable units. |
||||
$column-width : 4em !default; |
||||
$gutter-width : 1em !default; |
||||
|
||||
// Padding on the left and right of a Grid Container. |
||||
$grid-padding : $gutter-width !default; |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// Advanced Settings |
||||
|
||||
// From Direction: |
||||
// Controls for right-to-left or bi-directional sites. |
||||
$from-direction : left !default; |
||||
|
||||
// Omega Float Direction: |
||||
// The direction that +omega elements are floated by deafult. |
||||
$omega-float : opposite-position($from-direction) !default; |
||||
|
||||
// Container Width: |
||||
// Override the total width of your grid, using any length (50em, 75%, etc.) |
||||
$container-width : false !default; |
||||
|
||||
// Container Style: |
||||
// 'magic' - Static (fixed or elastic) when there's enough space, |
||||
// fluid when there isn't. This is the SUSY MAGIC SAUCE(TM). |
||||
// 'static' - Forces the grid container to remain static at all times. |
||||
// 'fluid' - Forces the grid to remain fluid at all times. |
||||
// (this will overrule any static $container-width settings) |
||||
$container-style : magic !default; |
||||
|
||||
// Border-Box Sizing |
||||
// Adjust the grid math appropriately for box-sizing: border-box; |
||||
// Warning: This does not actually apply the new box model! |
||||
// In most cases you can ignore this setting, |
||||
// and simply apply the border-box-sizing mixin. |
||||
$border-box-sizing : false !default; |
||||
|
||||
// Pixel Values only: |
||||
// Make sure only pixel values are set for the container width. |
||||
$pixel-values-only : false !default; |
||||
|
||||
// --------------------------------------------------------------------------- |
||||
// IE Settings |
||||
|
||||
// When you are using a seperate IE stylesheet, |
||||
// you can use these settings to control the output of at-breakpoint. |
||||
// By default, at-breakpoint will output media-queries as well as |
||||
// any defined ie-fallback classes. |
||||
$breakpoint-media-output : true !default; |
||||
$breakpoint-ie-output : true !default; |
||||
|
||||
// Danger Zone! Only set as 'true' in IE-specific style sheets. |
||||
$breakpoint-raw-output : false !default; |
@ -0,0 +1,9 @@
|
||||
// Float API |
||||
// ========= |
||||
|
||||
@import "shared"; |
||||
|
||||
@import "float/container"; |
||||
@import "float/span"; |
||||
@import "float/end"; |
||||
@import "float/isolate"; |
@ -0,0 +1,15 @@
|
||||
// Shared API |
||||
// ========== |
||||
|
||||
@import "support"; |
||||
|
||||
@import "shared/inspect"; |
||||
@import "shared/output"; |
||||
@import "shared/direction"; |
||||
@import "shared/background"; |
||||
@import "shared/container"; |
||||
@import "shared/margins"; |
||||
@import "shared/padding"; |
||||
|
||||
|
||||
|
@ -0,0 +1,9 @@
|
||||
// Susy Browser Support |
||||
// ==================== |
||||
|
||||
@import "support/support"; |
||||
@import "support/prefix"; |
||||
@import "support/background"; |
||||
@import "support/box-sizing"; |
||||
@import "support/rem"; |
||||
@import "support/clearfix"; |
@ -0,0 +1,16 @@
|
||||
// Float Container API |
||||
// =================== |
||||
|
||||
// Float Container |
||||
// --------------- |
||||
// - [$width] : <length> |
||||
// - [$justify] : left | center | right |
||||
// - [$math] : fluid | static |
||||
@mixin float-container( |
||||
$width, |
||||
$justify: auto auto, |
||||
$property: max-width |
||||
) { |
||||
@include susy-clearfix; |
||||
@include container-output($width, $justify, $property); |
||||
} |
@ -0,0 +1,40 @@
|
||||
// Float Ends API |
||||
// ============== |
||||
|
||||
// Susy End Defaults |
||||
// ----------------- |
||||
// - PRIVATE |
||||
@include susy-defaults(( |
||||
last-flow: to, |
||||
)); |
||||
|
||||
// Float Last |
||||
// ---------- |
||||
// - [$flow] : ltr | rtl |
||||
@mixin float-last( |
||||
$flow: map-get($susy-defaults, flow), |
||||
$last-flow: map-get($susy-defaults, last-flow), |
||||
$margin: 0 |
||||
) { |
||||
$to: to($flow); |
||||
|
||||
$output: ( |
||||
float: if($last-flow == to, $to, null), |
||||
margin-#{$to}: $margin, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
||||
|
||||
// Float First |
||||
// ----------- |
||||
// - [$flow] : ltr | rtl |
||||
@mixin float-first( |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
$output: ( |
||||
margin-#{from($flow)}: 0, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,22 @@
|
||||
// Float Isolation API |
||||
// =================== |
||||
|
||||
// Isolate Output |
||||
// -------------- |
||||
// - $push : <length> |
||||
// - [$flow] : ltr | rtl |
||||
@mixin isolate-output( |
||||
$push, |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
$to: to($flow); |
||||
$from: from($flow); |
||||
|
||||
$output: ( |
||||
float: $from, |
||||
margin-#{$from}: $push, |
||||
margin-#{$to}: -100%, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,35 @@
|
||||
// Float Span API |
||||
// ============== |
||||
|
||||
// Float Span Output |
||||
// ----------------- |
||||
// - $width : <length> |
||||
// - [$float] : from | to |
||||
// - [$margin-before] : <length> |
||||
// - [$margin-after] : <length> |
||||
// - [$padding-before] : <length> |
||||
// - [$padding-after] : <length> |
||||
// - [$flow] : ltr | rtl |
||||
@mixin float-span-output( |
||||
$width, |
||||
$float : from, |
||||
$margin-before : null, |
||||
$margin-after : null, |
||||
$padding-before : null, |
||||
$padding-after : null, |
||||
$flow : map-get($susy-defaults, flow) |
||||
) { |
||||
$to : to($flow); |
||||
$from : from($flow); |
||||
|
||||
$output: ( |
||||
width: $width, |
||||
float: if($float == to, $to, null) or if($float == from, $from, null), |
||||
margin-#{$from}: $margin-before, |
||||
margin-#{$to}: $margin-after, |
||||
padding-#{$from}: $padding-before, |
||||
padding-#{$to}: $padding-after, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,26 @@
|
||||
// Grid Background API |
||||
// =================== |
||||
// - Sub-pixel rounding can lead to several pixels variation between browsers. |
||||
|
||||
// Grid Background Output |
||||
// ---------------------- |
||||
// - $image: background-image |
||||
// - $size: background-size |
||||
// - $clip: background-clip |
||||
// - [$flow]: ltr | rtl |
||||
@mixin background-grid-output ( |
||||
$image, |
||||
$size: null, |
||||
$clip: null, |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
$output: ( |
||||
background-image: $image, |
||||
background-size: $size, |
||||
background-origin: $clip, |
||||
background-clip: $clip, |
||||
background-position: from($flow) top, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,21 @@
|
||||
// Shared Container API |
||||
// ==================== |
||||
|
||||
// Container Output |
||||
// ---------------- |
||||
// - [$width] : <length> |
||||
// - [$justify] : left | center | right |
||||
// - [$math] : fluid | static |
||||
@mixin container-output( |
||||
$width, |
||||
$justify: auto auto, |
||||
$property: max-width |
||||
) { |
||||
$output: ( |
||||
#{$property}: $width or 100%, |
||||
margin-left: nth($justify, 1), |
||||
margin-right: nth($justify, 2), |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,42 @@
|
||||
// Direction Helpers |
||||
// ================= |
||||
|
||||
// Susy Flow Defaults |
||||
// ------------------ |
||||
// - PRIVATE |
||||
@include susy-defaults(( |
||||
flow: ltr, |
||||
)); |
||||
|
||||
// Get Direction |
||||
// ------------- |
||||
// Return the 'from' or 'to' direction of a ltr or rtl flow. |
||||
// - [$flow] : ltr | rtl |
||||
// - [$key] : from | to |
||||
@function get-direction( |
||||
$flow: map-get($susy-defaults, flow), |
||||
$key: from |
||||
) { |
||||
$return: if($flow == rtl, (from: right, to: left), (from: left, to: right)); |
||||
@return map-get($return, $key); |
||||
} |
||||
|
||||
// To |
||||
// -- |
||||
// Return the 'to' direction of a flow |
||||
// - [$flow] : ltr | rtl |
||||
@function to( |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
@return get-direction($flow, to); |
||||
} |
||||
|
||||
// From |
||||
// ---- |
||||
// Return the 'from' direction of a flow |
||||
// - [$flow] : ltr | rtl |
||||
@function from( |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
@return get-direction($flow, from); |
||||
} |
@ -0,0 +1,25 @@
|
||||
// Debugging |
||||
// ========= |
||||
|
||||
// Susy Inspect |
||||
// ------------ |
||||
// Output arguments passed to a inspect. |
||||
// - $mixin : <susy mixin> |
||||
// - $inspec : <mixin arguments> |
||||
|
||||
@mixin susy-inspect( |
||||
$mixin, |
||||
$inspect |
||||
) { |
||||
$show: false; |
||||
|
||||
@each $item in $inspect { |
||||
@if index($item, inspect) { |
||||
$show: true; |
||||
} |
||||
} |
||||
|
||||
@if $show or susy-get(debug inspect) { |
||||
-susy-#{$mixin}: inspect($inspect); |
||||
} |
||||
} |
@ -0,0 +1,23 @@
|
||||
// Margins API |
||||
// =========== |
||||
|
||||
// Margin Output |
||||
// ------------- |
||||
// - $before : <length> |
||||
// - $after : <length> |
||||
// - [$flow] : ltr | rtl |
||||
@mixin margin-output( |
||||
$before, |
||||
$after, |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
$to: to($flow); |
||||
$from: from($flow); |
||||
|
||||
$output: ( |
||||
margin-#{$from}: $before, |
||||
margin-#{$to}: $after, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,14 @@
|
||||
// Output |
||||
// ====== |
||||
|
||||
// Output |
||||
// ------ |
||||
// Output CSS with proper browser support. |
||||
// - $styles : <map of css property-value pairs> |
||||
@mixin output( |
||||
$styles |
||||
) { |
||||
@each $prop, $val in $styles { |
||||
@include susy-support($prop, $val); |
||||
} |
||||
} |
@ -0,0 +1,23 @@
|
||||
// Padding API |
||||
// =========== |
||||
|
||||
// Padding Output |
||||
// -------------- |
||||
// - $before : <length> |
||||
// - $after : <length> |
||||
// - [$flow] : ltr | rtl |
||||
@mixin padding-output( |
||||
$before, |
||||
$after, |
||||
$flow: map-get($susy-defaults, flow) |
||||
) { |
||||
$to: to($flow); |
||||
$from: from($flow); |
||||
|
||||
$output: ( |
||||
padding-#{$from}: $before, |
||||
padding-#{$to}: $after, |
||||
); |
||||
|
||||
@include output($output); |
||||
} |
@ -0,0 +1,58 @@
|
||||
// Background Properties |
||||
// ===================== |
||||
|
||||
// Susy Background Image |
||||
// --------------------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
// - $image: <background-image> |
||||
@mixin susy-background-image( |
||||
$image |
||||
) { |
||||
@if susy-support(background-image, (mixin: background-image), $warn: false) { |
||||
@include background-image($image...); |
||||
} @else { |
||||
background-image: $image; |
||||
} |
||||
} |
||||
|
||||
// Susy Background Size |
||||
// --------------------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
// - $image: <background-size> |
||||
@mixin susy-background-size( |
||||
$size |
||||
) { |
||||
@if susy-support(background-options, (mixin: background-size)) { |
||||
@include background-size($size); |
||||
} @else { |
||||
background-size: $size; |
||||
} |
||||
} |
||||
|
||||
// Susy Background Origin |
||||
// ---------------------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
// - $image: <background-origin> |
||||
@mixin susy-background-origin( |
||||
$origin |
||||
) { |
||||
@if susy-support(background-options, (mixin: background-origin)) { |
||||
@include background-origin($origin); |
||||
} @else { |
||||
background-origin: $origin; |
||||
} |
||||
} |
||||
|
||||
// Susy Background Clip |
||||
// -------------------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
// - $image: <background-clip> |
||||
@mixin susy-background-clip( |
||||
$clip |
||||
) { |
||||
@if susy-support(background-options, (mixin: background-clip)) { |
||||
@include background-clip($clip); |
||||
} @else { |
||||
background-clip: $clip; |
||||
} |
||||
} |
@ -0,0 +1,19 @@
|
||||
// Box Sizing |
||||
// ========== |
||||
|
||||
// Box Sizing |
||||
// ---------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
// - $model: <box-sizing> |
||||
@mixin susy-box-sizing( |
||||
$model: content-box |
||||
) { |
||||
@if $model { |
||||
@if susy-support(box-sizing, (mixin: box-sizing), $warn: false) { |
||||
@include box-sizing($model); |
||||
} @else { |
||||
$prefix: (moz, webkit, official); |
||||
@include susy-prefix(box-sizing, $model, $prefix); |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,18 @@
|
||||
// Susy Fallback Clearfix |
||||
// ====================== |
||||
|
||||
|
||||
// Clearfix |
||||
// -------- |
||||
// Check for an existing support mixin, or provide a simple fallback. |
||||
@mixin susy-clearfix { |
||||
@if susy-support(clearfix, (mixin: clearfix)) { |
||||
@include clearfix; |
||||
} @else { |
||||
&:after { |
||||
content: " "; |
||||
display: block; |
||||
clear: both; |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,19 @@
|
||||
// Susy Prefix |
||||
// =========== |
||||
|
||||
// Prefix |
||||
// ------ |
||||
// Output simple prefixed properties. |
||||
// - $prop : <css property> |
||||
// - $val : <css value> |
||||
// - [$prefix] : <browser prefix list> |
||||
@mixin susy-prefix( |
||||
$prop, |
||||
$val, |
||||
$prefix: official |
||||
) { |
||||
@each $fix in $prefix { |
||||
$fix: if($fix == official or not($fix), $prop, '-#{$fix}-#{$prop}'); |
||||
@include susy-rem($fix, $val); |
||||
} |
||||
} |
@ -0,0 +1,22 @@
|
||||
// rem Support |
||||
// =========== |
||||
|
||||
// rem |
||||
// --- |
||||
// Check for an existing support mixin, or output directly. |
||||
// - $prop : <css property> |
||||
// - $val : <css value> |
||||
@mixin susy-rem( |
||||
$prop, |
||||
$val |
||||
) { |
||||
$_reqs: ( |
||||
variable: rhythm-unit rem-with-px-fallback, |
||||
mixin: rem, |
||||
); |
||||
@if susy-support(rem, $_reqs, $warn: false) and $rhythm-unit == rem { |
||||
@include rem($prop, $val); |
||||
} @else { |
||||
#{$prop}: $val; |
||||
} |
||||
} |
@ -0,0 +1,85 @@
|
||||
// Browser Support |
||||
// =============== |
||||
|
||||
// Susy Support Defaults |
||||
// --------------------- |
||||
@include susy-defaults(( |
||||
use-custom: ( |
||||
clearfix: false, |
||||
background-image: true, |
||||
background-options: false, |
||||
breakpoint: true, |
||||
box-sizing: true, |
||||
rem: true, |
||||
), |
||||
)); |
||||
|
||||
|
||||
// Susy Support [mixin] |
||||
// -------------------- |
||||
// Send property-value pairs to the proper support modules. |
||||
// - $prop : <css property> |
||||
// - $val : <css value> |
||||
@mixin susy-support( |
||||
$prop, |
||||
$val |
||||
) { |
||||
// Background Support |
||||
@if $prop == background-image { |
||||
@include susy-background-image($val); |
||||
} @else if $prop == background-size { |
||||
@include susy-background-size($val); |
||||
} @else if $prop == background-origin { |
||||
@include susy-background-origin($val); |
||||
} @else if $prop == background-clip { |
||||
@include susy-background-clip($val); |
||||
} |
||||
|
||||
// Box-Sizing Support |
||||
@else if $prop == box-sizing { |
||||
@include susy-box-sizing($val); |
||||
} |
||||
|
||||
// Rem Support |
||||
@else { |
||||
@include susy-rem($prop, $val); |
||||
} |
||||
} |
||||
|
||||
|
||||
// Susy Support [function] |
||||
// ----------------------- |
||||
// Check for support of a feature. |
||||
// - $feature : <string> |
||||
// - e.g "rem" or "box-sizing" |
||||
// - $requirements : <map> |
||||
// - e.g (variable: rem-with-px-fallback, mixin: rem) |
||||
// - $warn : <bool> |
||||
@function susy-support( |
||||
$feature, |
||||
$requirements: (), |
||||
$warn: true |
||||
) { |
||||
$_support: susy-get(use-custom $feature); |
||||
|
||||
@if $_support { |
||||
$_fail: false; |
||||
|
||||
@each $_type, $_req in $requirements { |
||||
@each $_i in $_req { |
||||
$_pass: call(unquote("#{$_type}-exists"), $_i); |
||||
|
||||
@if not($_pass) { |
||||
$_fail: true; |
||||
@if $warn { |
||||
@warn "You requested custom support of #{$feature}, but the #{$_i} #{$_type} is not available."; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
$_support: if($_fail, false, $_support); |
||||
} |
||||
|
||||
@return $_support; |
||||
} |
@ -0,0 +1,103 @@
|
||||
// Column math |
||||
// =========== |
||||
|
||||
|
||||
// Is Symmetrical |
||||
// -------------- |
||||
// Returns true if a grid is symmetrical. |
||||
// - [$columns] : <number> | <list> |
||||
@function is-symmetrical( |
||||
$columns: susy-get(columns) |
||||
) { |
||||
$columns: valid-columns($columns); |
||||
@return if(type-of($columns) == number, $columns, null); |
||||
} |
||||
|
||||
|
||||
// Susy Count |
||||
// ---------- |
||||
// Find the number of columns in a given layout |
||||
// - [$columns] : <number> | <list> |
||||
@function susy-count( |
||||
$columns: susy-get(columns) |
||||
) { |
||||
$columns: valid-columns($columns); |
||||
@return is-symmetrical($columns) or length($columns); |
||||
} |
||||
|
||||
|
||||
// Susy Sum |
||||
// -------- |
||||
// Find the total sum of column-units in a layout |
||||
// - [$columns] : <number> | <list> |
||||
// - [$gutters] : <ratio> |
||||
// - [$spread] : false/narrow | wide | wider |
||||
@function susy-sum( |
||||
$columns : susy-get(columns), |
||||
$gutters : susy-get(gutters), |
||||
$spread : false |
||||
) { |
||||
$columns: valid-columns($columns); |
||||
$gutters: valid-gutters($gutters); |
||||
|
||||
$spread: if($spread == wide, 0, if($spread == wider, 1, -1)); |
||||
$gutter-sum: (susy-count($columns) + $spread) * $gutters; |
||||
$column-sum: is-symmetrical($columns); |
||||
|
||||
@if not($column-sum) { |
||||
@each $column in $columns { |
||||
$column-sum: ($column-sum or 0) + $column; |
||||
} |
||||
} |
||||
|
||||
@return $column-sum + $gutter-sum; |
||||
} |
||||
|
||||
|
||||
// Susy Slice |
||||
// ---------- |
||||
// Return a subset of columns at a given location. |
||||
// - $span : <number> |
||||
// - $location : <number> |
||||
// - [$columns] : <number> | <list> |
||||
@function susy-slice( |
||||
$span, |
||||
$location, |
||||
$columns: susy-get(columns) |
||||
) { |
||||
$columns: valid-columns($columns); |
||||
$sub-columns: $span; |
||||
|
||||
@if not(is-symmetrical($columns)) { |
||||
$location: $location or 1; |
||||
$sub-columns: (); |
||||
@for $i from $location to ($location + $span) { |
||||
$sub-columns: append($sub-columns, nth($columns, $i)); |
||||
} |
||||
} |
||||
|
||||
@return $sub-columns; |
||||
} |
||||
|
||||
|
||||
// Susy |
||||
// ---- |
||||
// Find the sum of a column-span. |
||||
// - $span : <number> |
||||
// - $location : <number> |
||||
// - [$columns] : <number> | <list> |
||||
// - [$gutters] : <ratio> |
||||
// - [$spread] : false/narrow | wide | wider |
||||
@function susy( |
||||
$span, |
||||
$location : false, |
||||
$columns : susy-get(columns), |
||||
$gutters : susy-get(gutters), |
||||
$spread : false |
||||
) { |
||||
$columns: valid-columns($columns); |
||||
$gutters: valid-gutters($gutters); |
||||
$span: susy-slice($span, $location, $columns); |
||||
|
||||
@return susy-sum($span, $gutters, $spread); |
||||
} |
@ -0,0 +1,73 @@
|
||||
// Settings |
||||
// ======== |
||||
|
||||
// Version |
||||
// ------- |
||||
$su-version: 1.1; |
||||
|
||||
|
||||
// Default Settings |
||||
// ---------------- |
||||
// PRIVATE: The basic settings |
||||
$susy-defaults: ( |
||||
columns: 4, |
||||
gutters: .25, |
||||
); |
||||
|
||||
|
||||
// User Settings |
||||
// ------------- |
||||
// - Define the $susy variable with a map of your own settings. |
||||
// - Set EITHER $column-width OR $container |
||||
// - Use $column-width for static layouts |
||||
$susy: () !default; |
||||
|
||||
|
||||
// Susy Defaults |
||||
// ------------- |
||||
// PRIVATE: Add defaults to Susy |
||||
@mixin susy-defaults( |
||||
$defaults |
||||
) { |
||||
$susy-defaults: map-merge($susy-defaults, $defaults) !global; |
||||
} |
||||
|
||||
|
||||
// Susy Set |
||||
// -------- |
||||
// Change one setting |
||||
// - $key : setting name |
||||
// - $value : setting value |
||||
@mixin susy-set( |
||||
$key-value... |
||||
) { |
||||
$susy: _susy-deep-set($susy, $key-value...) !global; |
||||
} |
||||
|
||||
|
||||
// Susy Get |
||||
// -------- |
||||
// Return one setting from a grid |
||||
// - $key : <keyword> |
||||
// - $layout : <settings> |
||||
@function susy-get( |
||||
$key, |
||||
$layout: map-merge($susy-defaults, $susy) |
||||
) { |
||||
$layout: parse-grid($layout); |
||||
$_options: $layout $susy $susy-defaults; |
||||
$_break: false; |
||||
$_return: null; |
||||
|
||||
@each $opt in $_options { |
||||
@if type-of($opt) == map and not($_break) { |
||||
$_keyset: _susy-deep-has-key($opt, $key...); |
||||
@if $_keyset { |
||||
$_return: _susy-deep-get($opt, $key...); |
||||
$_break: true; |
||||
} |
||||
} |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
@ -0,0 +1,111 @@
|
||||
// Map Functions |
||||
// ============= |
||||
|
||||
|
||||
// Truncate List |
||||
// ------------- |
||||
// - Return a list, truncated to a given length |
||||
@function _susy-truncate-list( |
||||
$list, |
||||
$length |
||||
) { |
||||
$_return: (); |
||||
|
||||
@for $i from 1 through length($list) { |
||||
$_return: if($i <= $length, append($_return, nth($list, $i)), $_return); |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Deep Get |
||||
// -------- |
||||
// - Return a value deep in nested maps |
||||
@function _susy-deep-get( |
||||
$map, |
||||
$keys... |
||||
) { |
||||
$_return: $map; |
||||
|
||||
@each $key in $keys { |
||||
@if type-of($_return) == map { |
||||
$_return: map-get($_return, $key); |
||||
} |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Deep Set |
||||
// -------- |
||||
// - Set a value deep in nested maps |
||||
@function _susy-deep-set( |
||||
$map, |
||||
$keys-value... |
||||
) { |
||||
$_value: nth($keys-value, -1); |
||||
$_keys: _susy-truncate-list($keys-value, length($keys-value) - 1); |
||||
$_length: length($_keys); |
||||
$_return: (); |
||||
|
||||
@for $i from 1 through $_length { |
||||
$_n: 0 - $i; |
||||
$_level: _susy-truncate-list($_keys, $_length + $_n); |
||||
$_level: _susy-deep-get($map, $_level...); |
||||
$_merge: nth($_keys, $_n); |
||||
$_merge: ($_merge: $_value); |
||||
$_return: if($_level, map-merge($_level, $_merge), $_merge); |
||||
$_value: $_return; |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
||||
|
||||
|
||||
// Deep Merge |
||||
// ---------- |
||||
// Return 2 objects of any depth, merged |
||||
@function _susy-deep-merge( |
||||
$map1, |
||||
$map2 |
||||
) { |
||||
|
||||
@if type-of($map1) != map or type-of($map2) != map { |
||||
$map1: $map2; |
||||
} @else { |
||||
@each $key, $value in $map2 { |
||||
$_new: ($key: _susy_deep-merge(map-get($map1, $key), $value)); |
||||
$map1: map-merge($map1, $_new); |
||||
} |
||||
} |
||||
|
||||
@return $map1; |
||||
} |
||||
|
||||
|
||||
// Deep Has-Key |
||||
// ------------ |
||||
// - Return true if a deep key exists |
||||
@function _susy-deep-has-key( |
||||
$map, |
||||
$keys... |
||||
) { |
||||
$_return: null; |
||||
$_stop: false; |
||||
|
||||
@each $key in $keys { |
||||
@if not($_stop) { |
||||
$_return: map-has-key($map, $key); |
||||
} |
||||
|
||||
@if $_return { |
||||
$map: map-get($map, $key); |
||||
} @else { |
||||
$_stop: true; |
||||
} |
||||
} |
||||
|
||||
@return $_return; |
||||
} |
@ -0,0 +1,57 @@
|
||||
// Math Validation |
||||
// =============== |
||||
|
||||
|
||||
// Valid Columns |
||||
// ------------- |
||||
// Check that a column setting is valid. |
||||
@function valid-columns( |
||||
$columns, |
||||
$silent: false |
||||
) { |
||||
$type: type-of($columns); |
||||
$return: null; |
||||
|
||||
@if $type == number and unitless($columns) { |
||||
$return: $columns; |
||||
} @else if $type == list { |
||||
$fail: null; |
||||
@each $col in $columns { |
||||
@if type-of($col) == number { |
||||
$fail: $fail or if(unitless($col), null, true); |
||||
} @else { |
||||
$fail: true; |
||||
} |
||||
} |
||||
$return: if($fail, $return, $columns); |
||||
} |
||||
|
||||
@if $return != $columns and not($silent) { |
||||
$return: null; |
||||
$warn: '$columns must be a unitless number or list of unitless numbers.'; |
||||
@warn $warn + ' Current value [#{$type}]: #{$columns}'; |
||||
} |
||||
|
||||
@return $return; |
||||
} |
||||
|
||||
|
||||
// Valid Gutters |
||||
// ------------- |
||||
// Check that a gutter setting is valid. |
||||
@function valid-gutters( |
||||
$gutters, |
||||
$silent: false |
||||
) { |
||||
$type: type-of($gutters); |
||||
$return: null; |
||||
|
||||
@if $type == number and unitless($gutters) { |
||||
$return: $gutters; |
||||
} @else if not($silent) { |
||||
$warn: '$gutters must be a unitless number.'; |
||||
@warn $warn + ' Current value [#{$type}]: #{$gutters}'; |
||||
} |
||||
|
||||
@return $return; |
||||
} |
Loading…
Reference in new issue