Route::middleware('auth')->prefix('videos')->group(function () {
Route::get('/', [VideoController::class, 'index'])->name('video.index');
});
2.コントローラーを編集します。
VideoController.phpを編集します。
VideoController.phpを編集します。
public function index()
{
$videos = Video::all();
return Inertia::render('Videos/Index', [
'videos' => $videos
]);
}
3.ビューを作成します。
Index.jsx
import React from 'react';
import {Link} from "@inertiajs/react";
const Videos = ({ videos }) => {
return (
{videos.map((video, index) => (
{video.title} - 詳細
))}
新規作成
);
};
export default Videos
詳細画面を作成する
1.ルーティングを作成します。
routes/web.phpに下記を記載してください。
Route::middleware('auth')->prefix('videos')->group(function () {
Route::get('/detail/{id}', [VideoController::class, 'show'])->name('video.show');
});
2.コントローラーを編集します。
VideoController.phpを編集します。
VideoController.phpを編集します。
public function show(string $id)
{
$video = Video::find($id);
return Inertia::rende('Videos/Show', [
'video' => $video
]);
}
3.ビューを作成します。
Show.jsx
import React from 'react';
import {Link} from "@inertiajs/react";
import {Inertia} from "@inertiajs/inertia";
const Video = ({ video }) => {
const handleBack = () => {
window.history.back();
};
return (
{video.title}
{video.text}
{video.status}
{video.youtube_url}
更新
);
};
export default Video
新規作成画面を作成する
1.ルーティングを作成します。
routes/web.phpに下記を記載してください。
Route::middleware('auth')->prefix('videos')->group(function () {
Route::get('/create', [VideoController::class, 'create'])->name('video.create');
Route::post('/store', [VideoController::class, 'store'])->name('video.store');
});
2.コントローラーを編集します。
VideoController.phpを編集します。
VideoController.phpを編集します。
public function create()
{
return Inertia::rende('Videos/Create', []);
}
public function store(Request $request)
{
$data = $request->all();
$data['user_id'] = auth()->id();
Video::create($data);
return redirect()->route('video.index');
}
3.ビューを作成します。
Create.jsx
import React, {useState} from 'react';
import { Inertia } from '@inertiajs/inertia';
const Create = () => {
const handleBack = () => {
window.history.back();
};
// useStateはReactのフック(Hook)の一つで、関数コンポーネント内で状態(state)を持たせるために使用されます。
// 一番右がデフォルト値
// 左側が値、右型が値を設定するためのもの
// なので、setFormDataに値を詰めると、formDataとしてformの値が扱える。
const [formData, setFormData] = useState({
title: '',
text: '',
status: '',
youtube_url: ''
});
// name属性とvalue属性をformDataとして設定する。
// ここのsetFormDataで、useStateのtitleとかを変更している。
const handleChange = (e) => {
setFormData({ ...formData, [e.target.name]: e.target.value });
};
const handleSubmit = (e) => {
e.preventDefault();
console.log(111)
Inertia.post('/videos/store', formData)
}
return (
Create
);
};
export default Create
更新画面を作成する
1.ルーティングを作成します。
routes/web.phpに下記を記載してください。
Route::middleware('auth')->prefix('videos')->group(function () {
Route::get('/update/{id}', [VideoController::class, 'edit'])->name('video.edit');
Route::put('/update/{id}', [VideoController::class, 'update'])->name('video.update');
});
2.コントローラーを編集します。
VideoController.phpを編集します。
VideoController.phpを編集します。
public function edit(string $id)
{
$video = Video::find($id);
return Inertia::render('Videos/Update', [
'video' => $video
]);
}
public function update(Request $request, string $id)
{
// バリデーション
$validatedData = $request->validate([
'title' => 'required|max:255',
'text' => 'required',
'status' => 'required',
'youtube_url' => 'required|url'
]);
// データの更新
$video = Video::find($id);
$video->update($validatedData);
// 必要に応じてレスポンスを返す
return redirect()->route('video.index')->with('success', 'ビデオを更新しました。');
}
3.ビューを作成します。
Update.jsx
import React, {useEffect, useState} from 'react';
import { Inertia } from '@inertiajs/inertia';
import {Link} from "@inertiajs/react";
const Update = ( { video } ) => {
const handleBack = () => {
window.history.back();
};
// フォームデータの状態管理
const [formData, setFormData] = useState({
title: '',
text: '',
status: '',
youtube_url: ''
});
// 初期データの設定
useEffect(() => {
if (video) {
setFormData({
title: video.title,
text: video.text,
status: video.status,
youtube_url: video.youtube_url
});
}
}, );
const handleChange = (e) => {
setFormData({ ...formData, [e.target.name]: e.target.value });
};
const handleSubmit = (e) => {
e.preventDefault();
Inertia.put(`/videos/update/${video.id}`, formData)
}
return (
Update
);
};
export default Update
削除機能を作成する
1.ルーティングを作成します。
routes/web.phpに下記を記載してください。
Route::middleware('auth')->prefix('videos')->group(function () {
Route::delete('/delete/{id}', [VideoController::class, 'destroy'])->name('video.destroy');
});
2.コントローラーを編集します。
VideoController.phpを編集します。
VideoController.phpを編集します。
public function destroy(string $id)
{
$video = Video::find($id);
$video->delete();
return redirect()->route('video.index')->with('success', 'ビデオを削除しました。');
}
3.ビューを作成します。
Show.jsx
import React from 'react';
import {Link} from "@inertiajs/react";
import {Inertia} from "@inertiajs/inertia";
const Video = ({ video }) => {
const handleBack = () => {
window.history.back();
};
const handleDelete = () => {
if (window.confirm('本当に削除しますか?')) {
Inertia.delete(`/videos/delete/${video.id}`);
}
}
return (
{video.title}
{video.text}
{video.status}
{video.youtube_url}
更新
);
};
export default Video
Chakra UIをインストールする
npm i @chakra-ui/react @emotion/react @emotion/styled framer-motion
.tsxやindex.jsなどに作ったコンポーネントを”Chakra Provider”で囲います。
1.resources/js/Pages/Dashboard.jsxファイルに下記を記載してください。
import AuthenticatedLayout from '@/Layouts/AuthenticatedLayout';
import { Head } from '@inertiajs/react';
import {Box, ChakraProvider} from '@chakra-ui/react'
export default function Dashboard({ auth }) {
return (
You're logged in!
てすと23
import React from 'react';
import {Link} from "@inertiajs/react";
import {Box, HStack, StackDivider, VStack} from "@chakra-ui/react";
const Videos = ({ videos }) => {
return (
{videos.map((video, index) => (
{video.title}
詳細
))}
新規作成
);
};
【Chakura UI】Tableを利用する
Index.jsxを修正します。
import React from 'react';
import {Link} from "@inertiajs/react";
import {
Box,
HStack,
StackDivider,
Table,
TableCaption,
TableContainer,
Tbody,
Td,
Th,
Thead,
Tr,
VStack
} from "@chakra-ui/react";
const Videos = ({videos}) => {
return (
<>
タイトル
詳細
{videos.map((video, index) => (
{video.title}
詳細
))}
新規作成
>
);
};
export default Videos
import React from 'react';
import {Link} from "@inertiajs/react";
import {
Box,
HStack,
StackDivider,
Table,
TableCaption,
TableContainer,
Tbody,
Td,
Th,
Thead,
Tr,
VStack,
Text,
ChakraProvider
} from "@chakra-ui/react";
const Videos = ({videos}) => {
return (
<>
動画一覧
タイトル
詳細
{videos.map((video, index) => (
{video.title}
詳細
))}
新規作成
>
);
};
export default Videos
【Chakura UI】ボタンを利用する
Index.jsxを修正します。
import { Button } from "@chakra-ui/react";
Statusの数値を文字列に変換する
Models/Video.phpを修正します。
protected $appends = ['statusName'];
const STATUS_NOT_STARTED = 0;
const STATUS_PROCESSING = 1;
const STATUS_COMPLETED = 2;
const STATUS_PENDING = 3;
public static $statusNames = [
self::STATUS_NOT_STARTED => '未着手',
self::STATUS_PROCESSING => '着手',
self::STATUS_COMPLETED => '完了',
self::STATUS_PENDING => '保留',
];
public function getStatusNameAttribute()
{
return self::$statusNames[$this->status] ?? null;
}
【Chakura UI】詳細画面をデザインする
Show.jsxを修正します。
import React from 'react';
import {Link} from "@inertiajs/react";
import {Inertia} from "@inertiajs/inertia";
import {ChakraProvider, VStack, Text, HStack, Button} from "@chakra-ui/react";
const Video = ({video}) => {
const handleBack = () => {
window.history.back();
};
const handleDelete = () => {
if (window.confirm('本当に削除しますか?')) {
Inertia.delete(`/videos/delete/${video.id}`);
}
}
return (
動画詳細
タイトル
{video.title}
撮影内容
{video.text}
ステータス
{video.statusName}
URL
{video.youtube_url}
);
};
export default Video
【Chakura UI】編集画面をデザインする
Update.jsxを修正します。
import React, {useEffect, useState} from 'react';
import {Inertia} from '@inertiajs/inertia';
import {ChakraProvider, HStack, Text, VStack, Input, Textarea, Button, Select} from "@chakra-ui/react";
const Update = ({video, statuses}) => {
const handleBack = () => {
window.history.back();
};
// フォームデータの状態管理
const [formData, setFormData] = useState({
title: '',
text: '',
status: '',
youtube_url: ''
});
// 初期データの設定
useEffect(() => {
if (video) {
setFormData({
title: video.title,
text: video.text,
status: video.status,
youtube_url: video.youtube_url
});
}
}, );
const handleChange = (e) => {
setFormData({...formData, [e.target.name]: e.target.value});
};
const handleSubmit = (e) => {
e.preventDefault();
Inertia.put(`/videos/update/${video.id}`, formData)
}
return (
動画編集
);
};
export default Update
【Chakura UI】新規作成画面をデザインする
Create.jsxを修正します。
import React, {useState} from 'react';
import {Inertia} from '@inertiajs/inertia';
import {Button, ChakraProvider, HStack, Input, Select, Text, Textarea, VStack} from "@chakra-ui/react";
const Create = ({statuses}) => {
const handleBack = () => {
window.history.back();
};
// useStateはReactのフック(Hook)の一つで、関数コンポーネント内で状態(state)を持たせるために使用されます。
// 一番右がデフォルト値
// 左側が値、右型が値を設定するためのもの
// なので、setFormDataに値を詰めると、formDataとしてformの値が扱える。
const [formData, setFormData] = useState({
title: '',
text: '',
status: '',
youtube_url: ''
});
// name属性とvalue属性をformDataとして設定する。
// ここのsetFormDataで、useStateのtitleとかを変更している。
const handleChange = (e) => {
setFormData({...formData, [e.target.name]: e.target.value});
};
const handleSubmit = (e) => {
e.preventDefault();
console.log(111)
Inertia.post('/videos/store', formData)
}
return (
新規作成
);
};
export default Create
TypeScriptのインストール
(1)下記を見て、ts化する
https://github.com/laravel/breeze
TypescriptをLaravelにインストールします。
yarn add @types/react @types/react-dom typescript @types/node
作成したファイルをTS化する
型ファイルを作成する。
export interface VideoObject {
id: string
title: string
text: string
status: string
youtube_url: string
user_id: number
statusName: string
created_at: Date
updated_at: Date
}
export interface VideoProps {
video: VideoObject;
}
export interface VideosProps {
videos: VideoObject[];
}
// video propsにstatusesを追加する
export interface StatusesBase {
statuses: string[];
}
export interface UpdateProps extends VideoProps, StatusesBase {}
export interface StatusProps extends StatusesBase {}