読者です 読者をやめる 読者になる 読者になる

Nukindex 開発ブログ

アダルトサイトNukindexの開発ブログです

reset.cssを自作してみた

リセットCSSを導入した。

作成したもの

reset.css(自作)

期待する動き

デフォルトのマージンやパディングなどの無駄なスタイリングを削除し、ブラウザ間の差異を吸収する。

結果

不明

手順など

styles ディレクトリに reset.css を作成する。

ROOT_DIRECTORY/
  + node_modules/
  + build/
  + source/
  |   + renderer/
  |   |   + components/
  |   |   |   + app/
  |   |   |   |   + view.js
  |   |   |   |   + style.css
  |   |   |   |
  |   |   |   + header/
  |   |   |       + view.js
  |   |   |       + style.css
  |   |   |
  |   |   + renderer.js
  |   |
  |   + styles/
  |   |   + reset.css
  |   |
  |   + index.html
  |
  + gulpfile.babel.js
  + .babelrc
  + package.json

source/index.html

reset.css を読み込めるようにする。

<!DOCTYPE html>
<html>
<head>
  <title>Nukindex</title>
  <link rel="stylesheet" href="./styles/reset.css">
  <link rel="stylesheet" href="./styles/bundle.css">
</head>
<body>
  <div id="app"></div>

  <script src="./renderer/bundle.js"></script>
</body>
</html>

source/styles/reset.css

とりあえずよく気になる部分をリセットしてみた。

html, body {
  margin: 0;
  padding: 0;
  font-weight: 300;
  font-family:
      -apple-system, BlinkMacSystemFont,
      "Helvetica Neue",
      "Segoe UI",
      "Noto Sans Japanese",
      "ヒラギノ角ゴ ProN W3",
      Meiryo,
      sans-serif;
}

p {
  line-height: 1.5;
  font-size: 16px;
}

h1 {
  margin: 0;
  padding: 0;
  line-height: 1.2;
  font-size: 32px;
}

h2,
h3,
h4,
h5,
h6 {
  margin: 0;
  padding: 0;
  line-height: 1.2;
  font-size: 16px;
}

ol,
ul {
  margin: 0;
  padding: 0;
  list-style: none;
}

input,
textarea {
  box-sizing: border-box;
}

input:focus,
textarea:focus {
  outline: none;
}

[hidden="true"] {
  display: none;
}

gulpfile.babel.js

CSSをビルドする関数を追加する。 React 用のCSSはビルドしたくないので gulp.src から renderer 以下を除外する。

import gulp from "gulp";
import browserify from "browserify";
import babelify from "babelify";
import source from "vinyl-source-stream";
import transform from "vinyl-transform";
import cssModulesify from "css-modulesify";

gulp.task("build", () => {
  buildHTML();
  buildCSS();
  buildRenderer();
});

function buildHTML() {
  gulp.src(["source/**/*.html", "!source/renderer/**/*"])
      .pipe(gulp.dest("build"));
}

function buildCSS() {
  gulp.src(["source/**/*.css", "!source/renderer/**/*"])
      .pipe(gulp.dest("build"));
}

function buildRenderer() {
  browserify({
    "entries": ["source/renderer/renderer.js"],
    "extensions": ["", ".js", ".jsx", ".css"]
  }).plugin(cssModulesify, {
    "output": "./build/styles/bundle.css"
  }).transform(babelify).bundle()
      .pipe(source("bundle.js"))
      .pipe(gulp.dest("build/renderer"));
}

nukindex.com

CSS Moduleを導入した

View に関してはこれで一段落。

作成したもの

CSS Moduleの導入

期待する動き

cssファイルを使ってコンポーネント毎にスタイルを定義する。ビルド時にひとつのcssファイルにまとめて出力する。

結果

成功

事例が探せなかったので苦労した。

手順など

コンポーネントディレクトリに style.css を作成する。

ROOT_DIRECTORY/
  + node_modules/
  + build/
  + source/
  |   + renderer/
  |   |   + components/
  |   |   |   + app/
  |   |   |   |   + view.js
  |   |   |   |   + style.css
  |   |   |   |
  |   |   |   + header/
  |   |   |       + view.js
  |   |   |       + style.css
  |   |   |
  |   |   + renderer.js
  |   |
  |   + index.html
  |
  + gulpfile.babel.js
  + .babelrc
  + package.json

gulpfile 内にCSSモジュールの使用準備をする。

$ npm install css-modulesify --save-dev

gulpfile.babel.js

browserify のプラグインとして導入する。

import gulp from "gulp";
import browserify from "browserify";
import babelify from "babelify";
import source from "vinyl-source-stream";
import transform from "vinyl-transform";
import cssModulesify from "css-modulesify";

gulp.task("build", () => {
  buildHTML();
  buildRenderer();
});

function buildHTML() {
  gulp.src("source/**/*.html")
      .pipe(gulp.dest("build"));
}

