commit
message
DS, DS-smooth, and combined maps all working.
author
Ben Vogt <[email protected]>
date
2016-05-14 01:24:12
stats
3 file(s) changed,
939 insertions(+),
0 deletions(-)
files
index.html
main.js
style.css
1diff --git a/index.html b/index.html
2index e69de29..847ef4b 100644
3--- a/index.html
4+++ b/index.html
5@@ -0,0 +1,59 @@
6+<html lang="en">
7+ <head>
8+ <title>Terrain Maps</title>
9+ <link rel="stylesheet" type="text/css" href="style.css">
10+ <script type="text/javascript" src="https://code.jquery.com/jquery-2.2.3.min.js"></script>
11+ <script type="text/javascript" src="main.js"></script>
12+ </head>
13+ <body>
14+ <div class="container">
15+ <div class="row">
16+ <h1>Terrain Maps</h1>
17+ <h4>Generating terrain maps using Diamon-Square, smoothing, and erosion algorithms.</h4>
18+ <p>I've been messing around with different terrain smoothing algorithms to run on Diamond-Square-generated maps. I'm putting them here to so I remember them and write them out a little more clearly.</p>
19+ </div>
20+ </div>
21+ <div class="container">
22+ <hr>
23+ <div class="row">
24+ <h2>
25+ Standard Diamond-Square algorithm
26+ </h2>
27+ <p>
28+ Diamon-Square with smoothing of 10, and 20.
29+ <button class="run button-primary" id="standard">RUN</button>
30+ </p>
31+ </div>
32+ <div class="set-of" id="container-1"></div>
33+ <hr>
34+ <div class="row">
35+ <h2>
36+ Combining Diamond-Square maps
37+ </h2>
38+ <p>
39+ Combining a DS, DS smoothed (10), and DS smoothed (20) maps. This is done by generating <code>standard</code>, then <code>standard-two</code>, a completely different map. Then using each of these to generate a smoothed version of themselves. Then
40+ we can combine standard with <code>standard-10</code>, using <code>standard-two-20</code> as the map controlling which parts of the map are used for the result. For example the higher the value of a given point on <code>standard-two-20</code>, the
41+ stronger the value taken from <code>standard</code> and assigned to the resulting map. The lower the value of a given point on <code>standard-two-20</code>, the stronger the value taken from <code>standard-10</code> and assigned to the resulting
42+ map.
43+ </p>
44+ <p>
45+ This allows us to generate a map that has terrain that is smooth in some parts, and rugged in other parts.
46+ <br>The final <code>reverse</code> map, is with the <code>standard</code> and <code>standard-10</code> maps swapped, so the smooth and rugged values are reversed.
47+ <button class="run button-primary" id="combined">RUN</button>
48+ </p>
49+ </div>
50+ <div class="set-of" id="container-2"></div>
51+ </div>
52+ <div class="hidden">
53+ <canvas id="tmp" width="256" height="256"></canvas>
54+ </div>
55+ <div class="container">
56+ <hr>
57+ <div class="row">
58+ <p>
59+ That's all!
60+ </p>
61+ </div>.
62+ </div>
63+ </body>
64+</html>
65diff --git a/main.js b/main.js
66index e69de29..32e5550 100644
67--- a/main.js
68+++ b/main.js
69@@ -0,0 +1,232 @@
70+$(document).ready(function(){
71+ function LandMap(options) {
72+ var level = 8;
73+ this.containerId = options.containerId;
74+ this.title = options.title;
75+ this.size = Math.pow(2, level) + 1;
76+ this.max = this.size - 1;
77+ this.maps = {};
78+ }
79+
80+ LandMap.prototype.get = function(which, x, y) {
81+ if (x < 0 || x > this.max || y < 0 || y > this.max) {
82+ return -1;
83+ } else {
84+ return this.maps[which][x + this.size * y];
85+ }
86+ };
87+
88+ LandMap.prototype.set = function(which, x, y, value) {
89+ this.maps[which][(x + this.size * y)] = value;
90+ };
91+
92+ LandMap.prototype.generate = function(deviationAmount, feature) {
93+ var self = this;
94+
95+ if (!(feature in self.maps)) {
96+ this.maps[feature] = new Array(this.size * this.size);
97+ }
98+
99+ this.set(feature, 0, 0, Math.random() * self.max);
100+ this.set(feature, this.max, 0, Math.random() * self.max);
101+ this.set(feature, this.max, this.max, Math.random() * self.max);
102+ this.set(feature, 0, this.max, Math.random() * self.max);
103+
104+ subdivide(this.max);
105+
106+ function subdivide(size) {
107+ var x, y, half = size / 2;
108+ var scale = deviationAmount * size;
109+ if (half < 1) return;
110+
111+ for (y = half; y < self.max; y += size) {
112+ for (x = half; x < self.max; x += size) {
113+ square(feature, x, y, half, Math.random() * scale * 2 - scale);
114+ }
115+ }
116+ for (y = 0; y <= self.max; y += half) {
117+ for (x = (y + half) % size; x <= self.max; x += size) {
118+ diamond(feature, x, y, half, Math.random() * scale * 2 - scale);
119+ }
120+ }
121+ subdivide(size / 2);
122+ }
123+
124+ function average(values) {
125+ var valid = values.filter(function(val) {
126+ return val !== -1;
127+ });
128+ var total = valid.reduce(function(sum, val) {
129+ return sum + val;
130+ }, 0);
131+ return total / valid.length;
132+ }
133+
134+ function square(which, x, y, size, offset) {
135+ var ave = average([
136+ self.get(which, x - size, y - size), // upper left
137+ self.get(which, x + size, y - size), // upper right
138+ self.get(which, x + size, y + size), // lower right
139+ self.get(which, x - size, y + size) // lower left
140+ ]);
141+ self.set(which, x, y, ave + offset);
142+ }
143+
144+ function diamond(which, x, y, size, offset) {
145+ var ave = average([
146+ self.get(which, x, y - size), // top
147+ self.get(which, x + size, y), // right
148+ self.get(which, x, y + size), // bottom
149+ self.get(which, x - size, y) // left
150+ ]);
151+ self.set(which, x, y, ave + offset);
152+ }
153+ };
154+
155+ LandMap.prototype.smooth = function(amount, featureFrom, featureTo) {
156+ if (!(featureTo in this.maps)) {
157+ this.maps[featureTo] = new Array(this.size * this.size);
158+ }
159+
160+ var self = this;
161+ var MARGIN = amount;
162+ for (var y = 0; y < this.size; y++) {
163+ for (var x = 0; x < this.size; x++) {
164+ var nextValue = self.get(featureFrom, x, y);
165+ var nextValueCount = 0;
166+ for (var xRange = Math.max(x - Math.round(MARGIN), 0); xRange < Math.min(x + Math.round(MARGIN), this.size); xRange++) {
167+ for (var yRange = Math.max(y - Math.round(MARGIN), 0); yRange < Math.min(y + Math.round(MARGIN), this.size); yRange++) {
168+ if (distanceBetween(x, y, xRange, yRange) <= MARGIN) {
169+ var value = self.get(featureFrom, xRange, yRange);
170+ nextValue = nextValue + value;
171+ nextValueCount++;
172+ }
173+ }
174+ }
175+ var finalVal = ((nextValue / nextValueCount));
176+ self.set(featureTo, x, y, finalVal);
177+ }
178+ }
179+
180+ function distanceBetween(ax, ay, bx, by) {
181+ return Math.abs(Math.sqrt((ax - bx) * (ax - bx) + (ay - by) * (ay - by)));
182+ }
183+ };
184+
185+ LandMap.prototype.combine = function(one, two, three, result) {
186+
187+ function percent(value, max, min) {
188+ return value / Math.abs((max - min));
189+ }
190+
191+ if (!(result in this.maps)) {
192+ this.maps[result] = new Array(this.size * this.size);
193+ }
194+
195+ var max = Number.MIN_SAFE_INTEGER;
196+ var min = Number.MAX_SAFE_INTEGER;
197+ for (var y = 0; y < this.size; y++) {
198+ for (var x = 0; x < this.size; x++) {
199+ var val = this.get(two, x, y);
200+ if (val !== undefined) {
201+ max = Math.max(max, val);
202+ min = Math.min(min, val);
203+ }
204+ }
205+ }
206+
207+ for (var y = 0; y < this.size; y++) {
208+ for (var x = 0; x < this.size; x++) {
209+ var featureOne = this.get(one, x, y);
210+ var featureTwo = this.get(two, x, y);
211+ var featureThree = this.get(three, x, y);
212+ if (featureOne !== undefined && featureTwo !== undefined && featureThree !== undefined) {
213+ var featureThreePercent = percent(featureThree, min, max);
214+ var val = (1 - featureThreePercent) * featureOne + featureThreePercent * featureTwo;
215+ this.set(result, x, y, val);
216+ }
217+ }
218+ }
219+ };
220+
221+ LandMap.prototype.draw = function() {
222+ var html = '<div class="row">';
223+ var featureCount = 0;
224+ for (feature in this.maps) {
225+ html += '<div class="four columns"><strong>' + feature + '</strong><div class="box"><span id="' + this.containerId + feature + '"></span><span id="' + feature + '-description"></span></div></div>';
226+ featureCount++;
227+ if (featureCount == 3) {
228+ html += '</div><div class="row">'
229+ featureCount = 0;
230+ }
231+ }
232+ document.getElementById(this.containerId).innerHTML = html;
233+ for (feature in this.maps) {
234+ var display = document.getElementById("tmp");
235+ var ctx = display.getContext('2d');
236+ var width = display.width = 256;
237+ var height = display.height = 256;
238+ var self = this;
239+
240+ var cellWidth = 1;
241+
242+ function drawCell(x, y, inensity) {
243+ ctx.fillStyle = inensity;
244+ ctx.fillRect(x * cellWidth, y * cellWidth, cellWidth, cellWidth);
245+ }
246+
247+ // finding max, min
248+ var max = Number.MIN_SAFE_INTEGER;
249+ var min = Number.MAX_SAFE_INTEGER;
250+ for (var y = 0; y < this.size; y++) {
251+ for (var x = 0; x < this.size; x++) {
252+ var val = this.get(feature, x, y);
253+ if (val !== undefined) {
254+ max = Math.max(max, val);
255+ min = Math.min(min, val);
256+ }
257+ }
258+ }
259+ // Drawing each cell
260+ for (var y = 0; y < this.size; y++) {
261+ for (var x = 0; x < this.size; x++) {
262+ var val = this.get(feature, x, y);
263+ if (val !== undefined) {
264+ drawCell(x, y, brightness(val, max, min));
265+ }
266+ }
267+ }
268+
269+ document.getElementById(this.containerId + feature).innerHTML = '<img src="' + display.toDataURL("image/png") + '" class="u-max-full-width map"/>';
270+ }
271+
272+ function brightness(value, max, min) {
273+ var delta = Math.abs((max - min));
274+ var b = Math.floor((value / delta) * 255);
275+ return 'rgba(' + b + ',' + b + ',' + b + ',1)';
276+ }
277+ };
278+
279+ $("#standard").click(function() {
280+ var standardMap = new LandMap({
281+ containerId: "container-1"
282+ });
283+ standardMap.generate(0.75, "standard");
284+ standardMap.smooth(10, "standard", "smoothed-10");
285+ standardMap.smooth(20, "standard", "smoothed-20");
286+ standardMap.draw();
287+ });
288+
289+ $("#combined").click(function() {
290+ var terrain = new LandMap({
291+ containerId: "container-2"
292+ });
293+ terrain.generate(0.75, "standard");
294+ terrain.generate(0.75, "standard-two", "DS with 0.75");
295+ terrain.smooth(10, "standard", "standard-10");
296+ terrain.smooth(20, "standard-two", "standard-two-20");
297+ terrain.combine("standard", "standard-10", "standard-two-20", "combined");
298+ terrain.combine("standard-10", "standard", "standard-two-20", "reversed");
299+ terrain.draw();
300+ });
301+})
302diff --git a/style.css b/style.css
303index e69de29..8d6f247 100644
304--- a/style.css
305+++ b/style.css
306@@ -0,0 +1,648 @@
307+body {
308+ background: #FFFFFF;
309+}
310+
311+img.map {
312+ border: 1px solid #E0E0E0;
313+}
314+
315+div.set-of {
316+ min-height: 256px;
317+}
318+
319+div.set-of:empty {
320+ background: #F5F5F5;
321+}
322+
323+.run {
324+ float: right;
325+}
326+
327+.hidden {
328+ display: none;
329+}
330+
331+
332+/*
333+* Skeleton V2.0.4
334+* Copyright 2014, Dave Gamache
335+* www.getskeleton.com
336+* Free to use under the MIT license.
337+* http://www.opensource.org/licenses/mit-license.php
338+* 12/29/2014
339+*/
340+
341+
342+/* Table of contents
343+––––––––––––––––––––––––––––––––––––––––––––––––––
344+- Grid
345+- Base Styles
346+- Typography
347+- Links
348+- Buttons
349+- Forms
350+- Lists
351+- Code
352+- Tables
353+- Spacing
354+- Utilities
355+- Clearing
356+- Media Queries
357+*/
358+
359+
360+/* Grid
361+–––––––––––––––––––––––––––––––––––––––––––––––––– */
362+
363+.container {
364+ position: relative;
365+ width: 100%;
366+ max-width: 960px;
367+ margin: 0 auto;
368+ padding: 0 20px;
369+ box-sizing: border-box;
370+}
371+
372+.column,
373+.columns {
374+ width: 100%;
375+ float: left;
376+ box-sizing: border-box;
377+}
378+
379+
380+/* For devices larger than 400px */
381+
382+@media (min-width: 400px) {
383+ .container {
384+ width: 85%;
385+ padding: 0;
386+ }
387+}
388+
389+
390+/* For devices larger than 550px */
391+
392+@media (min-width: 550px) {
393+ .container {
394+ width: 80%;
395+ }
396+ .column,
397+ .columns {
398+ margin-left: 4%;
399+ }
400+ .column:first-child,
401+ .columns:first-child {
402+ margin-left: 0;
403+ }
404+ .one.column,
405+ .one.columns {
406+ width: 4.66666666667%;
407+ }
408+ .two.columns {
409+ width: 13.3333333333%;
410+ }
411+ .three.columns {
412+ width: 22%;
413+ }
414+ .four.columns {
415+ width: 30.6666666667%;
416+ }
417+ .five.columns {
418+ width: 39.3333333333%;
419+ }
420+ .six.columns {
421+ width: 48%;
422+ }
423+ .seven.columns {
424+ width: 56.6666666667%;
425+ }
426+ .eight.columns {
427+ width: 65.3333333333%;
428+ }
429+ .nine.columns {
430+ width: 74.0%;
431+ }
432+ .ten.columns {
433+ width: 82.6666666667%;
434+ }
435+ .eleven.columns {
436+ width: 91.3333333333%;
437+ }
438+ .twelve.columns {
439+ width: 100%;
440+ margin-left: 0;
441+ }
442+ .one-third.column {
443+ width: 30.6666666667%;
444+ }
445+ .two-thirds.column {
446+ width: 65.3333333333%;
447+ }
448+ .one-half.column {
449+ width: 48%;
450+ }
451+ /* Offsets */
452+ .offset-by-one.column,
453+ .offset-by-one.columns {
454+ margin-left: 8.66666666667%;
455+ }
456+ .offset-by-two.column,
457+ .offset-by-two.columns {
458+ margin-left: 17.3333333333%;
459+ }
460+ .offset-by-three.column,
461+ .offset-by-three.columns {
462+ margin-left: 26%;
463+ }
464+ .offset-by-four.column,
465+ .offset-by-four.columns {
466+ margin-left: 34.6666666667%;
467+ }
468+ .offset-by-five.column,
469+ .offset-by-five.columns {
470+ margin-left: 43.3333333333%;
471+ }
472+ .offset-by-six.column,
473+ .offset-by-six.columns {
474+ margin-left: 52%;
475+ }
476+ .offset-by-seven.column,
477+ .offset-by-seven.columns {
478+ margin-left: 60.6666666667%;
479+ }
480+ .offset-by-eight.column,
481+ .offset-by-eight.columns {
482+ margin-left: 69.3333333333%;
483+ }
484+ .offset-by-nine.column,
485+ .offset-by-nine.columns {
486+ margin-left: 78.0%;
487+ }
488+ .offset-by-ten.column,
489+ .offset-by-ten.columns {
490+ margin-left: 86.6666666667%;
491+ }
492+ .offset-by-eleven.column,
493+ .offset-by-eleven.columns {
494+ margin-left: 95.3333333333%;
495+ }
496+ .offset-by-one-third.column,
497+ .offset-by-one-third.columns {
498+ margin-left: 34.6666666667%;
499+ }
500+ .offset-by-two-thirds.column,
501+ .offset-by-two-thirds.columns {
502+ margin-left: 69.3333333333%;
503+ }
504+ .offset-by-one-half.column,
505+ .offset-by-one-half.columns {
506+ margin-left: 52%;
507+ }
508+}
509+
510+
511+/* Base Styles
512+–––––––––––––––––––––––––––––––––––––––––––––––––– */
513+
514+
515+/* NOTE
516+html is set to 62.5% so that all the REM measurements throughout Skeleton
517+are based on 10px sizing. So basically 1.5rem = 15px :) */
518+
519+html {
520+ font-size: 62.5%;
521+}
522+
523+body {
524+ font-size: 1.5em;
525+ /* currently ems cause chrome bug misinterpreting rems on body element */
526+ line-height: 1.6;
527+ font-weight: 400;
528+ font-family: Helvetica, Arial, sans-serif;
529+ color: #222;
530+}
531+
532+
533+/* Typography
534+–––––––––––––––––––––––––––––––––––––––––––––––––– */
535+
536+h1,
537+h2,
538+h3,
539+h4,
540+h5,
541+h6 {
542+ margin-top: 0;
543+ margin-bottom: 2rem;
544+ font-weight: 300;
545+}
546+
547+h1 {
548+ font-size: 4.0rem;
549+ line-height: 1.2;
550+ letter-spacing: -.1rem;
551+}
552+
553+h2 {
554+ font-size: 3.6rem;
555+ line-height: 1.25;
556+ letter-spacing: -.1rem;
557+}
558+
559+h3 {
560+ font-size: 3.0rem;
561+ line-height: 1.3;
562+ letter-spacing: -.1rem;
563+}
564+
565+h4 {
566+ font-size: 2.4rem;
567+ line-height: 1.35;
568+ letter-spacing: -.08rem;
569+}
570+
571+h5 {
572+ font-size: 1.8rem;
573+ line-height: 1.5;
574+ letter-spacing: -.05rem;
575+}
576+
577+h6 {
578+ font-size: 1.5rem;
579+ line-height: 1.6;
580+ letter-spacing: 0;
581+}
582+
583+
584+/* Larger than phablet */
585+
586+@media (min-width: 550px) {
587+ h1 {
588+ font-size: 5.0rem;
589+ }
590+ h2 {
591+ font-size: 4.2rem;
592+ }
593+ h3 {
594+ font-size: 3.6rem;
595+ }
596+ h4 {
597+ font-size: 3.0rem;
598+ }
599+ h5 {
600+ font-size: 2.4rem;
601+ }
602+ h6 {
603+ font-size: 1.5rem;
604+ }
605+}
606+
607+p {
608+ margin-top: 0;
609+}
610+
611+
612+/* Links
613+–––––––––––––––––––––––––––––––––––––––––––––––––– */
614+
615+a {
616+ color: #1EAEDB;
617+}
618+
619+a:hover {
620+ color: #0FA0CE;
621+}
622+
623+
624+/* Buttons
625+–––––––––––––––––––––––––––––––––––––––––––––––––– */
626+
627+.button,
628+button,
629+input[type="submit"],
630+input[type="reset"],
631+input[type="button"] {
632+ display: inline-block;
633+ height: 38px;
634+ padding: 0 30px;
635+ color: #555;
636+ text-align: center;
637+ font-size: 11px;
638+ font-weight: 600;
639+ line-height: 38px;
640+ letter-spacing: .1rem;
641+ text-transform: uppercase;
642+ text-decoration: none;
643+ white-space: nowrap;
644+ background-color: transparent;
645+ border-radius: 4px;
646+ border: 1px solid #bbb;
647+ cursor: pointer;
648+ box-sizing: border-box;
649+}
650+
651+.button:hover,
652+button:hover,
653+input[type="submit"]:hover,
654+input[type="reset"]:hover,
655+input[type="button"]:hover,
656+.button:focus,
657+button:focus,
658+input[type="submit"]:focus,
659+input[type="reset"]:focus,
660+input[type="button"]:focus {
661+ color: #333;
662+ border-color: #888;
663+ outline: 0;
664+}
665+
666+.button.button-primary,
667+button.button-primary,
668+input[type="submit"].button-primary,
669+input[type="reset"].button-primary,
670+input[type="button"].button-primary {
671+ color: #FFF;
672+ background-color: #2196F3;
673+ border-color: #2196F3;
674+}
675+
676+.button.button-primary:hover,
677+button.button-primary:hover,
678+input[type="submit"].button-primary:hover,
679+input[type="reset"].button-primary:hover,
680+input[type="button"].button-primary:hover,
681+.button.button-primary:focus,
682+button.button-primary:focus,
683+input[type="submit"].button-primary:focus,
684+input[type="reset"].button-primary:focus,
685+input[type="button"].button-primary:focus {
686+ color: #FFF;
687+ background-color: #1E88E5;
688+ border-color: #1E88E5;
689+}
690+
691+
692+/* Forms
693+–––––––––––––––––––––––––––––––––––––––––––––––––– */
694+
695+input[type="email"],
696+input[type="number"],
697+input[type="search"],
698+input[type="text"],
699+input[type="tel"],
700+input[type="url"],
701+input[type="password"],
702+textarea,
703+select {
704+ height: 38px;
705+ padding: 6px 10px;
706+ /* The 6px vertically centers text on FF, ignored by Webkit */
707+ background-color: #fff;
708+ border: 1px solid #D1D1D1;
709+ border-radius: 4px;
710+ box-shadow: none;
711+ box-sizing: border-box;
712+}
713+
714+
715+/* Removes awkward default styles on some inputs for iOS */
716+
717+input[type="email"],
718+input[type="number"],
719+input[type="search"],
720+input[type="text"],
721+input[type="tel"],
722+input[type="url"],
723+input[type="password"],
724+textarea {
725+ -webkit-appearance: none;
726+ -moz-appearance: none;
727+ appearance: none;
728+}
729+
730+textarea {
731+ min-height: 65px;
732+ padding-top: 6px;
733+ padding-bottom: 6px;
734+}
735+
736+input[type="email"]:focus,
737+input[type="number"]:focus,
738+input[type="search"]:focus,
739+input[type="text"]:focus,
740+input[type="tel"]:focus,
741+input[type="url"]:focus,
742+input[type="password"]:focus,
743+textarea:focus,
744+select:focus {
745+ border: 1px solid #33C3F0;
746+ outline: 0;
747+}
748+
749+label,
750+legend {
751+ display: block;
752+ margin-bottom: .5rem;
753+ font-weight: 600;
754+}
755+
756+fieldset {
757+ padding: 0;
758+ border-width: 0;
759+}
760+
761+input[type="checkbox"],
762+input[type="radio"] {
763+ display: inline;
764+}
765+
766+label > .label-body {
767+ display: inline-block;
768+ margin-left: .5rem;
769+ font-weight: normal;
770+}
771+
772+
773+/* Lists
774+–––––––––––––––––––––––––––––––––––––––––––––––––– */
775+
776+ul {
777+ list-style: circle inside;
778+}
779+
780+ol {
781+ list-style: decimal inside;
782+}
783+
784+ol,
785+ul {
786+ padding-left: 0;
787+ margin-top: 0;
788+}
789+
790+ul ul,
791+ul ol,
792+ol ol,
793+ol ul {
794+ margin: 1.5rem 0 1.5rem 3rem;
795+ font-size: 90%;
796+}
797+
798+li {
799+ margin-bottom: 1rem;
800+}
801+
802+
803+/* Code
804+–––––––––––––––––––––––––––––––––––––––––––––––––– */
805+
806+code {
807+ padding: .2rem .5rem;
808+ margin: 0 .2rem;
809+ font-size: 90%;
810+ white-space: nowrap;
811+ background: #F1F1F1;
812+ border: 1px solid #E1E1E1;
813+ border-radius: 4px;
814+}
815+
816+pre > code {
817+ display: block;
818+ padding: 1rem 1.5rem;
819+ white-space: pre;
820+}
821+
822+
823+/* Tables
824+–––––––––––––––––––––––––––––––––––––––––––––––––– */
825+
826+th,
827+td {
828+ padding: 12px 15px;
829+ text-align: left;
830+ border-bottom: 1px solid #E1E1E1;
831+}
832+
833+th:first-child,
834+td:first-child {
835+ padding-left: 0;
836+}
837+
838+th:last-child,
839+td:last-child {
840+ padding-right: 0;
841+}
842+
843+
844+/* Spacing
845+–––––––––––––––––––––––––––––––––––––––––––––––––– */
846+
847+button,
848+.button {
849+ margin-bottom: 1rem;
850+}
851+
852+input,
853+textarea,
854+select,
855+fieldset {
856+ margin-bottom: 1.5rem;
857+}
858+
859+pre,
860+blockquote,
861+dl,
862+figure,
863+table,
864+p,
865+ul,
866+ol,
867+form {
868+ margin-bottom: 2.5rem;
869+}
870+
871+
872+/* Utilities
873+–––––––––––––––––––––––––––––––––––––––––––––––––– */
874+
875+.u-full-width {
876+ width: 100%;
877+ box-sizing: border-box;
878+}
879+
880+.u-max-full-width {
881+ max-width: 100%;
882+ box-sizing: border-box;
883+}
884+
885+.u-pull-right {
886+ float: right;
887+}
888+
889+.u-pull-left {
890+ float: left;
891+}
892+
893+
894+/* Misc
895+–––––––––––––––––––––––––––––––––––––––––––––––––– */
896+
897+hr {
898+ margin-top: 3rem;
899+ margin-bottom: 3.5rem;
900+ border-width: 0;
901+ border-top: 1px solid #E1E1E1;
902+}
903+
904+
905+/* Clearing
906+–––––––––––––––––––––––––––––––––––––––––––––––––– */
907+
908+
909+/* Self Clearing Goodness */
910+
911+.container:after,
912+.row:after,
913+.u-cf {
914+ content: "";
915+ display: table;
916+ clear: both;
917+}
918+
919+
920+/* Media Queries
921+–––––––––––––––––––––––––––––––––––––––––––––––––– */
922+
923+
924+/*
925+Note: The best way to structure the use of media queries is to create the queries
926+near the relevant code. For example, if you wanted to change the styles for buttons
927+on small devices, paste the mobile query code up in the buttons section and style it
928+there.
929+*/
930+
931+
932+/* Larger than mobile */
933+
934+@media (min-width: 400px) {}
935+
936+
937+/* Larger than phablet (also point when grid becomes active) */
938+
939+@media (min-width: 550px) {}
940+
941+
942+/* Larger than tablet */
943+
944+@media (min-width: 750px) {}
945+
946+
947+/* Larger than desktop */
948+
949+@media (min-width: 1000px) {}
950+
951+
952+/* Larger than Desktop HD */
953+
954+@media (min-width: 1200px) {}