<!DOCTYPE html>
<html>
<head>
<link data-require="highlight.js@*" data-semver="0.7.3" rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/highlight.js/7.3/styles/solarized_dark.min.css" />
<link data-require="highlight.js@*" data-semver="0.7.3" rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/highlight.js/7.3/styles/github.min.css" />
<link data-require="highlight.js@*" data-semver="0.7.3" rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/highlight.js/7.3/styles/default.min.css" />
<link href="https://fonts.googleapis.com/css?family=Lato" rel="stylesheet">
<link href="https://fonts.googleapis.com/earlyaccess/mplus1p.css" rel="stylesheet" />
<link rel="stylesheet" href="guide.css" />
<link rel="stylesheet" href="style.css" />
</head>
<body>
<div id="app">
<header class="guide-header">
<h1 class="guide-heading-1">Vue.js de スタイルガイド</h1>
</header>
<ul class="guide-categories">
<li><button @click="setCategory('')">ホーム</button></li>
<li v-for="catItem in categories"><button @click="setCategory(catItem)">{{ catItem }}</button></li>
</ul>
<div v-if="curCategory === ''" class="guide-home">
<div v-html="description"></div>
</div>
<div v-for="style in curStyles" class="guide-wrapper">
<h2 class="guide-heading-2">{{ style.title }}</h2>
<div v-html="style.html" class="guide-body"></div>
<hr class="guide-divide">
</div>
</div>
<script data-require="jquery@2.2.4" data-semver="2.2.4" src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.4/jquery.min.js"></script>
<script data-require="vue.js@*" data-semver="10.0.26" src="https://cdn.jsdelivr.net/vue/1.0.26/vue.min.js"></script>
<script data-require="axios@*" data-semver="0.018.0" src="https://unpkg.com/axios@0.18.0/dist/axios.min.js"></script>
<script data-require="marked@*" data-semver="0.3.5" src="https://cdnjs.cloudflare.com/ajax/libs/marked/0.3.5/marked.min.js"></script>
<script data-require="highlight.js@*" data-semver="0.7.3" src="//cdnjs.cloudflare.com/ajax/libs/highlight.js/7.3/highlight.min.js"></script>
<script src="guide.js"></script>
</body>
</html>
(function(global, $) {
var styles = {};
marked.setOptions({
langPrefix: '',
highlight: function(code, lang) {
return hljs.highlightAuto(code, [lang]).value;
}
});
var app = new Vue({
el: '#app',
data: {
description: '',
categories: [],
curCategory: '',
curStyles: {
title: '',
name: '',
category: '',
html: ''
}
},
created: function() {
this.getReadme();
this.getStyles();
},
methods: {
getReadme: function() {
axios.get('README.md')
.then(function (response) {
app.description = marked(response.data);
})
.catch(function (error) {
console.log(error);
});
},
getStyles: function() {
axios.get('./style.css')
.then(function (response) {
var res = response.data.match(/\/\*docs[\s\S]*?\*\//gm);
var tmpStyles = [];
res.forEach(function(v,i,a) {
var info, html, sample;
var title = '';
var name = '';
var category = '';
// html = a[i];
html = v;
// 情報取得
info = html.match(/\-\-\-[\s\S]*?\-\-\-/gm);
if (info !== null) {
if (info[0].match(/title: ?(.*)[\s\S]/) !== null) {
title = info[0].match(/title: ?(.*)[\s\S]/)[1];
}
if (info[0].match(/name: ?(.*)[\s\S]/) !== null) {
name = info[0].match(/name: ?(.*)[\s\S]/)[1];
}
if (info[0].match(/category: ?(.*)[\s\S]/) !== null) {
category = info[0].match(/category: ?(.*)[\s\S]/)[1];
if (app.categories.indexOf(category) == -1) {
app.categories.push(category);
}
}
}
// sample表示用HTML取得
sample = html.match(/\`\`\`html[\s\S]*?\`\`\`/gm);
// 不要情報削除
html = html.replace(/\/\*docs[\s\S]/, '')
.replace(/[\s\S]\*\//, '')
.replace(/\-\-\-[\s\S]*?\-\-\-/gm, '');
// Markdown形式に変換
html = marked(html);
// sample表示用HTMLが存在する場合、サンプル枠を追加
if (sample !== null) {
sample = sample[0].replace(/\`\`\`html[\s\S]/, '').replace(/[\s\S]\`\`\`/, '');
html = html + '<div class="sample">' + sample + '</div>';
}
// tmpStyles
tmpStyles[i] = {
title: title,
name: name,
category: category,
html: html
};
});
styles = tmpStyles;
app.setCategory('');
})
.catch(function (error) {
console.log(error);
});
},
sortData: function(ary) {
// 並び替えしながらセット
app.curStyles = ary.sort(function(a, b) {
return (a["name"] > b["name"]) ? 1 : -1;
});
},
setCategory: function(str) {
app.curCategory = str;
// 選択したカテゴリからデータ抽出
var tmpStyles = styles;
var filtered = $.grep(tmpStyles,
function(elm, index) {
return (elm.category === app.curCategory);
}
);
app.sortData(filtered);
}
}
});
})(window, jQuery);
* {
box-sizing: border-box;
}
/* text */
/*docs
---
title: .text-red
name: text-red
category: text
---
テキストカラー:<span class="text-red">赤■</span>
```html
<span class="text-red">.text-red</span>
```
*/
.text-red {
color: #f66;
}
/*docs
---
title: .text-blue
name: text-blue
category: text
---
テキストカラー:<span class="text-blue">青■</span>
```html
<span class="text-blue">.text-blue</span>
```
*/
.text-blue {
color: #66f;
}
/*docs
---
title: .text-green
name: text-green
category: text
---
テキストカラー:<span class="text-green">緑■</span>
```html
<span class="text-green">.text-green</span>
```
*/
.text-green {
color: #6A6;
}
/* button */
/*docs
---
title: .btn-1
name: btn-1
category: btn
---
ボタン1
```html
<p><a href="DUMMY" class="btn-1">ボタン1</a></p>
<button class="btn-1">ボタン1</button>
```
*/
button.btn-1 {
-webkit-appearance: none;
-moz-appearance: none;
}
.btn-1 {
display: inline-block;
min-width: 140px;
padding: 5px 10px;
border: 1px solid #aaa;
border-radius: 3px;
background: #fff;
outline: none;
color: #333;
font-size: 14px;
text-align: center;
text-decoration: none;
transition: background .2s ease-in-out;
cursor: pointer;
}
.btn-1:hover {
background: #eaeaea;
}
/* link */
/*docs
---
title: .link-1
name: link-1
category: link
---
リンク
```html
<p><a href="DUMMY" class="link-1">リンク1</a></p>
```
*/
.link-1 {
color: #006;
}
## Vue.jsでCSSのスタイルガイドを作ってみる
README.md を読み込ませて、ホーム用の文章を表示しています。
このスタイルガイドを利用するには、以下のファイルが必要です。
- index.html(ファイル名変更可)
- guide.css(スタイルガイド用CSS)
- guide.js(スタイルガイド用JS)
- README.md(ホーム表示用Markdown)
- style.css(サイトで使用するサンプルCSS)
とかとか、説明文を書いたりします。
* {
font-family: "lato", "Mplus 1p", sans-serif;
}
pre {
margin-bottom: 0;
}
.guide-header {
margin: 0 0 15px;
border-bottom: 1px solid #eaeaea;
}
.guide-categories {
margin: 0 0 30px -5px;
padding: 0;
list-style: none;
letter-spacing: -.4em;
}
.guide-categories li {
display: inline-block;
margin: 0 0 0 5px;
letter-spacing: normal;
}
.guide-categories button {
display: inline-flex;
justify-content: center;
align-items: center;
-moz-appearance: none;
-webkit-appearance: none;
min-width: 80px;
height: 30px;
vertical-align: top;
outline: none;
}
.guide-body {
color: #333;
}
.guide-heading-1 {
margin: 10px 0;
color: #333;
font-size: 28px;
font-weight: normal;
}
.guide-heading-2 {
padding: 0 0 0 7px;
border-left: 3px solid #666;
color: #333;
font-size: 20px;
}
.guide-divide {
margin: 20px 0;
border: 1px solid #eaeaea;
box-shadow: 0 2px 2px rgba(0,0,0,.05);
}
.sample {
padding: 1px 0 0;
border: 1px dashed #eaeaea;
border-top: 0;
}