カラーミーでレイアウトするHTML・CSS知識と役立つ豆知識

HTMLとCSSを学ぶ

ご自身でカスタマイズするために、HTML・CSSを独学で学ばれる方も多いと思います。

入門書で基礎をインプットしたあとは実践あるのみですが、カラーミーショップとの違いに戸惑うこともしばしば。

カスタマイズで混乱しがちなポイントにしぼって、すぐ使う知識をまとめました。
入門書を読み終わった方を対象にしていますので、復習がてらに手を動かしながらいろいろ試してみてください。

CSSの効き方と継承

指定したスタイルやレイアウトが思ったように効かないことは、しょっちゅうあります。

文字サイズを大きくしたいのに、余白をあけたいのに、配置を変えたいのに、などなど。原因はどこあるのでしょうか。
単純な文法誤りの場合や、CSSの効き方の理解が不十分である場合が考えられます。

CSS(Cascading Style Sheets)

CSSには二つのルールがあります。カスケードと継承です。
あとで紹介するデベロッパーツールで見て、実践のなかで学ぶことができますので、細かく知らなくても大丈夫です。

知らない方は大まかな内容として理解しておいて、細かい話は入門書でインプットしてください。

カスケード

カスケードをざっくり説明すると、同じ厳密度であれば、スタイルの差分であれば追加されますし、重複している場合は上書きされるルールがあります。

p {
  font-size: 16px;
  color: red;
}
p {
  color: blue; //あとから読み込んだスタイルで文字色が上書きされる
}

CSSのスタイルを上書きする場合は後述の優先度をみて決まります。

優先度は 1. 重要度 > 2. 厳密度 > 3. ソース順 です。
重要度が同じなら厳密度の多寡で決まりますし、厳密度が同じであれば、ソース順で決まります。

1. 重要性…厳密度やソース順に関係なく、!importantを付けることで最優先される。
効きすぎるのでつけなくてよい箇所にはつけないのがよいマナーです。

2. 厳密度…セレクタに応じて点数が割り振られていて、点数の多寡でどのスタイルが反映するか決まる。
インラインスタイル(HTML内にstyle=~と直接書く)> id属性 > class属性 > タグ要素
追加したスタイルが効かない場合は(簡単に言うと)厳密度を上げる指定をすればよい。

3. ソース順…読み込み順であとのほうが優先度が高い。先 < 後
たとえば、独自タグ< {$slideshow_html} >でbxSliderを設置した場合、カラーミーショップの共通HTML内でbxSliderのCSSが読み込まれます。
bxSliderのスタイルを共通CSSに書いても効かないのは、共通CSSの読み込み順が先であるためです。

どの順番で読み込んでいるかは、ブラウザでソースコードを表示させることでわかります。
読み込み順が変更できない場合は、厳密度を上げるか、重要度を上げるかで対応します。

実際に作業しているときは、デベロッパーツールで優先度を確認します。優先度順に表示されますので、ここでの内容は大まかに知っておけば大丈夫です。

継承

スタイルが親要素から子要素へ受け継がれるルールです。
継承したりしなかったりする項目がありますが、これも細かい知識はほとんど使いません。

たとえば、親要素 body のスタイルが内包している子要素 div に文字フォントが継承します。このルールがあるおかげで、子要素に対してスタイルを入れなくてよいのです。

もちろん、カスケードを使って上書き可能です。

<style>
  body { font-family: sans-serif; }  
</style>

<body>
  <div>子要素(font-family: sans-serif;を継承)</div>
  <div>子要素(font-family: sans-serif;を継承)</div>
</body>

似たような〇〇の区別

HTML・CSSで「似たような〇〇の違いがわからない」ことがあります。
感覚的な部分もあって、入門書ではなかなか伝わらないところでもあります。
このあとはそういう部分を中心に解説します。

まず、用語についておさらいします。
<要素名 属性名="属性値">  例:<div class="sidebar">

要素名…div、a、img など。HTMLタグや簡単にタグと呼んだりします
属性名…class、href、src など。
属性値…sidebar、https://sample-site.com、./picture.jpg

class属性とid属性

