[EJS]カードレイアウトの作り方

EJSを使ってカードレイアウトを作っていきます。

まずはカード単体を p-card.ejsにて作成。

p-card.ejs  それぞれタイトル、テキスト、画像、カテゴリ名、投稿日を引数にしています。

<article class="p-card">
  <a href="">
    <div class="p-card__header">
      <figure class="p-card__figure">
        <img src="<%= image %>" alt="" >
      </figure>
    </div><!-- /.p-card__header -->
    <div class="p-card__body">
      <h3 class="p-card__title"><%= title %></h3>
      <p class="p-card__copy"><%- text %></p>
    </div><!-- /.p-card__body -->
    <div class="p-card__footer">
      <div class="p-card__category"><%- category %></div><!-- /.p-card__category -->
      <time class="p-card__time" datetime="<%- datetime %>"><%- time %></time>
    </div><!-- /.p-card__footer -->
  </a>
</article>

.p-card.scss ※ホバーすると画像が拡大するように作っています。

.p-card {
  width: 100%;
  height: 100%;
  background: transparent;
  box-shadow: 0 0 8px gray;
 
}
.p-card  a {
  width: 100%;
  height: 100%;
  display: flex;
  flex-direction: column;
}

.p-card a:hover {
  .p-card__figure img {
    transform: scale(1.3) translate(-40%, -40%);

  }
}

.p-card__figure {
  width: 100%;
  position: relative;
  overflow: hidden;
  
  }
  
  .p-card__figure::before {
    padding-top: 300 / 500 * 100%; //画像縦 / 横
    display: block;
    content: "";
  
  }
  
  .p-card__figure img {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    object-fit: cover;
    object-position: center;
    width: 100%;
    height: 100%;
    transition: all .3s;
  }

.p-card__body {
 padding: rem(26) rem(20);
}

.p-card__title{
font-size: rem(20);
line-height: 1.6
}

.p-card__copy{
font-size: rem(16);
line-height: 2;
margin-top: rem(21);
}

.p-card__footer{
  display: flex;
  align-items: center;
  margin-top: auto;
  padding: rem(0) rem(20) rem(25);

}

.p-card__category {
  padding: rem(5) rem(10);
  background-color: yellow;
  font-size: rem(16);

}

.p-card__time {
 font-size: rem(14);
 margin-left: auto;
}

.p-card__time {
 font-size: 14px;
 margin-left: auto;
}

index.ejs にて以下のように出力

<%- include('./parts/_p-card', {
    image: 'https://picsum.photos/id/1026/500/300',
    title: 'タイトル1',
    text: 'テキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト',
    category: 'カテゴリ1',
    datetime: '2021-10-24',
    time: '2021.10.24'
  } ) %>

すると以下のように表示されると思います。

p-cards.ejsの作成

次にp-card.ejsを囲むp-cards.ejsの作成

p-cards.ejs

<div class="p-cards">

  <div class="p-cards__item">
    <%- include('../parts/_p-card', {
      image: 'https://picsum.photos/id/1026/500/300',
      title: 'タイトル1',
      text: 'テキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト',
      category: 'カテゴリ1',
      datetime: '2021-10-24',
      time: '2021.10.24'
    } ) %>
  </div><!-- /.p-card__item -->

  <div class="p-cards__item">
    <%- include('../parts/_p-card', {
      image: 'https://picsum.photos/id/1026/500/300',
      title: 'タイトル1',
      text: 'テキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト',
      category: 'カテゴリ1',
      datetime: '2021-10-24',
      time: '2021.10.24'
    } ) %>
  </div><!-- /.p-card__item -->

  <div class="p-cards__item">
    <%- include('../parts/_p-card', {
      image: 'https://picsum.photos/id/1026/500/300',
      title: 'タイトル1',
      text: 'テキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト',
      category: 'カテゴリ1',
      datetime: '2021-10-24',
      time: '2021.10.24'
    } ) %>
  </div><!-- /.p-card__item -->

</div><!-- /.p-cards -->

p-cards.scss

.p-cards {
  display: flex;
  flex-wrap: wrap;
  padding: 0 25px;
  margin-top: -30px;
  margin-left: -20px;

}

.p-cards__item {
  width: calc(33.3% - 30px * 2 / 3);
  margin-left: 20px;
  margin-top: 30px;
}

index.ejs

<%- include('./parts/_p-cards') %>

すると以下のように表示されます。

3列表示が出来ました。
しかしせっかくのEJSなので、レイアウトはそのままにパーツとして使い回せるように次はfor文を使い作っていきましょう。

for文を使い繰り返し

p-cards.ejs

<div class="p-cards">

  <% for (var i=0; i < number; i++) { %>

  <div class="p-cards__item">
    <%- include('../parts/_p-card', {
      image: 'https://picsum.photos/id/1026/500/300',
      title: 'タイトル1',
      text: 'テキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキストテキスト',
      category: 'カテゴリ1',
      datetime: '2021-10-24',
      time: '2021.10.24'
    } ) %>
  </div><!-- /.p-card__item -->
  
  <% } %>

</div><!-- /.p-cards -->

index.ejs

<%- include('./parts/_p-cards',{number:3}) %>

すると同じように表示がされます。

