Merge commit 'eae47cae846c216098bcb6e264496c7abf72faf3' into develop

This commit is contained in:
harukin-expo-dev-env 2024-06-03 12:03:55 +00:00
commit b1924dffd9
25 changed files with 585 additions and 176 deletions

11
App.js
View File

@ -19,6 +19,7 @@ import "./components/ActionSheetComponents/sheets.js";
import { TrainDelayDataProvider } from "./stateBox/useTrainDelayData.js";
import { SafeAreaProvider } from "react-native-safe-area-context";
import { DeviceOrientationChangeProvider } from "./stateBox/useDeviceOrientationChange.js";
import { TrainMenuProvider } from "./stateBox/useTrainMenu.js";
LogBox.ignoreLogs([
"ViewPropTypes will be removed",
"ColorPropType will be removed",
@ -42,9 +43,11 @@ export default function App() {
<AreaInfoProvider>
<AllTrainDiagramProvider>
<BusAndTrainDataProvider>
<SheetProvider>
<AppContainer />
</SheetProvider>
<TrainMenuProvider>
<SheetProvider>
<AppContainer />
</SheetProvider>
</TrainMenuProvider>
</BusAndTrainDataProvider>
</AllTrainDiagramProvider>
</AreaInfoProvider>
@ -63,6 +66,8 @@ export function AppContainer() {
<NavigationContainer name="Root" style={{ flex: 1 }} ref={navigationRef}>
<Tab.Navigator
tabBarOptions={{ keyboardHidesTabBar: Platform.OS === "android" }}
initialRouteName="menuPage"
lazy={false}
>
<Tab.Screen
name="login"

26
Apps.js
View File

@ -14,7 +14,7 @@ import * as Updates from "expo-updates";
import { AS } from "./storageControl";
import { news } from "./config/newsUpdate";
import { getStationList, lineList } from "./lib/getStationList";
import { getStationList, lineList, lineListPair } from "./lib/getStationList";
import { injectJavascriptData } from "./lib/webViewInjectjavascript";
import { checkDuplicateTrainData } from "./lib/checkDuplicateTrainData";
import { useFavoriteStation } from "./stateBox/useFavoriteStation";
@ -25,11 +25,13 @@ import TrainMenu from "./components/trainMenu";
import { EachTrainInfoCore } from "./components/ActionSheetComponents/EachTrainInfoCore";
import { useNavigation } from "@react-navigation/native";
import { useTrainMenu } from "./stateBox/useTrainMenu";
import { stationNamePair } from "./lib/getStationList2";
/*
import StatusbarDetect from './StatusbarDetect';
var Status = StatusbarDetect(); */
export default function Apps({ stationData }) {
export default function Apps() {
const { webview, currentTrain } = useCurrentTrain();
const { height, width } = useWindowDimensions();
const { navigate } = useNavigation();
@ -37,6 +39,11 @@ export default function Apps({ stationData }) {
const { favoriteStation } = useFavoriteStation();
const { isLandscape, setIsLandscape } = useDeviceOrientationChange();
const handleLayout = () => {};
const {
setSelectedLine,
setInjectJavaScript,
mapsStationData: stationData,
} = useTrainMenu();
//画面表示関連
const [iconSetting, setIconSetting] = useState(undefined);
@ -164,6 +171,13 @@ export default function Apps({ stationData }) {
});
return;
}
case "currentLines": {
const lineInfo = dataSet.currentLines.split("\n")[0];
const lineID = stationNamePair[lineInfo];
setSelectedLine(lineID);
return;
}
default: {
return;
}
@ -322,7 +336,10 @@ export default function Apps({ stationData }) {
)}
{isLandscape || (
<MapsButton
onPress={() => navigate("trainMenu", { webview })}
onPress={() => {
setInjectJavaScript("");
navigate("trainMenu", { webview });
}}
top={Platform.OS == "ios" ? Constants.statusBarHeight : 0}
mapSwitch={mapSwitch == "true" ? "flex" : "none"}
/>
@ -467,12 +484,13 @@ const MapsButton = ({ onPress, top, mapSwitch }) => {
textAlignVertical: "center",
fontWeight: "bold",
color: "white",
fontSize: 20,
},
};
return (
<TouchableOpacity onPress={onPress} style={styles.touch}>
<View style={{ flex: 1 }} />
<Text style={styles.text}></Text>
<Text style={styles.text}></Text>
<View style={{ flex: 1 }} />
</TouchableOpacity>
);

21
Top.js
View File

@ -14,14 +14,16 @@ import { optionData } from "./lib/stackOption.js";
import { useNavigation } from "@react-navigation/native";
import { useCurrentTrain } from "./stateBox/useCurrentTrain.js";
import { AS } from "./storageControl.js";
import { useTrainMenu } from "./stateBox/useTrainMenu";
const Stack = createStackNavigator();
export const Top = ({ navigationRef }) => {
const { webview, getCurrentTrain } = useCurrentTrain();
const { webview } = useCurrentTrain();
const navigation = useNavigation();
const { navigate, addListener } = navigation;
//地図用
const [mapsStationData, setMapsStationData] = useState(undefined);
const { setMapsStationData, injectJavaScript, setInjectJavaScript } =
useTrainMenu();
useEffect(() => {
getStationList2().then(setMapsStationData);
@ -47,15 +49,22 @@ export const Top = ({ navigationRef }) => {
if (navigationRef.current?.getCurrentRoute().name == "Apps") {
if (mapSwitch == "true") {
navigation.navigate("trainMenu");
setInjectJavaScript("");
} else {
webview.current?.injectJavaScript(`AccordionClassEvent()`);
}
} else {
if (mapSwitch == "true") {
if (injectJavaScript) {
webview.current?.injectJavaScript(injectJavaScript);
setInjectJavaScript("");
}
}
navigation.navigate("Apps");
}
});
return unsubscribe;
}, [navigation, mapSwitch]);
}, [navigation, mapSwitch, injectJavaScript]);
return (
<Stack.Navigator>
@ -66,7 +75,7 @@ export const Top = ({ navigationRef }) => {
gestureEnabled: true,
headerTransparent: true,
}}
children={() => <Apps stationData={mapsStationData} />}
component={Apps}
/>
<Stack.Screen
name="trainbase"
@ -84,13 +93,13 @@ export const Top = ({ navigationRef }) => {
<Stack.Screen
name="trainMenu"
options={optionData}
children={() => <TrainMenu stationData={mapsStationData} />}
component={TrainMenu}
/>
<Stack.Screen
name="favoriteList"
options={{ ...optionData, gestureEnabled: false }}
children={() => <FavoriteList stationData={mapsStationData} />}
component={FavoriteList}
/>
</Stack.Navigator>
);

BIN
assets/reccha-small.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

BIN
assets/reccha.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 128 KiB

View File

@ -17,7 +17,9 @@ export const StateBox = ({ text, title, style, mode }) => (
<Text style={mode == 2 ? boxTextStyle2 : boxTextStyle}>
{text.split("")[0]}
</Text>
<Text style={{ color: "#0099CC", textAlign: "right" }}></Text>
<Text style={{ color: "#0099CC", textAlign: "right" }}>
{mode == 2 ? "→" : "↓"}
</Text>
<Text style={mode == 2 ? boxTextStyle2 : boxTextStyle}>
{text.split("")[1]}
</Text>

View File

@ -17,7 +17,7 @@ export const TrainDataView = ({
}) => {
const { width, height } = useWindowDimensions();
const { isLandscape } = useDeviceOrientationChange();
const { webview, getCurrentTrain } = useCurrentTrain();
const { webview, getCurrentTrain, inject } = useCurrentTrain();
const [mapsStationData, setMapsStationData] = useState(undefined);
useEffect(() => {
getStationList2().then(setMapsStationData);
@ -51,10 +51,10 @@ export const TrainDataView = ({
}
});
if (!test.length) return;
webview.current?.injectJavaScript(
`MoveDisplayStation('${test[0].line}_${test[0].station.MyStation}_${test[0].station.Station_JP}');setStrings();`
);
navigate("Apps");
inject(
`MoveDisplayStation('${test[0].line}_${test[0].station.MyStation}_${test[0].station.Station_JP}');document.getElementById("disp").insertAdjacentHTML("afterbegin", "<div />");`
);
SheetManager.hide("EachTrainInfo");
}}
>
@ -66,11 +66,11 @@ export const TrainDataView = ({
? `${
currentTrainData?.Pos.replace("(下り)", "")
.replace("(上り)", "")
.split("")[0]
.split("")[currentTrainData?.Direction == 1 ? 0 : 1]
}${
currentTrainData?.Pos.replace("(下り)", "")
.replace("(上り)", "")
.split("")[1]
.split("")[currentTrainData?.Direction == 1 ? 1 : 0]
}`
: currentTrainData?.Pos
}

View File

@ -7,6 +7,7 @@ import {
StyleSheet,
useWindowDimensions,
BackHandler,
Linking,
} from "react-native";
import { Ionicons } from "@expo/vector-icons";
import { SheetManager } from "react-native-actions-sheet";
@ -25,7 +26,7 @@ import { DynamicHeaderScrollView } from "../DynamicHeaderScrollView";
import { LongHeader } from "./EachTrainInfo/LongHeader";
import { ShortHeader } from "./EachTrainInfo/ShortHeader";
import { ScrollStickyContent } from "./EachTrainInfo/ScrollStickyContent";
import { getStationData } from "../../lib/eachTrainInfoCoreLib/getStationData";
import { getStationID } from "../../lib/eachTrainInfoCoreLib/getStationData";
import { findReversalPoints } from "../../lib/eachTrainInfoCoreLib/findReversalPoints";
import { migrateTrainName } from "../../lib/eachTrainInfoCoreLib/migrateTrainName";
import { getType } from "../../lib/eachTrainInfoCoreLib/getType";
@ -193,12 +194,20 @@ export const EachTrainInfoCore = ({
const pos = currentTrainData?.Pos.replace("(下り)", "")
.replace("(上り)", "")
.split("");
setCurrentPosition([
getStationData(pos[0], stationList),
getStationData(pos[1], stationList),
]);
const direction = parseInt(currentTrainData?.Direction) || 0;
if (direction == 0) {
setCurrentPosition([
getStationID(pos[1], stationList),
getStationID(pos[0], stationList),
]);
} else {
setCurrentPosition([
getStationID(pos[0], stationList),
getStationID(pos[1], stationList),
]);
}
} else {
setCurrentPosition([getStationData(currentTrainData?.Pos, stationList)]);
setCurrentPosition([getStationID(currentTrainData?.Pos, stationList)]);
}
}, [currentTrainData]);
@ -235,12 +244,18 @@ export const EachTrainInfoCore = ({
} else {
SheetManager.hide("EachTrainInfo").then(() => {
//0.1秒待機してから開く
setTimeout(() => {
SheetManager.show("EachTrainInfo", { payload });
}, 2);
setTimeout(() => SheetManager.show("EachTrainInfo", { payload }), 2);
});
}
};
const headerItem = {
currentTrainData,
currentPosition,
nearTrainIDList,
openTrainInfo,
navigate,
};
return (
<View
style={{
@ -303,24 +318,8 @@ export const EachTrainInfoCore = ({
maxHeight: isLandscape ? height - 94 : (height / 100) * 70,
},
}}
shortHeader={
<ShortHeader
currentTrainData={currentTrainData}
currentPosition={currentPosition}
nearTrainIDList={nearTrainIDList}
openTrainInfo={openTrainInfo}
navigate={navigate}
/>
}
longHeader={
<LongHeader
currentTrainData={currentTrainData}
currentPosition={currentPosition}
nearTrainIDList={nearTrainIDList}
openTrainInfo={openTrainInfo}
navigate={navigate}
/>
}
shortHeader={<ShortHeader {...headerItem} />}
longHeader={<LongHeader {...headerItem} />}
topStickyContent={
<ScrollStickyContent currentTrainData={currentTrainData} />
}
@ -361,6 +360,26 @@ export const EachTrainInfoCore = ({
trainList={trainList}
trueTrainID={trueTrainID}
/>
{!trainData.length && (
<TouchableOpacity
onPress={() =>
Linking.openURL(`https://twitter.com/search?q=${data.trainNum}`)
}
style={{
padding: 10,
flexDirection: "row",
borderColor: "blue",
borderWidth: 1,
margin: 10,
borderRadius: 5,
alignItems: "center",
}}
>
<Text style={{ fontSize: 18, fontWeight: "bold", color: "black" }}>
Twitterで検索
</Text>
</TouchableOpacity>
)}
{trainData.map((i, index) =>
i.split(",")[1] == "提" ? (
<DataFromButton i={i} />
@ -376,11 +395,11 @@ export const EachTrainInfoCore = ({
)
)}
{tailStation.length != 0 &&
tailStation.map((i, index) =>
tailStation.map(({ station, dia }, index) =>
showTailStation.findIndex((d) => d == index) == -1 ? (
<TouchableOpacity
onPress={() => {
const array = openBackTrainInfo(i.station, trainData, i.dia);
const array = openBackTrainInfo(station, trainData, dia);
if (!array) return;
setTrainData(array);

View File

@ -262,9 +262,9 @@ const NexPreStationLine = ({ currentStation, originalStationList }) => {
"土讃線(多度津-高知間)[D]",
"土讃線(高知-窪川間)[K]",
"高徳線(高松-徳島間)[T]",
"徳島線(徳島-阿波池田)[B]",
"徳島線(徳島-阿波池田)[B]",
"鳴門線(池谷-鳴門間)[N]",
"瀬戸大橋線(宇多津-児島間)[M]",
"瀬戸大橋線(児島-宇多津間)[M]",
];
let returnData;
lineList.forEach((d) => {

View File

@ -0,0 +1,138 @@
import React, { useEffect, useRef } from "react";
import {
View,
LayoutAnimation,
ScrollView,
Linking,
Text,
TouchableOpacity,
Platform,
BackHandler,
} from "react-native";
import { Ionicons, MaterialCommunityIcons } from "@expo/vector-icons";
import ActionSheet, {
SheetManager,
useScrollHandlers,
} from "react-native-actions-sheet";
import LottieView from "lottie-react-native";
import { useSafeAreaInsets } from "react-native-safe-area-context";
import ViewShot from "react-native-view-shot";
import * as Sharing from "expo-sharing";
import { useTrainDelayData } from "../../stateBox/useTrainDelayData";
import { useTrainMenu } from "../../stateBox/useTrainMenu";
import lineColorList from "../../assets/originData/lineColorList";
import { stationIDPair } from "../../lib/getStationList2";
import { lineListPair } from "../../lib/getStationList";
export const TrainMenuLineSelector = () => {
const { getTime, delayData, loadingDelayData, setLoadingDelayData } =
useTrainDelayData();
const {
selectedLine,
setSelectedLine,
mapsStationData: stationData,
setMapsStationData,
} = useTrainMenu();
const actionSheetRef = useRef(null);
const scrollHandlers = useScrollHandlers("scrollview-1", actionSheetRef);
const insets = useSafeAreaInsets();
const viewShot = useRef(null);
const platformIs = Platform.OS == "android";
return (
<ActionSheet
gestureEnabled
CustomHeaderComponent={<></>}
ref={actionSheetRef}
isModal={Platform.OS == "ios"}
containerStyle={platformIs ? { paddingBottom: insets.bottom } : {}}
useBottomSafeAreaPadding={platformIs}
>
<Handler />
<View style={{ height: 26, width: "100%", backgroundColor: "white" }}>
<View
style={{
height: 6,
width: 45,
borderRadius: 100,
backgroundColor: "#f0f0f0",
marginVertical: 10,
alignSelf: "center",
}}
/>
</View>
{Object.keys(stationData).map((d) => (
<TouchableOpacity
style={{
flexDirection: "row",
backgroundColor: selectedLine == d ? "#0099CC33" : "white",
}}
onPress={() => {
SheetManager.hide("TrainMenuLineSelector");
setSelectedLine(selectedLine == d ? undefined : d);
}}
>
<View
style={{
width: 35,
position: "relative",
marginHorizontal: 15,
flexDirection: "row",
height: "101%",
}}
>
<View
style={{
backgroundColor: lineColorList[stationIDPair[d]],
flex: 1,
}}
>
<View style={{ flex: 1 }} />
<Text
style={{
color: "white",
textAlign: "center",
fontSize: 12,
fontWeight: "bold",
}}
>
{stationIDPair[d]}
</Text>
<View style={{ flex: 1 }} />
</View>
</View>
<View
style={{
padding: 8,
flexDirection: "row",
borderBottomWidth: 1,
borderBottomColor: "#f0f0f0",
flex: 1,
alignContent: "center",
alignItems: "center",
}}
>
<Text style={{ fontSize: 20 }}>
{lineListPair[stationIDPair[d]]}
</Text>
<View style={{ flex: 1 }} />
</View>
</TouchableOpacity>
))}
</ActionSheet>
);
};
const Handler = () => {
useEffect(() => {
const backAction = () => {
SheetManager.hide("TrainMenuLineSelector");
return true;
};
const backHandler = BackHandler.addEventListener(
"hardwareBackPress",
backAction
);
return () => backHandler.remove();
}, []);
return <></>;
};

View File

@ -2,9 +2,11 @@ import { registerSheet } from "react-native-actions-sheet";
import { EachTrainInfo } from "./EachTrainInfo";
import { JRSTraInfo } from "./JRSTraInfo";
import { StationDeteilView } from "./StationDeteilView";
import { TrainMenuLineSelector } from "./TrainMenuLineSelector";
registerSheet("EachTrainInfo", EachTrainInfo);
registerSheet("JRSTraInfo", JRSTraInfo);
registerSheet("StationDetailView", StationDeteilView);
registerSheet("TrainMenuLineSelector", TrainMenuLineSelector);
export {};

View File

@ -81,17 +81,15 @@ export function InfoWidget({ time, text }) {
}}
>
{text ? (
<FlexWidget
<TextWidget
style={{
flexDirection: "row",
width: "match_parent",
backgroundColor: "#ffffff",
flex: 1,
color: "#000000",
fontSize: 20,
}}
clickAction="WIDGET_CLICK"
>
<FlexText flex={3} text={text} />
</FlexWidget>
clickAction="OPEN_APP"
text={text}
/>
) : (
<TextWidget
style={{

View File

@ -33,7 +33,9 @@ export async function widgetTaskHandler(props) {
switch (WidgetName) {
case "Info_Widget": {
const { time, text } = await getInfoString();
renderWidget(<InfoWidget time={time} text={text} />);
renderWidget(
<InfoWidget time={time} text={text && text.toString()} />
);
break;
}
case "JR_shikoku_train_info":

View File

@ -5,11 +5,13 @@ import Icon from "react-native-vector-icons/Entypo";
import { useFavoriteStation } from "../stateBox/useFavoriteStation";
import { useCurrentTrain } from "../stateBox/useCurrentTrain";
import { useNavigation } from "@react-navigation/native";
import { useTrainMenu } from "../stateBox/useTrainMenu";
import { FavoriteListItem } from "./atom/FavoriteListItem";
export default function FavoriteList({ stationData }) {
export default function FavoriteList() {
const { favoriteStation } = useFavoriteStation();
const { webview } = useCurrentTrain();
const { navigate, goBack } = useNavigation();
const { mapsStationData: stationData } = useTrainMenu();
return (
<View style={{ height: "100%", backgroundColor: "#0099CC" }}>
@ -45,7 +47,7 @@ export default function FavoriteList({ stationData }) {
webview.current?.injectJavaScript(
`MoveDisplayStation('${lineName}_${currentStation[0].MyStation}_${currentStation[0].Station_JP}');
setStrings();`
document.getElementById("disp").insertAdjacentHTML("afterbegin", "<div />");`
);
navigate("Apps");
}}

View File

@ -34,7 +34,7 @@ export const WidgetSettings = ({ navigate }) => {
});
getInfoString().then(({ time, text }) => {
setTime(time);
setTrainInfo(text);
setTrainInfo(text.toString());
});
}, []);
return (

View File

@ -1,21 +1,30 @@
import React, { useRef, useState, useEffect } from "react";
import { View, Text, TouchableOpacity, Linking } from "react-native";
import { View, Text, TouchableOpacity, Linking, Platform } from "react-native";
import MapView, { Marker } from "react-native-maps";
import { MaterialCommunityIcons } from "@expo/vector-icons";
import Constants from "expo-constants";
import { MaterialCommunityIcons, Ionicons } from "@expo/vector-icons";
import { useCurrentTrain } from "../stateBox/useCurrentTrain";
import { useNavigation } from "@react-navigation/native";
import lineColorList from "../assets/originData/lineColorList";
import { stationIDPair } from "../lib/getStationList2";
import { lineListPair } from "../lib/getStationList";
export default function TrainMenu({ stationData, style }) {
import { SheetManager } from "react-native-actions-sheet";
import { useTrainMenu } from "../stateBox/useTrainMenu";
export default function TrainMenu({ style }) {
const { webview } = useCurrentTrain();
const mapRef = useRef();
const { navigate } = useNavigation();
const [stationPin, setStationPin] = useState([]);
const [selectedLine, setSelectedLine] = useState(undefined);
const {
selectedLine,
setSelectedLine,
injectJavaScript,
setInjectJavaScript,
mapsStationData: stationData,
} = useTrainMenu();
useEffect(() => {
const stationPinData = [];
Object.keys(stationData).map((d, indexBase) =>
Object.keys(stationData).map((d, indexBase) => {
stationData[d].map((D, index) => {
if (!D.StationMap) return null;
if (selectedLine && selectedLine != d) return;
@ -24,9 +33,15 @@ export default function TrainMenu({ stationData, style }) {
""
).split(",");
if (latlng.length == 0) return null;
if (index == 0 && stationPin.length > 0) {
setInjectJavaScript(
`MoveDisplayStation('${d}_${D.MyStation}_${D.Station_JP}');
document.getElementById("disp").insertAdjacentHTML("afterbegin", "<div />");`
);
}
stationPinData.push({ D, d, latlng, indexBase: 0, index });
})
);
});
});
setStationPin(stationPinData);
}, [stationData, selectedLine]);
useEffect(() => {
@ -35,37 +50,11 @@ export default function TrainMenu({ stationData, style }) {
latitude: parseFloat(latlng[0]),
longitude: parseFloat(latlng[1]),
})),
{ edgePadding: { top: 100, bottom: 50, left: 50, right: 50 } } // Add margin values here
{ edgePadding: { top: 80, bottom: 120, left: 50, right: 50 } } // Add margin values here
);
}, [stationPin]);
return (
<View style={{ height: "100%", backgroundColor: "#0099CC", ...style }}>
{selectedLine && (
<View
style={{
position: "absolute",
top: 0,
left: 0,
right: 0,
backgroundColor: lineColorList[stationIDPair[selectedLine]],
padding: 10,
zIndex: 100,
alignItems: "center",
}}
>
<Text
style={{
color: "white",
fontWeight: "bold",
fontSize: 20,
textAlign: "center",
}}
>
{selectedLine ? lineListPair[stationIDPair[selectedLine]] : "全線"}
</Text>
</View>
)}
<MapView
style={{ flex: 1, width: "100%", height: "100%" }}
showsUserLocation={true}
@ -105,6 +94,44 @@ export default function TrainMenu({ stationData, style }) {
flex: 1,
}}
>
<TouchableOpacity
style={{
backgroundColor: selectedLine
? lineColorList[stationIDPair[selectedLine]]
: "#0099CC",
padding: 10,
zIndex: 1,
alignItems: "center",
position: "absolute",
bottom: 0,
width: "100%",
paddingBottom: 50,
}}
onPress={() => SheetManager.show("TrainMenuLineSelector")}
>
<Text
style={{
color: "white",
fontWeight: "bold",
fontSize: 10,
textAlign: "center",
}}
>
  ここを押して路線をフィルタリングできます  
</Text>
<Text
style={{
color: "white",
fontWeight: "bold",
fontSize: 20,
textAlign: "center",
}}
>
{selectedLine
? lineListPair[stationIDPair[selectedLine]]
: "JR四国 対象全駅"}
</Text>
</TouchableOpacity>
<Text style={{ position: "absolute", bottom: 40 }}>
路線記号からフィルタリング
</Text>
@ -116,8 +143,12 @@ export default function TrainMenu({ stationData, style }) {
padding: 5,
margin: 2,
borderRadius: 10,
borderColor: "white",
borderWidth: 1,
borderStyle: "solid",
alignItems: "center",
opacity: selectedLine == d ? 1 : !selectedLine ? 1 : 0.5,
zIndex: 10,
}}
onPress={() => setSelectedLine(selectedLine == d ? undefined : d)}
>
@ -166,26 +197,14 @@ export default function TrainMenu({ stationData, style }) {
</UsefulBox>
</View>
)}
{navigate && (
<TouchableOpacity
style={{
padding: 10,
flexDirection: "row",
borderColor: "white",
borderWidth: 1,
margin: 10,
borderRadius: 5,
alignItems: "center",
}}
onPress={() => navigate("Apps")}
>
<View style={{ flex: 1 }} />
<Text style={{ fontSize: 25, fontWeight: "bold", color: "white" }}>
閉じる
</Text>
<View style={{ flex: 1 }} />
</TouchableOpacity>
)}
<MapsButton
onPress={() => {
navigate("Apps");
webview.current?.injectJavaScript(injectJavaScript);
}}
top={0}
mapSwitch={"flex"}
/>
</View>
);
}
@ -221,10 +240,47 @@ const MapPin = ({ index, indexBase, latlng, D, d, navigate, webview }) => {
onPress={() => {
webview.current?.injectJavaScript(
`MoveDisplayStation('${d}_${D.MyStation}_${D.Station_JP}');
setStrings();`
document.getElementById("disp").insertAdjacentHTML("afterbegin", "<div />");`
);
if (navigate) navigate("Apps");
}}
image={require("../assets/reccha-small.png")}
></Marker>
);
};
const MapsButton = ({ onPress, top, mapSwitch }) => {
const styles = {
touch: {
position: "absolute",
top,
left: 10,
width: 50,
height: 50,
backgroundColor: "#0099CC",
borderColor: "white",
borderStyle: "solid",
borderWidth: 1,
borderRadius: 50,
alignContent: "center",
alignSelf: "center",
alignItems: "center",
display: mapSwitch,
},
text: {
textAlign: "center",
width: "auto",
height: "auto",
textAlignVertical: "center",
fontWeight: "bold",
color: "white",
},
};
return (
<TouchableOpacity onPress={onPress} style={styles.touch}>
<View style={{ flex: 1 }} />
<Ionicons name="close" color="white" size={30} />
<View style={{ flex: 1 }} />
</TouchableOpacity>
);
};

View File

@ -13,6 +13,7 @@ import { checkDuplicateTrainData } from "../../lib/checkDuplicateTrainData";
import { useCurrentTrain } from "../../stateBox/useCurrentTrain";
import { useAreaInfo } from "../../stateBox/useAreaInfo";
import { SheetManager } from "react-native-actions-sheet";
import { AS } from "../../storageControl";
/**
*
@ -59,6 +60,31 @@ export default function LED_vision(props) {
const [trainDescriptionSwitch, setTrainDescriptionSwitch] = useState(false);
const { areaInfo } = useAreaInfo();
useEffect(() => {
AS.getItem("LEDSettings/trainIDSwitch").then((data) => {
console.log(data);
if (data == "true") {
setTrainIDSwitch(true);
} else {
setTrainIDSwitch(false);
}
});
AS.getItem("LEDSettings/trainDescriptionSwitch").then((data) => {
if (data == "true") {
setTrainDescriptionSwitch(true);
} else {
setTrainDescriptionSwitch(false);
}
});
AS.getItem("LEDSettings/finalSwitch").then((data) => {
if (data == "true") {
setFinalSwitch(true);
} else {
setFinalSwitch(false);
}
});
}, []);
useEffect(() => {
// 現在の駅に停車するダイヤを作成する副作用[列車ダイヤと現在駅情報]
if (!trainDiagram) {
@ -164,14 +190,20 @@ export default function LED_vision(props) {
true
);
useEffect(() => {
if (!areaInfo) return () => {};
if (!areaInfo) {
setAreaString("");
return () => {};
}
setAreaString(
areaInfo.substring(move, areaInfo.length) + areaInfo.substring(0, move)
);
}, [move]);
useEffect(() => {
if (!areaInfo) return () => {};
if (!areaInfo) {
setAreaStringLength(0);
return () => {};
}
setAreaStringLength(areaInfo.length);
}, [areaInfo]);
@ -282,16 +314,31 @@ const Footer = (props) => {
return (
<View style={{ flexDirection: "row", padding: 10, alignItems: "center" }}>
<Text style={textStyle}>種別名 / 列番</Text>
<Switch value={trainIDSwitch} onValueChange={setTrainIDSwitch} />
<Switch
value={trainIDSwitch}
onValueChange={(value) => {
AS.setItem("LEDSettings/trainIDSwitch", value.toString());
setTrainIDSwitch(value);
}}
/>
<View style={{ flex: 1 }} />
<Text style={textStyle}>列車情報</Text>
<Switch
value={trainDescriptionSwitch}
onValueChange={setTrainDescriptionSwitch}
onValueChange={(value) => {
AS.setItem("LEDSettings/trainDescriptionSwitch", value.toString());
setTrainDescriptionSwitch(value);
}}
/>
<View style={{ flex: 1 }} />
<Text style={textStyle}>当駅止表示</Text>
<Switch value={finalSwitch} onValueChange={setFinalSwitch} />
<Switch
value={finalSwitch}
onValueChange={(value) => {
AS.setItem("LEDSettings/finalSwitch", value.toString());
setFinalSwitch(value);
}}
/>
</View>
);
};
@ -336,10 +383,24 @@ const EachData = ({
setTrain(customTrainDataDetector(d.train));
}, [currentTrain, d.train, trainDescriptionSwitch]);
// 土讃線複数存在対策
const currentTrainData = checkDuplicateTrainData(
currentTrain.filter((a) => a.num == d.train)
);
const trainDelayStatus = getTrainDelayStatus(
checkDuplicateTrainData(currentTrain.filter((a) => a.num == d.train)),
currentTrainData,
station.Station_JP
);
const trainPositionText = currentTrainData?.Pos.match("")
? `現在地:${
currentTrainData?.Pos.replace("(下り)", "")
.replace("(上り)", "")
.split("")[currentTrainData?.Direction == 1 ? 0 : 1]
}${
currentTrainData?.Pos.replace("(下り)", "")
.replace("(上り)", "")
.split("")[currentTrainData?.Direction == 1 ? 1 : 0]
}間を走行中`
: `現在地:${currentTrainData?.Pos}`;
return (
<>
<TouchableOpacity
@ -365,6 +426,7 @@ const EachData = ({
<DependTime time={d.time} />
<StatusAndDelay trainDelayStatus={trainDelayStatus} />
</TouchableOpacity>
{trainDescriptionSwitch && <Description info={`${trainPositionText}`} />}
{trainDescriptionSwitch && !!train.info && (
<Description info={train.info} />
)}

View File

@ -1,6 +1,7 @@
import React, { useRef, useState, useEffect, useLayoutEffect } from "react";
import { View, Text, TouchableOpacity } from "react-native";
import { widthPercentageToDP as wp } from "react-native-responsive-screen";
import { MaterialCommunityIcons } from "@expo/vector-icons";
import LottieView from "lottie-react-native";
import { useInterval } from "../../lib/useInterval";
import { AS } from "../../storageControl";
@ -9,7 +10,13 @@ import { useFavoriteStation } from "../../stateBox/useFavoriteStation";
import lineColorList from "../../assets/originData/lineColorList";
export default function Sign(props) {
const { currentStation, originalStationList, oP, oLP } = props;
const {
currentStation,
originalStationList,
oP,
oLP,
isCurrentStation = false,
} = props;
const { favoriteStation, setFavoriteStation } = useFavoriteStation();
const [nexPrePosition, setNexPrePosition] = useState(0);
@ -68,9 +75,9 @@ export default function Sign(props) {
"土讃線(多度津-高知間)[D]",
"土讃線(高知-窪川間)[K]",
"高徳線(高松-徳島間)[T]",
"徳島線(徳島-阿波池田)[B]",
"徳島線(徳島-阿波池田)[B]",
"鳴門線(池谷-鳴門間)[N]",
"瀬戸大橋線(宇多津-児島間)[M]",
"瀬戸大橋線(児島-宇多津間)[M]",
];
let returnData;
lineList.forEach((d) => {
@ -92,39 +99,50 @@ export default function Sign(props) {
<TouchableOpacity style={styleSheet.外枠} onPress={oP} onLongPress={oLP}>
<StationNumberMaker currentStation={currentStation} />
<StationNameArea currentStation={currentStation} />
<TouchableOpacity
style={{ position: "absolute", right: -15, top: -20 }}
onPress={() => {
if (testButtonStatus) {
const otherData = favoriteStation.filter((d) => {
const compare = JSON.stringify(d);
const current = JSON.stringify(currentStation);
if (compare !== current) {
return true;
} else {
return false;
}
});
AS.setItem("favoriteStation", JSON.stringify(otherData));
setFavoriteStation(otherData);
} else {
let ret = favoriteStation;
ret.push(currentStation);
AS.setItem("favoriteStation", JSON.stringify(ret));
setFavoriteStation(ret);
}
setTestButtonStatus(!testButtonStatus);
}}
>
<LottieDelayView
progress={testButtonStatus ? 1 : 0}
speed={1.4}
style={{ width: 80, height: 80 }}
source={require("../../assets/939-star.json")}
lottieRef={lottieRef}
loop={false}
/>
</TouchableOpacity>
{isCurrentStation ? (
<TouchableOpacity style={{ position: "absolute", right: 0, top: 0 }}>
<MaterialCommunityIcons
name="crosshairs-gps"
style={{ padding: 5 }}
color="#2E94BB"
size={30}
/>
</TouchableOpacity>
) : (
<TouchableOpacity
style={{ position: "absolute", right: -15, top: -20 }}
onPress={() => {
if (testButtonStatus) {
const otherData = favoriteStation.filter((d) => {
const compare = JSON.stringify(d);
const current = JSON.stringify(currentStation);
if (compare !== current) {
return true;
} else {
return false;
}
});
AS.setItem("favoriteStation", JSON.stringify(otherData));
setFavoriteStation(otherData);
} else {
let ret = favoriteStation;
ret.push(currentStation);
AS.setItem("favoriteStation", JSON.stringify(ret));
setFavoriteStation(ret);
}
setTestButtonStatus(!testButtonStatus);
}}
>
<LottieDelayView
progress={testButtonStatus ? 1 : 0}
speed={1.4}
style={{ width: 80, height: 80 }}
source={require("../../assets/939-star.json")}
lottieRef={lottieRef}
loop={false}
/>
</TouchableOpacity>
)}
<Text style={styleSheet.JRStyle}>JR</Text>
<View style={styleSheet.下帯} />

View File

@ -1,7 +1,7 @@
// 駅名から駅情報を取得する
//stationName: 駅名
//stationList: 駅情報リスト
export const getStationData = (stationName, stationList) => {
export const getStationID = (stationName, stationList) => {
const Stations = stationList.map((a) =>
a.filter((d) => d.StationName == stationName)
);
@ -13,3 +13,15 @@ export const getStationData = (stationName, stationList) => {
if (!Station[0]) return [];
return Station.map((d) => d.StationNumber)[0];
};
export const getStationName = (stationId, stationList) => {
const Stations = stationList.map((a) =>
a.filter((d) => d.StationNumber == stationId)
);
const Station =
Stations &&
Stations.reduce((newArray, e) => {
return newArray.concat(e);
}, []);
if (!Station[0]) return [];
return Station.map((d) => d.StaitonName)[0];
};

View File

@ -25,9 +25,9 @@ export const lineList = [
"土讃線(多度津-高知間)[D]",
"土讃線(高知-窪川間)[K]",
"高徳線(高松-徳島間)[T]",
"徳島線(徳島-阿波池田)[B]",
"徳島線(徳島-阿波池田)[B]",
"鳴門線(池谷-鳴門間)[N]",
"瀬戸大橋線(宇多津-児島間)[M]",
"瀬戸大橋線(児島-宇多津間)[M]",
];
export const lineListPair = {
Y: "予讃線(高松-松山間)[Y]",
@ -36,9 +36,9 @@ export const lineListPair = {
D: "土讃線(多度津-高知間)[D]",
K: "土讃線(高知-窪川間)[K]",
T: "高徳線(高松-徳島間)[T]",
B: "徳島線(徳島-阿波池田)[B]",
B: "徳島線(徳島-阿波池田)[B]",
N: "鳴門線(池谷-鳴門間)[N]",
M: "瀬戸大橋線(宇多津-児島間)[M]",
M: "瀬戸大橋線(児島-宇多津間)[M]",
};
export const getStationList = async (props) => {
@ -65,9 +65,9 @@ export const getStationList = async (props) => {
stationList["土讃線(多度津-高知間)[D]"],
stationList["土讃線(高知-窪川間)[K]"],
stationList["高徳線(高松-徳島間)[T]"],
stationList["徳島線(徳島-阿波池田)[B]"],
stationList["徳島線(徳島-阿波池田)[B]"],
stationList["鳴門線(池谷-鳴門間)[N]"],
stationList["瀬戸大橋線(宇多津-児島間)[M]"],
stationList["瀬戸大橋線(児島-宇多津間)[M]"],
stationList.駅間リスト,
stationList.日英対応表,
] = values;
@ -160,16 +160,16 @@ export const getStationList = async (props) => {
stationList.日英対応表
);
const tokushimaCurrent = addStationPosition(
concatBetweenStations(stationList["徳島線(徳島-阿波池田)[B]"]),
concatBetweenStations(stationList["徳島線(徳島-阿波池田)[B]"]),
徳島線,
stationList.日英対応表
);
stationList["徳島線(徳島-阿波池田)[B]"] = [
stationList["徳島線(徳島-阿波池田)[B]"] = [
tokushimaCurrent[tokushimaCurrent.length - 1],
...tokushimaCurrent,
];
stationList["徳島線(徳島-阿波池田)[B]"].pop();
stationList["瀬戸大橋線(宇多津-児島間)[M]"] = [
stationList["徳島線(徳島-阿波池田)[B]"].pop();
stationList["瀬戸大橋線(児島-宇多津間)[M]"] = [
{
Station_JP: "坂出",
Station_EN: "Sakaide",

View File

@ -32,3 +32,15 @@ export const stationIDPair = {
naruto: "N",
seto: "M",
};
export const stationNamePair = {
"予讃線(高松 - 松山)": "yosan",
"予讃線・内子線(松山 - 内子 - 宇和島)": "uwajima",
"予讃線・伊予灘線(向井原 - 伊予大洲)": "uwajima2",
"土讃線(多度津 - 高知)": "dosan",
"土讃線(高知 - 窪川)": "dosan2",
"高徳線(高松 - 徳島)": "koutoku",
"徳島線(徳島 - 阿波池田)": "tokushima",
"鳴門線(池谷 - 鳴門)": "naruto",
"瀬戸大橋線(児島 - 宇多津)": "seto",
};

View File

@ -696,7 +696,11 @@ const setStrings = () =>{
} catch (e) {}
}
const textInsert = new MutationObserver( (mutations) => setStrings());
const textInsert = new MutationObserver( (mutations) =>{
setStrings();
const currentLines = document.querySelector('#topHeader div').innerText;
window.ReactNativeWebView.postMessage(JSON.stringify({type:"currentLines",currentLines}));
});
// 監視を開始
textInsert.observe(document.getElementById('disp'), {

View File

@ -52,7 +52,7 @@ export default function Menu({ getCurrentTrain }) {
const makeCurrentStation = (location) => {
if (!originalStationList) return () => {};
const findStationEachLine = (selectLine) => {
const searchArea = 0.0015;
const searchArea = 0.002;
const _calcDistance = (from, to) => {
let lat = Math.abs(from.lat - to.lat);
let lng = Math.abs(from.lng - to.lng);
@ -172,6 +172,7 @@ export default function Menu({ getCurrentTrain }) {
<Sign
currentStation={item}
originalStationList={originalStationList}
isCurrentStation={item == currentStation}
oP={() => {
const payload = {
currentStation:

View File

@ -31,14 +31,23 @@ export const CurrentTrainProvider = ({ children }) => {
.then((response) => response.json())
.then((d) => d.data)
.then((d) =>
d.map((x) => ({ num: x.TrainNum, delay: x.delay, Pos: x.Pos }))
d.map((x) => ({
Index: x.Index,
num: x.TrainNum,
delay: x.delay,
Pos: x.Pos,
PosNum: x.PosNum,
Direction: x.Direction,
Type: x.Type,
Line: x.Line,
}))
)
.then((d) => {
setCurrentTrain(d);
setCurrentTrainLoading("success");
})
.catch(() => {
alert("現在の全在線列車取得エラー/再取得します");
//alert("現在の全在線列車取得エラー/再取得します");
fetch(
"https://script.google.com/macros/s/AKfycby9Y2-Bm75J_WkbZimi7iS8v5r9wMa9wtzpdwES9sOGF4i6HIYEJOM60W6gM1gXzt1o/exec",
HeaderConfig
@ -57,6 +66,9 @@ export const CurrentTrainProvider = ({ children }) => {
});
});
};
const inject = (i) => {
webview.current?.injectJavaScript(i);
};
useEffect(getCurrentTrain, []); //初回だけ現在の全在線列車取得
@ -72,6 +84,7 @@ export const CurrentTrainProvider = ({ children }) => {
currentTrainLoading,
setCurrentTrainLoading,
getCurrentTrain,
inject,
}}
>
{children}

36
stateBox/useTrainMenu.js Normal file
View File

@ -0,0 +1,36 @@
import React, { createContext, useContext, useState } from "react";
const initialState = {
selectedLine: undefined,
setSelectedLine: () => {},
mapsStationData: undefined,
setMapsStationData: () => {},
injectJavaScript: "",
setInjectJavaScript: () => {},
};
const TrainMenuContext = createContext(initialState);
export const useTrainMenu = () => {
return useContext(TrainMenuContext);
};
export const TrainMenuProvider = ({ children }) => {
const [selectedLine, setSelectedLine] = useState(undefined);
const [mapsStationData, setMapsStationData] = useState(undefined);
const [injectJavaScript, setInjectJavaScript] = useState();
return (
<TrainMenuContext.Provider
value={{
selectedLine,
setSelectedLine,
mapsStationData,
setMapsStationData,
injectJavaScript,
setInjectJavaScript,
}}
>
{children}
</TrainMenuContext.Provider>
);
};