20190804のCSSに関する記事は4件です。

固定幅+変動幅混在でヘッダ固定スクロールしたい~flexboxはいいぞ~

目次

  • 対象問題
  • 課題点
  • 解決策
  • 補足

対象問題

下記条件を同時に満たす表を作成する

  • 固定幅の表の一番最後の列だけ変動幅にする
  • ヘッダは固定でボディ部だけスクロールする 固定幅+変動幅混在とヘッダ固定スクロール.png

課題点

  • ヘッダ固定でスクロールするには
    • thead, tbody タグにdisplay: blockまたはdisplay: inline-blockを設定する必要がある。
  • 変動幅を実現できない
    • テーブルをブロック要素にすると、変動幅のセルが中の要素に合わせて縮むのでレイアウトが崩れてしまう。

解決策

テーブル部品をflexbox化する

※下記のCodePenをResultだけ表示させること

See the Pen flexbox_table by T.T (@tkrtmy1031) on CodePen.

flexbox.html
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <link rel="stylesheet" type="text/css" href="./css/flexbox.css" />
    <link rel="stylesheet" type="text/css" href="./css/view.css" />
    <title>flexbox</title>
</head>
<body>
    <table>
        <thead>
            <tr>
                <th class="seq">No</th>
                <th class="fixable">固定幅列</th>
                <th class="flexible">変動幅列</th>
            </tr>
        </thead>
        <tbody>
            <tr>
                <td class="seq">1</td>
                <td class="fixable">400px</td>
                <td class="flexible">テーブル幅の余り</td>
            </tr>
            <tr>
                <td class="seq">2</td>
                <td class="fixable">400px</td>
                <td class="flexible">テーブル幅の余り</td>
            </tr>
            <tr>
                <td class="seq">3</td>
                <td class="fixable">400px</td>
                <td class="flexible">テーブル幅の余り</td>
            </tr>
            <tr>
                <td class="seq">4</td>
                <td class="fixable">400px</td>
                <td class="flexible">テーブル幅の余り</td>
            </tr>
            <tr>
                <td class="seq">5</td>
                <td class="fixable">400px</td>
                <td class="flexible">テーブル幅の余り</td>
            </tr>
       </tbody>
    </table>
</body>
</html>

flexbox.css
/* テーブル制御用CSS */

/* 固定+変動幅混在レイアウト */

/* 1. table部品をflexbox化 */
thead, tbody, tr, th, td { 
    display: flex;
}

/* 2. セルの折り返し */
thead, tbody, tr {
    flex-direction: row;
    flex-wrap: wrap;
}

/* 3. 各行をテーブル幅いっぱいに整列 */
tr {
    width: 100%;
}

/* 4. 列(固定幅) */
.seq {
    width: 50px;
}

.fixable {
    width: 400px;
}

/* 5. 列(変動幅) */
.flexible {
    flex: 1;
}


/* スクロール(ヘッダ固定) */

/* 6. スクロール表示 */
tbody {
    height: 150px; 
    overflow-y: scroll;
}

補足

対象問題の条件を同時に満たさなくていいなら、下記の方法で作成できる。

  • 固定幅の表の一番最後の列だけ変動幅にする
    • 変動幅にしたい列のwidthを設定しない

See the Pen Flexible Table by T.T (@tkrtmy1031) on CodePen.

  • ヘッダは固定でボディ部だけスクロールする
    • テーブル部品をブロック要素化する(正確にはinline-block)

See the Pen Body Scroll by T.T (@tkrtmy1031) on CodePen.






※とはいえ、全く同一の部品を作るのは難しい。用途と工数に応じて的確に使い分けること。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

laravelで外部ファイルを使用してcssを適用する手順

laravelでcssを適用する時に躓いたので、メモをします。

  1. /public/css/にcssファイルを作成します。例としてstyles.cssという名前で作成したとします。

  2. viewファイルに以下の一文を記述します。
    <link rel="stylesheet" href="{{ asset('css/styles.css') }}">
    httpsで表示するページなら、assetの部分がsecure_assetになります。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

[HTML/CSS] ある要素をWindowに無理やり合わせつつ、拡大率に対応する

はじめに

「普段は画面の横幅いっぱいに表示されてほしいけど、ブラウザの拡大率を操作したら拡大はされてほしい」を出来るだけ簡単に(雑に)実現する。
(ブラウザ依存、PC以外の動作は見ていません)

背景

普通は、

  1. 要素のwidthを100%にする
  2. Viewportで調整する1

で、解決すると思いますが、
例えば、対象の要素を直接触れないとか、画面ないの一部の要素だけに適用したいとかで使えない想定。

方針

transformでどんなサイズでも合わせてしまえばいいじゃない

結果

CSSだけで実現できないかと思ったが、早々に断念しJavascriptを利用。
(Javascriptを使うのであれば如何様にもやり方はあると思うが)

  • スクロールバーに対応してない
  • ほかのWidth:100%のものと横幅が合わなくなる

あたりは対応していない。

※Windowにfitするように試してるのでCodePenだと確認し辛いです。

