Skip to content

Commit 5b0e487

Browse files
TinyKittenclaude
andcommitted
プリセット機能の大幅改善: direction/notifyStationIds保存、始発駅選択UI、PresetCard表示改善
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent b10e877 commit 5b0e487

16 files changed

+682
-137
lines changed

assets/translations/en.json

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -278,7 +278,10 @@
278278
"settingsWalkthroughTitle4": "Display Languages",
279279
"settingsWalkthroughDescription4": "Set the languages to display on screen. You can choose from Japanese, English, Chinese, and Korean.",
280280
"requireJapaneseOrEnglish": "Either Japanese or English must be set.",
281-
"presetNameInputTitle": "Enter preset name",
281+
"savePresetTitle": "Save preset",
282+
"presetNameLabel": "Preset name",
282283
"presetNamePlaceholder": "Preset name",
283-
"save": "Save"
284+
"save": "Save",
285+
"selectStartStationTitle": "Select starting station",
286+
"departure": "Dep."
284287
}

assets/translations/ja.json

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -279,7 +279,10 @@
279279
"settingsWalkthroughTitle4": "表示言語",
280280
"settingsWalkthroughDescription4": "画面に表示する言語を設定できます。日本語、英語、中国語、韓国語から選択可能です。",
281281
"requireJapaneseOrEnglish": "日本語または英語のいずれかを設定する必要があります",
282-
"presetNameInputTitle": "プリセット名を入力",
282+
"savePresetTitle": "プリセットを保存",
283+
"presetNameLabel": "プリセット名",
283284
"presetNamePlaceholder": "プリセット名",
284-
"save": "保存"
285+
"save": "保存",
286+
"selectStartStationTitle": "始発駅を選択",
287+
"departure": "始発"
285288
}

src/components/CommonCard.tsx

