一部の画像や動画に異なるUIがありますが、CSS修正の有無によるものでプログラム部分には影響はありません。
今回はrecordsテーブルに格納している収支データを画面に出力していきます。
前回の記事はこちら↓
今回は「SQLの発行」と「呼び出しデータをテーブルに出力」の2本柱で進めていきます。
SQLの発行
まず収支データを登録しているrecordsテーブルのデータの入り方をおさらいします。
赤枠で囲ったカラムを出力します。
赤枠左から3カラム分とmemoカラムはそのまま呼び出して出力すればOKですが、それ以外のカラムは数値になっているので、文字列の値を出力できるようにする必要があります。
このrecordsに記録されている数値は、該当するテーブルのidと連動しています。
なのでSQLを発行するときに、それぞれのテーブルを見に行って文字列を取得するようにします。
そのSQLというのが以下になります。
<tr class="p-table__head">
<th>収支日</th>
<th>タイトル</th>
<th>収入</th>
<th>支出</th>
<th>支出詳細</th>
<th>操作</th>
</tr>
<!--以下を追加-->
<?php
$sql_dataoutput = 'SELECT records.id, records.date, records.title, records.amount,
spending_category.name, income_category.name, records.type,
payment_method.name, creditcard.name, qr.name, records.memo, records.input_time
FROM records
LEFT JOIN spending_category ON records.spending_category = spending_category.id
LEFT JOIN income_category ON records.income_category = income_category.id
LEFT JOIN payment_method ON records.payment_method = payment_method.id
LEFT JOIN creditcard ON records.credit = creditcard.id
LEFT JOIN qr ON records.qr = qr.id
ORDER BY date DESC, input_time DESC';
まずはSELECTで取得するカラムを指定しています。基本形は「〇〇.△△」で〇〇にテーブル名を、△△にカラム名を記述します。
今回はrecordsテーブルからそのまま取得するデータはrecords.カラム名、他のテーブルを参照するデータは該当テーブル名.nameと記述します。
そしてLEFT JOINで該当カラムの数値とidが連携しているテーブルをつなげて参照します。
基本形は「LEFT JOIN 参照するテーブル名 ON records.カラム名 = 参照するテーブル名.id」です。
最後にデータの日付が近いものを先頭に並べるよう「date DESC」で指示をし、データの日付が同じ場合は入力した日付が遅いデータを先頭に並べるよう「input_time DESC」で指示をしています。
実際にどんなデータが返ってくるのかを見たい場合は、phpMyAdminのrecordsテーブルを開き、SQLタブで実行すると連結されたデータを見ることができます。
続いてこれまで通りSQLの実行と得られた値を変数に格納しループを始めます。
サンプルとして入れていた<tr>〜</tr>はコメントアウトか削除してください。
$stmt_dataoutput = $db->prepare($sql_dataoutput);
sql_check($stmt_dataoutput, $db);
$stmt_dataoutput->bind_result(
$id,
$date,
$title,
$amount,
$spending_category,
$income_category,
$type,
$paymentmethod,
$credit,
$qr,
$memo,
$input_time
);
while ($stmt_dataoutput->fetch()) : ?>
<tr class="p-table__item item1">
<td> 2022/06/11 </td>
<td> サンプル1 <span> (食費) <i class="fa-regular fa-message" onclick=""></i> </span> </td>
<td></td>
<td> ¥3,000 <span> (クレジット) </span> </td>
<td>カードB </td>
<td>
<form action="./record-edit.php" method="POST">
<input type="hidden" name="record_id" value="1">
<input type="submit" class='c-button c-button--bg-green edit fas' id="" value="">
</form>
<a class='c-button c-button--bg-red delete' id="" href='' onclick="">
<i class="fa-regular fa-trash-can"></i>
</a>
</td>
</tr>
<?php endwhile;?> <!--←追記忘れず!-->
<!--以下は削除-->
<tr class="p-table__item item2">
<td>
<input type="hidden" name="record_id" value="2">
2022/06/11
</td>
<td class="">
サンプル2 <span> (給料) <i class="fa-regular fa-message" onclick=""></i> </span>
</td>
<td> ¥200,000 </td>
<td><span></span> </td>
<td></td>
<td>
<form action="./record-edit.php" method="POST">
<input type="hidden" name="record_id" value="2">
<input type="submit" class='c-button c-button--bg-green edit fas' id="" value="">
</form>
<a class='c-button c-button--bg-red delete' id="" href='' onclick="">
<i class="fa-regular fa-trash-can"></i>
</a>
</td>
</tr>
それでは取り出したデータを出力していきます。
データを出力
出力テーブルの左カラムから順番に実装していきます。
trタグのclassにデータidを出力
現在trタグのclassにitem1とデータidを入れています。この「1」がrecordsのidと連携するようにします。
<!--書き換え前-->
<tr class="p-table__item item1">
<!--書き換え後-->
<tr class="p-table__item item<?php echo h($id); ?>">
日付を出力
<!--書き換え前-->
<td>2022-05-02</td>
<!--書き換え後-->
<td><?php echo date('Y/m/d', strtotime($date)); ?></td>
date関数を使って「ー」区切りを「/」区切りにするよう変換して出力しています。
date関数は第1引数にフォーマットを指定し、第2引数に指定したフォーマットに変換したいタイムスタンプを指定します。第2引数は省略することができ、省略した場合は現在の時刻が自動的に入れられます。
ここまでを指定すると収支日カラムだけDBと連携します。(データの数はDBに登録しているデータ数によって異なります)
タイトル・カテゴリー出力
続いてタイトルとカテゴリーを出力します。カテゴリーについてはデータが支出か収入かで呼び出す変数が異なるのでif文を使って条件分岐を行います。
<!--書き換え前-->
<td>
サンプル1
<span> (食費) <i class="fa-regular fa-message" onclick=""></i> </span>
</td>
<!--書き換え後-->
<td>
<?php echo h($title); ?>
<span>
<?php
if ($type === 0 && $spending_category !== null) :
echo '(' . h($spending_category) . ')';
elseif ($type === 1 && $income_category !== null) :
echo '(' . $income_category . ')';
else :
echo '(不明)';
endif;
?>
<i class="fa-regular fa-message" onclick=""></i> </span>
</td>
タイトルはそのままechoします。
カテゴリーの出力は$typeに格納されている数値を使って、支出か収入かを判断しカテゴリーが「0」ではないときにそれぞれのカテゴリーを出力するよう指示しています。
ここまで実装すると以下のようにタイトルカラムも連携しました。
収入金額の出力
収入金額と支出金額も$typeの値を使って出力します。
<!--書き換え前-->
<td></td>
<!--書き換え後-->
<td>
<?php echo $type === 1 ? '¥' . number_format(h($amount)) : ''; ?>
</td>
$type === 1 という条件(収入データかどうか)を評価し、trueであれば ‘¥’ . number_format($amount)を返し、falseであれば ‘ ‘ (空)を返す演算子です。
number_format($amount)で3桁ごと「,」で区切るようフォーマット指定しています。
支出金額と支払い方法の出力
続いて支出カラムを出力します。金額については収入カラム同様に三項演算子を使って出力します。
<!--書き換え前-->
<td> ¥3,000 <span> (クレジット) </span> </td>
<!--書き換え後-->
<td>
<?php echo $type === 0 ? '¥' . number_format($amount) : ''; ?>
<span>
<?php
if ($type === 0 && $paymentmethod !== null) {
echo '(' . h($paymentmethod) . ')';
} else if ($type === 1) {
echo "";
} else {
echo "(不明)";
}
?>
</span>
</td>
支出or収入の数値が入っている$typeを使って、支出データ&支払い方法が記録されている場合は支払い方法を出力します。
収入データのときは空文字を出力し、どの条件にも当てはまらない場合は(不明)を出力するよう記述しています。
ここまで実装すると、支出収入カラムがDBと連携します。
支出詳細の出力
続いて支払い方法が「クレジットカード」「スマホ決済」だったとき、その項目を支出詳細カラムに出力します。
<!--書き換え前-->
<td>カードB </td>
<!--書き換え後-->
<td>
<?php echo $paymentmethod === "クレジット" ? h($credit) : '' ?>
<?php echo $paymentmethod === "スマホ決済" ? h($qr) : '' ?>
</td>
金額の出力と同様に三項演算子で条件式を評価し値を返すよう記述しました。
このとき、recordsに登録されている数値がそれぞれの項目を保存しているテーブル(spending_categoryやincome_category、creditcard、qrなど)のidに存在していない場合は、正しく出力されません。
recordsのcreditに「1」が入っているのに出力されない…となったら、creditcardテーブルにidが「1」のデータがあるか確認しましょう。
メモアイコンの出力
現在タイトルカラムに表示しているメモのアイコンを、メモがあるデータのみ出力するようにします。
trタグのclassにメモがある場合には「hasmemo」を出力し、hasmemoを持つtrタグのiタグだけ表示するようにします。
<!--書き換え前-->
<tr class="p-table__item item<?php echo h($id); ?>">
<!--書き換え後-->
<tr class="p-table__item item<?php echo h($id); ?> <?php echo $memo !== '' ? 'hasmemo' : ''; ?>">
現在入っているデータに全てメモを入れているとわかりにくいので、メモなしのデータを登録するか、すでに登録しているデータのmemoを削除するなどして見やすくします。
<?php
$sql_dataoutput = 'SELECT records.id, records.date, records.title, records.amount,
spending_category.name, income_category.name, records.type,
payment_method.name, creditcard.name, qr.name, records.memo, records.input_time
FROM records
LEFT JOIN spending_category ON records.spending_category = spending_category.id
LEFT JOIN income_category ON records.income_category = income_category.id
LEFT JOIN payment_method ON records.payment_method = payment_method.id
LEFT JOIN creditcard ON records.credit = creditcard.id
LEFT JOIN qr ON records.qr = qr.id
ORDER BY date DESC, input_time DESC';
$stmt_dataoutput = $db->prepare($sql_dataoutput);
sql_check($stmt_dataoutput, $db);
$stmt_dataoutput->bind_result(
$id,
$date,
$title,
$amount,
$spending_category,
$income_category,
$type,
$paymentmethod,
$credit,
$qr,
$memo,
$input_time
);
while ($stmt_dataoutput->fetch()) : ?>
<tr class="p-table__item item<?php echo h($id); ?> <?php echo $memo !== '' ? 'hasmemo' : ''; ?>">
<td> <?php echo date('Y/m/d', strtotime($date)); ?> </td>
<td>
<?php echo h($title); ?>
<span>
<?php
if ($type === 0 && $spending_category !== 0) :
echo '(' . h($spending_category) . ')';
elseif ($type === 1 && $income_category !== 0) :
echo '(' . $income_category . ')';
else :
echo '(不明)';
endif;
?>
<i class="fa-regular fa-message" onclick=""></i>
</span>
</td>
<td>
<?php echo $type === 1 ? '¥' . number_format(h($amount)) : ''; ?>
</td>
<td>
<?php echo $type === 0 ? '¥' . number_format($amount) : ''; ?>
<span>
<?php
if ($type === 0 && $paymentmethod !== 0) {
echo '(' . h($paymentmethod) . ')';
} else if ($type === 1) {
echo "";
} else {
echo "(不明)";
}
?>
</span>
</td>
<td>
<?php echo $paymentmethod === "クレジット" ? h($credit) : '' ?>
<?php echo $paymentmethod === "スマホ決済" ? h($qr) : '' ?>
</td>
<td>
<form action="./record-edit.php" method="POST">
<input type="hidden" name="record_id" value="1">
<input type="submit" class='c-button c-button--bg-green edit fas' id="" value="">
</form>
<a class='c-button c-button--bg-red delete' id="" href='' onclick="">
<i class="fa-regular fa-trash-can"></i>
</a>
</td>
</tr>
<?php endwhile; ?>
スマホ画面のデータ出力
今回はスマホの場合は、tableタグではなくdivタグで表示するようにしています。
レスポンシブの要素もデータベースと連携するようにします。
タグの種類が異なるだけで、出力方法は基本PCと同じです。
SQLの発行と実行
PCの出力の際に記述した「$sql_dataoutput」は再度記述する必要はありません。
以下のようにSQL分を格納している変数をセット→SQL実行チェック→値を受け取るプログラムから記述し、whileでループを始めます。
<?php
$stmt_dataoutput = $db->prepare($sql_dataoutput);
sql_check($stmt_dataoutput, $db);
$stmt_dataoutput->bind_result(
$id,
$date,
$title,
$amount,
$spending_category,
$income_category,
$type,
$paymentmethod,
$credit,
$qr,
$memo,
$input_time
);
while ($stmt_dataoutput->fetch()) : ?>
divタグのclassにデータidを出力
<!--書き換え前-->
<div class="p-sp-data-box item1">
<!--書き換え後-->
<div class="p-sp-data-box item<?php echo h($id); ?>">
タイトルとカテゴリーの出力
<!--書き換え前-->
<p> aaaaaa
<span> (不明) <i class="fa-regular fa-message" onclick=""></i> </span>
</p>
<!--書き換え後-->
<p> <?php echo h($title); ?>
<span>
<?php
if ($type === 0 && $spending_category !== null) {
echo '(' . h($spending_category) . ')';
} else if ($type === 1 && $income_category !== null) {
echo '(' . h($income_category) . ')';
} else {
echo "(カテゴリー不明)";
}
?>
<i class="fa-regular fa-message" onclick=""></i> </span>
</p>
金額の出力
スマホの画面では、金額の出力場所が支出も収入も同じ要素です。
テキストの色を変えることで、支出なのか収入かを区別するようにしています。
<!--書き換え前-->
<p class="text-red"> -¥30,000 </p>
<!--書き換え後-->
<p class="<?php echo $type === 0 ? 'text-red' : 'text-blue' ?>">
<?php echo h($type) === "0" ? '-¥' . number_format($amount) : ''; ?>
<?php echo h($type) === "1" ? '+¥' . number_format($amount) : ''; ?>
</p>
まず、pタグのclassに$typeによって「text-red」「text-blue」を出力するように記述しています。このクラス名によってCSS側でテキストの色を変えることができるようにしています。
同じく金額も$typeが0か1によって、符号を変えるよう三項演算子で記述しています。
日付と支払い方法の出力
最後に日付と、支出データのみ支払い方法を出力するように記述します。
<!--書き換え前-->
<div class="p-sp-data-box__detail">
<p>2022/06/11</p>
<p> (不明) </p>
</div>
<!--書き換え後-->
<div class="p-sp-data-box__detail">
<p><?php echo date('Y/m/d', strtotime($date)); ?></p>
<p>
<?php
//支払い方法の出力
if ($type === 0 && $paymentmethod !== null) {
echo '支払い方法:' . h($paymentmethod);
} else if ($type === 1) {
echo "";
} else {
echo "支払い方法:不明";
}
?>
</p>
<!--静的コーディングスタイルから少し変更-->
<?php if ($paymentmethod === "クレジット" || $paymentmethod === "スマホ決済") : ?>
<p>
<?php
//クレジット、スマホ決済の詳細出力
if ($paymentmethod === "クレジット") {
if ($credit !== null) {
echo 'カード種類:' . h($credit);
} else {
echo "カード種類:不明";
}
} else if ($paymentmethod === "スマホ決済") {
if ($qr !== null) {
echo 'スマホ決済種類:' . h($qr);
} else {
echo "スマホ決済種類:不明";
}
}
?>
</p>
<?php endif; ?>
</div>
日付の出力方法はPCと同じです。
支出データのときの支払い方法の出力は、それぞれif文で条件にあったときのみ出力するようにしています。
そしてクレジットやスマホ決済の種類は、支払い方法がクレジットカードかスマホ決済のときだけ支払い方法の下に<p>を出力し、中に条件分岐で文字列を出力する方法に変更しています。
メモアイコンの出力
PC同様にメモがあるデータだけアイコンが出力されるようにします。
<!--書き換え前-->
<div class="u-flex-box p-sp-data-box__overview">
<!--書き換え後-->
<div class="u-flex-box p-sp-data-box__overview <?php echo $memo !== '' ? 'hasmemo' : ''; ?>">
最後に
ここまでで収支一覧テーブルにデータを出力することができました。
次回は操作カラムの削除ボタンでデータを操作できるように実装していきます。
最後までお読みいただきありがとうございました。
コメント
質問失礼します。
PC用画面の一覧の表示まではできたのですが、スマホ用一覧画面のレイアウトが崩れてしまい、うまく表示されません。
スマホ用一覧画面の箇所のPHPソースを開示頂けないでしょうか。
コメントありがとうございます。
今シリーズは記事を書きながら開発を進めているため、クラス名やCSSを逐次修正しております。
そのためPHPのプログラムに問題がない場合は、お手数ですがCSSをGitHubから再ダウンロードしていただけると幸いです。
再度記事の見直しも致しますので、よろしくお願い致します。
以下追記になります。————
記事を見直したところ、スマホ表示のクラス名(正)「p-sp-data-box」とするところが、(誤)「p-sp-date-box」になっていたためレイアウトが崩れてしまったと思います。
お手数ですが以上を修正していただくと、正しく表示されるかと思います。