function buildRenderer() {
  browserify({
    "entries": ["source/renderer/renderer.js"],
    "extensions": ["", ".js", ".jsx", ".css"]
  }).plugin(cssModulesify, {
    "output": "./build/styles/bundle.css" // CSSファイルの出力先を指定
  }).transform(babelify).bundle()
      .pipe(source("bundle.js"))
      .pipe(gulp.dest("build/renderer"));
}

source/renderer/components/header/style.css

普通のCSSファイル。

.container {
  background-color: #fff;
}

.title {
  margin: 16px 0 12px;
  padding: 0 24px;
}

.description {
  margin: 12px 0 16px;
  padding: 0 24px;
}

source/renderer/components/header/view.js

stylesCSSファイルをインポートする。 styles にはCSSファイルに定義したクラス名がプロパティとして入る。 className にそのプロパティを入れ込む。

import React from "react";
import CSSModules from "react-css-modules";
import styles from "./style";

export default class Component extends React.Component {
  render() {
    return (
      <header className={styles.container}>
        <h1 className={styles.title}>
          <a href="/">Nukindex</a>
        </h1>

        <p className={styles.description}>
          毎日のおかずを提供するサイトです
        </p>
      </header>
    );
  }
}

source/index.html

ビルドしたCSSファイルを読み込む。

<!DOCTYPE html>
<html>
<head>
  <title>Nukindex</title>
  <link rel="stylesheet" href="./styles/bundle.css">
</head>
<body>
  <div id="app"></div>

  <script src="./renderer/bundle.js"></script>
</body>
</html>

React のスタイリングとしては CSS in JS がメジャーなのか、 CSS modules の使用例はあまり見つけられなかった。

先例がないと初心者にはつらい。

nukindex.com

React + Redux 開発用のディレクトリ構造を作った

先を見据えて丁寧に作っていきたいが先がどうなるか分からない。

作成したもの

React + Redux 開発用のディレクトリ構造

期待する動き

コンポーネント毎に独立したディレクトリ構造を作る

結果

成功

手順など

ROOT_DIRECTORY/
  + node_modules/
  + build/
  + source/
  |   + renderer/
  |   |   + components/
  |   |   |   + app/
  |   |   |   |   + view.js
  |   |   |   |
  |   |   |   + header/
  |   |   |       + view.js
  |   |   |
  |   |   + renderer.js
  |   |
  |   + index.html
  |
  + gulpfile.babel.js
  + .babelrc
  + package.json

source/index.html

React 描画エリアと React 描画ファイルを配置する。

<!DOCTYPE html>
<html>
<head>
  <title>Nukindex</title>
</head>
<body>
  <div id="app"></div>

  <script src="./renderer/bundle.js"></script>
</body>
</html>

source/renderer/renderer.js

React コンポーネントと DOM を結びつける。

React クラスは処理部分で使用していないが、これを削除するとブラウザ実行時にエラーになる。

import React from "react";
import ReactDOM from "react-dom";

import App from "./components/app/view";

ReactDOM.render(
  <App />,
  document.getElementById("app")
);

source/renderer/components/header/view.js

コンポーネントは components 以下に配置していく。 コンポーネント毎に MVC を用意していく予定なので js ファイルではなくディレクトリにまとめる。

import React from "react";

export default class HeaderComponent extends React.Component {
  render() {
    return (
      <header>
        <h1>
          <a href="/">Nukindex</a>
        </h1>

        <p>毎日のおかずを提供するサイトです</p>
      </header>
    );
  }
}

source/renderer/components/app/view.js

コンポーネントは別コンポーネントを呼び出し、使用することができる。

import React from "react";

import HeaderComponent from "../header/view";

export default class App extends React.Component {
  render() {
    return (
      <div>
        <HeaderComponent />
      </div>
    );
  }
}

詰まったのは ReactDOM クラスが React クラスに依存しているところくらいだった。

React クラスは処理部分で使用していないが、これを削除するとブラウザ実行時にエラーになる。

nukindex.com

gulpを使ってES2015+で書いたReactのファイルをトランスパイルする。

日本語がよく分からなくなってきた。 「gulpを使ってES2015+で書いたReactのファイルをトランスパイルする。」 もっと分かりやすい題にならないのか。

とにかく題の通り環境構築に成功した。 失敗の積み重ねの上に成功した。

主にbrowserify周りの失敗だ。 なんとなくWebpackが流行っている理由が分かった気がする。

作成したもの

gulp build コマンド

期待する動き

JSX と ES2015+ で書かれた依存関係のあるファイルを、ブラウザで実行可能な bundle.js ファイルとして出力する。

結果

成功

手順など

ROOT_DIRECTORY/
  + node_modules/
  + build/
  + source/
  |   + index.html
  |   + renderer.js
  |
  + gulpfile.babel.js
  + .babelrc
  + package.json

React のファイルを作成する

$ npm install react --save-dev
$ npm install react-dom --save-dev

index.html

React 描画エリアになる要素を作っておく。ここでは <div id="app"></div> のとこ。

React のファイルはコンポーネントごとに分けて作成することになるので、トランスパイル時に bundle.js としてまとめて出力し、それを HTML で読み込む予定。