Lines changed: 30 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,14 @@ type Props = {
2020
targetStation?: Station;
2121
stations?: Station[];
2222
title?: string;
23+
/** カッコ内の文字を小さく表示する際、カッコ自体を非表示にする */
24+
hideParens?: boolean;
2325
subtitle?: string;
2426
subtitleNumberOfLines?: number;
27+
/** 右端のシェブロンを非表示にする */
28+
hideChevron?: boolean;
29+
/** 右端にチェックマークを表示する */
30+
checked?: boolean;
2531
disabled?: boolean;
2632
testID?: string;
2733
loading?: boolean;
@@ -166,8 +172,11 @@ export const CommonCard: React.FC<Props> = ({
166172
targetStation,
167173
stations = [],
168174
title,
175+
hideParens,
169176
subtitle,
170177
subtitleNumberOfLines,
178+
hideChevron,
179+
checked,
171180
disabled,
172181
testID,
173182
loading,
@@ -297,8 +306,9 @@ export const CommonCard: React.FC<Props> = ({
297306
/^\(.*\)$/.test(part) ? (
298307
<Typography key={`${index}-${part}`} style={styles.titleParens}>
299308
{index > 0 && !/\s$/.test(titleParts[index - 1] ?? '')
300-
? ` ${part}`
301-
: part}
309+
? ' '
310+
: ''}
311+
{hideParens ? part.slice(1, -1) : part}
302312
</Typography>
303313
) : (
304314
part
@@ -323,7 +333,24 @@ export const CommonCard: React.FC<Props> = ({
323333
)}
324334
</View>
325335
<View style={styles.chevron}>
326-
<CardChevron />
336+
{!hideChevron && <CardChevron />}
337+
{hideChevron && !checked && (
338+
<Svg width={24} height={24} viewBox="0 0 24 24">
339+
<Path
340+
d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm0 18c-4.42 0-8-3.58-8-8s3.58-8 8-8 8 3.58 8 8-3.58 8-8 8z"
341+
fill="#fff"
342+
opacity={0.5}
343+
/>
344+
</Svg>
345+
)}
346+
{hideChevron && checked && (
347+
<Svg width={24} height={24} viewBox="0 0 24 24">
348+
<Path
349+
d="M12 2C6.48 2 2 6.48 2 12s4.48 10 10 10 10-4.48 10-10S17.52 2 12 2zm-2 15l-5-5 1.41-1.41L10 14.17l7.59-7.59L19 8l-9 9z"
350+
fill="#fff"
351+
/>
352+
</Svg>
353+
)}
327354
</View>
328355
</TouchableOpacity>
329356
);

src/components/CustomModal.tsx

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import React, { useEffect, useRef, useState } from 'react';
44
import type { StyleProp, ViewStyle } from 'react-native';
55
import {
66
Animated,
7+
type GestureResponderEvent,
78
Keyboard,
89
KeyboardAvoidingView,
910
Pressable,
@@ -29,6 +30,10 @@ type Props = {
2930

3031
const ANIMATION_DURATION = 180;
3132
const AnimatedPressable = Animated.createAnimatedComponent(Pressable);
33+
const captureModalTouch = () => true;
34+
const stopModalTouchPropagation = (event: GestureResponderEvent) => {
35+
event.stopPropagation();
36+
};
3237

3338
export const CustomModal: React.FC<Props> = ({
3439
visible,
@@ -128,6 +133,8 @@ export const CustomModal: React.FC<Props> = ({
128133
animatedContentStyle,
129134
]}
130135
pointerEvents="auto"
136+
onStartShouldSetResponder={captureModalTouch}
137+
onTouchEnd={stopModalTouchPropagation}
131138
>
132139
{children}
133140
</Animated.View>
@@ -147,6 +154,8 @@ export const CustomModal: React.FC<Props> = ({
147154
animatedContentStyle,
148155
]}
149156
pointerEvents="auto"
157+
onStartShouldSetResponder={captureModalTouch}
158+
onTouchEnd={stopModalTouchPropagation}
150159
>
151160
{children}
152161
</Animated.View>

src/components/PresetCard.tsx

Lines changed: 34 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import { isJapanese, translate } from '~/translation';
1010
import isTablet from '~/utils/isTablet';
1111
import { RFValue } from '~/utils/rfValue';
1212
import { getStationName, getStationPrimaryCode } from '~/utils/station';
13+
import { getIsLocal } from '~/utils/trainTypeString';
1314
import { NoPresetsCard } from './NoPresetsCard';
1415
import TransferLineMark from './TransferLineMark';
1516
import Typography from './Typography';
@@ -77,7 +78,7 @@ const styles = StyleSheet.create({
7778
gap: 8,
7879
},
7980
stationName: {
80-
fontSize: RFValue(21),
81+
fontSize: RFValue(17),
8182
fontWeight: 'bold',
8283
textAlignVertical: 'auto',
8384
},
@@ -91,6 +92,11 @@ const styles = StyleSheet.create({
9192
fontWeight: 'bold',
9293
textAlignVertical: 'auto',
9394
},
95+
trainTypeName: {
96+
fontSize: RFValue(9),
97+
fontWeight: 'bold',
98+
paddingLeft: 24,
99+
},
94100
lineDot: {
95101
width: 16,
96102
height: 16,
@@ -184,6 +190,17 @@ const PresetCardBase: React.FC<Props> = ({ title, from, to }) => {
184190
: (rightLine.nameRoman ?? rightLine.nameShort ?? null);
185191
})();
186192

193+
const leftTrainType = (() => {
194+
const tt = from?.trainType;
195+
if (!tt || getIsLocal(tt)) return null;
196+
return isJapanese ? (tt.name ?? null) : (tt.nameRoman ?? null);
197+
})();
198+
const rightTrainType = (() => {
199+
const tt = to?.trainType;
200+
if (!tt || getIsLocal(tt)) return null;
201+
return isJapanese ? (tt.name ?? null) : (tt.nameRoman ?? null);
202+
})();
203+
187204
const leftCodeRendered = useMemo(
188205
() =>
189206
renderTextWithSmallerParens(
@@ -252,6 +269,14 @@ const PresetCardBase: React.FC<Props> = ({ title, from, to }) => {
252269
</Typography>
253270
</View>
254271
) : null}
272+
{leftTrainType ? (
273+
<Typography
274+
style={[styles.trainTypeName, { color: metaFg }]}
275+
numberOfLines={1}
276+
>
277+
{leftTrainType}
278+
</Typography>
279+
) : null}
255280
</View>
256281
<View style={styles.colCenter} />
257282
<View style={styles.colRight}>
@@ -282,6 +307,14 @@ const PresetCardBase: React.FC<Props> = ({ title, from, to }) => {
282307
</Typography>
283308
</View>
284309
) : null}
310+
{rightTrainType ? (
311+
<Typography
312+
style={[styles.trainTypeName, { color: metaFg }]}
313+
numberOfLines={1}
314+
>
315+
{rightTrainType}
316+
</Typography>
317+
) : null}
285318
</View>
286319
</View>
287320
)}

0 commit comments

Comments
 (0)