class…同じ属性値を1ページに複数回書いても大丈夫。
id…固有の識別子。同じ属性値は1ページにつき一回しか書いてはいけません(文法上の制約)。

文法上の制約以外に、感覚的にも使い分けします(明示的な意味合いを持たせる場合など)。
idを使わずともほとんどの場合classで代用できますので、もし悩むようならclassで書けばいいです。

カラーミーショップの既存テンプレートでは、idをこんな風に使っています。
かならずしも必須ではありませんが、使い方のニュアンスは伝わると思います。

ページ内のパーツ・レイアウトに対して
<div id="header">~</div>
<div id="side">~</div>
<div id="main">~</div>
<div id="contents">~</div>
<div id="footer">~</div>

テンプレートページに対して
<body id="top">~</body>
<body id="product">~</body>

CSSの厳密度の違い

CSSの厳密度は id > class です(idの方がよく効きます)。
もちろん、きちんと指定してやれば、idでなくても classでも十分効きますので、厳密度の違いでidとclassを使い分けることはあまりありません。

大外の要素(<body>など) に id を用意しておくと、ページごとに指定しやすいです(トップページの〇〇に××を効かせたい、商品ページの〇〇に△△ を効かせたいなど)。

#top p { margin: 10px; }
#product p { margin: 20px; }

jQueryのセレクタとして

セレクタを$('#id')のように、id属性値で指定する方が処理のパフォーマンスが上がります。

paddingとmargin

パディング(padding)、マージン(margin)は要素間の余白を調整するさいによく使います。
境界線(border)の内(パディング)、外(マージン)で区別します。

境界線がない場合はどちらで指定すべきか迷いますが、同じ結果になることも多く、そういう場合はどちらでもいいんですよね。

使い分けの場面(マージン)

ブロック要素の縦方向のマージンは相殺されます
たとえば、上要素(margin-bottom: 30px;)下要素 (margin-top: 20px;)では、50pxの余白にならずに、重なるようにして30pxの余白になります。

・マージンは透明です
背景色、背景画像を入れる場合は、境界線(border)の内側の領域に表示されます。

・ネガティブマージンという便利技
margin: -10px; とマージンにマイナス値を指定すると、その分の領域が広がります。

たとえば、親要素(padding: 1em;)子要素(margin: 0 -1em;)とすれば、子要素の左右にあった余白を打ち消すことができます。
スマートフォン時に特定の要素だけ横幅いっぱいに広げたいときや、横並び商品の左右のpaddingを打ち消して、見出し行の先頭と揃えるときに使います。

negative-margin-block
<div style="padding: 1em; background-color: red;">
  <div style="margin: 0 -1em; background-color: yellow;">
    negative-margin-block
  </div>
</div>

横方向のセンタリング(中央揃え)

インライン要素ブロックレベル要素の違いはよく理解しておく必要があります。
思ったようにレイアウトできない場合に、インライン要素・ブロックレベル要素の違いによることがよくあるからです 。
たとえば、インライン要素では幅(width)、高さ(height)の指定が効きません。(それらはpaddingで調整するわけですが)違いがちょいちょいあるわけです。

センタリングについても異なります。
センタリングの文法、スタイルを指定する場所、親要素の幅に対してセンタリングしている点に注意です。

インライン要素のセンタリング

text-alignはインライン要素を左揃え・右揃え・中央揃えするプロパティです。
子要素(インライン要素)を含む親要素(ブロックレベル要素である場合が多い)に対して、text-align: center;します。

<div style="text-align: center; width: 100%;">
  <a href="#">中央揃え</a>
</div>

ブロックレベル要素のセンタリング

子要素に対して、margin: 0 auto;で行います。
親要素(ブロックレベル要素)の幅に対して、センタリングします。

<div style="width: 100%;">
  <div style="margin: 0 auto; width: 10%;">中央揃え</div>
</div>

縦方向のセンタリング (中央揃え)

親要素(灰色)の中央に子要素(画像)を配置します。
横方向のセンタリングは子要素がインライン要素なので、親要素にtext-align: center;とすればOKです。

縦方向については、3つのスタイルを指定します(y-centeringがそれです)。
position: relative; top: 50%;は親要素の高さのちょうど真ん中から子要素を配置します(親要素にheight指定がないとズレます)。

