import React, { useEffect, useState } from 'react'; import { Box, Typography, Paper, Button, IconButton, Accordion, AccordionSummary, AccordionDetails, Dialog, DialogTitle, DialogActions, TextField } from '@mui/material'; // TextFieldを追加 import { DragDropContext, Droppable, Draggable } from 'react-beautiful-dnd'; import DeleteIcon from '@mui/icons-material/Delete'; import ExpandMoreIcon from '@mui/icons-material/ExpandMore'; import DeleteOutlineIcon from '@mui/icons-material/DeleteOutline'; // 需要アイコン import AccessTimeIcon from '@mui/icons-material/AccessTime'; // 時間アイコン import axios from 'axios'; // axiosを追加 const PickupList = ({ routes, isWide, routeName, onRoutesUpdate }) => { const [vehicleRoutes, setVehicleRoutes] = useState([]); const [openDialog, setOpenDialog] = useState(false); // ダイアログ表示用の状態管理 const [currentRouteName, setCurrentRouteName] = useState(''); // 現在のルート名 const [customRouteName, setCustomRouteName] = useState(''); // 新規または変更されたルート名 const [nameError, setNameError] = useState(false); // エラーステート管理 useEffect(() => { if (Array.isArray(routes)) { if (routes.every(route => !route.vehicle_name)) { setVehicleRoutes(routes); } else { const groupedRoutes = routes.reduce((acc, route) => { const vehicleName = route.vehicle_name; if (!acc[vehicleName]) { acc[vehicleName] = []; } acc[vehicleName].push(...route.route); return acc; }, {}); const arrayRoutes = Object.values(groupedRoutes); setVehicleRoutes(arrayRoutes); } } else { console.error('Received invalid routes:', routes); } }, [routes]); const updateRouteDataForMap = (newVehicleRoutes) => { const formattedRoutes = Object.keys(newVehicleRoutes).map((vehicleName, idx) => { const route = newVehicleRoutes[vehicleName]; if (!Array.isArray(route) || route.length === 0) { return null; } return { vehicle_name: vehicleName, route_id: idx, route: route }; }).filter(route => route !== null); onRoutesUpdate(formattedRoutes); }; // ルート保存処理 const handleSaveRoutes = async () => { if (routes?.[0]?.route_id) { // 既存ルートの場合 setCurrentRouteName(routes[0].route_name || '既存ルート'); setCustomRouteName(routes[0].route_name || '既存ルート'); // ルート名を表示 } else { // 新規ルートの場合 setCurrentRouteName('新規ルート'); setCustomRouteName(''); } setOpenDialog(true); // ダイアログを表示 }; // ダイアログでの保存方法の選択または確認 const handleDialogClose = async () => { if (!customRouteName.trim()) { setNameError(true); // ルート名が空の場合、エラーステートを設定 return; } if (currentRouteName === '新規ルート' || customRouteName !== currentRouteName) { // ルート名が変更された場合や新規ルートの場合は新しいルートとして保存 await saveNewRoute(); } else { // ルート名が変更されていない場合は上書き保存 await saveExistingRoute(); } setOpenDialog(false); }; const saveNewRoute = async () => { try { const formattedRoutes = vehicleRoutes.map((vehicleRoute, vehicleIndex) => { return { vehicle_name: `車両_${vehicleIndex + 1}`, route: vehicleRoute }; }); const response = await axios.post('/api/save-route', { routeName: customRouteName, // 入力されたルート名で保存 routes: formattedRoutes }); console.log('ルート保存成功:', response.data); } catch (error) { console.error('ルート保存失敗:', error); } }; const saveExistingRoute = async () => { try { const routeId = routes?.[0]?.route_id; if (routeId) { const formattedRoutes = vehicleRoutes.map((vehicleRoute, vehicleIndex) => { return { vehicle_name: `車両_${vehicleIndex + 1}`, route: vehicleRoute }; }); const response = await axios.put(`/api/update-route/${routeId}`, { routes: formattedRoutes }); console.log('既存ルート更新成功:', response.data); } } catch (error) { console.error('ルート更新失敗:', error); } }; // ドラッグ終了時のイベントハンドラ const onDragEnd = (result) => { const { source, destination } = result; if (!destination) return; const sourceIndex = parseInt(source.droppableId, 10); const destinationIndex = parseInt(destination.droppableId, 10); if (sourceIndex === destinationIndex) { const items = reorder(vehicleRoutes[sourceIndex], source.index, destination.index); const newRoutes = [...vehicleRoutes]; newRoutes[sourceIndex] = items; setVehicleRoutes(newRoutes); updateRouteDataForMap(newRoutes); // ドラッグ操作後にマップデータを更新 } else { const result = move( vehicleRoutes[sourceIndex], vehicleRoutes[destinationIndex], source.index, destination.index ); const newRoutes = [...vehicleRoutes]; newRoutes[sourceIndex] = result.source; newRoutes[destinationIndex] = result.destination; setVehicleRoutes(newRoutes); updateRouteDataForMap(newRoutes); // ドラッグ操作後にマップデータを更新 } }; // 車両リスト削除処理 const handleDeleteVehicle = (vehicleIndex) => { const newRoutes = vehicleRoutes.filter((_, i) => i !== vehicleIndex); setVehicleRoutes(newRoutes); updateRouteDataForMap(newRoutes); // 削除後にマップデータを更新 }; return ( {/* ヘッダーにルート保存ボタン */} {Object.keys(vehicleRoutes).map((vehicleName, vehicleIndex) => { const totalDemand = calculateTotalDemand(vehicleRoutes[vehicleIndex]); // 需要合計を計算 const borderColor = routeColors[vehicleIndex % routeColors.length]; // 各車両のルート色を設定 return ( {(provided) => ( }> {vehicleName} {/* 車両名を表示 */} 需要合計: {totalDemand} {/* 需要合計を表示 */} handleDeleteVehicle(vehicleIndex)} sx={{ marginLeft: 'auto' }} > {(vehicleRoutes[vehicleName] || []).map((stop, index) => ( {(provided) => ( {stop.place || '未設定'} {stop.name || '名前不明'} {/* 需要アイコンと値 */} {stop.demand || 0} {/* 時間アイコンと値 */} {stop.jikan || '-'} )} ))} {provided.placeholder} )} ); })} {/* 保存方法を選択するダイアログ */} setOpenDialog(false)}> ルート名を確認してください { setCustomRouteName(e.target.value); setNameError(false); }} error={nameError} helperText={nameError ? 'ルート名を入力してください' : ''} /> ); }; export default PickupList;