Files
jrshikoku/components/Apps/FixedPositionBox/FixedStationBox.tsx

355 lines
11 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import lineColorList from "@/assets/originData/lineColorList";
import { customTrainDataDetector } from "@/components/custom-train-data";
import { StationNumberMaker } from "@/components/駅名表/StationNumberMaker";
import { checkDuplicateTrainData } from "@/lib/checkDuplicateTrainData";
import { typeID } from "@/lib/getStringConfig";
import { getTrainDelayStatus } from "@/lib/getTrainDelayStatus";
import { getTrainType } from "@/lib/getTrainType";
import { objectIsEmpty } from "@/lib/objectIsEmpty";
import { trainPosition } from "@/lib/trainPositionTextArray";
import { useAllTrainDiagram } from "@/stateBox/useAllTrainDiagram";
import { useAreaInfo } from "@/stateBox/useAreaInfo";
import { useCurrentTrain } from "@/stateBox/useCurrentTrain";
import { useStationList, StationProps } from "@/stateBox/useStationList";
import dayjs from "dayjs";
import { useEffect, useState } from "react";
import { Text, TouchableOpacity, View } from "react-native";
export const FixedStation = ({ stationID }) => {
const { fixedPosition, setFixedPosition } = useCurrentTrain();
const { getStationDataFromId } = useStationList();
const [station, setStation] = useState<StationProps[]>([]);
useEffect(() => {
const data = getStationDataFromId(stationID);
setStation(data);
}, [stationID]);
const lineColor =
station.length > 0
? lineColorList[station[0]?.StationNumber.slice(0, 1)]
: "white";
////
const timeFiltering = (d) => {
const baseTime = 2;
if (currentTrain.filter((t) => t.num == d.train).length == 0) {
const date = dayjs();
const trainTime = date
.hour(parseInt(d.time.split(":")[0]))
.minute(parseInt(d.time.split(":")[1]));
if (date.isAfter(trainTime)) {
return false;
} else if (trainTime.diff(date) < baseTime * 60 * 60 * 1000) {
return true;
}
return false;
} else {
const Pos = trainPosition(
currentTrain.filter((t) => t.num == d.train)[0]
);
const nextPos = Pos.isBetween ? Pos.Pos.to : Pos.Pos.Pos;
const PrePos = Pos.isBetween ? Pos.Pos.from : "";
if (station[0].Station_JP == nextPos) {
if (d.lastStation != station[0].Station_JP) return true;
} else if (station[0].Station_JP == PrePos) {
return false;
}
let [h, m] = d.time.split(":");
let delay = isNaN(currentTrain.filter((t) => t.num == d.train)[0].delay)
? 0
: currentTrain.filter((t) => t.num == d.train)[0].delay;
const date = dayjs();
let targetHour = parseInt(h);
// 4時を日付変更線として処理
if (targetHour < 4) {
targetHour += 24;
}
let currentHour = date.hour();
if (currentHour < 4) {
currentHour += 24;
}
const db = dayjs()
.hour(targetHour)
.minute(parseInt(m) + parseInt(delay));
const currentTime = dayjs().hour(currentHour);
return !currentTime.isAfter(db);
}
};
type trainDataProps = {
train?: string;
lastStation?: string;
time?: string;
isThrough?: boolean;
};
const getTime = (stationDiagram, station) => {
const returnData = Object.keys(stationDiagram)
.map((trainNum) => {
let trainData: trainDataProps = {};
stationDiagram[trainNum].split("#").forEach((data) => {
if (data.match("着")) {
trainData.lastStation = data.split(",着,")[0];
}
if (data.match("着編")) {
trainData.lastStation = data.split(",着編,")[0];
}
if (data.split(",")[0] === station.Station_JP) {
if (data.match(",発,")) {
trainData.time = data.split(",発,")[1];
} else if (data.match(",発編,")) {
trainData.time = data.split(",発編,")[1];
} else if (data.match(",通編,")) {
trainData.time = data.split(",通編,")[1];
trainData.isThrough = true;
} else if (data.match(",着,")) {
trainData.time = data.split(",着,")[1];
} else if (data.match(",着編,")) {
trainData.time = data.split(",着編,")[1];
}
}
});
return {
train: trainNum,
time: trainData.time,
lastStation: trainData.lastStation,
isThrough: trainData.isThrough,
};
})
.filter((d) => d.time);
return returnData.sort((a, b) => {
switch (true) {
case parseInt(a.time.split(":")[0]) < parseInt(b.time.split(":")[0]):
return -1;
case parseInt(a.time.split(":")[0]) > parseInt(b.time.split(":")[0]):
return 1;
case parseInt(a.time.split(":")[1]) < parseInt(b.time.split(":")[1]):
return -1;
case parseInt(a.time.split(":")[1]) > parseInt(b.time.split(":")[1]):
return 1;
default:
return 0;
}
});
};
const { allTrainDiagram } = useAllTrainDiagram();
const { areaInfo, areaStationID } = useAreaInfo();
const [stationDiagram, setStationDiagram] = useState({}); //当該駅の全時刻表
const [isInfoArea, setIsInfoArea] = useState(false);
const { currentTrain } = useCurrentTrain();
useEffect(() => {
// 現在の駅に停車するダイヤを作成する副作用[列車ダイヤと現在駅情報]
if (!allTrainDiagram) {
setStationDiagram({});
return;
}
if (station.length == 0) {
setStationDiagram({});
return;
}
let returnData = {};
Object.keys(allTrainDiagram).forEach((key) => {
if (allTrainDiagram[key].match(station[0].Station_JP + ",")) {
returnData[key] = allTrainDiagram[key];
}
});
setStationDiagram(returnData);
setIsInfoArea(station.some((s) => areaStationID.includes(s.StationNumber)));
}, [allTrainDiagram, station]);
const [trainTimeAndNumber, setTrainTimeAndNumber] = useState([]);
useEffect(() => {
//現在の駅に停車する列車から時刻を切り出してLEDベースにフォーマット
if (objectIsEmpty(stationDiagram)) return () => {};
const getTimeData = getTime(stationDiagram, station[0]);
setTrainTimeAndNumber(getTimeData);
}, [stationDiagram]);
const [selectedTrain, setSelectedTrain] = useState<
{
isThrough?: boolean;
train?: string;
lastStation?: string;
time?: string;
}[]
>([]);
useEffect(() => {
if (!trainTimeAndNumber) return () => {};
if (!currentTrain) return () => {};
const data = trainTimeAndNumber
.filter((d) => currentTrain.map((m) => m.num).includes(d.train)) //現在の列車に絞る[ToDo]
.filter(timeFiltering).filter(d=>!d.isThrough)
.filter((d) => d.lastStation != station[0].Station_JP) //最終列車表示設定
setSelectedTrain(data);
}, [trainTimeAndNumber, currentTrain /*finalSwitch*/]);
return (
<TouchableOpacity
style={{ flex: 1, flexDirection: "row" }}
onPress={() => {
setFixedPosition({ type: null, value: null });
}}
>
<View
style={{
flex: 3,
flexDirection: "column",
alignContent: "center",
alignSelf: "center",
alignItems: "center",
height: "100%",
backgroundColor: "white",
}}
>
<View
style={{
backgroundColor: lineColor,
flexDirection: "row",
width: "100%",
alignContent: "center",
alignItems: "center",
}}
>
<StationNumberMaker
currentStation={station}
singleSize={18}
useEach={true}
/>
<Text
style={{
fontSize: 18,
textAlignVertical: "center",
margin: 0,
padding: 0,
flex: 1,
color:"white"
}}
>
{station[0]?.Station_JP}
</Text>
<View
style={{
backgroundColor: "white",
width: 10,
borderLeftColor: lineColor,
borderTopColor: lineColor,
borderBottomColor: "white",
borderBottomWidth: 16,
borderLeftWidth: 8,
borderRightWidth: 0,
borderTopWidth: 5,
height: "100%",
}}
/>
</View>
<View
style={{
height: "100%",
backgroundColor: "white",
flex: 1,
}}
>
<Text style={{ fontSize: 20 }}></Text>
</View>
</View>
<View
style={{
flex: 5,
flexDirection: "column",
backgroundColor: "white",
borderTopWidth: 5,
borderTopColor: lineColor,
overflow: "hidden",
}}
>
{selectedTrain.length > 0 ? (
selectedTrain.map((d) => (
<FixedStationBoxEachTrain
d={d}
station={station[0]}
key={d.train + "-fixedStationBox"}
/>
))
) : (
<View style={{ backgroundColor: "white", flex: 1 }}>
<Text style={{ fontSize: 20 }}>
</Text>
</View>
)}
</View>
</TouchableOpacity>
);
};
const FixedStationBoxEachTrain = ({ d, station }) => {
const { currentTrain } = useCurrentTrain();
const { stationList } = useStationList();
const { allCustomTrainData } = useAllTrainDiagram();
const currentTrainData = checkDuplicateTrainData(
currentTrain.filter((a) => a.num == d.train),
stationList
);
const trainDelayStatus = `${getTrainDelayStatus(
currentTrainData,
station.Station_JP
)}`;
const getTrainDataFromCurrentTrain = (trainNum: string) => {
const customTrainData = customTrainDataDetector(
d.train,
allCustomTrainData
);
switch (customTrainData.type) {
case "Normal":
case "OneMan":
const currentTrainData = currentTrain.filter((a) => a.num == trainNum);
if (currentTrainData.length == 0) return customTrainData;
else if (currentTrainData[0].Type.includes("rapid:")) {
const typeText = currentTrainData[0].Type.split(":");
const returnData = {
type: "Rapid",
trainName: typeText[1].replace("\r", ""),
trainIcon: null,
trainNumDistance: null,
info: "",
};
return returnData;
}
return customTrainData;
default:
return customTrainData;
}
};
const [train, setTrain] = useState<{
ToData: string;
TrainNumber: string;
id: string;
img: string;
isWanman: boolean;
trainName: string;
trainNumDistance: number;
type: typeID;
viaData: string;
info?: string;
uwasa?: string;
}>(getTrainDataFromCurrentTrain(d.train));
useEffect(() => {
setTrain(getTrainDataFromCurrentTrain(d.train));
}, [currentTrain, d.train]);
const { name, color } = getTrainType(train.type, true);
return (
<View style={{ backgroundColor: "white", flexDirection: "row",height:"33%",overflow:"visible" }}>
<Text style={{ fontSize: 14, flex: 3 }}>{d.time}</Text>
<Text style={{ fontSize: 14, flex: 4, color }}>{name}</Text>
<Text style={{ fontSize: 14, flex: 4 }}>{d.lastStation}</Text>
<Text style={{ fontSize: 14, flex: 3 }}>{trainDelayStatus}</Text>
</View>
);
};