transform: translateY(-50%);は子要素の高さ半分を上方向にずらします。
これらが組み合わさって、縦方向のセンタリングが実現します。

<div style="height: 200px; background-color: gray; text-align: center;">
  <img class="y-centering" src="https://naeco.jp/wp/wp-content/uploads/2018/08/iine_banner.jpg"> 
</div>

<style>
  .y-centering { 
    position: relative;
    top: 50%;
    transform: translateY(-50%);
  }
</style>

要素を非表示にする

レンダリングする・しない、アニメーションする・しない、などの違いがあります。
display: none;を一番使いますが、これでは無理な場合もありますので、別の方法も覚えておきます。

display: none;

display: none; (非表示) display: block; (表示・block以外でもよい)
opacity: 0、visibility: hidden;と違って、要素は削除されます(配置されませんので、間が詰まります)。

レスポンシブテンプレートでよく見かけます。
たとえば、スマートフォン閲覧時にコンテンツを非表示にする場合は display: none; を使います。

<style>
@media (max-width: 768px) {
  .hidden-phone {
    display: none;
  }
}
</style>

<div class="hidden-phone">
  コンテンツ
</div>

opacity: 0;

opacity: 0; (透明) → opacity: 1; (不透明)
display: none;と違って、要素はそこに配置されています。要素を透明にすることで、非表示にしています。
transitionでアニメーションさせることができます。

たとえば、bxSlider ロード中に画像が縦並びになり、レイアウトが崩れるさいに使います。
opacity: 0; であらかじめ非表示にして、ロードが終わるまで見えないようにしておきます。
bxSliderのonSliderLoadはコールバック関数です(興味があれば検索してみて)。
ロード後はopacityで0→1。

<style>
#slider { 
  opacity: 0;
  transition: opacity .3s linear;//ふんわりとアニメーションする
}
</style>

<script type="text/javascript">
$(function() {
  $('#slider').bxSlider({
    onSliderLoad: function(index){
      $('#slider').css('opacity','1');
    }
  });
});
</script>

visibility: hidden;

visibility: hidden;(非表示)、visibility: visible;(表示)
挙動はopacityと大体似ていて、非表示であっても要素はそこに配置されています。
即時表示しますので、ふんわりと表示させるのには向いていないようです。

下のような入れ子の場合、childが表示されます。
opacityの場合、親要素で透明にすると子要素は不透明にできませんので、こういう部分に違いがあります。

<div style="visibility: hidden;">
  parent
  <div style="visibility: visible;">
    child
  </div>
</div>

並べる。レイアウトのあれこれ

インライン要素とブロックレベル要素

HTMLはブロックレベル要素で書けば、自動的に縦方向に並びます。ということで、縦方向の並べ方はほとんど問題になりません。並べる場合に問題になるのは横方向です。

インライン要素は幅(width)、高さ(height)の指定が効きません。続けて書くと自動的に横並びになります。ブロックレベル要素は、続けて書くと自動的に改行して、下にブロックを表示します。

div要素はブロックレベル要素ですが、display: inline-block; を指定すると、幅・高さを指定できるブロックレベル要素の特徴と、横並びにできるインライン要素の特徴を兼ね備えた要素にすることができます。

高さ(height)を指定しないと、自動的には揃いません。
カスタマイズするときは揃えたいときが多いので、高さが自動的に揃う・揃わないが使い分けのポイントです。

inlineとinline-blockの場合、改行すると余分な余白が空きます
収めるには、幅(width)をすこし減らす工夫が必要です(ネット検索するとCSSで回避する別の方法も見つかります)。

left-block
right-block
高さが揃わない
<div style="display: inline-block; padding: 1em; background-color: red; width: 50%;">left-block</div>
<div style="display: inline-block; padding: 1em; background-color: yellow; width: 50%;">right-block<br>高さが揃わない</div>


<div>~</div>の2行だったところを、改行せずにくっつければぴったり収まります。
このレイアウト崩れよく見かけるので、意図しない隙間があるときは改行を削って確かめてみましょう。読みにくくはなりますが、簡単に修正できます。

