こんにちは!Masaです。
今回も引き続き、家計簿アプリの作成を続けていきたいと思います!
前回の記事↓
- Django初心者で簡単なWebアプリケーション作成を考えている人
- Djangoの学び直しをしている人
- Djangoの基礎を身に付けたい人
前回のおさらいと今回やること
前回の記事では、ベースのテンプレートにナビゲーションバーを設置して各ページ(月次別収支や資産推移ページなど)にどのページからでも飛べるようにしました。
<!DOCTYPE html>
<html lang="ja" dir="ltr">
<head>
<meta charset="utf-8">
<title>家計簿アプリ</title>
<!-- Bootstrap CSS -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous">
</head>
<body>
<nav class="navbar navbar-expand-lg navbar-light bg-light">
<div class="container-fluid">
<a class="navbar-brand" href="#">家計簿アプリ</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="navbarSupportedContent">
<ul class="navbar-nav me-auto mb-2 mb-lg-0">
<li class="nav-item">
<a class="nav-link" href="{% url 'index' %}">Home</a>
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'monthly_details' %}">月別詳細</a>
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'by_account' %}">資産詳細</a>
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'assets' %}">資産推移</a>
</li>
<li class="nav-item">
<a class="nav-link" href="{% url 'setup' %}">設定</a>
</li>
</ul>
<form class="d-flex">
<input class="form-control me-2" type="search" placeholder="Search" aria-label="Search">
<button class="btn btn-outline-success" type="submit">Search</button>
</form>
</div>
</div>
</nav>
{% block content %}{% endblock %}
<!-- Bootstrap Javascript -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/js/bootstrap.bundle.min.js" integrity="sha384-MrcW6ZMFYlzcLA8Nl+NtUVF0sA7MsXsP1UyJoMp4YLEuNSfAP+JcXn/tWtIaxVXM" crossorigin="anonymous"></script>
</body>
</html>
今回の記事では
- 収入・支出の入力をモーダルで行う
- 収入・支出のカテゴリー入力を選択方式にする
を行っていきたいと思います!
頑張っていきましょう👍
収入・支出をモーダルで行う
みなさん、モーダルという言葉はご存じでしょうか。
Webにおいては「モーダルウインドウ」のことを指し、最終確認や削除を行うときの最終確認で画面に別ウインドウで表示させるものです。
今回はモーダルはBootstrapで作成します。
Bootstrapのモーダルのページでは、以下のようなサンプルが載っています。
今回はこのモーダル内に入力フォームを表示させ、収入・支出を入力できるようにしたいと思います。
ちなみにモーダルを使用することで
- トップページを整えられる
- わざわざ他ページにとんで入力する手間が省ける
という利点があると考えています。
モーダルの表示
モーダルを表示するために、“index.html”を編集します。
{% extends 'money_diary/base.html' %}
{% block content %}
<!-- 収入のモーダルボタン -->
<button type="button" class="btn btn-primary" data-bs-toggle="modal" data-bs-target="#incomeModal">収入の入力</button>
<!-- 収入のモーダル -->
<div class="modal fade" id="incomeModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">収入の入力</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<form method="post">
<div class="modal-body">
{% csrf_token %}
{{ incomeform.as_p }}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
<button type="submit" name="income_register_button" class="btn btn-primary">追加</button>
</div>
</form>
</div>
</div>
</div>
<!-- 支出のモーダルボタン -->
<button type="button" class="btn btn-primary" data-bs-toggle="modal" data-bs-target="#expenseModal">支出の入力</button>
<!-- 支出のモーダル -->
<div class="modal fade" id="expenseModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">支出の入力</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<form method="post">
<div class="modal-body">
{% csrf_token %}
{{ expenseform.as_p }}
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
<button type="submit" name="expense_register_button" class="btn btn-primary">追加</button>
</div>
</form>
</div>
</div>
</div>
<h2>収入履歴</h2>
<table>
{% for item in income %}
<tr>
<td>{{ item.date }}{{ item.kind }}{{ item.amount }}</td>
</tr>
{% endfor %}
</table>
<h2>支出の履歴</h2>
<table>
{% for item in expense %}
<tr>
<td>{{ item.date }}{{ item.kind }}{{ item.amount }}</td>
</tr>
{% endfor %}
</table>
{% endblock %}
モーダルのポイントとしては、モーダルを呼び出すボタン(6行目と30行目)のdata-bs-target(#は必須らしいです)と8行目、32行目のidが対応しています。
ここを対応させることで、表示させたいモーダルウインドウを呼び出すことができます。
モーダルウインドのフォーム部分は以前のフォームをそのまま使用しています。
POST時の処理も変更がありません。
追加ボタンでnameを指定し、ビューの方で処理しています。
以上でフォームのモダール化は完了です!
収入・支出のカテゴリー入力を選択方式にする
次に収入・支出のカテゴリー入力を選択方式にします。
例えば、支出の内容は食費や交通費、光熱費などがあると思いますが、それを選択から選べるようにするということです。
今回、初期の選択肢として以下のように設定します。
これらはモデルクラスを作成し、追加や削除できるようにしたいと思います。
モデルクラスの作成
まずモデルクラスを作成していきましょう。
以下のコードを“models.py”に追記してください。
IncomeCategoiresはIncomeの上に、ExpenseCategoriesはExpenseの上に配置します。(呼び出し順序の関係です)
#収入のカテゴリー
class IncomeCategories(models.Model):
name = models.CharField(max_length=30) #収入カテゴリーの名前
def __str__(self):
return self.name
#支出のカテゴリー
class ExpenseCategories(models.Model):
name = models.CharField(max_length=30) #支出カテゴリーの名前
def __str__(self):
return self.name
次にマイグレーションをしましょう。
以下のコードをコマンドラインに入力して、実行してください。
python manage.py makemigrations
python manage.py migrate
また、“admin.py”にも登録をします。
from django.contrib import admin
from .models import (
Income,
Expense,
Account,
Assets,
IncomeCategories, #追加
ExpenseCategories, #追加
)
admin.site.register(Income)
admin.site.register(Expense)
admin.site.register(Account)
admin.site.register(Assets)
admin.site.register(IncomeCategories) #追加
admin.site.register(ExpenseCategories) #追加
リレーションの設定
次に収支のモデルとカテゴリーのモデルのリレーションシップ(関連付け)を行いましょう。
リレーションシップは以下の記事で解説していますので、ぜひご覧ください。
今回は1対1の関係でリレーションシップを構築していきます。
(1つの収支に対してカテゴリーは1個のため)
#収入のモデル
class Income(models.Model):
date = models.DateField(default=timezone.now) #日付
category = models.OneToOneField(IncomeCategories, on_delete=models.CASCADE) #カテゴリ(編集)
account = models.CharField(max_length=30) #入金
amount = models.IntegerField() #金額
memo = models.TextField(null=True, blank=True, max_length=100) #メモ
def __str__(self):
return self.category.name + str(self.amount)
支出のモデル
class Expense(models.Model):
date = models.DateField(default=timezone.now) #日付
category = models.OneToOneField(ExpenseCategories, on_delete=models.CASCADE) #カテゴリ(編集)
account = models.CharField(max_length=30) #出所
amount = models.IntegerField() #金額
memo = models.TextField(null=True, blank=True, max_length=100) #メモ
管理者画面から初期カテゴリーの追加
次に上記のカテゴリーを管理者画面から追加していきましょう。
コマンドラインに以下の命令を入力して実行してください。
python manage.py createsuperuser
ユーザ名、メールアドレス、パスワードの入力を求められると思うので新規設定してください。
ちなみにユーザ名、パスワードだけで大丈夫です。(パスワードはタイプしても画面には反映されません)
管理者登録が終われば、開発用サーバを起動します。
その後、ブラウザに”http://127.0.0.1:8000/admin”と入力し、管理者画面を開きます。
先ほど設定したユーザ名、パスワードを入力すると、以下の画面が出てきます。
IncomeCategories、ExpenseCategoriesをそれぞれクリックするとデータの追加ができるので、上記の初期カテゴリーを追加しましょう。
forms.pyを変更して選択式に変える
最後にforms.pyに追加を加えて、入力フォームのカテゴリー欄を選択方式にします。
以下のように変更してください。
from django import forms
from django.forms.models import ModelChoiceField #追加
from .models import(
Income,
Expense,
IncomeCategories, #追加
ExpenseCategories, #追加
)
#収入入力のフォーム
class IncomeForm(forms.ModelForm):
category = ModelChoiceField(queryset=IncomeCategories.objects.all()) #追加
class Meta:
model = Income
fields = '__all__'
#支出入力のフォーム
class ExpenseForm(forms.ModelForm):
category = ModelChoiceField(queryset=ExpenseCategories.objects.all()) #追加
class Meta:
model = Expense
fields = '__all__'
ModelChoiceFieldを使用して、取得したクエリセットを選択方式にしています。
これで完成です。
モーダルが以下のように選択できるようになっていたら成功です👍
まとめ
今回はフォームのモーダル化、カテゴリー選択の適用でした。
通常より長くなってしまい少し大変だったと思いますが、よく使うものなのでぜひマスターしていただきたいです。
次回からは月別詳細ページを作成していきたいと思います。ぜひご覧ください!
最後まで読んでいただきありがとうございます。
自己学習に役立てていただけたら嬉しく思います
またSNSやブログでシェアしていただくことや、誤植などをコメントで指摘いただけたら幸いです。
次回の記事↓
コメント