Compare commits
2 Commits
luggage-li
...
luggage-li
| Author | SHA1 | Date | |
|---|---|---|---|
| fbdae66c9b | |||
| e8ffab355e |
@@ -22,7 +22,6 @@ const emptyTripForm = () => ({
|
|||||||
location: '',
|
location: '',
|
||||||
startDate: todayYMD(),
|
startDate: todayYMD(),
|
||||||
endDate: todayYMD(),
|
endDate: todayYMD(),
|
||||||
imageUri: '',
|
|
||||||
copyDefaultTemplate: true,
|
copyDefaultTemplate: true,
|
||||||
setAsDefaultTemplate: false,
|
setAsDefaultTemplate: false,
|
||||||
});
|
});
|
||||||
@@ -279,7 +278,7 @@ export default function AppRoot() {
|
|||||||
location: tripForm.location.trim(),
|
location: tripForm.location.trim(),
|
||||||
startDate: tripForm.startDate,
|
startDate: tripForm.startDate,
|
||||||
endDate: tripForm.endDate,
|
endDate: tripForm.endDate,
|
||||||
imageUri: tripForm.imageUri,
|
imageUri: '',
|
||||||
archived: false,
|
archived: false,
|
||||||
createdAt: now,
|
createdAt: now,
|
||||||
updatedAt: now,
|
updatedAt: now,
|
||||||
@@ -344,7 +343,6 @@ export default function AppRoot() {
|
|||||||
location: patch.location.trim(),
|
location: patch.location.trim(),
|
||||||
startDate: patch.startDate,
|
startDate: patch.startDate,
|
||||||
endDate: patch.endDate,
|
endDate: patch.endDate,
|
||||||
imageUri: patch.imageUri,
|
|
||||||
updatedAt: Date.now(),
|
updatedAt: Date.now(),
|
||||||
}
|
}
|
||||||
: trip
|
: trip
|
||||||
@@ -763,18 +761,6 @@ export default function AppRoot() {
|
|||||||
<TripsTab
|
<TripsTab
|
||||||
tripForm={tripForm}
|
tripForm={tripForm}
|
||||||
updateTripForm={updateTripForm}
|
updateTripForm={updateTripForm}
|
||||||
pickTripImage={(onPicked) =>
|
|
||||||
pickImage((uri) => {
|
|
||||||
if (typeof onPicked === 'function') onPicked(uri);
|
|
||||||
else updateTripForm('imageUri', uri);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
takeTripImage={(onPicked) =>
|
|
||||||
takeImage((uri) => {
|
|
||||||
if (typeof onPicked === 'function') onPicked(uri);
|
|
||||||
else updateTripForm('imageUri', uri);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
templateTrip={templateTrip}
|
templateTrip={templateTrip}
|
||||||
createTrip={createTrip}
|
createTrip={createTrip}
|
||||||
trips={data.trips}
|
trips={data.trips}
|
||||||
|
|||||||
@@ -14,6 +14,17 @@ export default function ItemCard({ item, onEdit, onDelete, onQuickPack, onQuickU
|
|||||||
return (
|
return (
|
||||||
<View style={styles.itemCard}>
|
<View style={styles.itemCard}>
|
||||||
<View style={[styles.itemAccent, { backgroundColor: statusAccent(item.status) }]} />
|
<View style={[styles.itemAccent, { backgroundColor: statusAccent(item.status) }]} />
|
||||||
|
|
||||||
|
<View style={styles.itemThumbWrap}>
|
||||||
|
{item.imageUri ? (
|
||||||
|
<Image source={{ uri: item.imageUri }} style={styles.itemThumbSmall} />
|
||||||
|
) : (
|
||||||
|
<View style={styles.itemThumbPlaceholder}>
|
||||||
|
<Text style={styles.itemThumbPlaceholderText}>🧳</Text>
|
||||||
|
</View>
|
||||||
|
)}
|
||||||
|
</View>
|
||||||
|
|
||||||
<View style={styles.itemMain}>
|
<View style={styles.itemMain}>
|
||||||
<View style={styles.cardRow}>
|
<View style={styles.cardRow}>
|
||||||
<View style={styles.flex}>
|
<View style={styles.flex}>
|
||||||
@@ -41,8 +52,6 @@ export default function ItemCard({ item, onEdit, onDelete, onQuickPack, onQuickU
|
|||||||
<Text style={[styles.quickStatusBtnText, isUnpacked && styles.quickStatusBtnTextActive]}>Unpack</Text>
|
<Text style={[styles.quickStatusBtnText, isUnpacked && styles.quickStatusBtnTextActive]}>Unpack</Text>
|
||||||
</Pressable>
|
</Pressable>
|
||||||
</View>
|
</View>
|
||||||
|
|
||||||
{item.imageUri ? <Image source={{ uri: item.imageUri }} style={styles.previewImageSmall} /> : null}
|
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -282,13 +282,38 @@ export const styles = StyleSheet.create({
|
|||||||
borderColor: '#1f2937',
|
borderColor: '#1f2937',
|
||||||
overflow: 'hidden',
|
overflow: 'hidden',
|
||||||
flexDirection: 'row',
|
flexDirection: 'row',
|
||||||
|
alignItems: 'flex-start',
|
||||||
},
|
},
|
||||||
itemAccent: {
|
itemAccent: {
|
||||||
width: 5,
|
width: 5,
|
||||||
|
alignSelf: 'stretch',
|
||||||
|
},
|
||||||
|
itemThumbWrap: {
|
||||||
|
paddingTop: 10,
|
||||||
|
paddingLeft: 10,
|
||||||
|
},
|
||||||
|
itemThumbSmall: {
|
||||||
|
width: 46,
|
||||||
|
height: 46,
|
||||||
|
borderRadius: 8,
|
||||||
|
backgroundColor: '#0b1220',
|
||||||
|
},
|
||||||
|
itemThumbPlaceholder: {
|
||||||
|
width: 46,
|
||||||
|
height: 46,
|
||||||
|
borderRadius: 8,
|
||||||
|
backgroundColor: '#0b1220',
|
||||||
|
alignItems: 'center',
|
||||||
|
justifyContent: 'center',
|
||||||
|
borderWidth: 1,
|
||||||
|
borderColor: '#243244',
|
||||||
|
},
|
||||||
|
itemThumbPlaceholderText: {
|
||||||
|
fontSize: 18,
|
||||||
},
|
},
|
||||||
itemMain: {
|
itemMain: {
|
||||||
flex: 1,
|
flex: 1,
|
||||||
padding: 12,
|
padding: 10,
|
||||||
gap: 8,
|
gap: 8,
|
||||||
},
|
},
|
||||||
itemTitle: {
|
itemTitle: {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
import React, { useMemo, useState } from 'react';
|
import React, { useMemo, useState } from 'react';
|
||||||
import { Image, KeyboardAvoidingView, Modal, Platform, Pressable, ScrollView, Text, TextInput, View } from 'react-native';
|
import { KeyboardAvoidingView, Modal, Platform, Pressable, ScrollView, Text, TextInput, View } from 'react-native';
|
||||||
import DatePickerModal from '../components/DatePickerModal';
|
import DatePickerModal from '../components/DatePickerModal';
|
||||||
import Field from '../components/Field';
|
import Field from '../components/Field';
|
||||||
import { styles } from '../styles';
|
import { styles } from '../styles';
|
||||||
@@ -19,14 +19,11 @@ const emptyEditForm = {
|
|||||||
location: '',
|
location: '',
|
||||||
startDate: '',
|
startDate: '',
|
||||||
endDate: '',
|
endDate: '',
|
||||||
imageUri: '',
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default function TripsTab({
|
export default function TripsTab({
|
||||||
tripForm,
|
tripForm,
|
||||||
updateTripForm,
|
updateTripForm,
|
||||||
pickTripImage,
|
|
||||||
takeTripImage,
|
|
||||||
templateTrip,
|
templateTrip,
|
||||||
createTrip,
|
createTrip,
|
||||||
trips,
|
trips,
|
||||||
@@ -68,7 +65,6 @@ export default function TripsTab({
|
|||||||
location: trip.location || '',
|
location: trip.location || '',
|
||||||
startDate: trip.startDate || '',
|
startDate: trip.startDate || '',
|
||||||
endDate: trip.endDate || '',
|
endDate: trip.endDate || '',
|
||||||
imageUri: trip.imageUri || '',
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -83,14 +79,6 @@ export default function TripsTab({
|
|||||||
setEditMode(false);
|
setEditMode(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
function pickViewTripImage() {
|
|
||||||
pickTripImage((uri) => updateEditForm('imageUri', uri));
|
|
||||||
}
|
|
||||||
|
|
||||||
function takeViewTripImage() {
|
|
||||||
takeTripImage((uri) => updateEditForm('imageUri', uri));
|
|
||||||
}
|
|
||||||
|
|
||||||
function applyTemplateFromView() {
|
function applyTemplateFromView() {
|
||||||
if (!viewingTrip) return;
|
if (!viewingTrip) return;
|
||||||
setTripAsTemplate(viewingTrip.id);
|
setTripAsTemplate(viewingTrip.id);
|
||||||
@@ -124,7 +112,6 @@ export default function TripsTab({
|
|||||||
|
|
||||||
{activeTrip ? (
|
{activeTrip ? (
|
||||||
<View style={styles.tripHeroCard}>
|
<View style={styles.tripHeroCard}>
|
||||||
{activeTrip.imageUri ? <Image source={{ uri: activeTrip.imageUri }} style={styles.tripHeroImage} /> : null}
|
|
||||||
<Text style={styles.tripHeroTitle}>{activeTrip.name}</Text>
|
<Text style={styles.tripHeroTitle}>{activeTrip.name}</Text>
|
||||||
<Text style={styles.cardMeta}>{activeTrip.location || 'No location'} · {activeTrip.startDate} → {activeTrip.endDate}</Text>
|
<Text style={styles.cardMeta}>{activeTrip.location || 'No location'} · {activeTrip.startDate} → {activeTrip.endDate}</Text>
|
||||||
<Text style={styles.cardMeta}>{activeTripItemCount} items · {activeTripCheckupCount} check-ups</Text>
|
<Text style={styles.cardMeta}>{activeTripItemCount} items · {activeTripCheckupCount} check-ups</Text>
|
||||||
@@ -155,7 +142,6 @@ export default function TripsTab({
|
|||||||
</Pressable>
|
</Pressable>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
{trip.imageUri ? <Image source={{ uri: trip.imageUri }} style={styles.previewImageSmall} /> : null}
|
|
||||||
</View>
|
</View>
|
||||||
))}
|
))}
|
||||||
|
|
||||||
@@ -226,17 +212,6 @@ export default function TripsTab({
|
|||||||
<DateField label="Start Date" value={tripForm.startDate} onPress={() => openDatePicker('startDate')} />
|
<DateField label="Start Date" value={tripForm.startDate} onPress={() => openDatePicker('startDate')} />
|
||||||
<DateField label="End Date" value={tripForm.endDate} onPress={() => openDatePicker('endDate')} />
|
<DateField label="End Date" value={tripForm.endDate} onPress={() => openDatePicker('endDate')} />
|
||||||
|
|
||||||
<View style={styles.actionRow}>
|
|
||||||
<Pressable style={[styles.secondaryBtnTight, styles.flex]} onPress={takeTripImage}>
|
|
||||||
<Text style={styles.secondaryBtnText}>Take photo</Text>
|
|
||||||
</Pressable>
|
|
||||||
<Pressable style={[styles.secondaryBtnTight, styles.flex]} onPress={pickTripImage}>
|
|
||||||
<Text style={styles.secondaryBtnText}>{tripForm.imageUri ? 'From gallery (change)' : 'From gallery'}</Text>
|
|
||||||
</Pressable>
|
|
||||||
</View>
|
|
||||||
|
|
||||||
{tripForm.imageUri ? <Image source={{ uri: tripForm.imageUri }} style={styles.previewImage} /> : null}
|
|
||||||
|
|
||||||
{templateTrip ? (
|
{templateTrip ? (
|
||||||
<Pressable style={styles.inlineToggle} onPress={() => updateTripForm('copyDefaultTemplate', !tripForm.copyDefaultTemplate)}>
|
<Pressable style={styles.inlineToggle} onPress={() => updateTripForm('copyDefaultTemplate', !tripForm.copyDefaultTemplate)}>
|
||||||
<Text style={styles.inlineToggleText}>
|
<Text style={styles.inlineToggleText}>
|
||||||
@@ -283,7 +258,6 @@ export default function TripsTab({
|
|||||||
>
|
>
|
||||||
{!editMode ? (
|
{!editMode ? (
|
||||||
<>
|
<>
|
||||||
{viewingTrip.imageUri ? <Image source={{ uri: viewingTrip.imageUri }} style={styles.previewImage} /> : null}
|
|
||||||
<Text style={styles.tripHeroTitle}>{viewingTrip.name}</Text>
|
<Text style={styles.tripHeroTitle}>{viewingTrip.name}</Text>
|
||||||
<Text style={styles.cardMeta}>{viewingTrip.location || 'No location'}</Text>
|
<Text style={styles.cardMeta}>{viewingTrip.location || 'No location'}</Text>
|
||||||
<Text style={styles.cardMeta}>{viewingTrip.startDate} → {viewingTrip.endDate}</Text>
|
<Text style={styles.cardMeta}>{viewingTrip.startDate} → {viewingTrip.endDate}</Text>
|
||||||
@@ -333,17 +307,6 @@ export default function TripsTab({
|
|||||||
<DateField label="Start Date" value={editForm.startDate} onPress={() => setViewDatePicker({ visible: true, field: 'startDate' })} />
|
<DateField label="Start Date" value={editForm.startDate} onPress={() => setViewDatePicker({ visible: true, field: 'startDate' })} />
|
||||||
<DateField label="End Date" value={editForm.endDate} onPress={() => setViewDatePicker({ visible: true, field: 'endDate' })} />
|
<DateField label="End Date" value={editForm.endDate} onPress={() => setViewDatePicker({ visible: true, field: 'endDate' })} />
|
||||||
|
|
||||||
<View style={styles.actionRow}>
|
|
||||||
<Pressable style={[styles.secondaryBtnTight, styles.flex]} onPress={takeViewTripImage}>
|
|
||||||
<Text style={styles.secondaryBtnText}>Take photo</Text>
|
|
||||||
</Pressable>
|
|
||||||
<Pressable style={[styles.secondaryBtnTight, styles.flex]} onPress={pickViewTripImage}>
|
|
||||||
<Text style={styles.secondaryBtnText}>{editForm.imageUri ? 'From gallery (change)' : 'From gallery'}</Text>
|
|
||||||
</Pressable>
|
|
||||||
</View>
|
|
||||||
|
|
||||||
{editForm.imageUri ? <Image source={{ uri: editForm.imageUri }} style={styles.previewImage} /> : null}
|
|
||||||
|
|
||||||
<Pressable style={styles.primaryBtn} onPress={saveEditFromView}>
|
<Pressable style={styles.primaryBtn} onPress={saveEditFromView}>
|
||||||
<Text style={styles.primaryBtnText}>Save Trip</Text>
|
<Text style={styles.primaryBtnText}>Save Trip</Text>
|
||||||
</Pressable>
|
</Pressable>
|
||||||
|
|||||||
Reference in New Issue
Block a user