left-block
right-block
高さが揃わない
<div style="display: inline-block; padding: 1em; background-color: red; width: 50%;">left-block</div><div style="display: inline-block; padding: 1em; background-color: yellow; width: 50%;">right-block<br>高さが揃わない</div>

float

float: left; すると、ブロックライン要素でも横並びします。幅の端まで左から順に詰めて並べます。clear: both; は横並び解除の意味(clearfixを使うことのほうが多い)。
これまでは一番よく使われていました

カラーミーキットのサイドバーとコンテンツ、商品一覧の横並びも float: left; で並べています。

その他の既存テンプレートもfloatで横並びさせていることが多いです。その場合、自動的には高さは揃いませんので、jquery.tile.jsを使って、要素の高さを計算して揃えています。

参考)フロート - Web 開発を学ぶ | MDN

side
contents
高さが揃わない

<div style="float: left; padding: 1em; background-color: red; width: 30%;">side</div>
<div style="float: left; padding: 1em; background-color: yellow; width: 70%;">contents<br>高さが揃わない</div>
<br style="clear: both;">

table-cell

表組み(table)して並べる方法。高さが自動的に揃う点と高さ方向の中央揃えが効きます
レスポンシブ時は display: block; にして、横幅に応じて1列表示に変更します。

スマートフォンのヘッダーメニューで、ロゴ+アイコンを並べるのによく使われています。

logo
search
高さが揃う
login
<div style="display: table; width: 100%;">
  <div style="display: table-cell; padding: 1em; background-color: red; width: 25%; vertical-align: middle;">logo</div>
  <div style="display: table-cell; padding: 1em; background-color: yellow; width: 50%; vertical-align: middle;">search<br>高さが揃う</div>
  <div style="display: table-cell; padding: 1em; background-color: green; width: 25%; vertical-align: middle;">login</div>
</div>

flex

フレックスボックスという比較的新しい機能です。多機能なので今後はflexが普及していくはずです
MONOテンプレートのおすすめ商品の横並びは display: flex; で実装しています。

参考)CSS flexible box の利用 - CSS: カスケーディングスタイルシート | MDN
参考)Can I use… Support tables for HTML5, CSS3, etc

logo
search
高さが揃う
login
<div style="display: flex;">
  <div style="padding: 1em; background-color: red; width: 25%;">logo</div>
  <div style="padding: 1em; background-color: yellow; width: 50%;">search<br>高さが揃う</div>
  <div style="padding: 1em; background-color: green; width: 25%;">login</div>
</div>


商品画像を並べたいときにも便利です(特に横幅にぴったり寄せたいとき)。
というのも、カラーミーキットなどがそうですが、floatで商品横並びさせるときはパディング(padding)が入っていて、上の要素と左右の端を揃えたいのに揃わないということもしばしば。

flexだとぴったりよせられます(justify-content: space-between;の効果)。
レスポンシブも可能で、widthの指定で対応します。アイテム間の余白もwidthの調整で空けるのがよいでしょう。

Item 1
Item 2
高さが揃う
Item 3
Item 4
<div class="flex-container">
  <div class="flex-item">Item 1</div>
  <div class="flex-item">Item 2</div>
  <div class="flex-item">Item 3</div>
  <div class="flex-item">Item 4</div>
</div>

<style>
.flex-container {
  display: flex;
  justify-content: space-between;
  flex-wrap: wrap;
  width: 100%;
}
.flex-item {
  width: 23%;
  background-color: #ccc; 
  padding: 1em;
}
@media (max-width:768px){
  .item{
    width: 48%; //4カラム → 2カラムのレスポンシブ対応
  } 
}
</style>

配置する。レイアウトのあれこれ

margin

下の例では(左)画像、(右)文字で、両方ともインライン要素ですと、自動的に横並びします。
文字を高さ方向に中央揃えしたいことがあります。

そういう場合にマージンを入れることで、簡単に要素を上下させることができます。
ネガティブマージンも可能で、マイナス値を入れると要素は上にあがります。

たとえば、カテゴリー画像とカテゴリー名をきれいに並べたい場合は、横幅に対して文字をどれくらいの割合で下げるか計算して、セットすればよいです。
例) margin-top: calc(7.5% - 5px); /*画像の半分を目安に、文字分を微調整*/