<!DOCTYPE html>
<html>
<head>
  <title>Nukindex</title>
</head>
<body>
  <div id="app"></div>

  <script src="./renderer/bundle.js"></script>
</body>
</html>

renderer.js

とりあえず簡単なコンポーネントを作ってレンダリングする。

今回の目的はブラウザで読み込んで描画できる形で出力することなので複雑にしない。

import React from "react";
import ReactDOM from "react-dom";

class App extends React.Component {
  render() {
    return (
      <div>
        <h1>Nukindex</h1>
      </div>
    );
  }
}

ReactDOM.render(
  <App />,
  document.getElementById("app")
);

gulpfile を設定する。

$ npm install browserify --save-dev
$ npm install babelify --save-dev
$ npm install vinyl-source-stream --save-dev
$ npm install vinyl-transform --save-dev

gulpfile.babel.js

返り値はストリームになるのでそれをパイプしていくとのこと(謎)

gulpデビュー - Nukindex 開発ブログ

これな。。。こうなると思ってたけどstream関係の仕様が謎過ぎてめっちゃ時間かかった。 とりあえず中身。

import gulp from "gulp";
import browserify from "browserify";
import babelify from "babelify";
import source from "vinyl-source-stream";
import transform from "vinyl-transform";

gulp.task("build", () => {
  buildHTML();
  buildRenderer();
});

function buildHTML() {
  gulp.src("source/**/*.html")
      .pipe(gulp.dest("build"));
}

function buildRenderer() {
  // ブラウザでも読み込める形にしてくれるやつ。
  // 主に require などで依存関係を持つファイルをうまいこと結合してくれる。
  browserify({
    "entries": ["source/renderer.js"],
    // 指定した拡張子を省略できる。
    // import Abc from "abc.js"; を import Abc from "abc"; と書ける。
    "extensions": ["", ".js", ".jsx"]
  }).transform(babelify).bundle()  // transform も babelify も bundle も謎
      .pipe(source("bundle.js"))  // source も謎
      .pipe(gulp.dest("build/renderer"));
}

ここらへんはググっても「これが正解!」みたいなやり方を見つけられなかった。 みんな同じところで同じように困ってるみたい。

gulp.src("source/renderer.js")
    .pipe(babel({
      "target": "browser",
      "presets": ["react", "es2015"]
    })
    .pipe(rename("bundle.js"))
    .pipe(gulp.dest("source/renderer"));

とか

browserify({
  "entries": ["source/renderer.js"],
  "extensions": ["", ".js", ".jsx"],
  "presets": ["react", "es2015"]
})
    .pipe(gulp.dest("build/renderer"));

みたいな感じでシンプルにできるようにしてほしい。。。

.babelrc

わすれがち

{
  "presets": [
    "react",
    "es2015"
  ]
}

ここまでで gulp build コマンドによりブラウザで読み込める bundle.js ファイルを出力することができる。

めんどくさかった上にすっきりしない。

nukindex.com

gulpデビュー

「Reactデビュー」と言う題で書き始めたが、道が遠いので「gulpデビュー」に変えた。

gulpというのはタスクランナーの一種で、現在最も主流であるらしい。 感覚的には開発の面倒なことを自動化してくれるお助けツールだ。 一部では脱gulpの動きもあるようだが、どうも便利そうなので使っておきたい。

作成したもの

gulp build コマンド

期待する動き

source ディレクトリのファイルを build ディレクトリへ移動する

結果

成功

手順など

npmの初期化

> npm init

gulp のパッケージをインストール

gulp 自体も ES2015+ で書きたいのでそのためのパッケージもインストール

> npm install babel --save-dev
> npm install babel-preset-es2015 --save-dev
> npm install gulp --save-dev
> npm install gulp-babel --save-dev

必要なディレクトリ、ファイルを作成

ROOT_DIRECTORY/
  + node_modules/
  + build/
  + source/
  |   + index.html
  |
  + gulpfile.babel.js
  + .babelrc
  + package.json

.babelrc

babel の設定ファイル。 babel は ES2015+ で書かれたJSファイルを古い環境でも実行できるように変換するツール。

{
  "presets": [
    "es2015"
  ]
}

gulpfile.babel.js

gulp コマンドの設定ファイル。

import gulp from "gulp";

// この部分が gulp build コマンドで動く
gulp.task("build", () => {
  buildHTML();
});

function buildHTML() {
  // gulp で操作する対象ファイルを指定
  // 返り値はストリームになるのでそれをパイプしていくとのこと(謎)
  gulp.src("source/**/*.html")
      // 最後は出力先を指定する
      .pipe(gulp.dest("build"));
}

返り値はストリームになるのでそれをパイプしていくとのこと(謎)

ここな。このブラックボックス感が嫌でいつもライブラリ使わずにフルスクラッチしてるんだけど。

でもそんなこと言い出したらマシン語まで理解しないといけないような気もしてきた。 どこで妥協するかの問題か。

ここまでで gulp build コマンドが通って期待どおりの動きとなった。

調べながらだと時間がかかる。

nukindex.com