See the Pen Element Window Fit Test by minilabo (@minilabo) on CodePen.

試したこと

CSSだけで実現

最初はCSSだけで実現できないかと試したが、scale + calcを上手く扱えず、時間がかかりそうだったので断念

example.css
/* 計算結果の単位のせいか適用されない */
.ng {
  transform: scale(calc(100vw/2))
}

/* これだと動く */
.ok {
  transform: scale(calc(100/2))
}

諦めてJavascript使って動的に適用する

Javascriptで大きさを合わせるだけだと拡大率などに関わらず、Windowに合うだけなので、そのあたりの情報を調査する。

  • 拡大しているかの判定
    innerWidthが表示領域、outerWidthがwindowの大きさを表す。
    ブラウザの機能で拡大するとinnerWidthが小さくなるので、outerWidthに比べてinnerWidthが小さい場合、拡大されている。
main.js
// スクロールバーなどが含まれる為、このまま計算すると少しずれる(が、雑に丸める)
const zoom = Math.round(window.outerWidth / window.innerWidth);
  • transformでサイズを変更しても親の要素のサイズに反映されない
    element.getBoundingClientRect()で高さを取得して、親要素に適用(単純にelement.offsetHeightだと、transform前の大きさがとれる)
    この関数はとても便利だが、環境によってはダメかも?(参考: https://developer.mozilla.org/ja/docs/Web/API/Element/getBoundingClientRect)
main.js
// tramsformの適用後の高さを取得して、親要素に適用してスペースを確保(今回は高さのみ)
parent.style.height = element.getBoundingClientRect().height;

  1. Viewportで初期の拡大率を1以下にすると問題があるよという記事を見たので参考に > もう逃げない。HTMLのviewportをちゃんと理解する 

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

ナビゲーションバーをグリッドレイアウトにしてみた

1ヶ月くらい、HTMLの書籍を読んで、一通り目を目を通した。
(といっても、まだ、理解できていないが...)

タイトルの通り、ナビゲーションバーをグリッドレイアウトでやってみた。

レイアウト

navbar.PNG

ソース1

最初に書いたソースは下記の通り。

grid_practice1.html
<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>グリッドレイアウト 練習</title>
    <link rel="stylesheet" href="base.css">
</head>
<body>
    <header>
        <nav id="nav_bar">
            <ul>
                <li><a href="#">ナビ1</a></li>
                <li><a href="#">ナビ2</a></li>
                <li><a href="#">ナビ3</a></li>
                <li><a href="#">ナビ4</a></li>
                <li><a href="#">ナビ5</a></li>
                <li><a href="#">ナビ6</a></li>
            </ul>
        </nav>
    </header>
</body>
</html>
base.css
body {
    width: 600px;
    margin-left: auto;
    margin-right: auto;
}

/* ヘッダー */
header {
    text-align: center;
}

#nav_bar {
    display: grid;
    grid-template-columns: 1fr 1fr 1fr;
    grid-template-rows: auto auto;
    margin: 0;
    padding: 0;
}

#nav_bar li {
    list-style: none;
    margin: 0;
    padding: 0;
    border: solid 1px;
    background: #f3f3f3;
}

#nav_bar a {
    text-decoration: none;
    margin: 0;
    padding: 0;
}

結果1

上記のソースで行けると思っていたが、結果は下のようなレイアウトになった...
navbar2.PNG

cssが適用されていないのかと思ったが、きちんとソースには書いている..
デバッグモードで確認してみた。
すると、下の画像のように右に2つ領域が割り当てられているのを確認できた。
navbar2_debug.PNG

左端に、カーソルを合わせると、下のようになった。
navbar2_debug2.PNG

ソース2

上の画像から、nav要素はきちんと適用されているが、ul要素には適用されていない。
ソースを変更してみた。

grid_practice2.html
<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>グリッドレイアウト 練習</title>
    <link rel="stylesheet" href="base.css">
</head>
<body>
    <header>
        <nav>←元々、ここにidを書いていた
            <ul id="nav_bar">←ここにidを移動した
                <li><a href="#">ナビ1</a></li>
                <li><a href="#">ナビ2</a></li>
                <li><a href="#">ナビ3</a></li>
                <li><a href="#">ナビ4</a></li>
                <li><a href="#">ナビ5</a></li>
                <li><a href="#">ナビ6</a></li>
            </ul>
        </nav>
    </header>
</body>
</html>

すると、望んだレイアウトになった。
idを書く場所を間違えていた...
グリッドの適用先が間違ってた...

おわりに

なぜ、うまくいかなかったのか?
nav要素に適用すれば、ul要素が自動的に割り当てられると思っていた。
けど、グリッドを適用したのはnavであって、ulではない。
だから、うまくいかなかった。
レイアウトの左上にulが埋め込まれ、そのなかで上から順にli要素が並んだ。

適用先をulに変えることで、li要素が左上から右に割り当てられた。
(この考えであってるはず...)

ここまで読んでくれた上で、自分の考えが間違えていたら、指摘してくれるとありがたいです。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む