calcを使えば、レスポンシブ時にも高さ方向の中央揃えが可能です。
自分で計算できるときは、上で説明した表組み(table)よりも断然使いやすいです。

position

マージンでできることは極力マージンでやります。positionは挙動がややこしいので。

position: relative;(相対位置) や position: absolute;(絶対位置) で基準点を定めて、top/bottom/left/rightで場所指定します。

絶対位置の基準点はデフォルトではページの左上隅です。
親要素に position: relative; とすると親要素の左上隅が基準点に変わります。
position: absolute; で座標指定する場合は、今回のように親要素の左上隅を基準点にする使い方が多いです。

浮いているので、通常のブロックレベル要素の配置とは大分異なります(そういう意味でわりと理解しづらいです)。
レイヤーのように重なりますので、z-indexで重なり順を操作します。

スマートフォン用ドロワーメニュー、パソコン用ドロップダウンメニュー、最上部に貼りつくヘッダーメニュー、モーダルウィンドウ(画面全面に半透明のグレーの背景色にキャンペーン告知をするウィンドウ)などは、positionを使って実装しています。

parent-red
child-yellow
child-green
<div style="position: relative; background-color: red; width: 100px; height: 100px; margin-bottom: 100px;">
  parent-red
  <div style="position: absolute; left: 50px; top: 50px; background-color: yellow; width: 100px; height: 100px;">
    child-yellow
  </div>
  <div style="position: absolute; left: 100px; top: 100px; background-color: green; width: 100px; height: 100px;">
  child-green
  </div>
</div>

カラーミーショップをカスタマイズする知識

ここから先は、知っておくと得するカラーミーショップの知識になります。
すこしマニアックかもしれませんが、カスタマイズしているとおいおい疑問に思うところです。

文書型宣言 !DOCTYPE html について

カラーミーショップでHTML5を使っているショップサイトは、わりと見かけます。
動画を<video>タグで埋め込んでいたり、セマンティックなタグ<header><section><aside>などを使ってコーディングされているのを見かけます。

HTML5はブラウザが対応していたら動くとは聞いていたんですが、気になっていたのは文書型宣言との関係です。どうなんでしょう?
テンプレートを書く場合は、XHTMLで書くほうが正しいのかモヤモヤしていました。

というのも、カラーミーショップの文書型定義は、いまでもXHTML 1.0なんですよね。
中のコードはXHTMLで書いてありますし。

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">


ということで調べてきました。

もともとは、文書型宣言には文書型定義(文書構造の定義との紐づけ)とDOCTYPEスイッチ(描画モードの指定)の役割があたえられていましたが、HTML5以降は描画モードの指定にしか使っていません。

いまは先頭に<!DOCTYPE html>と書いてあれば、ブラウザは「標準準拠モード(もっとも新しい標準に準拠)」でHTML・CSS解析し、何も書いていない場合は「後方互換モード」でHTML・CSS解析します。
古い文書型宣言の場合(=カラーミーショップが該当)は、各ブラウザで 「完全標準準拠」「ほぼ標準準拠」「後方互換」 から自動的にモードを選んでくれるそうです。

さて、カラーミーショップのショップサイトでページの情報を表示してみます(下画像はFirefoxのもの)。
標準準拠モードになっていますね。新しい標準(HTML5・CSS3やその他)でページを描画しています。

文書型定義が XHTML になっているからといって、昨今のモダンブラウザはそれどおりに構文解釈している訳ではないんですね。
新規制作の場合はHTML5で書くのがよさそうです。 修正の場合は、、、現状と要望に合わせて。


下記の資料を読むところでは、カラーミーショップで書いてあるXHTMLの構文は不正確なHTMLとして、ブラウザが気を利かせて解釈して表示してくれているらしい(えーマジで?)。

参考)Activating Browser Modes with Doctype
参考)XHTML | MDN

文字エンコーディングはEUC-JP

文字化けするときは、これが原因の場合が多いです。
font-familyの日本語フォント名(全角文字)が文字化けして、ページに反映していなかったのを見たことがあります(どういう風にしてなったのか)。
その他でもたまに影響が出ますので注意が必要です。

