├── .editorconfig
├── .eslintrc
├── .gitattributes
├── .github
└── browsersync.png
├── .gitignore
├── .nvmrc
├── LICENSE
├── README.md
├── docs
└── single-file-components.md
├── package.json
├── src
├── assets
│ └── images
│ │ ├── favicon.ico
│ │ └── logo.png
├── components
│ ├── Home
│ │ ├── home.html
│ │ └── home.js
│ ├── Loader
│ │ ├── Loader.js
│ │ ├── loader.js
│ │ └── loader.scss
│ ├── Navigation
│ │ ├── navigation.html
│ │ └── navigation.js
│ ├── NotFound
│ │ └── notFound.js
│ └── Posts
│ │ ├── createPost.js
│ │ ├── editPost.html
│ │ ├── editPost.js
│ │ ├── post.html
│ │ ├── post.js
│ │ ├── posts.html
│ │ └── posts.js
├── config
│ ├── constants.js
│ ├── http.js
│ └── loading-state.js
├── index.html
├── main.js
├── routes.js
├── style.scss
├── styles
│ ├── _animate.scss
│ ├── _global.scss
│ └── _variables.scss
└── util
│ ├── helpers.js
│ └── resources.js
├── webpack
├── development.js
├── plugins.js
├── production.js
└── webpack.base.js
└── yarn.lock
/.editorconfig:
--------------------------------------------------------------------------------
1 | root = true
2 |
3 | [*]
4 | charset = utf-8
5 | indent_style = space
6 | indent_size = 2
7 | end_of_line = lf
8 | insert_final_newline = true
9 | trim_trailing_whitespace = true
10 |
--------------------------------------------------------------------------------
/.eslintrc:
--------------------------------------------------------------------------------
1 | {
2 | "root": true,
3 | "extends": "eslint:recommended",
4 | "globals": {
5 | "window": true,
6 | "document": true,
7 | "fetch": true,
8 | "Headers": true,
9 | "Request": true,
10 | "FormData": true,
11 | "FileReader": true,
12 | "localStorage": true
13 | },
14 | "env": {
15 | "node": true,
16 | "es6": true,
17 | "amd": true,
18 | "browser": true,
19 | "jquery": true
20 | },
21 | "parserOptions": {
22 | "ecmaFeatures": {
23 | "globalReturn": true,
24 | "generators": false,
25 | "objectLiteralDuplicateProperties": false,
26 | "experimentalObjectRestSpread": true
27 | },
28 | "ecmaVersion": 2017,
29 | "sourceType": "module"
30 | },
31 | "plugins": [
32 | "import",
33 | "html",
34 | "jsx-a11y"
35 | ],
36 | "settings": {
37 | "import/core-modules": [],
38 | "import/ignore": [
39 | "node_modules",
40 | "\\.(coffee|scss|css|less|hbs|svg|json)$"
41 | ]
42 | },
43 | "rules": {
44 | "no-console": 0
45 | }
46 | }
47 |
--------------------------------------------------------------------------------
/.gitattributes:
--------------------------------------------------------------------------------
1 | src/styles/* linguist-vendored
2 |
--------------------------------------------------------------------------------
/.github/browsersync.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/villeristi/vue.js-starter-template/6f0088e9eedcb194ba7284c1f02a6e9fbd56d17b/.github/browsersync.png
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | node_modules
2 | build
3 | *.log
4 |
--------------------------------------------------------------------------------
/.nvmrc:
--------------------------------------------------------------------------------
1 | 8.6.0
2 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 Ville Ristimäki
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Vue.js starter template
2 |
3 |
4 |
5 |
6 |
7 | A bare-bones starter-template to get your hands dirty with awesome [Vue.js](https://github.com/vuejs/vue) library.
8 |
9 | Built with:
10 | * [Vue.js 2](https://github.com/vuejs/vue)
11 | * [Vue Router 2](https://github.com/vuejs/vue-router)
12 | * [Axios](https://github.com/mzabriskie/axios)
13 | * [Animate.css](https://github.com/daneden/animate.css)
14 | * [Babel](https://babeljs.io/)
15 | * [Bootstrap 4](https://v4-alpha.getbootstrap.com/)
16 | * [BrowserSync](https://www.browsersync.io/)
17 | * [ESLint](http://eslint.org/)
18 | * [Font Awesome](http://fontawesome.io/)
19 | * [JSONPlaceholder](http://jsonplaceholder.typicode.com/)
20 | * [SASS](http://sass-lang.com/)
21 | * [Webpack 2](https://webpack.js.org/)
22 | * [Yarn](https://yarnpkg.com/en/docs/install)
23 | * ...and many more
24 |
25 | ## Getting started
26 |
27 | 1. Be sure you have [Yarn](https://yarnpkg.com/en/docs/install) installed globally.
28 | 2. Clone the repo & run `yarn` from the project root
29 |
30 | ## Single File Components
31 | See [instructions](docs/single-file-components.md) for example usage of [single file components](https://vuejs.org/v2/guide/single-file-components.html).
32 |
33 | ## Available commands
34 |
35 | ```sh
36 | yarn start
37 | ```
38 |
39 | Runs the Webpack module-bundler, starts watching for changes & launches the BrowserSync server to [http://localhost:3000](http://localhost:3000) (it's possible to change the port from `package.json` config-section). Uses [Webpack Dashboard](https://github.com/FormidableLabs/webpack-dashboard)
40 |
41 | **Note!** Webpack handles all the reloading stuff while BrowserSync just proxies the default webpack-port (`8080`) giving the possibility to connect to dev-server from multiple devices:
42 | 
43 |
44 |
45 | ```sh
46 | yarn lint:js
47 | ```
48 |
49 | Lints javascript-files inside `/src` directory
50 |
51 | ```sh
52 | yarn build
53 | ```
54 |
55 | Runs the webpack module-bundler with production-settings (compress etc.) and builds the project to `/build` directory.
56 |
57 | ## Demo
58 | Navigate to [https://vue-starter.ville.io/](https://vue-starter.ville.io/) and see the awesomeness IRL :bowtie:
59 |
--------------------------------------------------------------------------------
/docs/single-file-components.md:
--------------------------------------------------------------------------------
1 | # Single File Components
2 |
3 | It's also possible to define your components with a [single file components](https://vuejs.org/v2/guide/single-file-components.html) fashion. Below is an example how to turn the `Loader` into a single-file-component and make use of the `vue-loader`:
4 |
5 | 1. Remove all files from `src/components/Loader`
6 | 2. Add a `Loader.vue` -file populated with below content:
7 |
8 | ```vue
9 |
10 |
11 |
12 |
53 |
59 | ```
60 |
61 | 3. Import the file with `.vue`-extension in `main.js`:
62 | ```javascript
63 | import Loader from 'components/Loader/Loader.vue';
64 | ```
65 |
66 | 4. Edit your webpack config `webpack/webpack.base.js` so that `.vue` files are linted. Look for `eslint-loader` part of module rules and change the `test` attribute:
67 | ```javascript
68 | {
69 | enforce: 'pre',
70 | exclude: /node_modules/,
71 | loader: 'eslint-loader',
72 | test: /\.(js?|vue)$/
73 | },
74 |
75 | ```
76 |
77 | 5. Optionally, in the same config `webpack/webpack.base.js`, define `resolve.extensions` for [automatic extension resolution](https://webpack.js.org/configuration/resolve/#resolve-extensions) :
78 | ```javascript
79 | resolve: {
80 | alias: {
81 | ...
82 | },
83 | extensions: ['*','.js','.vue']
84 | },
85 | ```
86 | This will allow you to import `.js` and `.vue` files without having to specify their extension, i.e.
87 | ```javascript
88 | import Loader from 'components/Loader/Loader';
89 | ```
90 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "vue.js-starter-template",
3 | "version": "0.10.0",
4 | "description": "A starter for Vue.js-projects",
5 | "keywords": [
6 | "vue.js",
7 | "vue.js router",
8 | "axios",
9 | "webpack 2",
10 | "animate.css"
11 | ],
12 | "author": "Wille Ristimäki ",
13 | "license": "MIT",
14 | "repository": {
15 | "type": "git",
16 | "url": "git@github.com:villeristi/vue.js-starter-template.git"
17 | },
18 | "config": {
19 | "port": 3000
20 | },
21 | "scripts": {
22 | "start": "webpack-dashboard -c magenta -t 'Vue.js-Starter-Template' -- webpack-dev-server --config webpack/development.js --progress --hot",
23 | "build": "webpack --config webpack/production.js -p --progress",
24 | "lint:js": "eslint src"
25 | },
26 | "dependencies": {
27 | "axios": "^0.16.2",
28 | "bootstrap": "4.0.0-alpha.6",
29 | "css-hot-loader": "^1.3.1",
30 | "font-awesome": "^4.7.0",
31 | "vee-validate": "^2.0.0-rc.5",
32 | "vue": "^2.3.4",
33 | "vue-router": "^2.5.3"
34 | },
35 | "devDependencies": {
36 | "babel-core": "^6.26.0",
37 | "babel-eslint": "^8.0.1",
38 | "babel-loader": "^7.0.0",
39 | "babel-plugin-transform-runtime": "^6.15.0",
40 | "babel-preset-es2015": "^6.24.1",
41 | "babel-preset-stage-2": "^6.24.1",
42 | "browser-sync": "^2.18.12",
43 | "browser-sync-webpack-plugin": "^1.1.3",
44 | "copy-webpack-plugin": "^4.0.1",
45 | "css-loader": "^0.28.7",
46 | "eslint": "^4.7.2",
47 | "eslint-friendly-formatter": "^3.0.0",
48 | "eslint-loader": "^1.7.1",
49 | "eslint-plugin-html": "^3.2.2",
50 | "eslint-plugin-import": "^2.3.0",
51 | "eslint-plugin-jsx-a11y": "^6.0.2",
52 | "exports-loader": "^0.6.3",
53 | "extract-text-webpack-plugin": "^3.0.0",
54 | "favicons-webpack-plugin": "0.0.7",
55 | "file-loader": "^0.11.2",
56 | "html-loader": "^0.5.1",
57 | "html-webpack-plugin": "^2.26.0",
58 | "imagemin-mozjpeg": "^6.0.0",
59 | "imagemin-webpack-plugin": "^1.2.1",
60 | "imports-loader": "^0.7.1",
61 | "minimist": "^1.2.0",
62 | "node-sass": "^4.5.3",
63 | "optimize-css-assets-webpack-plugin": "^1.3.2",
64 | "require-dir": "^0.3.2",
65 | "resolve-url-loader": "^2.1.0",
66 | "sass-loader": "^6.0.6",
67 | "source-map-loader": "^0.2.1",
68 | "style-loader": "^0.18.2",
69 | "url-loader": "^0.5.9",
70 | "vue-loader": "^13.0.5",
71 | "vue-template-compiler": "^2.3.4",
72 | "webpack": "^3.6.0",
73 | "webpack-cleanup-plugin": "^0.5.1",
74 | "webpack-dashboard": "^0.2.1",
75 | "webpack-dev-server": "^2.9.1",
76 | "webpack-merge": "^0.14.0",
77 | "webpack-notifier": "^1.5.0"
78 | },
79 | "babel": {
80 | "presets": [
81 | "es2015"
82 | ]
83 | }
84 | }
85 |
--------------------------------------------------------------------------------
/src/assets/images/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/villeristi/vue.js-starter-template/6f0088e9eedcb194ba7284c1f02a6e9fbd56d17b/src/assets/images/favicon.ico
--------------------------------------------------------------------------------
/src/assets/images/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/villeristi/vue.js-starter-template/6f0088e9eedcb194ba7284c1f02a6e9fbd56d17b/src/assets/images/logo.png
--------------------------------------------------------------------------------
/src/components/Home/home.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
My awesome project
4 |
5 |
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut dictum accumsan lorem in aliquam. Vestibulum ante
6 | ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Vivamus orci orci, cursus vulputate
7 | hendrerit eu, dapibus eu nisi. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos
8 | himenaeos. Nullam placerat dapibus tempor. Suspendisse nec mi at erat tincidunt mattis ut nec lacus. Praesent
9 | non nisl sed libero convallis tincidunt. Curabitur commodo aliquam vestibulum. Etiam rutrum risus quam, eget
10 | faucibus diam ornare in.
11 |
12 |
Morbi sollicitudin enim a rhoncus varius. Sed a lacus eu diam dapibus pellentesque sit amet at sem. Sed
13 | scelerisque pretium metus, sed mollis sem molestie eu. Suspendisse iaculis non erat ac consectetur. Phasellus
14 | placerat, eros ornare dictum efficitur, mauris dui varius risus, ac dignissim erat dolor lobortis augue.
15 | Praesent lectus augue, dignissim et sagittis in, convallis id nisl. Morbi interdum neque nec massa facilisis, ut
16 | rutrum justo semper. Phasellus fringilla auctor blandit. Maecenas nibh mi, cursus sed velit id, sodales semper
17 | sapien. Curabitur vitae nisl porta, tempus neque vitae, finibus nulla. Nam condimentum elit vel enim commodo, a
18 | tincidunt ante ornare. Duis libero sem, ultricies eu neque id, dapibus accumsan lectus.
19 |
20 |
21 |
--------------------------------------------------------------------------------
/src/components/Home/home.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 | import template from './home.html';
3 |
4 | export default Vue.extend({
5 | template,
6 | });
7 |
--------------------------------------------------------------------------------
/src/components/Loader/Loader.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | import './loader.scss';
4 |
5 | export default Vue.extend({
6 | template: '
'
7 | });
8 |
--------------------------------------------------------------------------------
/src/components/Loader/loader.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | import './loader.scss';
4 |
5 | export default Vue.extend({
6 | template: '
'
7 | });
8 |
--------------------------------------------------------------------------------
/src/components/Loader/loader.scss:
--------------------------------------------------------------------------------
1 | $vue-green: #41b883;
2 |
3 | .loader {
4 | font-size: 10px;
5 | position: absolute;
6 | z-index: 9999; // Above everything...
7 | top: 50%;
8 | left: 50%;
9 | margin: -20px 0 0 -20px;
10 | text-indent: -9999em;
11 | border-top: 5px solid lighten($vue-green, 35%);
12 | border-right: 5px solid lighten($vue-green, 35%);
13 | border-bottom: 5px solid lighten($vue-green, 35%);
14 | border-left: 5px solid $vue-green;
15 | -webkit-transform: translateZ(0);
16 | -ms-transform: translateZ(0);
17 | transform: translateZ(0);
18 | -webkit-animation: loaderSpinner 1.1s infinite linear;
19 | animation: loaderSpinner 1.1s infinite linear;
20 |
21 | &,
22 | &:after {
23 | border-radius: 50%;
24 | width: 40px;
25 | height: 40px
26 | }
27 | }
28 |
29 | @-webkit-keyframes loaderSpinner {
30 | 0% {
31 | -webkit-transform: rotate(0deg);
32 | transform: rotate(0deg);
33 | }
34 | 100% {
35 | -webkit-transform: rotate(360deg);
36 | transform: rotate(360deg);
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/src/components/Navigation/navigation.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
16 |
17 |
--------------------------------------------------------------------------------
/src/components/Navigation/navigation.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 | import template from './navigation.html';
3 |
4 | export default Vue.extend({
5 | template,
6 | });
7 |
--------------------------------------------------------------------------------
/src/components/NotFound/notFound.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | export default Vue.extend({
4 | template: `
5 |
6 |
Not found...
7 |
Sorry
8 |
9 | `,
10 | });
11 |
--------------------------------------------------------------------------------
/src/components/Posts/createPost.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 | import VeeValidate from 'vee-validate';
3 |
4 | Vue.use(VeeValidate);
5 |
6 | import { postsResource } from 'src/util/resources';
7 | import template from './editPost.html';
8 |
9 | export default Vue.extend({
10 | template,
11 |
12 | data() {
13 | return {
14 | post: {},
15 | message: null
16 | };
17 | },
18 |
19 | computed: {
20 | isDirty() {
21 | return Object.keys(this.fields).some(key => this.fields[key].dirty);
22 | }
23 | },
24 |
25 | methods: {
26 | handleSubmit(){
27 | this.$validator.validateAll().then((success) => {
28 | if (success) {
29 | return this.savePost();
30 | }
31 |
32 | return this;
33 | });
34 | },
35 |
36 | showMessage(message = {}, timeout = 2000){
37 | this.message = message;
38 | setTimeout(() => {
39 | this.message = null;
40 | }, timeout);
41 | },
42 |
43 | savePost(){
44 | return postsResource.post('/', this.post)
45 | .then((response) => {
46 | this.post = response.data;
47 |
48 | this.showMessage({
49 | type: 'success',
50 | text: 'Post created!'
51 | });
52 |
53 | // TODO: We need to reset the form after success....
54 | // this.fields.reset();
55 | })
56 | .catch((errorResponse) => {
57 | // Handle error...
58 | this.showMessage({
59 | type: 'danger',
60 | text: errorResponse
61 | });
62 | console.log('API responded with:', errorResponse);
63 | });
64 | }
65 | }
66 | });
67 |
--------------------------------------------------------------------------------
/src/components/Posts/editPost.html:
--------------------------------------------------------------------------------
1 |
4 |
5 |
6 | {{ post.title }}
7 |
8 |
9 |
69 |
70 |
71 | Back to posts
72 |
73 |
74 |
75 |
--------------------------------------------------------------------------------
/src/components/Posts/editPost.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 | import VeeValidate from 'vee-validate';
3 |
4 | Vue.use(VeeValidate);
5 |
6 | import { postsResource } from 'src/util/resources';
7 | import template from './editPost.html';
8 |
9 | export default Vue.extend({
10 | template,
11 |
12 | data() {
13 | return {
14 | post: {},
15 | message: null,
16 | id: this.$route.params.id,
17 | };
18 | },
19 |
20 | computed: {
21 | isDirty() {
22 | return Object.keys(this.fields).some(key => this.fields[key].dirty);
23 | }
24 | },
25 |
26 | created(){
27 | this.fetchPost();
28 | },
29 |
30 | methods: {
31 | handleSubmit(){
32 | this.$validator.validateAll().then((success) => {
33 | if (success) {
34 | return this.savePost();
35 | }
36 |
37 | return this;
38 | });
39 | },
40 |
41 | showMessage(message = {}, timeout = 2000){
42 | this.message = message;
43 | setTimeout(() => {
44 | this.message = null;
45 | }, timeout);
46 | },
47 |
48 | savePost(){
49 | return postsResource.put(`${this.id}`, this.post)
50 | .then((response) => {
51 | this.post = response.data;
52 |
53 | this.showMessage({
54 | type: 'success',
55 | text: 'Post updated!'
56 | });
57 |
58 | // TODO: We need to reset the form after success....
59 | // this.fields.reset();
60 | })
61 | .catch((errorResponse) => {
62 | // Handle error...
63 | this.showMessage({
64 | type: 'danger',
65 | text: errorResponse
66 | });
67 | console.log('API responded with:', errorResponse);
68 | });
69 | },
70 |
71 | fetchPost(){
72 | return postsResource.get(`${this.id}`)
73 | .then((response) => {
74 | this.post = response.data;
75 | })
76 | .catch((errorResponse) => {
77 | // Handle error...
78 | console.log('API responded with:', errorResponse);
79 | });
80 | }
81 | }
82 | });
83 |
--------------------------------------------------------------------------------
/src/components/Posts/post.html:
--------------------------------------------------------------------------------
1 |
4 |
5 |
6 |
{{ post.title }}
7 |
{{ post.body }}
8 |
9 |
10 |
11 | Back to posts
12 |
13 |
14 | Edit
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/src/components/Posts/post.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | import { postsResource } from 'src/util/resources';
4 | import template from './post.html';
5 |
6 | export default Vue.extend({
7 | template,
8 |
9 | data() {
10 | return {
11 | post: {}
12 | };
13 | },
14 |
15 | created(){
16 | this.fetchPost();
17 | },
18 |
19 | methods: {
20 | fetchPost(){
21 | const id = this.$route.params.id;
22 |
23 | return postsResource.get(`${id}`)
24 | .then((response) => {
25 | this.post = response.data;
26 | })
27 | .catch((errorResponse) => {
28 | // Handle error...
29 | console.log('API responded with:', errorResponse);
30 | });
31 | }
32 | }
33 | });
34 |
--------------------------------------------------------------------------------
/src/components/Posts/posts.html:
--------------------------------------------------------------------------------
1 |
2 |
Posts
3 |
4 |
5 |
6 |
7 |
8 |
14 |
20 | #{{ index+1 }} {{ post.title }}
21 |
22 |
23 |
24 |
--------------------------------------------------------------------------------
/src/components/Posts/posts.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | import { postsResource } from 'src/util/resources';
4 | import template from './posts.html';
5 |
6 | const animation = 'flipInX';
7 | const animationDelay = 25; // in ms
8 |
9 | export default Vue.extend({
10 | template,
11 |
12 | data() {
13 | return {
14 | postsFilter: '',
15 | posts: []
16 | };
17 | },
18 |
19 | computed: {
20 | filteredPosts() {
21 | return this.posts.filter((post) => post.title.toLowerCase().indexOf(this.postsFilter.toLowerCase()) !== -1);
22 | }
23 | },
24 |
25 | created(){
26 | this.fetchPosts();
27 | },
28 |
29 | methods: {
30 | fetchPosts(){
31 | return postsResource.get('/')
32 | .then((response) => {
33 | this.posts = response.data;
34 | })
35 | .catch((errorResponse) => {
36 | // Handle error...
37 | console.log('API responded with:', errorResponse);
38 | });
39 | },
40 |
41 | // Methods for transitions
42 | handleBeforeEnter(el) {
43 | el.style.opacity = 0;
44 | el.classList.add('animated');
45 | },
46 |
47 | handleEnter(el) {
48 | const delay = el.dataset.index * animationDelay;
49 | setTimeout(() => {
50 | el.style.opacity = 1;
51 | el.classList.add(animation);
52 | }, delay);
53 | }
54 | }
55 | });
56 |
--------------------------------------------------------------------------------
/src/config/constants.js:
--------------------------------------------------------------------------------
1 | // A global API-root
2 | export const API_BASE = 'https://jsonplaceholder.typicode.com';
3 |
--------------------------------------------------------------------------------
/src/config/http.js:
--------------------------------------------------------------------------------
1 | import { setLoading } from 'src/util/helpers';
2 | import { postsResource } from 'src/util/resources';
3 |
4 | // Request interceptor
5 | postsResource.interceptors.request.use((config) => {
6 | setLoading(true);
7 | return config;
8 | }, (error) => {
9 | setLoading(false);
10 | console.log('RequestError: ', error);
11 | // Do something with request error
12 | return Promise.reject(error);
13 | });
14 |
15 | // Response interceptor
16 | postsResource.interceptors.response.use((response) => {
17 | setLoading(false);
18 | return response;
19 | }, (error) => {
20 | setLoading(false);
21 | console.log('ResponseError: ', error);
22 | // Do something with response error
23 | return Promise.reject(error);
24 | });
25 |
--------------------------------------------------------------------------------
/src/config/loading-state.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 |
3 | // Loading state handler
4 | export const LoadingState = new Vue();
5 |
--------------------------------------------------------------------------------
/src/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
7 |
8 | Vue.js starter
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
--------------------------------------------------------------------------------
/src/main.js:
--------------------------------------------------------------------------------
1 | import Vue from 'vue';
2 | import VueRouter from 'vue-router';
3 |
4 | import { LoadingState } from 'src/config/loading-state';
5 | import Navigation from 'components/Navigation/navigation';
6 | import Loader from 'components/Loader/loader';
7 |
8 | Vue.use(VueRouter);
9 |
10 | import 'src/config/http';
11 | import routes from 'src/routes';
12 | import 'src/style.scss';
13 |
14 | export const router = new VueRouter({
15 | routes,
16 | mode: 'history',
17 | linkActiveClass: 'active'
18 | });
19 |
20 | new Vue({
21 | router,
22 | components: {
23 | Navigation,
24 | Loader
25 | },
26 |
27 | data(){
28 | return {
29 | isLoading: false
30 | };
31 | },
32 |
33 | created(){
34 | LoadingState.$on('toggle', (isLoading) => {
35 | this.isLoading = isLoading;
36 | });
37 | }
38 | }).$mount('#app');
39 |
--------------------------------------------------------------------------------
/src/routes.js:
--------------------------------------------------------------------------------
1 | import Home from 'components/Home/home';
2 | import Posts from 'components/Posts/posts';
3 | import Post from 'components/Posts/post';
4 | import CreatePost from 'components/Posts/createPost';
5 | import EditPost from 'components/Posts/editPost';
6 | import NotFound from 'components/NotFound/notFound';
7 |
8 | const routes = [
9 | {
10 | path: '/',
11 | component: Home
12 | },
13 | {
14 | path: '/posts',
15 | component: Posts
16 | },
17 | {
18 | path: '/posts/create',
19 | name: 'createPost',
20 | component: CreatePost
21 | },
22 | {
23 | path: '/post/:id',
24 | name: 'post',
25 | component: Post
26 | },
27 | {
28 | path: '/post/:id/edit',
29 | name: 'editPost',
30 | component: EditPost
31 | },
32 | {
33 | path: '*',
34 | component: NotFound
35 | }
36 | ];
37 |
38 | export default routes;
39 |
--------------------------------------------------------------------------------
/src/style.scss:
--------------------------------------------------------------------------------
1 | @import "styles/variables";
2 |
3 | // npm depencies
4 | @import "~bootstrap/scss/bootstrap";
5 | @import "~font-awesome/scss/font-awesome";
6 |
7 | // Project specific
8 | @import "styles/global";
9 | @import "styles/animate";
10 |
--------------------------------------------------------------------------------
/src/styles/_animate.scss:
--------------------------------------------------------------------------------
1 | @charset "UTF-8";
2 |
3 | /*!
4 | * animate.css -http://daneden.me/animate
5 | * Version - 3.5.0
6 | * Licensed under the MIT license - http://opensource.org/licenses/MIT
7 | *
8 | * Copyright (c) 2016 Daniel Eden
9 | */
10 |
11 | .animated{-webkit-animation-duration:1s;animation-duration:1s;-webkit-animation-fill-mode:both;animation-fill-mode:both}.animated.infinite{-webkit-animation-iteration-count:infinite;animation-iteration-count:infinite}.animated.hinge{-webkit-animation-duration:2s;animation-duration:2s}.animated.bounceIn,.animated.bounceOut,.animated.flipOutX,.animated.flipOutY{-webkit-animation-duration:.75s;animation-duration:.75s}@-webkit-keyframes bounce{0%,20%,53%,80%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1);-webkit-transform:translateZ(0);transform:translateZ(0)}40%,43%{-webkit-transform:translate3d(0,-30px,0);transform:translate3d(0,-30px,0)}40%,43%,70%{-webkit-animation-timing-function:cubic-bezier(.755,.05,.855,.06);animation-timing-function:cubic-bezier(.755,.05,.855,.06)}70%{-webkit-transform:translate3d(0,-15px,0);transform:translate3d(0,-15px,0)}90%{-webkit-transform:translate3d(0,-4px,0);transform:translate3d(0,-4px,0)}}@keyframes bounce{0%,20%,53%,80%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1);-webkit-transform:translateZ(0);transform:translateZ(0)}40%,43%{-webkit-transform:translate3d(0,-30px,0);transform:translate3d(0,-30px,0)}40%,43%,70%{-webkit-animation-timing-function:cubic-bezier(.755,.05,.855,.06);animation-timing-function:cubic-bezier(.755,.05,.855,.06)}70%{-webkit-transform:translate3d(0,-15px,0);transform:translate3d(0,-15px,0)}90%{-webkit-transform:translate3d(0,-4px,0);transform:translate3d(0,-4px,0)}}.bounce{-webkit-animation-name:bounce;animation-name:bounce;-webkit-transform-origin:center bottom;transform-origin:center bottom}@-webkit-keyframes flash{0%,50%,to{opacity:1}25%,75%{opacity:0}}@keyframes flash{0%,50%,to{opacity:1}25%,75%{opacity:0}}.flash{-webkit-animation-name:flash;animation-name:flash}@-webkit-keyframes pulse{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}50%{-webkit-transform:scale3d(1.05,1.05,1.05);transform:scale3d(1.05,1.05,1.05)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}@keyframes pulse{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}50%{-webkit-transform:scale3d(1.05,1.05,1.05);transform:scale3d(1.05,1.05,1.05)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}.pulse{-webkit-animation-name:pulse;animation-name:pulse}@-webkit-keyframes rubberBand{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}30%{-webkit-transform:scale3d(1.25,.75,1);transform:scale3d(1.25,.75,1)}40%{-webkit-transform:scale3d(.75,1.25,1);transform:scale3d(.75,1.25,1)}50%{-webkit-transform:scale3d(1.15,.85,1);transform:scale3d(1.15,.85,1)}65%{-webkit-transform:scale3d(.95,1.05,1);transform:scale3d(.95,1.05,1)}75%{-webkit-transform:scale3d(1.05,.95,1);transform:scale3d(1.05,.95,1)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}@keyframes rubberBand{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}30%{-webkit-transform:scale3d(1.25,.75,1);transform:scale3d(1.25,.75,1)}40%{-webkit-transform:scale3d(.75,1.25,1);transform:scale3d(.75,1.25,1)}50%{-webkit-transform:scale3d(1.15,.85,1);transform:scale3d(1.15,.85,1)}65%{-webkit-transform:scale3d(.95,1.05,1);transform:scale3d(.95,1.05,1)}75%{-webkit-transform:scale3d(1.05,.95,1);transform:scale3d(1.05,.95,1)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}.rubberBand{-webkit-animation-name:rubberBand;animation-name:rubberBand}@-webkit-keyframes shake{0%,to{-webkit-transform:translateZ(0);transform:translateZ(0)}10%,30%,50%,70%,90%{-webkit-transform:translate3d(-10px,0,0);transform:translate3d(-10px,0,0)}20%,40%,60%,80%{-webkit-transform:translate3d(10px,0,0);transform:translate3d(10px,0,0)}}@keyframes shake{0%,to{-webkit-transform:translateZ(0);transform:translateZ(0)}10%,30%,50%,70%,90%{-webkit-transform:translate3d(-10px,0,0);transform:translate3d(-10px,0,0)}20%,40%,60%,80%{-webkit-transform:translate3d(10px,0,0);transform:translate3d(10px,0,0)}}.shake{-webkit-animation-name:shake;animation-name:shake}@-webkit-keyframes headShake{0%{-webkit-transform:translateX(0);transform:translateX(0)}6.5%{-webkit-transform:translateX(-6px) rotateY(-9deg);transform:translateX(-6px) rotateY(-9deg)}18.5%{-webkit-transform:translateX(5px) rotateY(7deg);transform:translateX(5px) rotateY(7deg)}31.5%{-webkit-transform:translateX(-3px) rotateY(-5deg);transform:translateX(-3px) rotateY(-5deg)}43.5%{-webkit-transform:translateX(2px) rotateY(3deg);transform:translateX(2px) rotateY(3deg)}50%{-webkit-transform:translateX(0);transform:translateX(0)}}@keyframes headShake{0%{-webkit-transform:translateX(0);transform:translateX(0)}6.5%{-webkit-transform:translateX(-6px) rotateY(-9deg);transform:translateX(-6px) rotateY(-9deg)}18.5%{-webkit-transform:translateX(5px) rotateY(7deg);transform:translateX(5px) rotateY(7deg)}31.5%{-webkit-transform:translateX(-3px) rotateY(-5deg);transform:translateX(-3px) rotateY(-5deg)}43.5%{-webkit-transform:translateX(2px) rotateY(3deg);transform:translateX(2px) rotateY(3deg)}50%{-webkit-transform:translateX(0);transform:translateX(0)}}.headShake{-webkit-animation-timing-function:ease-in-out;animation-timing-function:ease-in-out;-webkit-animation-name:headShake;animation-name:headShake}@-webkit-keyframes swing{20%{-webkit-transform:rotate(15deg);transform:rotate(15deg)}40%{-webkit-transform:rotate(-10deg);transform:rotate(-10deg)}60%{-webkit-transform:rotate(5deg);transform:rotate(5deg)}80%{-webkit-transform:rotate(-5deg);transform:rotate(-5deg)}to{-webkit-transform:rotate(0deg);transform:rotate(0deg)}}@keyframes swing{20%{-webkit-transform:rotate(15deg);transform:rotate(15deg)}40%{-webkit-transform:rotate(-10deg);transform:rotate(-10deg)}60%{-webkit-transform:rotate(5deg);transform:rotate(5deg)}80%{-webkit-transform:rotate(-5deg);transform:rotate(-5deg)}to{-webkit-transform:rotate(0deg);transform:rotate(0deg)}}.swing{-webkit-transform-origin:top center;transform-origin:top center;-webkit-animation-name:swing;animation-name:swing}@-webkit-keyframes tada{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}10%,20%{-webkit-transform:scale3d(.9,.9,.9) rotate(-3deg);transform:scale3d(.9,.9,.9) rotate(-3deg)}30%,50%,70%,90%{-webkit-transform:scale3d(1.1,1.1,1.1) rotate(3deg);transform:scale3d(1.1,1.1,1.1) rotate(3deg)}40%,60%,80%{-webkit-transform:scale3d(1.1,1.1,1.1) rotate(-3deg);transform:scale3d(1.1,1.1,1.1) rotate(-3deg)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}@keyframes tada{0%{-webkit-transform:scaleX(1);transform:scaleX(1)}10%,20%{-webkit-transform:scale3d(.9,.9,.9) rotate(-3deg);transform:scale3d(.9,.9,.9) rotate(-3deg)}30%,50%,70%,90%{-webkit-transform:scale3d(1.1,1.1,1.1) rotate(3deg);transform:scale3d(1.1,1.1,1.1) rotate(3deg)}40%,60%,80%{-webkit-transform:scale3d(1.1,1.1,1.1) rotate(-3deg);transform:scale3d(1.1,1.1,1.1) rotate(-3deg)}to{-webkit-transform:scaleX(1);transform:scaleX(1)}}.tada{-webkit-animation-name:tada;animation-name:tada}@-webkit-keyframes wobble{0%{-webkit-transform:none;transform:none}15%{-webkit-transform:translate3d(-25%,0,0) rotate(-5deg);transform:translate3d(-25%,0,0) rotate(-5deg)}30%{-webkit-transform:translate3d(20%,0,0) rotate(3deg);transform:translate3d(20%,0,0) rotate(3deg)}45%{-webkit-transform:translate3d(-15%,0,0) rotate(-3deg);transform:translate3d(-15%,0,0) rotate(-3deg)}60%{-webkit-transform:translate3d(10%,0,0) rotate(2deg);transform:translate3d(10%,0,0) rotate(2deg)}75%{-webkit-transform:translate3d(-5%,0,0) rotate(-1deg);transform:translate3d(-5%,0,0) rotate(-1deg)}to{-webkit-transform:none;transform:none}}@keyframes wobble{0%{-webkit-transform:none;transform:none}15%{-webkit-transform:translate3d(-25%,0,0) rotate(-5deg);transform:translate3d(-25%,0,0) rotate(-5deg)}30%{-webkit-transform:translate3d(20%,0,0) rotate(3deg);transform:translate3d(20%,0,0) rotate(3deg)}45%{-webkit-transform:translate3d(-15%,0,0) rotate(-3deg);transform:translate3d(-15%,0,0) rotate(-3deg)}60%{-webkit-transform:translate3d(10%,0,0) rotate(2deg);transform:translate3d(10%,0,0) rotate(2deg)}75%{-webkit-transform:translate3d(-5%,0,0) rotate(-1deg);transform:translate3d(-5%,0,0) rotate(-1deg)}to{-webkit-transform:none;transform:none}}.wobble{-webkit-animation-name:wobble;animation-name:wobble}@-webkit-keyframes jello{0%,11.1%,to{-webkit-transform:none;transform:none}22.2%{-webkit-transform:skewX(-12.5deg) skewY(-12.5deg);transform:skewX(-12.5deg) skewY(-12.5deg)}33.3%{-webkit-transform:skewX(6.25deg) skewY(6.25deg);transform:skewX(6.25deg) skewY(6.25deg)}44.4%{-webkit-transform:skewX(-3.125deg) skewY(-3.125deg);transform:skewX(-3.125deg) skewY(-3.125deg)}55.5%{-webkit-transform:skewX(1.5625deg) skewY(1.5625deg);transform:skewX(1.5625deg) skewY(1.5625deg)}66.6%{-webkit-transform:skewX(-.78125deg) skewY(-.78125deg);transform:skewX(-.78125deg) skewY(-.78125deg)}77.7%{-webkit-transform:skewX(.390625deg) skewY(.390625deg);transform:skewX(.390625deg) skewY(.390625deg)}88.8%{-webkit-transform:skewX(-.1953125deg) skewY(-.1953125deg);transform:skewX(-.1953125deg) skewY(-.1953125deg)}}@keyframes jello{0%,11.1%,to{-webkit-transform:none;transform:none}22.2%{-webkit-transform:skewX(-12.5deg) skewY(-12.5deg);transform:skewX(-12.5deg) skewY(-12.5deg)}33.3%{-webkit-transform:skewX(6.25deg) skewY(6.25deg);transform:skewX(6.25deg) skewY(6.25deg)}44.4%{-webkit-transform:skewX(-3.125deg) skewY(-3.125deg);transform:skewX(-3.125deg) skewY(-3.125deg)}55.5%{-webkit-transform:skewX(1.5625deg) skewY(1.5625deg);transform:skewX(1.5625deg) skewY(1.5625deg)}66.6%{-webkit-transform:skewX(-.78125deg) skewY(-.78125deg);transform:skewX(-.78125deg) skewY(-.78125deg)}77.7%{-webkit-transform:skewX(.390625deg) skewY(.390625deg);transform:skewX(.390625deg) skewY(.390625deg)}88.8%{-webkit-transform:skewX(-.1953125deg) skewY(-.1953125deg);transform:skewX(-.1953125deg) skewY(-.1953125deg)}}.jello{-webkit-animation-name:jello;animation-name:jello;-webkit-transform-origin:center;transform-origin:center}@-webkit-keyframes bounceIn{0%,20%,40%,60%,80%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}20%{-webkit-transform:scale3d(1.1,1.1,1.1);transform:scale3d(1.1,1.1,1.1)}40%{-webkit-transform:scale3d(.9,.9,.9);transform:scale3d(.9,.9,.9)}60%{opacity:1;-webkit-transform:scale3d(1.03,1.03,1.03);transform:scale3d(1.03,1.03,1.03)}80%{-webkit-transform:scale3d(.97,.97,.97);transform:scale3d(.97,.97,.97)}to{opacity:1;-webkit-transform:scaleX(1);transform:scaleX(1)}}@keyframes bounceIn{0%,20%,40%,60%,80%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}20%{-webkit-transform:scale3d(1.1,1.1,1.1);transform:scale3d(1.1,1.1,1.1)}40%{-webkit-transform:scale3d(.9,.9,.9);transform:scale3d(.9,.9,.9)}60%{opacity:1;-webkit-transform:scale3d(1.03,1.03,1.03);transform:scale3d(1.03,1.03,1.03)}80%{-webkit-transform:scale3d(.97,.97,.97);transform:scale3d(.97,.97,.97)}to{opacity:1;-webkit-transform:scaleX(1);transform:scaleX(1)}}.bounceIn{-webkit-animation-name:bounceIn;animation-name:bounceIn}@-webkit-keyframes bounceInDown{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(0,-3000px,0);transform:translate3d(0,-3000px,0)}60%{opacity:1;-webkit-transform:translate3d(0,25px,0);transform:translate3d(0,25px,0)}75%{-webkit-transform:translate3d(0,-10px,0);transform:translate3d(0,-10px,0)}90%{-webkit-transform:translate3d(0,5px,0);transform:translate3d(0,5px,0)}to{-webkit-transform:none;transform:none}}@keyframes bounceInDown{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(0,-3000px,0);transform:translate3d(0,-3000px,0)}60%{opacity:1;-webkit-transform:translate3d(0,25px,0);transform:translate3d(0,25px,0)}75%{-webkit-transform:translate3d(0,-10px,0);transform:translate3d(0,-10px,0)}90%{-webkit-transform:translate3d(0,5px,0);transform:translate3d(0,5px,0)}to{-webkit-transform:none;transform:none}}.bounceInDown{-webkit-animation-name:bounceInDown;animation-name:bounceInDown}@-webkit-keyframes bounceInLeft{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(-3000px,0,0);transform:translate3d(-3000px,0,0)}60%{opacity:1;-webkit-transform:translate3d(25px,0,0);transform:translate3d(25px,0,0)}75%{-webkit-transform:translate3d(-10px,0,0);transform:translate3d(-10px,0,0)}90%{-webkit-transform:translate3d(5px,0,0);transform:translate3d(5px,0,0)}to{-webkit-transform:none;transform:none}}@keyframes bounceInLeft{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(-3000px,0,0);transform:translate3d(-3000px,0,0)}60%{opacity:1;-webkit-transform:translate3d(25px,0,0);transform:translate3d(25px,0,0)}75%{-webkit-transform:translate3d(-10px,0,0);transform:translate3d(-10px,0,0)}90%{-webkit-transform:translate3d(5px,0,0);transform:translate3d(5px,0,0)}to{-webkit-transform:none;transform:none}}.bounceInLeft{-webkit-animation-name:bounceInLeft;animation-name:bounceInLeft}@-webkit-keyframes bounceInRight{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(3000px,0,0);transform:translate3d(3000px,0,0)}60%{opacity:1;-webkit-transform:translate3d(-25px,0,0);transform:translate3d(-25px,0,0)}75%{-webkit-transform:translate3d(10px,0,0);transform:translate3d(10px,0,0)}90%{-webkit-transform:translate3d(-5px,0,0);transform:translate3d(-5px,0,0)}to{-webkit-transform:none;transform:none}}@keyframes bounceInRight{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(3000px,0,0);transform:translate3d(3000px,0,0)}60%{opacity:1;-webkit-transform:translate3d(-25px,0,0);transform:translate3d(-25px,0,0)}75%{-webkit-transform:translate3d(10px,0,0);transform:translate3d(10px,0,0)}90%{-webkit-transform:translate3d(-5px,0,0);transform:translate3d(-5px,0,0)}to{-webkit-transform:none;transform:none}}.bounceInRight{-webkit-animation-name:bounceInRight;animation-name:bounceInRight}@-webkit-keyframes bounceInUp{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(0,3000px,0);transform:translate3d(0,3000px,0)}60%{opacity:1;-webkit-transform:translate3d(0,-20px,0);transform:translate3d(0,-20px,0)}75%{-webkit-transform:translate3d(0,10px,0);transform:translate3d(0,10px,0)}90%{-webkit-transform:translate3d(0,-5px,0);transform:translate3d(0,-5px,0)}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}@keyframes bounceInUp{0%,60%,75%,90%,to{-webkit-animation-timing-function:cubic-bezier(.215,.61,.355,1);animation-timing-function:cubic-bezier(.215,.61,.355,1)}0%{opacity:0;-webkit-transform:translate3d(0,3000px,0);transform:translate3d(0,3000px,0)}60%{opacity:1;-webkit-transform:translate3d(0,-20px,0);transform:translate3d(0,-20px,0)}75%{-webkit-transform:translate3d(0,10px,0);transform:translate3d(0,10px,0)}90%{-webkit-transform:translate3d(0,-5px,0);transform:translate3d(0,-5px,0)}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}.bounceInUp{-webkit-animation-name:bounceInUp;animation-name:bounceInUp}@-webkit-keyframes bounceOut{20%{-webkit-transform:scale3d(.9,.9,.9);transform:scale3d(.9,.9,.9)}50%,55%{opacity:1;-webkit-transform:scale3d(1.1,1.1,1.1);transform:scale3d(1.1,1.1,1.1)}to{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}}@keyframes bounceOut{20%{-webkit-transform:scale3d(.9,.9,.9);transform:scale3d(.9,.9,.9)}50%,55%{opacity:1;-webkit-transform:scale3d(1.1,1.1,1.1);transform:scale3d(1.1,1.1,1.1)}to{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}}.bounceOut{-webkit-animation-name:bounceOut;animation-name:bounceOut}@-webkit-keyframes bounceOutDown{20%{-webkit-transform:translate3d(0,10px,0);transform:translate3d(0,10px,0)}40%,45%{opacity:1;-webkit-transform:translate3d(0,-20px,0);transform:translate3d(0,-20px,0)}to{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}}@keyframes bounceOutDown{20%{-webkit-transform:translate3d(0,10px,0);transform:translate3d(0,10px,0)}40%,45%{opacity:1;-webkit-transform:translate3d(0,-20px,0);transform:translate3d(0,-20px,0)}to{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}}.bounceOutDown{-webkit-animation-name:bounceOutDown;animation-name:bounceOutDown}@-webkit-keyframes bounceOutLeft{20%{opacity:1;-webkit-transform:translate3d(20px,0,0);transform:translate3d(20px,0,0)}to{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}}@keyframes bounceOutLeft{20%{opacity:1;-webkit-transform:translate3d(20px,0,0);transform:translate3d(20px,0,0)}to{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}}.bounceOutLeft{-webkit-animation-name:bounceOutLeft;animation-name:bounceOutLeft}@-webkit-keyframes bounceOutRight{20%{opacity:1;-webkit-transform:translate3d(-20px,0,0);transform:translate3d(-20px,0,0)}to{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}}@keyframes bounceOutRight{20%{opacity:1;-webkit-transform:translate3d(-20px,0,0);transform:translate3d(-20px,0,0)}to{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}}.bounceOutRight{-webkit-animation-name:bounceOutRight;animation-name:bounceOutRight}@-webkit-keyframes bounceOutUp{20%{-webkit-transform:translate3d(0,-10px,0);transform:translate3d(0,-10px,0)}40%,45%{opacity:1;-webkit-transform:translate3d(0,20px,0);transform:translate3d(0,20px,0)}to{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}}@keyframes bounceOutUp{20%{-webkit-transform:translate3d(0,-10px,0);transform:translate3d(0,-10px,0)}40%,45%{opacity:1;-webkit-transform:translate3d(0,20px,0);transform:translate3d(0,20px,0)}to{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}}.bounceOutUp{-webkit-animation-name:bounceOutUp;animation-name:bounceOutUp}@-webkit-keyframes fadeIn{0%{opacity:0}to{opacity:1}}@keyframes fadeIn{0%{opacity:0}to{opacity:1}}.fadeIn{-webkit-animation-name:fadeIn;animation-name:fadeIn}@-webkit-keyframes fadeInDown{0%{opacity:0;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInDown{0%{opacity:0;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInDown{-webkit-animation-name:fadeInDown;animation-name:fadeInDown}@-webkit-keyframes fadeInDownBig{0%{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInDownBig{0%{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInDownBig{-webkit-animation-name:fadeInDownBig;animation-name:fadeInDownBig}@-webkit-keyframes fadeInLeft{0%{opacity:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInLeft{0%{opacity:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInLeft{-webkit-animation-name:fadeInLeft;animation-name:fadeInLeft}@-webkit-keyframes fadeInLeftBig{0%{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInLeftBig{0%{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInLeftBig{-webkit-animation-name:fadeInLeftBig;animation-name:fadeInLeftBig}@-webkit-keyframes fadeInRight{0%{opacity:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInRight{0%{opacity:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInRight{-webkit-animation-name:fadeInRight;animation-name:fadeInRight}@-webkit-keyframes fadeInRightBig{0%{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInRightBig{0%{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInRightBig{-webkit-animation-name:fadeInRightBig;animation-name:fadeInRightBig}@-webkit-keyframes fadeInUp{0%{opacity:0;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInUp{0%{opacity:0;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInUp{-webkit-animation-name:fadeInUp;animation-name:fadeInUp}@-webkit-keyframes fadeInUpBig{0%{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes fadeInUpBig{0%{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}to{opacity:1;-webkit-transform:none;transform:none}}.fadeInUpBig{-webkit-animation-name:fadeInUpBig;animation-name:fadeInUpBig}@-webkit-keyframes fadeOut{0%{opacity:1}to{opacity:0}}@keyframes fadeOut{0%{opacity:1}to{opacity:0}}.fadeOut{-webkit-animation-name:fadeOut;animation-name:fadeOut}@-webkit-keyframes fadeOutDown{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}}@keyframes fadeOutDown{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}}.fadeOutDown{-webkit-animation-name:fadeOutDown;animation-name:fadeOutDown}@-webkit-keyframes fadeOutDownBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}}@keyframes fadeOutDownBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,2000px,0);transform:translate3d(0,2000px,0)}}.fadeOutDownBig{-webkit-animation-name:fadeOutDownBig;animation-name:fadeOutDownBig}@-webkit-keyframes fadeOutLeft{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}}@keyframes fadeOutLeft{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}}.fadeOutLeft{-webkit-animation-name:fadeOutLeft;animation-name:fadeOutLeft}@-webkit-keyframes fadeOutLeftBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}}@keyframes fadeOutLeftBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(-2000px,0,0);transform:translate3d(-2000px,0,0)}}.fadeOutLeftBig{-webkit-animation-name:fadeOutLeftBig;animation-name:fadeOutLeftBig}@-webkit-keyframes fadeOutRight{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}}@keyframes fadeOutRight{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}}.fadeOutRight{-webkit-animation-name:fadeOutRight;animation-name:fadeOutRight}@-webkit-keyframes fadeOutRightBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}}@keyframes fadeOutRightBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(2000px,0,0);transform:translate3d(2000px,0,0)}}.fadeOutRightBig{-webkit-animation-name:fadeOutRightBig;animation-name:fadeOutRightBig}@-webkit-keyframes fadeOutUp{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}}@keyframes fadeOutUp{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}}.fadeOutUp{-webkit-animation-name:fadeOutUp;animation-name:fadeOutUp}@-webkit-keyframes fadeOutUpBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}}@keyframes fadeOutUpBig{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(0,-2000px,0);transform:translate3d(0,-2000px,0)}}.fadeOutUpBig{-webkit-animation-name:fadeOutUpBig;animation-name:fadeOutUpBig}@-webkit-keyframes flip{0%{-webkit-transform:perspective(400px) rotateY(-1turn);transform:perspective(400px) rotateY(-1turn)}0%,40%{-webkit-animation-timing-function:ease-out;animation-timing-function:ease-out}40%{-webkit-transform:perspective(400px) translateZ(150px) rotateY(-190deg);transform:perspective(400px) translateZ(150px) rotateY(-190deg)}50%{-webkit-transform:perspective(400px) translateZ(150px) rotateY(-170deg);transform:perspective(400px) translateZ(150px) rotateY(-170deg)}50%,80%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}80%{-webkit-transform:perspective(400px) scale3d(.95,.95,.95);transform:perspective(400px) scale3d(.95,.95,.95)}to{-webkit-transform:perspective(400px);transform:perspective(400px);-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}}@keyframes flip{0%{-webkit-transform:perspective(400px) rotateY(-1turn);transform:perspective(400px) rotateY(-1turn)}0%,40%{-webkit-animation-timing-function:ease-out;animation-timing-function:ease-out}40%{-webkit-transform:perspective(400px) translateZ(150px) rotateY(-190deg);transform:perspective(400px) translateZ(150px) rotateY(-190deg)}50%{-webkit-transform:perspective(400px) translateZ(150px) rotateY(-170deg);transform:perspective(400px) translateZ(150px) rotateY(-170deg)}50%,80%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}80%{-webkit-transform:perspective(400px) scale3d(.95,.95,.95);transform:perspective(400px) scale3d(.95,.95,.95)}to{-webkit-transform:perspective(400px);transform:perspective(400px);-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}}.animated.flip{-webkit-backface-visibility:visible;backface-visibility:visible;-webkit-animation-name:flip;animation-name:flip}@-webkit-keyframes flipInX{0%{-webkit-transform:perspective(400px) rotateX(90deg);transform:perspective(400px) rotateX(90deg);opacity:0}0%,40%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}40%{-webkit-transform:perspective(400px) rotateX(-20deg);transform:perspective(400px) rotateX(-20deg)}60%{-webkit-transform:perspective(400px) rotateX(10deg);transform:perspective(400px) rotateX(10deg);opacity:1}80%{-webkit-transform:perspective(400px) rotateX(-5deg);transform:perspective(400px) rotateX(-5deg)}to{-webkit-transform:perspective(400px);transform:perspective(400px)}}@keyframes flipInX{0%{-webkit-transform:perspective(400px) rotateX(90deg);transform:perspective(400px) rotateX(90deg);opacity:0}0%,40%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}40%{-webkit-transform:perspective(400px) rotateX(-20deg);transform:perspective(400px) rotateX(-20deg)}60%{-webkit-transform:perspective(400px) rotateX(10deg);transform:perspective(400px) rotateX(10deg);opacity:1}80%{-webkit-transform:perspective(400px) rotateX(-5deg);transform:perspective(400px) rotateX(-5deg)}to{-webkit-transform:perspective(400px);transform:perspective(400px)}}.flipInX{-webkit-backface-visibility:visible!important;backface-visibility:visible!important;-webkit-animation-name:flipInX;animation-name:flipInX}@-webkit-keyframes flipInY{0%{-webkit-transform:perspective(400px) rotateY(90deg);transform:perspective(400px) rotateY(90deg);opacity:0}0%,40%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}40%{-webkit-transform:perspective(400px) rotateY(-20deg);transform:perspective(400px) rotateY(-20deg)}60%{-webkit-transform:perspective(400px) rotateY(10deg);transform:perspective(400px) rotateY(10deg);opacity:1}80%{-webkit-transform:perspective(400px) rotateY(-5deg);transform:perspective(400px) rotateY(-5deg)}to{-webkit-transform:perspective(400px);transform:perspective(400px)}}@keyframes flipInY{0%{-webkit-transform:perspective(400px) rotateY(90deg);transform:perspective(400px) rotateY(90deg);opacity:0}0%,40%{-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}40%{-webkit-transform:perspective(400px) rotateY(-20deg);transform:perspective(400px) rotateY(-20deg)}60%{-webkit-transform:perspective(400px) rotateY(10deg);transform:perspective(400px) rotateY(10deg);opacity:1}80%{-webkit-transform:perspective(400px) rotateY(-5deg);transform:perspective(400px) rotateY(-5deg)}to{-webkit-transform:perspective(400px);transform:perspective(400px)}}.flipInY{-webkit-backface-visibility:visible!important;backface-visibility:visible!important;-webkit-animation-name:flipInY;animation-name:flipInY}@-webkit-keyframes flipOutX{0%{-webkit-transform:perspective(400px);transform:perspective(400px)}30%{-webkit-transform:perspective(400px) rotateX(-20deg);transform:perspective(400px) rotateX(-20deg);opacity:1}to{-webkit-transform:perspective(400px) rotateX(90deg);transform:perspective(400px) rotateX(90deg);opacity:0}}@keyframes flipOutX{0%{-webkit-transform:perspective(400px);transform:perspective(400px)}30%{-webkit-transform:perspective(400px) rotateX(-20deg);transform:perspective(400px) rotateX(-20deg);opacity:1}to{-webkit-transform:perspective(400px) rotateX(90deg);transform:perspective(400px) rotateX(90deg);opacity:0}}.flipOutX{-webkit-animation-name:flipOutX;animation-name:flipOutX;-webkit-backface-visibility:visible!important;backface-visibility:visible!important}@-webkit-keyframes flipOutY{0%{-webkit-transform:perspective(400px);transform:perspective(400px)}30%{-webkit-transform:perspective(400px) rotateY(-15deg);transform:perspective(400px) rotateY(-15deg);opacity:1}to{-webkit-transform:perspective(400px) rotateY(90deg);transform:perspective(400px) rotateY(90deg);opacity:0}}@keyframes flipOutY{0%{-webkit-transform:perspective(400px);transform:perspective(400px)}30%{-webkit-transform:perspective(400px) rotateY(-15deg);transform:perspective(400px) rotateY(-15deg);opacity:1}to{-webkit-transform:perspective(400px) rotateY(90deg);transform:perspective(400px) rotateY(90deg);opacity:0}}.flipOutY{-webkit-backface-visibility:visible!important;backface-visibility:visible!important;-webkit-animation-name:flipOutY;animation-name:flipOutY}@-webkit-keyframes lightSpeedIn{0%{-webkit-transform:translate3d(100%,0,0) skewX(-30deg);transform:translate3d(100%,0,0) skewX(-30deg);opacity:0}60%{-webkit-transform:skewX(20deg);transform:skewX(20deg)}60%,80%{opacity:1}80%{-webkit-transform:skewX(-5deg);transform:skewX(-5deg)}to{-webkit-transform:none;transform:none;opacity:1}}@keyframes lightSpeedIn{0%{-webkit-transform:translate3d(100%,0,0) skewX(-30deg);transform:translate3d(100%,0,0) skewX(-30deg);opacity:0}60%{-webkit-transform:skewX(20deg);transform:skewX(20deg)}60%,80%{opacity:1}80%{-webkit-transform:skewX(-5deg);transform:skewX(-5deg)}to{-webkit-transform:none;transform:none;opacity:1}}.lightSpeedIn{-webkit-animation-name:lightSpeedIn;animation-name:lightSpeedIn;-webkit-animation-timing-function:ease-out;animation-timing-function:ease-out}@-webkit-keyframes lightSpeedOut{0%{opacity:1}to{-webkit-transform:translate3d(100%,0,0) skewX(30deg);transform:translate3d(100%,0,0) skewX(30deg);opacity:0}}@keyframes lightSpeedOut{0%{opacity:1}to{-webkit-transform:translate3d(100%,0,0) skewX(30deg);transform:translate3d(100%,0,0) skewX(30deg);opacity:0}}.lightSpeedOut{-webkit-animation-name:lightSpeedOut;animation-name:lightSpeedOut;-webkit-animation-timing-function:ease-in;animation-timing-function:ease-in}@-webkit-keyframes rotateIn{0%{transform-origin:center;-webkit-transform:rotate(-200deg);transform:rotate(-200deg);opacity:0}0%,to{-webkit-transform-origin:center}to{transform-origin:center;-webkit-transform:none;transform:none;opacity:1}}@keyframes rotateIn{0%{transform-origin:center;-webkit-transform:rotate(-200deg);transform:rotate(-200deg);opacity:0}0%,to{-webkit-transform-origin:center}to{transform-origin:center;-webkit-transform:none;transform:none;opacity:1}}.rotateIn{-webkit-animation-name:rotateIn;animation-name:rotateIn}@-webkit-keyframes rotateInDownLeft{0%{transform-origin:left bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:none;transform:none;opacity:1}}@keyframes rotateInDownLeft{0%{transform-origin:left bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:none;transform:none;opacity:1}}.rotateInDownLeft{-webkit-animation-name:rotateInDownLeft;animation-name:rotateInDownLeft}@-webkit-keyframes rotateInDownRight{0%{transform-origin:right bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:none;transform:none;opacity:1}}@keyframes rotateInDownRight{0%{transform-origin:right bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:none;transform:none;opacity:1}}.rotateInDownRight{-webkit-animation-name:rotateInDownRight;animation-name:rotateInDownRight}@-webkit-keyframes rotateInUpLeft{0%{transform-origin:left bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:none;transform:none;opacity:1}}@keyframes rotateInUpLeft{0%{transform-origin:left bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:none;transform:none;opacity:1}}.rotateInUpLeft{-webkit-animation-name:rotateInUpLeft;animation-name:rotateInUpLeft}@-webkit-keyframes rotateInUpRight{0%{transform-origin:right bottom;-webkit-transform:rotate(-90deg);transform:rotate(-90deg);opacity:0}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:none;transform:none;opacity:1}}@keyframes rotateInUpRight{0%{transform-origin:right bottom;-webkit-transform:rotate(-90deg);transform:rotate(-90deg);opacity:0}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:none;transform:none;opacity:1}}.rotateInUpRight{-webkit-animation-name:rotateInUpRight;animation-name:rotateInUpRight}@-webkit-keyframes rotateOut{0%{transform-origin:center;opacity:1}0%,to{-webkit-transform-origin:center}to{transform-origin:center;-webkit-transform:rotate(200deg);transform:rotate(200deg);opacity:0}}@keyframes rotateOut{0%{transform-origin:center;opacity:1}0%,to{-webkit-transform-origin:center}to{transform-origin:center;-webkit-transform:rotate(200deg);transform:rotate(200deg);opacity:0}}.rotateOut{-webkit-animation-name:rotateOut;animation-name:rotateOut}@-webkit-keyframes rotateOutDownLeft{0%{transform-origin:left bottom;opacity:1}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}}@keyframes rotateOutDownLeft{0%{transform-origin:left bottom;opacity:1}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:rotate(45deg);transform:rotate(45deg);opacity:0}}.rotateOutDownLeft{-webkit-animation-name:rotateOutDownLeft;animation-name:rotateOutDownLeft}@-webkit-keyframes rotateOutDownRight{0%{transform-origin:right bottom;opacity:1}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}}@keyframes rotateOutDownRight{0%{transform-origin:right bottom;opacity:1}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}}.rotateOutDownRight{-webkit-animation-name:rotateOutDownRight;animation-name:rotateOutDownRight}@-webkit-keyframes rotateOutUpLeft{0%{transform-origin:left bottom;opacity:1}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}}@keyframes rotateOutUpLeft{0%{transform-origin:left bottom;opacity:1}0%,to{-webkit-transform-origin:left bottom}to{transform-origin:left bottom;-webkit-transform:rotate(-45deg);transform:rotate(-45deg);opacity:0}}.rotateOutUpLeft{-webkit-animation-name:rotateOutUpLeft;animation-name:rotateOutUpLeft}@-webkit-keyframes rotateOutUpRight{0%{transform-origin:right bottom;opacity:1}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:rotate(90deg);transform:rotate(90deg);opacity:0}}@keyframes rotateOutUpRight{0%{transform-origin:right bottom;opacity:1}0%,to{-webkit-transform-origin:right bottom}to{transform-origin:right bottom;-webkit-transform:rotate(90deg);transform:rotate(90deg);opacity:0}}.rotateOutUpRight{-webkit-animation-name:rotateOutUpRight;animation-name:rotateOutUpRight}@-webkit-keyframes hinge{0%{transform-origin:top left}0%,20%,60%{-webkit-transform-origin:top left;-webkit-animation-timing-function:ease-in-out;animation-timing-function:ease-in-out}20%,60%{-webkit-transform:rotate(80deg);transform:rotate(80deg);transform-origin:top left}40%,80%{-webkit-transform:rotate(60deg);transform:rotate(60deg);-webkit-transform-origin:top left;transform-origin:top left;-webkit-animation-timing-function:ease-in-out;animation-timing-function:ease-in-out;opacity:1}to{-webkit-transform:translate3d(0,700px,0);transform:translate3d(0,700px,0);opacity:0}}@keyframes hinge{0%{transform-origin:top left}0%,20%,60%{-webkit-transform-origin:top left;-webkit-animation-timing-function:ease-in-out;animation-timing-function:ease-in-out}20%,60%{-webkit-transform:rotate(80deg);transform:rotate(80deg);transform-origin:top left}40%,80%{-webkit-transform:rotate(60deg);transform:rotate(60deg);-webkit-transform-origin:top left;transform-origin:top left;-webkit-animation-timing-function:ease-in-out;animation-timing-function:ease-in-out;opacity:1}to{-webkit-transform:translate3d(0,700px,0);transform:translate3d(0,700px,0);opacity:0}}.hinge{-webkit-animation-name:hinge;animation-name:hinge}@-webkit-keyframes rollIn{0%{opacity:0;-webkit-transform:translate3d(-100%,0,0) rotate(-120deg);transform:translate3d(-100%,0,0) rotate(-120deg)}to{opacity:1;-webkit-transform:none;transform:none}}@keyframes rollIn{0%{opacity:0;-webkit-transform:translate3d(-100%,0,0) rotate(-120deg);transform:translate3d(-100%,0,0) rotate(-120deg)}to{opacity:1;-webkit-transform:none;transform:none}}.rollIn{-webkit-animation-name:rollIn;animation-name:rollIn}@-webkit-keyframes rollOut{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(100%,0,0) rotate(120deg);transform:translate3d(100%,0,0) rotate(120deg)}}@keyframes rollOut{0%{opacity:1}to{opacity:0;-webkit-transform:translate3d(100%,0,0) rotate(120deg);transform:translate3d(100%,0,0) rotate(120deg)}}.rollOut{-webkit-animation-name:rollOut;animation-name:rollOut}@-webkit-keyframes zoomIn{0%{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}50%{opacity:1}}@keyframes zoomIn{0%{opacity:0;-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}50%{opacity:1}}.zoomIn{-webkit-animation-name:zoomIn;animation-name:zoomIn}@-webkit-keyframes zoomInDown{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,-1000px,0);transform:scale3d(.1,.1,.1) translate3d(0,-1000px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,60px,0);transform:scale3d(.475,.475,.475) translate3d(0,60px,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomInDown{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,-1000px,0);transform:scale3d(.1,.1,.1) translate3d(0,-1000px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,60px,0);transform:scale3d(.475,.475,.475) translate3d(0,60px,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomInDown{-webkit-animation-name:zoomInDown;animation-name:zoomInDown}@-webkit-keyframes zoomInLeft{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(-1000px,0,0);transform:scale3d(.1,.1,.1) translate3d(-1000px,0,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(10px,0,0);transform:scale3d(.475,.475,.475) translate3d(10px,0,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomInLeft{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(-1000px,0,0);transform:scale3d(.1,.1,.1) translate3d(-1000px,0,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(10px,0,0);transform:scale3d(.475,.475,.475) translate3d(10px,0,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomInLeft{-webkit-animation-name:zoomInLeft;animation-name:zoomInLeft}@-webkit-keyframes zoomInRight{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(1000px,0,0);transform:scale3d(.1,.1,.1) translate3d(1000px,0,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(-10px,0,0);transform:scale3d(.475,.475,.475) translate3d(-10px,0,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomInRight{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(1000px,0,0);transform:scale3d(.1,.1,.1) translate3d(1000px,0,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(-10px,0,0);transform:scale3d(.475,.475,.475) translate3d(-10px,0,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomInRight{-webkit-animation-name:zoomInRight;animation-name:zoomInRight}@-webkit-keyframes zoomInUp{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,1000px,0);transform:scale3d(.1,.1,.1) translate3d(0,1000px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomInUp{0%{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,1000px,0);transform:scale3d(.1,.1,.1) translate3d(0,1000px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}60%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomInUp{-webkit-animation-name:zoomInUp;animation-name:zoomInUp}@-webkit-keyframes zoomOut{0%{opacity:1}50%{-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}50%,to{opacity:0}}@keyframes zoomOut{0%{opacity:1}50%{-webkit-transform:scale3d(.3,.3,.3);transform:scale3d(.3,.3,.3)}50%,to{opacity:0}}.zoomOut{-webkit-animation-name:zoomOut;animation-name:zoomOut}@-webkit-keyframes zoomOutDown{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}to{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,2000px,0);transform:scale3d(.1,.1,.1) translate3d(0,2000px,0);-webkit-transform-origin:center bottom;transform-origin:center bottom;-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomOutDown{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);transform:scale3d(.475,.475,.475) translate3d(0,-60px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}to{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,2000px,0);transform:scale3d(.1,.1,.1) translate3d(0,2000px,0);-webkit-transform-origin:center bottom;transform-origin:center bottom;-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomOutDown{-webkit-animation-name:zoomOutDown;animation-name:zoomOutDown}@-webkit-keyframes zoomOutLeft{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(42px,0,0);transform:scale3d(.475,.475,.475) translate3d(42px,0,0)}to{opacity:0;-webkit-transform:scale(.1) translate3d(-2000px,0,0);transform:scale(.1) translate3d(-2000px,0,0);-webkit-transform-origin:left center;transform-origin:left center}}@keyframes zoomOutLeft{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(42px,0,0);transform:scale3d(.475,.475,.475) translate3d(42px,0,0)}to{opacity:0;-webkit-transform:scale(.1) translate3d(-2000px,0,0);transform:scale(.1) translate3d(-2000px,0,0);-webkit-transform-origin:left center;transform-origin:left center}}.zoomOutLeft{-webkit-animation-name:zoomOutLeft;animation-name:zoomOutLeft}@-webkit-keyframes zoomOutRight{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(-42px,0,0);transform:scale3d(.475,.475,.475) translate3d(-42px,0,0)}to{opacity:0;-webkit-transform:scale(.1) translate3d(2000px,0,0);transform:scale(.1) translate3d(2000px,0,0);-webkit-transform-origin:right center;transform-origin:right center}}@keyframes zoomOutRight{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(-42px,0,0);transform:scale3d(.475,.475,.475) translate3d(-42px,0,0)}to{opacity:0;-webkit-transform:scale(.1) translate3d(2000px,0,0);transform:scale(.1) translate3d(2000px,0,0);-webkit-transform-origin:right center;transform-origin:right center}}.zoomOutRight{-webkit-animation-name:zoomOutRight;animation-name:zoomOutRight}@-webkit-keyframes zoomOutUp{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,60px,0);transform:scale3d(.475,.475,.475) translate3d(0,60px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}to{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,-2000px,0);transform:scale3d(.1,.1,.1) translate3d(0,-2000px,0);-webkit-transform-origin:center bottom;transform-origin:center bottom;-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}@keyframes zoomOutUp{40%{opacity:1;-webkit-transform:scale3d(.475,.475,.475) translate3d(0,60px,0);transform:scale3d(.475,.475,.475) translate3d(0,60px,0);-webkit-animation-timing-function:cubic-bezier(.55,.055,.675,.19);animation-timing-function:cubic-bezier(.55,.055,.675,.19)}to{opacity:0;-webkit-transform:scale3d(.1,.1,.1) translate3d(0,-2000px,0);transform:scale3d(.1,.1,.1) translate3d(0,-2000px,0);-webkit-transform-origin:center bottom;transform-origin:center bottom;-webkit-animation-timing-function:cubic-bezier(.175,.885,.32,1);animation-timing-function:cubic-bezier(.175,.885,.32,1)}}.zoomOutUp{-webkit-animation-name:zoomOutUp;animation-name:zoomOutUp}@-webkit-keyframes slideInDown{0%{-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}@keyframes slideInDown{0%{-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}.slideInDown{-webkit-animation-name:slideInDown;animation-name:slideInDown}@-webkit-keyframes slideInLeft{0%{-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}@keyframes slideInLeft{0%{-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}.slideInLeft{-webkit-animation-name:slideInLeft;animation-name:slideInLeft}@-webkit-keyframes slideInRight{0%{-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}@keyframes slideInRight{0%{-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}.slideInRight{-webkit-animation-name:slideInRight;animation-name:slideInRight}@-webkit-keyframes slideInUp{0%{-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}@keyframes slideInUp{0%{-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0);visibility:visible}to{-webkit-transform:translateZ(0);transform:translateZ(0)}}.slideInUp{-webkit-animation-name:slideInUp;animation-name:slideInUp}@-webkit-keyframes slideOutDown{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}}@keyframes slideOutDown{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(0,100%,0);transform:translate3d(0,100%,0)}}.slideOutDown{-webkit-animation-name:slideOutDown;animation-name:slideOutDown}@-webkit-keyframes slideOutLeft{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}}@keyframes slideOutLeft{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(-100%,0,0);transform:translate3d(-100%,0,0)}}.slideOutLeft{-webkit-animation-name:slideOutLeft;animation-name:slideOutLeft}@-webkit-keyframes slideOutRight{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}}@keyframes slideOutRight{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(100%,0,0);transform:translate3d(100%,0,0)}}.slideOutRight{-webkit-animation-name:slideOutRight;animation-name:slideOutRight}@-webkit-keyframes slideOutUp{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}}@keyframes slideOutUp{0%{-webkit-transform:translateZ(0);transform:translateZ(0)}to{visibility:hidden;-webkit-transform:translate3d(0,-100%,0);transform:translate3d(0,-100%,0)}}.slideOutUp{-webkit-animation-name:slideOutUp;animation-name:slideOutUp}
12 |
--------------------------------------------------------------------------------
/src/styles/_global.scss:
--------------------------------------------------------------------------------
1 | ::selection {
2 | background: $brand-primary;
3 | color: #fff;
4 | text-shadow: 0px 0px 0px;
5 | }
6 |
7 | ::-moz-selection {
8 | background: $brand-primary;
9 | color: #fff;
10 | text-shadow: 0px 0px 0px;
11 | }
12 |
13 | ::-webkit-selection {
14 | background: $brand-primary;
15 | color: #fff;
16 | text-shadow: 0px 0px 0px;
17 | }
18 |
19 | html {
20 | -webkit-font-smoothing: antialiased;
21 | -moz-osx-font-smoothing: grayscale;
22 | height: 100%;
23 | }
24 |
25 | body {
26 | padding-top: 5em;
27 | }
28 |
--------------------------------------------------------------------------------
/src/styles/_variables.scss:
--------------------------------------------------------------------------------
1 | // Table of Contents
2 | //
3 | // Colors
4 | // Options
5 | // Spacing
6 | // Body
7 | // Links
8 | // Grid breakpoints
9 | // Grid containers
10 | // Grid columns
11 | // Fonts
12 | // Components
13 | // Tables
14 | // Buttons
15 | // Forms
16 | // Dropdowns
17 | // Z-index master list
18 | // Navbar
19 | // Navs
20 | // Pagination
21 | // Jumbotron
22 | // Form states and alerts
23 | // Cards
24 | // Tooltips
25 | // Popovers
26 | // Badges
27 | // Modals
28 | // Alerts
29 | // Progress bars
30 | // List group
31 | // Image thumbnails
32 | // Figures
33 | // Breadcrumbs
34 | // Carousel
35 | // Close
36 | // Code
37 |
38 | @mixin _assert-ascending($map, $map-name) {
39 | $prev-key: null;
40 | $prev-num: null;
41 | @each $key, $num in $map {
42 | @if $prev-num == null {
43 | // Do nothing
44 | } @else if not comparable($prev-num, $num) {
45 | @warn "Potentially invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} whose unit makes it incomparable to #{$prev-num}, the value of the previous key '#{$prev-key}' !";
46 | } @else if $prev-num >= $num {
47 | @warn "Invalid value for #{$map-name}: This map must be in ascending order, but key '#{$key}' has value #{$num} which isn't greater than #{$prev-num}, the value of the previous key '#{$prev-key}' !";
48 | }
49 | $prev-key: $key;
50 | $prev-num: $num;
51 | }
52 | }
53 |
54 | // Replace `$search` with `$replace` in `$string`
55 | // @author Hugo Giraudel
56 | // @param {String} $string - Initial string
57 | // @param {String} $search - Substring to replace
58 | // @param {String} $replace ('') - New value
59 | // @return {String} - Updated string
60 | @function str-replace($string, $search, $replace: "") {
61 | $index: str-index($string, $search);
62 |
63 | @if $index {
64 | @return str-slice($string, 1, $index - 1) + $replace + str-replace(str-slice($string, $index + str-length($search)), $search, $replace);
65 | }
66 |
67 | @return $string;
68 | }
69 |
70 | @mixin _assert-starts-at-zero($map) {
71 | $values: map-values($map);
72 | $first-value: nth($values, 1);
73 | @if $first-value != 0 {
74 | @warn "First breakpoint in `$grid-breakpoints` must start at 0, but starts at #{$first-value}.";
75 | }
76 | }
77 |
78 |
79 | // General variable structure
80 | //
81 | // Variable format should follow the `$component-modifier-state-property` order.
82 |
83 | $fa-font-path: "~font-awesome/fonts";
84 |
85 | // Colors
86 | //
87 | // Grayscale and brand colors for use across Bootstrap.
88 |
89 | // Start with assigning color names to specific hex values.
90 | $white: #fff !default;
91 | $black: #000 !default;
92 | $red: #d9534f !default;
93 | $orange: #f0ad4e !default;
94 | $yellow: #ffd500 !default;
95 | $green: #5cb85c !default;
96 | $blue: #0275d8 !default;
97 | $teal: #5bc0de !default;
98 | $pink: #ff5b77 !default;
99 | $purple: #613d7c !default;
100 |
101 | // Create grayscale
102 | $gray-dark: #292b2c !default;
103 | $gray: #464a4c !default;
104 | $gray-light: #636c72 !default;
105 | $gray-lighter: #eceeef !default;
106 | $gray-lightest: #f7f7f9 !default;
107 |
108 | // Reassign color vars to semantic color scheme
109 | $brand-primary: $blue !default;
110 | $brand-success: $green !default;
111 | $brand-info: $teal !default;
112 | $brand-warning: $orange !default;
113 | $brand-danger: $red !default;
114 | $brand-inverse: $gray-dark !default;
115 |
116 |
117 | // Options
118 | //
119 | // Quickly modify global styling by enabling or disabling optional features.
120 |
121 | $enable-rounded: true !default;
122 | $enable-shadows: false !default;
123 | $enable-gradients: false !default;
124 | $enable-transitions: true !default;
125 | $enable-hover-media-query: false !default;
126 | $enable-grid-classes: true !default;
127 | $enable-print-styles: true !default;
128 |
129 |
130 | // Spacing
131 | //
132 | // Control the default styling of most Bootstrap elements by modifying these
133 | // variables. Mostly focused on spacing.
134 | // You can add more entries to the $spacers map, should you need more variation.
135 |
136 | $spacer: 1rem !default;
137 | $spacer-x: $spacer !default;
138 | $spacer-y: $spacer !default;
139 | $spacers: (
140 | 0: (
141 | x: 0,
142 | y: 0
143 | ),
144 | 1: (
145 | x: ($spacer-x * .25),
146 | y: ($spacer-y * .25)
147 | ),
148 | 2: (
149 | x: ($spacer-x * .5),
150 | y: ($spacer-y * .5)
151 | ),
152 | 3: (
153 | x: $spacer-x,
154 | y: $spacer-y
155 | ),
156 | 4: (
157 | x: ($spacer-x * 1.5),
158 | y: ($spacer-y * 1.5)
159 | ),
160 | 5: (
161 | x: ($spacer-x * 3),
162 | y: ($spacer-y * 3)
163 | )
164 | ) !default;
165 | $border-width: 1px !default;
166 |
167 | // This variable affects the `.h-*` and `.w-*` classes.
168 | $sizes: (
169 | 25: 25%,
170 | 50: 50%,
171 | 75: 75%,
172 | 100: 100%
173 | ) !default;
174 |
175 | // Body
176 | //
177 | // Settings for the `` element.
178 |
179 | $body-bg: $white !default;
180 | $body-color: $gray-dark !default;
181 | $inverse-bg: $gray-dark !default;
182 | $inverse-color: $gray-lighter !default;
183 |
184 |
185 | // Links
186 | //
187 | // Style anchor elements.
188 |
189 | $link-color: $brand-primary !default;
190 | $link-decoration: none !default;
191 | $link-hover-color: darken($link-color, 15%) !default;
192 | $link-hover-decoration: underline !default;
193 |
194 |
195 | // Grid breakpoints
196 | //
197 | // Define the minimum dimensions at which your layout will change,
198 | // adapting to different screen sizes, for use in media queries.
199 |
200 | $grid-breakpoints: (
201 | xs: 0,
202 | sm: 576px,
203 | md: 768px,
204 | lg: 992px,
205 | xl: 1200px
206 | ) !default;
207 | @include _assert-ascending($grid-breakpoints, "$grid-breakpoints");
208 | @include _assert-starts-at-zero($grid-breakpoints);
209 |
210 |
211 | // Grid containers
212 | //
213 | // Define the maximum width of `.container` for different screen sizes.
214 |
215 | $container-max-widths: (
216 | sm: 540px,
217 | md: 720px,
218 | lg: 960px,
219 | xl: 1140px
220 | ) !default;
221 | @include _assert-ascending($container-max-widths, "$container-max-widths");
222 |
223 |
224 | // Grid columns
225 | //
226 | // Set the number of columns and specify the width of the gutters.
227 |
228 | $grid-columns: 12 !default;
229 | $grid-gutter-width-base: 30px !default;
230 | $grid-gutter-widths: (
231 | xs: $grid-gutter-width-base,
232 | sm: $grid-gutter-width-base,
233 | md: $grid-gutter-width-base,
234 | lg: $grid-gutter-width-base,
235 | xl: $grid-gutter-width-base
236 | ) !default;
237 |
238 | // Fonts
239 | //
240 | // Font, line-height, and color for body text, headings, and more.
241 |
242 | $font-family-sans-serif: -apple-system, system-ui, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif !default;
243 | $font-family-serif: Georgia, "Times New Roman", Times, serif !default;
244 | $font-family-monospace: Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace !default;
245 | $font-family-base: $font-family-sans-serif !default;
246 |
247 | $font-size-base: 1rem !default; // Assumes the browser default, typically `16px`
248 | $font-size-lg: 1.25rem !default;
249 | $font-size-sm: .875rem !default;
250 | $font-size-xs: .75rem !default;
251 |
252 | $font-weight-normal: normal !default;
253 | $font-weight-bold: bold !default;
254 |
255 | $font-weight-base: $font-weight-normal !default;
256 | $line-height-base: 1.5 !default;
257 |
258 | $font-size-h1: 2.5rem !default;
259 | $font-size-h2: 2rem !default;
260 | $font-size-h3: 1.75rem !default;
261 | $font-size-h4: 1.5rem !default;
262 | $font-size-h5: 1.25rem !default;
263 | $font-size-h6: 1rem !default;
264 |
265 | $headings-margin-bottom: ($spacer / 2) !default;
266 | $headings-font-family: inherit !default;
267 | $headings-font-weight: 500 !default;
268 | $headings-line-height: 1.1 !default;
269 | $headings-color: inherit !default;
270 |
271 | $display1-size: 6rem !default;
272 | $display2-size: 5.5rem !default;
273 | $display3-size: 4.5rem !default;
274 | $display4-size: 3.5rem !default;
275 |
276 | $display1-weight: 300 !default;
277 | $display2-weight: 300 !default;
278 | $display3-weight: 300 !default;
279 | $display4-weight: 300 !default;
280 | $display-line-height: $headings-line-height !default;
281 |
282 | $lead-font-size: 1.25rem !default;
283 | $lead-font-weight: 300 !default;
284 |
285 | $small-font-size: 80% !default;
286 |
287 | $text-muted: $gray-light !default;
288 |
289 | $abbr-border-color: $gray-light !default;
290 |
291 | $blockquote-small-color: $gray-light !default;
292 | $blockquote-font-size: ($font-size-base * 1.25) !default;
293 | $blockquote-border-color: $gray-lighter !default;
294 | $blockquote-border-width: .25rem !default;
295 |
296 | $hr-border-color: rgba($black,.1) !default;
297 | $hr-border-width: $border-width !default;
298 |
299 | $mark-padding: .2em !default;
300 |
301 | $dt-font-weight: $font-weight-bold !default;
302 |
303 | $kbd-box-shadow: inset 0 -.1rem 0 rgba($black,.25) !default;
304 | $nested-kbd-font-weight: $font-weight-bold !default;
305 |
306 | $list-inline-padding: 5px !default;
307 |
308 |
309 | // Components
310 | //
311 | // Define common padding and border radius sizes and more.
312 |
313 | $line-height-lg: (4 / 3) !default;
314 | $line-height-sm: 1.5 !default;
315 |
316 | $border-radius: .25rem !default;
317 | $border-radius-lg: .3rem !default;
318 | $border-radius-sm: .2rem !default;
319 |
320 | $component-active-color: $white !default;
321 | $component-active-bg: $brand-primary !default;
322 |
323 | $caret-width: .3em !default;
324 |
325 | $transition-base: all .2s ease-in-out !default;
326 | $transition-fade: opacity .15s linear !default;
327 | $transition-collapse: height .35s ease !default;
328 |
329 |
330 | // Tables
331 | //
332 | // Customizes the `.table` component with basic values, each used across all table variations.
333 |
334 | $table-cell-padding: .75rem !default;
335 | $table-sm-cell-padding: .3rem !default;
336 |
337 | $table-bg: transparent !default;
338 |
339 | $table-inverse-bg: $gray-dark !default;
340 | $table-inverse-color: $body-bg !default;
341 |
342 | $table-bg-accent: rgba($black,.05) !default;
343 | $table-bg-hover: rgba($black,.075) !default;
344 | $table-bg-active: $table-bg-hover !default;
345 |
346 | $table-head-bg: $gray-lighter !default;
347 | $table-head-color: $gray !default;
348 |
349 | $table-border-width: $border-width !default;
350 | $table-border-color: $gray-lighter !default;
351 |
352 |
353 | // Buttons
354 | //
355 | // For each of Bootstrap's buttons, define text, background and border color.
356 |
357 | $btn-padding-x: 1rem !default;
358 | $btn-padding-y: .5rem !default;
359 | $btn-line-height: 1.25 !default;
360 | $btn-font-weight: $font-weight-normal !default;
361 | $btn-box-shadow: inset 0 1px 0 rgba($white,.15), 0 1px 1px rgba($black,.075) !default;
362 | $btn-focus-box-shadow: 0 0 0 2px rgba($brand-primary, .25) !default;
363 | $btn-active-box-shadow: inset 0 3px 5px rgba($black,.125) !default;
364 |
365 | $btn-primary-color: $white !default;
366 | $btn-primary-bg: $brand-primary !default;
367 | $btn-primary-border: $btn-primary-bg !default;
368 |
369 | $btn-secondary-color: $gray-dark !default;
370 | $btn-secondary-bg: $white !default;
371 | $btn-secondary-border: #ccc !default;
372 |
373 | $btn-info-color: $white !default;
374 | $btn-info-bg: $brand-info !default;
375 | $btn-info-border: $btn-info-bg !default;
376 |
377 | $btn-success-color: $white !default;
378 | $btn-success-bg: $brand-success !default;
379 | $btn-success-border: $btn-success-bg !default;
380 |
381 | $btn-warning-color: $white !default;
382 | $btn-warning-bg: $brand-warning !default;
383 | $btn-warning-border: $btn-warning-bg !default;
384 |
385 | $btn-danger-color: $white !default;
386 | $btn-danger-bg: $brand-danger !default;
387 | $btn-danger-border: $btn-danger-bg !default;
388 |
389 | $btn-link-disabled-color: $gray-light !default;
390 |
391 | $btn-padding-x-sm: .5rem !default;
392 | $btn-padding-y-sm: .25rem !default;
393 |
394 | $btn-padding-x-lg: 1.5rem !default;
395 | $btn-padding-y-lg: .75rem !default;
396 |
397 | $btn-block-spacing-y: .5rem !default;
398 | $btn-toolbar-margin: .5rem !default;
399 |
400 | // Allows for customizing button radius independently from global border radius
401 | $btn-border-radius: $border-radius !default;
402 | $btn-border-radius-lg: $border-radius-lg !default;
403 | $btn-border-radius-sm: $border-radius-sm !default;
404 |
405 | $btn-transition: all .2s ease-in-out !default;
406 |
407 |
408 | // Forms
409 |
410 | $input-padding-x: .75rem !default;
411 | $input-padding-y: .5rem !default;
412 | $input-line-height: 1.25 !default;
413 |
414 | $input-bg: $white !default;
415 | $input-bg-disabled: $gray-lighter !default;
416 |
417 | $input-color: $gray !default;
418 | $input-border-color: rgba($black,.15) !default;
419 | $input-btn-border-width: $border-width !default; // For form controls and buttons
420 | $input-box-shadow: inset 0 1px 1px rgba($black,.075) !default;
421 |
422 | $input-border-radius: $border-radius !default;
423 | $input-border-radius-lg: $border-radius-lg !default;
424 | $input-border-radius-sm: $border-radius-sm !default;
425 |
426 | $input-bg-focus: $input-bg !default;
427 | $input-border-focus: lighten($brand-primary, 25%) !default;
428 | $input-box-shadow-focus: $input-box-shadow, rgba($input-border-focus, .6) !default;
429 | $input-color-focus: $input-color !default;
430 |
431 | $input-color-placeholder: $gray-light !default;
432 |
433 | $input-padding-x-sm: .5rem !default;
434 | $input-padding-y-sm: .25rem !default;
435 |
436 | $input-padding-x-lg: 1.5rem !default;
437 | $input-padding-y-lg: .75rem !default;
438 |
439 | $input-height: (($font-size-base * $input-line-height) + ($input-padding-y * 2)) !default;
440 | $input-height-lg: (($font-size-lg * $line-height-lg) + ($input-padding-y-lg * 2)) !default;
441 | $input-height-sm: (($font-size-sm * $line-height-sm) + ($input-padding-y-sm * 2)) !default;
442 |
443 | $input-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s !default;
444 |
445 | $form-text-margin-top: .25rem !default;
446 | $form-feedback-margin-top: $form-text-margin-top !default;
447 |
448 | $form-check-margin-bottom: .5rem !default;
449 | $form-check-input-gutter: 1.25rem !default;
450 | $form-check-input-margin-y: .25rem !default;
451 | $form-check-input-margin-x: .25rem !default;
452 |
453 | $form-check-inline-margin-x: .75rem !default;
454 |
455 | $form-group-margin-bottom: $spacer-y !default;
456 |
457 | $input-group-addon-bg: $gray-lighter !default;
458 | $input-group-addon-border-color: $input-border-color !default;
459 |
460 | $cursor-disabled: not-allowed !default;
461 |
462 | $custom-control-gutter: 1.5rem !default;
463 | $custom-control-spacer-x: 1rem !default;
464 | $custom-control-spacer-y: .25rem !default;
465 |
466 | $custom-control-indicator-size: 1rem !default;
467 | $custom-control-indicator-margin-y: (($line-height-base * 1rem) - $custom-control-indicator-size) / -2 !default;
468 | $custom-control-indicator-bg: #ddd !default;
469 | $custom-control-indicator-bg-size: 50% 50% !default;
470 | $custom-control-indicator-box-shadow: inset 0 .25rem .25rem rgba($black,.1) !default;
471 |
472 | $custom-control-disabled-cursor: $cursor-disabled !default;
473 | $custom-control-disabled-indicator-bg: $gray-lighter !default;
474 | $custom-control-disabled-description-color: $gray-light !default;
475 |
476 | $custom-control-checked-indicator-color: $white !default;
477 | $custom-control-checked-indicator-bg: $brand-primary !default;
478 | $custom-control-checked-indicator-box-shadow: none !default;
479 |
480 | $custom-control-focus-indicator-box-shadow: 0 0 0 1px $body-bg, 0 0 0 3px $brand-primary !default;
481 |
482 | $custom-control-active-indicator-color: $white !default;
483 | $custom-control-active-indicator-bg: lighten($brand-primary, 35%) !default;
484 | $custom-control-active-indicator-box-shadow: none !default;
485 |
486 | $custom-checkbox-radius: $border-radius !default;
487 | $custom-checkbox-checked-icon: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$custom-control-checked-indicator-color}' d='M6.564.75l-3.59 3.612-1.538-1.55L0 4.26 2.974 7.25 8 2.193z'/%3E%3C/svg%3E"), "#", "%23") !default;
488 |
489 | $custom-checkbox-indeterminate-bg: $brand-primary !default;
490 | $custom-checkbox-indeterminate-indicator-color: $custom-control-checked-indicator-color !default;
491 | $custom-checkbox-indeterminate-icon: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 4'%3E%3Cpath stroke='#{$custom-checkbox-indeterminate-indicator-color}' d='M0 2h4'/%3E%3C/svg%3E"), "#", "%23") !default;
492 | $custom-checkbox-indeterminate-box-shadow: none !default;
493 |
494 | $custom-radio-radius: 50% !default;
495 | $custom-radio-checked-icon: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'%3E%3Ccircle r='3' fill='#{$custom-control-checked-indicator-color}'/%3E%3C/svg%3E"), "#", "%23") !default;
496 |
497 | $custom-select-padding-x: .75rem !default;
498 | $custom-select-padding-y: .375rem !default;
499 | $custom-select-indicator-padding: 1rem !default; // Extra padding to account for the presence of the background-image based indicator
500 | $custom-select-line-height: $input-line-height !default;
501 | $custom-select-color: $input-color !default;
502 | $custom-select-disabled-color: $gray-light !default;
503 | $custom-select-bg: $white !default;
504 | $custom-select-disabled-bg: $gray-lighter !default;
505 | $custom-select-bg-size: 8px 10px !default; // In pixels because image dimensions
506 | $custom-select-indicator-color: #333 !default;
507 | $custom-select-indicator: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 4 5'%3E%3Cpath fill='#{$custom-select-indicator-color}' d='M2 0L0 2h4zm0 5L0 3h4z'/%3E%3C/svg%3E"), "#", "%23") !default;
508 | $custom-select-border-width: $input-btn-border-width !default;
509 | $custom-select-border-color: $input-border-color !default;
510 | $custom-select-border-radius: $border-radius !default;
511 |
512 | $custom-select-focus-border-color: lighten($brand-primary, 25%) !default;
513 | $custom-select-focus-box-shadow: inset 0 1px 2px rgba($black, .075), 0 0 5px rgba($custom-select-focus-border-color, .5) !default;
514 |
515 | $custom-select-sm-padding-y: .2rem !default;
516 | $custom-select-sm-font-size: 75% !default;
517 |
518 | $custom-file-height: 2.5rem !default;
519 | $custom-file-width: 14rem !default;
520 | $custom-file-focus-box-shadow: 0 0 0 .075rem $white, 0 0 0 .2rem $brand-primary !default;
521 |
522 | $custom-file-padding-x: .5rem !default;
523 | $custom-file-padding-y: 1rem !default;
524 | $custom-file-line-height: 1.5 !default;
525 | $custom-file-color: $gray !default;
526 | $custom-file-bg: $white !default;
527 | $custom-file-border-width: $border-width !default;
528 | $custom-file-border-color: $input-border-color !default;
529 | $custom-file-border-radius: $border-radius !default;
530 | $custom-file-box-shadow: inset 0 .2rem .4rem rgba($black,.05) !default;
531 | $custom-file-button-color: $custom-file-color !default;
532 | $custom-file-button-bg: $gray-lighter !default;
533 | $custom-file-text: (
534 | placeholder: (
535 | en: "Choose file..."
536 | ),
537 | button-label: (
538 | en: "Browse"
539 | )
540 | ) !default;
541 |
542 |
543 | // Form validation icons
544 | $form-icon-success-color: $brand-success !default;
545 | $form-icon-success: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$form-icon-success-color}' d='M2.3 6.73L.6 4.53c-.4-1.04.46-1.4 1.1-.8l1.1 1.4 3.4-3.8c.6-.63 1.6-.27 1.2.7l-4 4.6c-.43.5-.8.4-1.1.1z'/%3E%3C/svg%3E"), "#", "%23") !default;
546 |
547 | $form-icon-warning-color: $brand-warning !default;
548 | $form-icon-warning: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 8 8'%3E%3Cpath fill='#{$form-icon-warning-color}' d='M4.4 5.324h-.8v-2.46h.8zm0 1.42h-.8V5.89h.8zM3.76.63L.04 7.075c-.115.2.016.425.26.426h7.397c.242 0 .372-.226.258-.426C6.726 4.924 5.47 2.79 4.253.63c-.113-.174-.39-.174-.494 0z'/%3E%3C/svg%3E"), "#", "%23") !default;
549 |
550 | $form-icon-danger-color: $brand-danger !default;
551 | $form-icon-danger: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$form-icon-danger-color}' viewBox='-2 -2 7 7'%3E%3Cpath stroke='%23d9534f' d='M0 0l3 3m0-3L0 3'/%3E%3Ccircle r='.5'/%3E%3Ccircle cx='3' r='.5'/%3E%3Ccircle cy='3' r='.5'/%3E%3Ccircle cx='3' cy='3' r='.5'/%3E%3C/svg%3E"), "#", "%23") !default;
552 |
553 |
554 | // Dropdowns
555 | //
556 | // Dropdown menu container and contents.
557 |
558 | $dropdown-min-width: 10rem !default;
559 | $dropdown-padding-y: .5rem !default;
560 | $dropdown-margin-top: .125rem !default;
561 | $dropdown-bg: $white !default;
562 | $dropdown-border-color: rgba($black,.15) !default;
563 | $dropdown-border-width: $border-width !default;
564 | $dropdown-divider-bg: $gray-lighter !default;
565 | $dropdown-box-shadow: 0 .5rem 1rem rgba($black,.175) !default;
566 |
567 | $dropdown-link-color: $gray-dark !default;
568 | $dropdown-link-hover-color: darken($gray-dark, 5%) !default;
569 | $dropdown-link-hover-bg: $gray-lightest !default;
570 |
571 | $dropdown-link-active-color: $component-active-color !default;
572 | $dropdown-link-active-bg: $component-active-bg !default;
573 |
574 | $dropdown-link-disabled-color: $gray-light !default;
575 |
576 | $dropdown-item-padding-x: 1.5rem !default;
577 |
578 | $dropdown-header-color: $gray-light !default;
579 |
580 |
581 | // Z-index master list
582 | //
583 | // Warning: Avoid customizing these values. They're used for a bird's eye view
584 | // of components dependent on the z-axis and are designed to all work together.
585 |
586 | $zindex-dropdown-backdrop: 990 !default;
587 | $zindex-navbar: 1000 !default;
588 | $zindex-dropdown: 1000 !default;
589 | $zindex-fixed: 1030 !default;
590 | $zindex-sticky: 1030 !default;
591 | $zindex-modal-backdrop: 1040 !default;
592 | $zindex-modal: 1050 !default;
593 | $zindex-popover: 1060 !default;
594 | $zindex-tooltip: 1070 !default;
595 |
596 |
597 | // Navbar
598 |
599 | $navbar-border-radius: $border-radius !default;
600 | $navbar-padding-x: $spacer !default;
601 | $navbar-padding-y: ($spacer / 2) !default;
602 |
603 | $navbar-brand-padding-y: .25rem !default;
604 |
605 | $navbar-toggler-padding-x: .75rem !default;
606 | $navbar-toggler-padding-y: .25rem !default;
607 | $navbar-toggler-font-size: $font-size-lg !default;
608 | $navbar-toggler-border-radius: $btn-border-radius !default;
609 |
610 | $navbar-inverse-color: rgba($white,.5) !default;
611 | $navbar-inverse-hover-color: rgba($white,.75) !default;
612 | $navbar-inverse-active-color: rgba($white,1) !default;
613 | $navbar-inverse-disabled-color: rgba($white,.25) !default;
614 | $navbar-inverse-toggler-bg: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 32 32' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-inverse-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 8h24M4 16h24M4 24h24'/%3E%3C/svg%3E"), "#", "%23") !default;
615 | $navbar-inverse-toggler-border: rgba($white,.1) !default;
616 |
617 | $navbar-light-color: rgba($black,.5) !default;
618 | $navbar-light-hover-color: rgba($black,.7) !default;
619 | $navbar-light-active-color: rgba($black,.9) !default;
620 | $navbar-light-disabled-color: rgba($black,.3) !default;
621 | $navbar-light-toggler-bg: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg viewBox='0 0 32 32' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath stroke='#{$navbar-light-color}' stroke-width='2' stroke-linecap='round' stroke-miterlimit='10' d='M4 8h24M4 16h24M4 24h24'/%3E%3C/svg%3E"), "#", "%23") !default;
622 | $navbar-light-toggler-border: rgba($black,.1) !default;
623 |
624 | // Navs
625 |
626 | $nav-item-margin: .2rem !default;
627 | $nav-item-inline-spacer: 1rem !default;
628 | $nav-link-padding: .5em 1em !default;
629 | $nav-link-hover-bg: $gray-lighter !default;
630 | $nav-disabled-link-color: $gray-light !default;
631 |
632 | $nav-tabs-border-color: #ddd !default;
633 | $nav-tabs-border-width: $border-width !default;
634 | $nav-tabs-border-radius: $border-radius !default;
635 | $nav-tabs-link-hover-border-color: $gray-lighter !default;
636 | $nav-tabs-active-link-hover-color: $gray !default;
637 | $nav-tabs-active-link-hover-bg: $body-bg !default;
638 | $nav-tabs-active-link-hover-border-color: #ddd !default;
639 | $nav-tabs-justified-link-border-color: #ddd !default;
640 | $nav-tabs-justified-active-link-border-color: $body-bg !default;
641 |
642 | $nav-pills-border-radius: $border-radius !default;
643 | $nav-pills-active-link-color: $component-active-color !default;
644 | $nav-pills-active-link-bg: $component-active-bg !default;
645 |
646 |
647 | // Pagination
648 |
649 | $pagination-padding-x: .75rem !default;
650 | $pagination-padding-y: .5rem !default;
651 | $pagination-padding-x-sm: .5rem !default;
652 | $pagination-padding-y-sm: .25rem !default;
653 | $pagination-padding-x-lg: 1.5rem !default;
654 | $pagination-padding-y-lg: .75rem !default;
655 | $pagination-line-height: 1.25 !default;
656 |
657 | $pagination-color: $link-color !default;
658 | $pagination-bg: $white !default;
659 | $pagination-border-width: $border-width !default;
660 | $pagination-border-color: #ddd !default;
661 |
662 | $pagination-hover-color: $link-hover-color !default;
663 | $pagination-hover-bg: $gray-lighter !default;
664 | $pagination-hover-border: #ddd !default;
665 |
666 | $pagination-active-color: $white !default;
667 | $pagination-active-bg: $brand-primary !default;
668 | $pagination-active-border: $brand-primary !default;
669 |
670 | $pagination-disabled-color: $gray-light !default;
671 | $pagination-disabled-bg: $white !default;
672 | $pagination-disabled-border: #ddd !default;
673 |
674 |
675 | // Jumbotron
676 |
677 | $jumbotron-padding: 2rem !default;
678 | $jumbotron-bg: $gray-lighter !default;
679 |
680 |
681 | // Form states and alerts
682 | //
683 | // Define colors for form feedback states and, by default, alerts.
684 |
685 | $state-success-text: #3c763d !default;
686 | $state-success-bg: #dff0d8 !default;
687 | $state-success-border: darken($state-success-bg, 5%) !default;
688 |
689 | $state-info-text: #31708f !default;
690 | $state-info-bg: #d9edf7 !default;
691 | $state-info-border: darken($state-info-bg, 7%) !default;
692 |
693 | $state-warning-text: #8a6d3b !default;
694 | $state-warning-bg: #fcf8e3 !default;
695 | $mark-bg: $state-warning-bg !default;
696 | $state-warning-border: darken($state-warning-bg, 5%) !default;
697 |
698 | $state-danger-text: #a94442 !default;
699 | $state-danger-bg: #f2dede !default;
700 | $state-danger-border: darken($state-danger-bg, 5%) !default;
701 |
702 |
703 | // Cards
704 |
705 | $card-spacer-x: 1.25rem !default;
706 | $card-spacer-y: .75rem !default;
707 | $card-border-width: 1px !default;
708 | $card-border-radius: $border-radius !default;
709 | $card-border-color: rgba($black,.125) !default;
710 | $card-border-radius-inner: calc(#{$card-border-radius} - #{$card-border-width}) !default;
711 | $card-cap-bg: $gray-lightest !default;
712 | $card-bg: $white !default;
713 |
714 | $card-link-hover-color: $white !default;
715 |
716 | $card-img-overlay-padding: 1.25rem !default;
717 |
718 | $card-deck-margin: ($grid-gutter-width-base / 2) !default;
719 |
720 | $card-columns-count: 3 !default;
721 | $card-columns-gap: 1.25rem !default;
722 | $card-columns-margin: $card-spacer-y !default;
723 |
724 |
725 | // Tooltips
726 |
727 | $tooltip-max-width: 200px !default;
728 | $tooltip-color: $white !default;
729 | $tooltip-bg: $black !default;
730 | $tooltip-opacity: .9 !default;
731 | $tooltip-padding-y: 3px !default;
732 | $tooltip-padding-x: 8px !default;
733 | $tooltip-margin: 3px !default;
734 |
735 | $tooltip-arrow-width: 5px !default;
736 | $tooltip-arrow-color: $tooltip-bg !default;
737 |
738 |
739 | // Popovers
740 |
741 | $popover-inner-padding: 1px !default;
742 | $popover-bg: $white !default;
743 | $popover-max-width: 276px !default;
744 | $popover-border-width: $border-width !default;
745 | $popover-border-color: rgba($black,.2) !default;
746 | $popover-box-shadow: 0 5px 10px rgba($black,.2) !default;
747 |
748 | $popover-title-bg: darken($popover-bg, 3%) !default;
749 | $popover-title-padding-x: 14px !default;
750 | $popover-title-padding-y: 8px !default;
751 |
752 | $popover-content-padding-x: 14px !default;
753 | $popover-content-padding-y: 9px !default;
754 |
755 | $popover-arrow-width: 10px !default;
756 | $popover-arrow-color: $popover-bg !default;
757 |
758 | $popover-arrow-outer-width: ($popover-arrow-width + 1px) !default;
759 | $popover-arrow-outer-color: fade-in($popover-border-color, .05) !default;
760 |
761 |
762 | // Badges
763 |
764 | $badge-default-bg: $gray-light !default;
765 | $badge-primary-bg: $brand-primary !default;
766 | $badge-success-bg: $brand-success !default;
767 | $badge-info-bg: $brand-info !default;
768 | $badge-warning-bg: $brand-warning !default;
769 | $badge-danger-bg: $brand-danger !default;
770 |
771 | $badge-color: $white !default;
772 | $badge-link-hover-color: $white !default;
773 | $badge-font-size: 75% !default;
774 | $badge-font-weight: $font-weight-bold !default;
775 | $badge-padding-x: .4em !default;
776 | $badge-padding-y: .25em !default;
777 |
778 | $badge-pill-padding-x: .6em !default;
779 | // Use a higher than normal value to ensure completely rounded edges when
780 | // customizing padding or font-size on labels.
781 | $badge-pill-border-radius: 10rem !default;
782 |
783 |
784 | // Modals
785 |
786 | // Padding applied to the modal body
787 | $modal-inner-padding: 15px !default;
788 |
789 | $modal-dialog-margin: 10px !default;
790 | $modal-dialog-sm-up-margin-y: 30px !default;
791 |
792 | $modal-title-line-height: $line-height-base !default;
793 |
794 | $modal-content-bg: $white !default;
795 | $modal-content-border-color: rgba($black,.2) !default;
796 | $modal-content-border-width: $border-width !default;
797 | $modal-content-xs-box-shadow: 0 3px 9px rgba($black,.5) !default;
798 | $modal-content-sm-up-box-shadow: 0 5px 15px rgba($black,.5) !default;
799 |
800 | $modal-backdrop-bg: $black !default;
801 | $modal-backdrop-opacity: .5 !default;
802 | $modal-header-border-color: $gray-lighter !default;
803 | $modal-footer-border-color: $modal-header-border-color !default;
804 | $modal-header-border-width: $modal-content-border-width !default;
805 | $modal-footer-border-width: $modal-header-border-width !default;
806 | $modal-header-padding: 15px !default;
807 |
808 | $modal-lg: 800px !default;
809 | $modal-md: 500px !default;
810 | $modal-sm: 300px !default;
811 |
812 | $modal-transition: transform .3s ease-out !default;
813 |
814 |
815 | // Alerts
816 | //
817 | // Define alert colors, border radius, and padding.
818 |
819 | $alert-padding-x: 1.25rem !default;
820 | $alert-padding-y: .75rem !default;
821 | $alert-margin-bottom: $spacer-y !default;
822 | $alert-border-radius: $border-radius !default;
823 | $alert-link-font-weight: $font-weight-bold !default;
824 | $alert-border-width: $border-width !default;
825 |
826 | $alert-success-bg: $state-success-bg !default;
827 | $alert-success-text: $state-success-text !default;
828 | $alert-success-border: $state-success-border !default;
829 |
830 | $alert-info-bg: $state-info-bg !default;
831 | $alert-info-text: $state-info-text !default;
832 | $alert-info-border: $state-info-border !default;
833 |
834 | $alert-warning-bg: $state-warning-bg !default;
835 | $alert-warning-text: $state-warning-text !default;
836 | $alert-warning-border: $state-warning-border !default;
837 |
838 | $alert-danger-bg: $state-danger-bg !default;
839 | $alert-danger-text: $state-danger-text !default;
840 | $alert-danger-border: $state-danger-border !default;
841 |
842 |
843 | // Progress bars
844 |
845 | $progress-height: 1rem !default;
846 | $progress-font-size: .75rem !default;
847 | $progress-bg: $gray-lighter !default;
848 | $progress-border-radius: $border-radius !default;
849 | $progress-box-shadow: inset 0 .1rem .1rem rgba($black,.1) !default;
850 | $progress-bar-color: $white !default;
851 | $progress-bar-bg: $brand-primary !default;
852 | $progress-bar-animation-timing: 1s linear infinite !default;
853 |
854 | // List group
855 |
856 | $list-group-color: $body-color !default;
857 | $list-group-bg: $white !default;
858 | $list-group-border-color: rgba($black,.125) !default;
859 | $list-group-border-width: $border-width !default;
860 | $list-group-border-radius: $border-radius !default;
861 |
862 | $list-group-item-padding-x: 1.25rem !default;
863 | $list-group-item-padding-y: .75rem !default;
864 |
865 | $list-group-hover-bg: $gray-lightest !default;
866 | $list-group-active-color: $component-active-color !default;
867 | $list-group-active-bg: $component-active-bg !default;
868 | $list-group-active-border: $list-group-active-bg !default;
869 | $list-group-active-text-color: lighten($list-group-active-bg, 50%) !default;
870 |
871 | $list-group-disabled-color: $gray-light !default;
872 | $list-group-disabled-bg: $list-group-bg !default;
873 | $list-group-disabled-text-color: $list-group-disabled-color !default;
874 |
875 | $list-group-link-color: $gray !default;
876 | $list-group-link-heading-color: $gray-dark !default;
877 | $list-group-link-hover-color: $list-group-link-color !default;
878 |
879 | $list-group-link-active-color: $list-group-color !default;
880 | $list-group-link-active-bg: $gray-lighter !default;
881 |
882 |
883 | // Image thumbnails
884 |
885 | $thumbnail-padding: .25rem !default;
886 | $thumbnail-bg: $body-bg !default;
887 | $thumbnail-border-width: $border-width !default;
888 | $thumbnail-border-color: #ddd !default;
889 | $thumbnail-border-radius: $border-radius !default;
890 | $thumbnail-box-shadow: 0 1px 2px rgba($black,.075) !default;
891 | $thumbnail-transition: all .2s ease-in-out !default;
892 |
893 |
894 | // Figures
895 |
896 | $figure-caption-font-size: 90% !default;
897 | $figure-caption-color: $gray-light !default;
898 |
899 |
900 | // Breadcrumbs
901 |
902 | $breadcrumb-padding-y: .75rem !default;
903 | $breadcrumb-padding-x: 1rem !default;
904 | $breadcrumb-item-padding: .5rem !default;
905 |
906 | $breadcrumb-bg: $gray-lighter !default;
907 | $breadcrumb-divider-color: $gray-light !default;
908 | $breadcrumb-active-color: $gray-light !default;
909 | $breadcrumb-divider: "/" !default;
910 |
911 |
912 | // Carousel
913 |
914 | $carousel-control-color: $white !default;
915 | $carousel-control-width: 15% !default;
916 | $carousel-control-opacity: .5 !default;
917 |
918 | $carousel-indicator-width: 30px !default;
919 | $carousel-indicator-height: 3px !default;
920 | $carousel-indicator-spacer: 3px !default;
921 | $carousel-indicator-active-bg: $white !default;
922 |
923 | $carousel-caption-width: 70% !default;
924 | $carousel-caption-color: $white !default;
925 |
926 | $carousel-control-icon-width: 20px !default;
927 |
928 | $carousel-control-prev-icon-bg: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M4 0l-4 4 4 4 1.5-1.5-2.5-2.5 2.5-2.5-1.5-1.5z'/%3E%3C/svg%3E"), "#", "%23") !default;
929 | $carousel-control-next-icon-bg: str-replace(url("data:image/svg+xml;charset=utf8,%3Csvg xmlns='http://www.w3.org/2000/svg' fill='#{$carousel-control-color}' viewBox='0 0 8 8'%3E%3Cpath d='M1.5 0l-1.5 1.5 2.5 2.5-2.5 2.5 1.5 1.5 4-4-4-4z'/%3E%3C/svg%3E"), "#", "%23") !default;
930 |
931 | $carousel-transition: transform .6s ease-in-out !default;
932 |
933 |
934 | // Close
935 |
936 | $close-font-size: $font-size-base * 1.5 !default;
937 | $close-font-weight: $font-weight-bold !default;
938 | $close-color: $black !default;
939 | $close-text-shadow: 0 1px 0 $white !default;
940 |
941 |
942 | // Code
943 |
944 | $code-font-size: 90% !default;
945 | $code-padding-x: .4rem !default;
946 | $code-padding-y: .2rem !default;
947 | $code-color: #bd4147 !default;
948 | $code-bg: $gray-lightest !default;
949 |
950 | $kbd-color: $white !default;
951 | $kbd-bg: $gray-dark !default;
952 |
953 | $pre-bg: $gray-lightest !default;
954 | $pre-color: $gray-dark !default;
955 | $pre-border-color: #ccc !default;
956 | $pre-scrollable-max-height: 340px !default;
957 |
--------------------------------------------------------------------------------
/src/util/helpers.js:
--------------------------------------------------------------------------------
1 | import { LoadingState } from 'src/config/loading-state';
2 |
3 | // Helper to set global loading state
4 | export const setLoading = (isLoading = false) => LoadingState.$emit('toggle', isLoading);
5 |
--------------------------------------------------------------------------------
/src/util/resources.js:
--------------------------------------------------------------------------------
1 | import axios from 'axios';
2 |
3 | import { API_BASE } from 'src/config/constants';
4 |
5 | // Resources for /posts endpoint on API
6 | // @see https://github.com/mzabriskie/axios#creating-an-instance
7 | export const postsResource = axios.create({
8 | baseURL: `${API_BASE}/posts/`
9 | });
10 |
--------------------------------------------------------------------------------
/webpack/development.js:
--------------------------------------------------------------------------------
1 | const merge = require('webpack-merge');
2 |
3 | const webpackBase = require('./webpack.base.js');
4 | const plugins = require('./plugins');
5 |
6 | module.exports = merge(webpackBase, {
7 | devtool: 'inline-source-map',
8 | plugins: plugins.develop
9 | });
10 |
--------------------------------------------------------------------------------
/webpack/plugins.js:
--------------------------------------------------------------------------------
1 | const argv = require('minimist')(process.argv.slice(2));
2 | const BrowserSyncPlugin = require('browser-sync-webpack-plugin');
3 | const DashboardPlugin = require('webpack-dashboard/plugin');
4 | const ExtractTextPlugin = require('extract-text-webpack-plugin');
5 | const FaviconsWebpackPlugin = require('favicons-webpack-plugin');
6 | const HtmlWebpackPlugin = require('html-webpack-plugin');
7 | const imageminMozjpeg = require('imagemin-mozjpeg');
8 | const ImageminPlugin = require('imagemin-webpack-plugin').default;
9 | const OptimizeCssAssetsPlugin = require('optimize-css-assets-webpack-plugin');
10 | const path = require('path');
11 | const webpack = require('webpack');
12 | const WebpackCleanupPlugin = require('webpack-cleanup-plugin');
13 | const WebpackNotifierPlugin = require('webpack-notifier');
14 |
15 | const pkg = require('../package.json');
16 |
17 | const isProduction = !!((argv.env && argv.env.production) || argv.p);
18 |
19 | /**
20 | * Common plugins
21 | * @type {*[]}
22 | */
23 | const commonPlugins = [
24 | new HtmlWebpackPlugin({
25 | inject: 'body',
26 | template: path.resolve(__dirname, '../src/index.html'),
27 | favicon: path.resolve(__dirname, '../src/assets/images/favicon.ico')
28 | }),
29 | new webpack.LoaderOptionsPlugin({
30 | minimize: isProduction,
31 | debug: !isProduction,
32 | stats: {colors: true},
33 | eslint: {
34 | configFile: path.resolve(__dirname, '../.eslintrc'),
35 | failOnWarning: false,
36 | failOnError: true,
37 | },
38 | }),
39 | new ImageminPlugin({
40 | disable: false,
41 | optipng: {
42 | optimizationLevel: 7,
43 | },
44 | gifsicle: {
45 | optimizationLevel: 3,
46 | },
47 | pngquant: {
48 | quality: '65-90',
49 | speed: 4,
50 | },
51 | svgo: {
52 | removeUnknownsAndDefaults: false,
53 | cleanupIDs: false,
54 | },
55 | jpegtran: null,
56 | plugins: [imageminMozjpeg({
57 | quality: 75,
58 | })]
59 | }),
60 | new ExtractTextPlugin({
61 | filename: 'styles/[name].[hash].css',
62 | allChunks: true,
63 | }),
64 | ];
65 |
66 | /**
67 | * Develop plugins
68 | * @type {Array.<*>}
69 | */
70 | const developPlugins = [
71 | new DashboardPlugin(),
72 | new webpack.NamedModulesPlugin(),
73 | new WebpackNotifierPlugin({
74 | title: pkg.name,
75 | contentImage: path.join(__dirname, '../src/assets/images/logo.png')
76 | }),
77 | new BrowserSyncPlugin(
78 | {
79 | host: 'localhost',
80 | port: pkg.config.port,
81 | // Proxy the default webpack dev-server port
82 | proxy: 'http://localhost:8080/',
83 | notify: false,
84 | open: false,
85 | // Let webpack handle the reload
86 | codeSync: false
87 | }
88 | ),
89 | new webpack.optimize.OccurrenceOrderPlugin(),
90 | new webpack.NoEmitOnErrorsPlugin()
91 | ];
92 |
93 | /**
94 | * Production plugins
95 | * @type {Array.<*>}
96 | */
97 | const productionPLugins = [
98 | new webpack.DefinePlugin({
99 | 'process.env': {
100 | NODE_ENV: '"production"'
101 | }
102 | }),
103 | new WebpackCleanupPlugin(),
104 | new webpack.optimize.OccurrenceOrderPlugin(),
105 | new webpack.optimize.UglifyJsPlugin({
106 | compressor: {
107 | drop_console: true,
108 | warnings: false
109 | }
110 | }),
111 | new OptimizeCssAssetsPlugin({
112 | cssProcessorOptions: {
113 | discardComments: {
114 | removeAll: true
115 | }
116 | }
117 | }),
118 | new FaviconsWebpackPlugin({
119 | title: `${pkg.name} - ${pkg.description}`,
120 | logo: path.resolve(__dirname, '../src/assets/images/logo.png'),
121 | prefix: 'assets/img/icons/',
122 | statsFilename: 'iconstats-[hash].json',
123 | icons: {
124 | android: true, // Create Android homescreen icon. `boolean`
125 | appleIcon: true, // Create Apple touch icons. `boolean` or `{ offset: offsetInPercentage }`
126 | appleStartup: false, // Create Apple startup images. `boolean`
127 | coast: {offset: 25}, // Create Opera Coast icon with offset 25%. `boolean` or `{ offset: offsetInPercentage }`
128 | favicons: true, // Create regular favicons. `boolean`
129 | firefox: true, // Create Firefox OS icons. `boolean` or `{ offset: offsetInPercentage }`
130 | windows: true, // Create Windows 8 tile icons. `boolean`
131 | yandex: true // Create Yandex browser icon. `boolean`
132 | }
133 | })
134 | ];
135 |
136 | module.exports = {
137 | develop: commonPlugins.concat(developPlugins),
138 | production: commonPlugins.concat(productionPLugins)
139 | };
140 |
--------------------------------------------------------------------------------
/webpack/production.js:
--------------------------------------------------------------------------------
1 | const merge = require('webpack-merge');
2 |
3 | const webpackBase = require('./webpack.base.js');
4 | const plugins = require('./plugins');
5 |
6 | module.exports = merge(webpackBase, {
7 | plugins: plugins.production,
8 | performance: {
9 | hints: 'warning'
10 | }
11 | });
12 |
--------------------------------------------------------------------------------
/webpack/webpack.base.js:
--------------------------------------------------------------------------------
1 | const path = require('path');
2 | const argv = require('minimist')(process.argv.slice(2));
3 | const ExtractTextPlugin = require('extract-text-webpack-plugin');
4 |
5 | const isProduction = !!((argv.env && argv.env.production) || argv.p);
6 |
7 | module.exports = {
8 | entry: {
9 | app: [path.resolve(__dirname, '../src/main.js')]
10 | },
11 | output: {
12 | chunkFilename: '[id].chunk.js',
13 | filename: 'js/[name].[hash].js',
14 | path: path.resolve(__dirname, '../build'),
15 | publicPath: '/',
16 | sourceMapFilename: '[name].[hash].js.map',
17 | // pathinfo: true
18 | },
19 | resolve: {
20 | alias: {
21 | 'assets': path.resolve(__dirname, '../src/assets'),
22 | 'components': path.resolve(__dirname, '../src/components'),
23 | 'src': path.resolve(__dirname, '../src'),
24 | 'vue$': 'vue/dist/vue.js'
25 | },
26 | extensions: ['*', '.js', '.vue', 'html'],
27 | },
28 | devServer: {
29 | historyApiFallback: true,
30 | inline: true,
31 | contentBase: path.resolve(__dirname, '../src'),
32 | compress: true
33 | },
34 | module: {
35 | rules: [
36 | {
37 | enforce: 'pre',
38 | exclude: /node_modules/,
39 | loader: 'eslint-loader',
40 | test: /\.js?$/
41 | },
42 | {
43 | exclude: [/(node_modules)(?)/],
44 | test: /\.js$/,
45 | use: [{
46 | loader: 'babel-loader',
47 | query: {
48 | cacheDirectory: true
49 | }
50 | }]
51 | },
52 | {
53 | exclude: /node_modules/,
54 | loader: 'vue-loader',
55 | test: /\.vue$/
56 | },
57 | {
58 | exclude: /node_modules/,
59 | loader: 'html-loader',
60 | test: /\.html$/
61 | },
62 | {
63 | test: /\.css$/,
64 | loader: ['css-hot-loader'].concat(ExtractTextPlugin.extract({
65 | fallback: 'style-loader',
66 | use: [
67 | {
68 | loader: 'cache-loader'
69 | },
70 | {
71 | loader: 'css-loader',
72 | options: {
73 | sourceMap: !isProduction
74 | }
75 | }],
76 | })),
77 | },
78 | {
79 | test: /\.scss$/,
80 | include: path.resolve(__dirname, '../src'),
81 | loader: ['css-hot-loader'].concat(ExtractTextPlugin.extract({
82 | fallback: 'style-loader',
83 | use: [
84 | {
85 | loader: 'css-loader',
86 | options: {
87 | sourceMap: !isProduction
88 | }
89 | },
90 | {
91 | loader: 'resolve-url-loader',
92 | options: {
93 | sourceMap: !isProduction
94 | }
95 | },
96 | {
97 | loader: 'sass-loader',
98 | options: {
99 | sourceMap: !isProduction
100 | }
101 | },
102 | ],
103 | }))
104 | },
105 | {
106 | test: /\.(png|jpe?g|gif|svg|xml|json)$/,
107 | include: path.resolve(__dirname, '../src'),
108 | use: {
109 | loader: 'file-loader',
110 | options: {
111 | name: 'assets/img/[name].[ext]',
112 | },
113 | },
114 | },
115 | {
116 | test: /\.(ttf|eot)$/,
117 | include: path.resolve(__dirname, '../src'),
118 | use: {
119 | loader: 'file-loader',
120 | options: {
121 | name: 'assets/vendor/[name].[ext]',
122 | },
123 | },
124 | },
125 | {
126 | test: /\.woff2?$/,
127 | include: path.resolve(__dirname, '../src'),
128 | use: {
129 | loader: 'url-loader',
130 | options: {
131 | limit: 10000,
132 | mimetype: 'application/font-woff',
133 | name: 'assets/vendor/[name].[ext]',
134 | },
135 | },
136 | },
137 | {
138 | test: /\.(ttf|eot|woff2?|png|jpe?g|gif|svg)$/,
139 | include: /node_modules/,
140 | use: {
141 | loader: 'file-loader',
142 | query: {
143 | name: 'assets/vendor/[name].[ext]'
144 | },
145 | },
146 | },
147 | ],
148 | },
149 | };
150 |
--------------------------------------------------------------------------------