ここでの仕組みはfor文の中にnumberの引数を入れていますので、

  <% for (var i=0; i < number; i++) { %>

includeの第2引数を変えていけばnumberの値が変わり繰り返しの数が変動します。

例えば number の値を「6」に変えてみると

<%- include('./parts/_p-cards',{number:6}) %>

カードが6個に増えました。
これを使えば使用する場所に応じて簡単にカード枚数を変えることが出来ます。

画像、テキストをそれぞれ変える方法

これまでの内容ではカードの数は変えることは出来ましたが、中身は変えれていません。
最終的にWordPress化するなら先程の方法で行けますが、静的サイトのままで公開するならカードの中身を変えないと行けません。
ここではforEachを使用していきます。

<div class="p-cards">
  <% 
  var images = [
  'https://picsum.photos/id/1026/500/300',
  'https://picsum.photos/id/1027/500/300',
  'https://picsum.photos/id/1028/500/300',
  ]; 
  var titles =[
  'タイトル1',
  'タイトル2',
  'タイトル3',
  ]; 
  var texts =[
  'テキスト1テキスト1テキスト1テキスト1',
  'テキスト2テキスト2テキスト2テキスト2',
  'テキスト3テキスト3テキスト3テキスト3',
  ]; 
  var categories =[
  'カテゴリ1',
  'カテゴリ2',
  'カテゴリ3',
  ]; 
  var datetimes =[
  '2020-10-24',
  '2020-10-25',
  '2020-10-26',
  ]; 
  var times =[
  '2020.10.24',
  '2020.10.25',
  '2020.10.26',
  ]; 
  %>

  <% images.forEach(function (image1, index) { %>
    <% const title1 = titles[index]; %>
    <% const text1 = texts[index]; %>
    <% const category1 = categories[index]; %>
    <% const datetime1 = datetimes[index]; %>
    <% const time1 = times[index]; %>
       
  
  <div class="p-cards__item">
    <%- include('../parts/_p-card', {
      image: image1,
      title:title1,
      text: text1,
      category: category1,
      datetime: datetime1,
      time:time1
    } ) %>
  </div><!-- /.p-card__item -->

  <% }); %>
  
  


</div><!-- /.p-cards ejs -->

すると以下のように表示がされます。

解説をしていくと

まずは、画像、タイトル、テキスト、カテゴリ、投稿日として入れ込む内容を配列で作っていきます。

<div class="p-cards">
  <% 
  var images = [
  'https://picsum.photos/id/1026/500/300',
  'https://picsum.photos/id/1027/500/300',
  'https://picsum.photos/id/1028/500/300',
  ]; 
  var titles =[
  'タイトル1',
  'タイトル2',
  'タイトル3',
  ]; 
  var texts =[
  'テキスト1テキスト1テキスト1テキスト1',
  'テキスト2テキスト2テキスト2テキスト2',
  'テキスト3テキスト3テキスト3テキスト3',
  ]; 
  var categories =[
  'カテゴリ1',
  'カテゴリ2',
  'カテゴリ3',
  ]; 
  var datetimes =[
  '2020-10-24',
  '2020-10-25',
  '2020-10-26',
  ]; 
  var times =[
  '2020.10.24',
  '2020.10.25',
  '2020.10.26',
  ]; 
  %>

次にforEach文を作っていきます。

  <% images.forEach(function (image1, index) { %>
    <% const title1 = titles[index]; %>
    <% const text1 = texts[index]; %>
    <% const category1 = categories[index]; %>
    <% const datetime1 = datetimes[index]; %>
    <% const time1 = times[index]; %>
       

ここで行っている処理は、

<% images.forEach(function (image1, index) { %>

変数imagesからforEachで値を出力
image1は配列の値を、indexは配列の番号を出力
つまり https://picsum.photos/id/1026/500/300 番号0
    https://picsum.photos/id/1027/500/300 番号1
    https://picsum.photos/id/1028/500/300 番号2
が順番に出力される

   <% const title1 = titles[index]; %>

imagesのforEachで出力された番号であるindexをtitlesに引数として入れる。
imagesの0番目である https://picsum.photos/id/1026/500/300が出力されている時、
titlesの0番目である タイトル1が出力される。それを定数 title1に代入する。


imagesの1番目である https://picsum.photos/id/1027/500/300が出力されている時、
titlesの1番目である タイトル2が出力される。それを定数 title1に代入する。


imagesの2番目である https://picsum.photos/id/1028/500/300が出力されている時、
titlesの2番目である タイトル3が出力される。それを定数 title1に代入する。

以下のような処理が実行されます。

それが同じようにtexts, categories, datetimes, times, にて処理が行われます。

つまり以上の処理で、
https://picsum.photos/id/1026/500/300, タイトル1, テキスト1テキスト1, カテゴリ1, 2020-10-24, 2020.10.24
https://picsum.photos/id/1027/500/300, タイトル2, テキスト2テキスト2, カテゴリ2, 2020-10-25, 2020.10.25
https://picsum.photos/id/1028/500/300, タイトル3, テキスト3テキスト3, カテゴリ3, 2020-10-26, 2020.10.26
の3つのパターンが出力されます。
それぞれの変数・定数をp-card.ejsのincludeの引数に渡してあげると、
p-card.ejsが3パターン出力されます。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です