カラーミーショップのお問い合わせはカスタマイズしにくいので、WordPressで凝ったお問い合わせページを作りたいことがあります。

文字コードがWordPress(UTF-8)、カラーミーショップ(EUC-JP)と異なるため、WordPressのお問い合わせフォームにクエリパラメータ経由で商品名を渡したい場合は全角文字をエンコードしておく必要があります。
EUC-JP → UTF-8 のエンコードにはJavaScriptのencodeURI関数を使います。

CSSの外部ファイルは共通HTMLの先頭でも読み込む

入門書では<head>内に書くように説明されていますが、昔から<body>内に書いても読み込みます(たぶん文法エラーですが)。
JavaScriptの外部ファイルも同様です。

たとえば、カラーミーショップの共通HTMLの先頭に

<link rel="stylesheet" type="text/css" href="./js/jquery.bxslider/jquery.bxslider.css" />
<script type="text/javascript" src="./js/jquery.bxslider/jquery.bxslider.min.js"></script>

旧ショッピングカート決済画面は結構いじれる

カラーミーショップの旧ショッピングカートはCSSが使えます。
線や背景色、背景画像は変更できそうなのはわかると思います。線の太さ・色や背景色のグレー、ショップ名の部分に画像を入れたり、ボタンを今風のフラットなタイプに変えているショップをみかけます。

その他には、
・セレクタを駆使して、画像を別の画像に差し替えたり(background-imageに入れる)
・ボタンの画像を変えたり
・商品名のリンクをpointer-event: none;で飛ばなくしたり (ブログ+どこでもカラーミーのときに)
・疑似要素 ::before ::after で文字やアイコンフォントを追加したり
・不要部分をdisplay: none;で非表示にしたり
いろいろなパーツが差し替え可能です。

HTMLのエラーの見つけ方

どのブラウザも、ある程度のエラーは適当に解釈して表示してくれます。
エラーがあってもレイアウトが崩れることなく表示されてしてしまうので、気づかないことも多いです。

テンプレート編集の編集画面で見かける赤字は大体エラーです。赤字の前後を注意深くみましょう。
</div>が赤くなっていることがありますが、<div>~</div>の対応が正しいか確認します。問題ないこともあります。

下の例では、</spam>になっていますので、スペルミスです。


Firefoxでは「ページのソースを表示」すると、エラー部分は赤字で表示されます(エラーでないこともあります)。
余談ですが、外部ファイルの読み込み順もソースを見ないことにはわかりません。カスタマイズする知識として、ソースコードは一度見ておいた方がよいです。

文法誤りもしっかりチェックしてくれます。
・よくあるのが、閉じタグが対応していないコード
・インライン要素の内側にブロックレベル要素を入れたり
・要素が正しい入れ子の状態になっていなかったり
・ダブルクォーテーション「”」を全角文字で書いたり
・コード内の文字参照(&nbsp;など)。HTML5からは文法エラーです


トラブったときに焦らないためにも、こまめにバックアップすること、やったことをメモすることです。
それさえできていれば、エラー時の原因究明もなんとかなります。

おわりに

今回は重要な三つを取り上げました。

  • CSSの効き方
  • インライン要素とブロックレベル要素(レイアウト崩れの原因になる)
  • レイアウトの方法

今回紹介したレイアウトの話は難易度高めですが、あれ以上難しい話もそうないので、凹む必要はないです(とはいえよく使います)。
自分でレイアウト変更したい場合は、腰を据えて学びましょう。

いまあるものをいじりたいのであれば、それほどハードルを上げなくてもよいと思います。
フォントを大きくしたり、色を変えたり、余白を増やしたりは、デベロッパーツールで修正箇所が見つけられれば、すぐにできます。

デベロッパーツールは必須なので、自習してください。

執筆者

えいじ@naeco.jp この記事を書いた人

メーカー系情報システム部門出身の個人事業主。
自作するのが好きですぐに試したくなる、凝り性なWebエンジニア。
カラーミーショップ、モールなどのECについて記事にしています。

ご相談・お問い合わせはこちら