241 lines
6.9 KiB
JavaScript
241 lines
6.9 KiB
JavaScript
import React, { useState, useEffect } from "react";
|
||
import {
|
||
View,
|
||
Text,
|
||
TouchableOpacity,
|
||
FlatList,
|
||
KeyboardAvoidingView,
|
||
TextInput,
|
||
Platform,
|
||
Keyboard,
|
||
ScrollView,
|
||
Linking,
|
||
} from "react-native";
|
||
import { useAllTrainDiagram } from "../stateBox/useAllTrainDiagram";
|
||
|
||
import { customTrainDataDetector } from "./custom-train-data";
|
||
import { getTrainType } from "../lib/getTrainType";
|
||
import { SheetManager } from "react-native-actions-sheet";
|
||
import { useNavigation } from "@react-navigation/native";
|
||
import { BigButton } from "./atom/BigButton";
|
||
import { Switch } from "react-native-elements";
|
||
export default function AllTrainDiagramView() {
|
||
const { goBack, navigate } = useNavigation();
|
||
const { keyList, allTrainDiagram } = useAllTrainDiagram();
|
||
const [input, setInput] = useState(""); // 文字入力
|
||
const [keyBoardVisible, setKeyBoardVisible] = useState(false);
|
||
const [useStationName, setUseStationName] = useState(false);
|
||
const [useRegex, setUseRegex] = useState(false);
|
||
const regexTextStyle = {
|
||
color: "white",
|
||
fontSize: 20,
|
||
margin: 3,
|
||
padding: 3,
|
||
};
|
||
const regexTextButtonStyle = {
|
||
...regexTextStyle,
|
||
borderWidth: 1,
|
||
borderColor: "white",
|
||
borderRadius: 3,
|
||
};
|
||
useEffect(() => {
|
||
const showSubscription = Keyboard.addListener("keyboardDidShow", () => {
|
||
setKeyBoardVisible(true);
|
||
});
|
||
const hideSubscription = Keyboard.addListener("keyboardDidHide", () => {
|
||
setKeyBoardVisible(false);
|
||
});
|
||
|
||
return () => {
|
||
showSubscription.remove();
|
||
hideSubscription.remove();
|
||
};
|
||
}, []);
|
||
|
||
const openTrainInfo = (d) => {
|
||
const train = customTrainDataDetector(d);
|
||
let TrainNumber = "";
|
||
if (train.trainNumDistance != undefined) {
|
||
const timeInfo =
|
||
parseInt(d.replace("M", "").replace("D", "")) - train.trainNumDistance;
|
||
TrainNumber = timeInfo + "号";
|
||
}
|
||
const type = getTrainType(train.type).data;
|
||
const limited = `${type}:${train.trainName}${TrainNumber}`;
|
||
const payload = {
|
||
data: { trainNum: d, limited },
|
||
navigate,
|
||
from: "AllTrainIDList",
|
||
};
|
||
SheetManager.show("EachTrainInfo", {
|
||
payload,
|
||
});
|
||
};
|
||
return (
|
||
<View style={{ backgroundColor: "#0099CC", height: "100%" }}>
|
||
<FlatList
|
||
style={{ flex: 1 }}
|
||
data={keyList?.filter((d) => {
|
||
if (useStationName) {
|
||
const ls = input.split(",").map((stationName) => {
|
||
return allTrainDiagram[d].includes(stationName);
|
||
});
|
||
return !ls.includes(false);
|
||
}
|
||
if (useRegex) {
|
||
try {
|
||
const regex = new RegExp(input);
|
||
return regex.test(d);
|
||
} catch (e) {
|
||
return false;
|
||
}
|
||
}
|
||
return d.includes(input);
|
||
})}
|
||
renderItem={({ item }) => <Item {...{ openTrainInfo, id: item }} />}
|
||
keyExtractor={(item) => item}
|
||
//initialNumToRender={100}
|
||
/>
|
||
<KeyboardAvoidingView
|
||
behavior="padding"
|
||
keyboardVerticalOffset={80}
|
||
enabled={Platform.OS === "ios"}
|
||
>
|
||
<View style={{ height: 35, flexDirection: "row" }}>
|
||
<Switch
|
||
value={useRegex}
|
||
onValueChange={() => {
|
||
setUseRegex(!useRegex);
|
||
setUseStationName(false);
|
||
}}
|
||
color="red"
|
||
style={{ margin: 5 }}
|
||
/>
|
||
<Text style={{ color: "white", fontSize: 20, margin: 5 }}>
|
||
正規表現を使用
|
||
</Text>
|
||
<Switch
|
||
value={useStationName}
|
||
onValueChange={() => {
|
||
setUseRegex(false);
|
||
setUseStationName(!useStationName);
|
||
}}
|
||
color="red"
|
||
style={{ margin: 5 }}
|
||
/>
|
||
<Text style={{ color: "white", fontSize: 20, margin: 5 }}>
|
||
駅名で検索
|
||
</Text>
|
||
</View>
|
||
<ScrollView
|
||
style={{
|
||
height: 35,
|
||
flexDirection: "row",
|
||
backgroundColor: "#0099CC",
|
||
margin: 5,
|
||
display: useRegex ? "flex" : "none",
|
||
}}
|
||
horizontal={true}
|
||
>
|
||
<Text style={regexTextStyle}>正規表現のサンプル:</Text>
|
||
<Text style={regexTextButtonStyle} onPress={() => setInput("D")}>
|
||
気動車を選択
|
||
</Text>
|
||
<Text
|
||
style={regexTextButtonStyle}
|
||
onPress={() => setInput("3\\d\\d\\dM")}
|
||
>
|
||
マリンライナーを選択
|
||
</Text>
|
||
<Text
|
||
style={regexTextButtonStyle}
|
||
onPress={() => setInput("[4,5]\\d\\d\\d[D,M]")}
|
||
>
|
||
ワンマン列車を選択
|
||
</Text>
|
||
<Text
|
||
style={regexTextButtonStyle}
|
||
onPress={() => setInput("^\\d?\\dM")}
|
||
>
|
||
しおかぜを選択
|
||
</Text>
|
||
<Text
|
||
style={regexTextButtonStyle}
|
||
onPress={() => setInput("^\\d?[0,2,4,6,8]D")}
|
||
>
|
||
下り南風を選択
|
||
</Text>
|
||
<Text
|
||
style={regexTextButtonStyle}
|
||
onPress={() => setInput("^([\\d])+\\1")}
|
||
>
|
||
数字が二桁揃っている列車を選択
|
||
</Text>
|
||
<Text
|
||
style={{ ...regexTextButtonStyle, backgroundColor: "green" }}
|
||
onPress={() =>
|
||
Linking.openURL(
|
||
"https://qiita.com/tossh/items/635aea9a529b9deb3038"
|
||
)
|
||
}
|
||
>
|
||
参考資料(Qiita)
|
||
</Text>
|
||
</ScrollView>
|
||
<View
|
||
style={{
|
||
height: 35,
|
||
margin: 5,
|
||
alignItems: "center",
|
||
backgroundColor: "#F4F4F4",
|
||
flexDirection: "row",
|
||
paddingLeft: 10,
|
||
paddingRight: 10,
|
||
borderRadius: 25,
|
||
borderColor: "#F4F4F4",
|
||
}}
|
||
>
|
||
<TextInput
|
||
placeholder="列番を入力してフィルタリングします。"
|
||
onFocus={() => setKeyBoardVisible(true)}
|
||
onEndEditing={() => {}}
|
||
onChange={(ret) => setInput(ret.nativeEvent.text)}
|
||
value={input}
|
||
style={{ flex: 1 }}
|
||
/>
|
||
</View>
|
||
</KeyboardAvoidingView>
|
||
<BigButton
|
||
onPress={goBack}
|
||
string="閉じる"
|
||
style={{
|
||
display:
|
||
Platform.OS === "ios" ? "flex" : keyBoardVisible ? "none" : "flex",
|
||
}}
|
||
/>
|
||
</View>
|
||
);
|
||
}
|
||
const Item = ({ id, openTrainInfo }) => {
|
||
return (
|
||
<TouchableOpacity
|
||
style={{
|
||
padding: 5,
|
||
flexDirection: "row",
|
||
borderColor: "white",
|
||
borderWidth: 1,
|
||
margin: 5,
|
||
borderRadius: 5,
|
||
alignItems: "center",
|
||
}}
|
||
onPress={() => openTrainInfo(id)}
|
||
>
|
||
<View style={{ flex: 1 }} />
|
||
<Text style={{ fontSize: 25, fontWeight: "bold", color: "white" }}>
|
||
{id}
|
||
</Text>
|
||
<View style={{ flex: 1 }} />
|
||
</TouchableOpacity>
|
||
);
|
||
};
|