chore: add options for alerts

This commit is contained in:
2026-03-08 18:59:52 +01:00
parent 8d63ecd496
commit 70b1f26425
5 changed files with 104 additions and 4 deletions
+2 -2
View File
@@ -205,14 +205,14 @@ export const getMyLocation = async (): Promise<{
// ALERTES
// ============================================
export const triggerPoliceAlert = async (): Promise<{
export const triggerPoliceAlert = async (alertMessage: string): Promise<{
success: boolean;
alert_id?: number;
message?: string;
error?: string;
}> => {
try {
const { data } = await apiClient.post(`${API}/alert`);
const { data } = await apiClient.post(`${API}/alert`, { message: alertMessage });
return {
success: true,
alert_id: data.alert_id,
+1
View File
@@ -60,6 +60,7 @@ export interface Alert {
id: number;
username: string;
status: string;
message: string;
created_at: string;
updated_at: string;
}
@@ -44,6 +44,12 @@ export default function AlertsScreen() {
fontSize: fontSize.md,
fontWeight: "600",
},
alertMessage: {
color: colors.danger,
fontSize: fontSize.sm,
fontWeight: "600",
marginTop: 2,
},
date: {
color: colors.textMuted,
fontSize: fontSize.xs,
@@ -75,6 +81,9 @@ export default function AlertsScreen() {
<Text style={styles.username}>
Livreur: {item.username}
</Text>
{item.message ? (
<Text style={styles.alertMessage}>{item.message}</Text>
) : null}
<Text style={styles.date}>
{new Date(item.created_at).toLocaleString("fr-FR")}
</Text>
@@ -56,6 +56,12 @@ export default function AlertsScreen() {
fontSize: fontSize.md,
fontWeight: "600",
},
alertMessage: {
color: colors.danger,
fontSize: fontSize.sm,
fontWeight: "600",
marginTop: 2,
},
date: {
color: colors.textMuted,
fontSize: fontSize.xs,
@@ -108,6 +114,9 @@ export default function AlertsScreen() {
<Text style={styles.username}>
Livreur: {item.username}
</Text>
{item.message ? (
<Text style={styles.alertMessage}>{item.message}</Text>
) : null}
<Text style={styles.date}>
{new Date(item.created_at).toLocaleString("fr-FR")}
</Text>
@@ -25,14 +25,21 @@ import Button from "../../components/ui/Button";
import AlertModal from "../../components/ui/AlertModal";
import { useAlert } from "../../hooks/useAlert";
const ALERT_PHRASES = [
{ label: "Contrôle de police", icon: "shield-outline" as const },
{ label: "Guet-apens", icon: "warning-outline" as const },
];
export default function AlertsScreen() {
const { colors } = useTheme();
const [alerts, setAlerts] = useState<AlertType[]>([]);
const [loading, setLoading] = useState(true);
const [refreshing, setRefreshing] = useState(false);
const [triggering, setTriggering] = useState(false);
const [showPhraseModal, setShowPhraseModal] = useState(false);
const [showConfirmModal, setShowConfirmModal] = useState(false);
const [showSuccessModal, setShowSuccessModal] = useState(false);
const [selectedPhrase, setSelectedPhrase] = useState("");
const [successMessage, setSuccessMessage] = useState("");
const [pulseAnim] = useState(() => new Animated.Value(1));
const { alert: alertModal, showError, hideAlert } = useAlert();
@@ -77,10 +84,16 @@ export default function AlertsScreen() {
setRefreshing(false);
};
const handleSelectPhrase = (phrase: string) => {
setSelectedPhrase(phrase);
setShowPhraseModal(false);
setShowConfirmModal(true);
};
const handleConfirmTrigger = async () => {
setShowConfirmModal(false);
setTriggering(true);
const res = await triggerPoliceAlert();
const res = await triggerPoliceAlert(selectedPhrase);
setTriggering(false);
if (res.success) {
setSuccessMessage(res.message || "Alerte déclenchée avec succès");
@@ -113,6 +126,9 @@ export default function AlertsScreen() {
}
/>
<View style={{ flex: 1, marginLeft: spacing.m }}>
{item.message ? (
<Text style={styles.alertMessage}>{item.message}</Text>
) : null}
<Text style={styles.date}>
{new Date(item.created_at).toLocaleString("fr-FR")}
</Text>
@@ -142,6 +158,7 @@ export default function AlertsScreen() {
StyleSheet.create({
container: { flex: 1, backgroundColor: colors.bgPrimary },
row: { flexDirection: "row", alignItems: "center" },
alertMessage: { color: colors.textPrimary, fontSize: fontSize.md, fontWeight: "600", marginBottom: 2 },
date: { color: colors.textMuted, fontSize: fontSize.sm },
empty: {
color: colors.textMuted,
@@ -303,6 +320,21 @@ export default function AlertsScreen() {
fontSize: fontSize.md,
fontWeight: "700",
},
phraseBtn: {
flexDirection: "row",
alignItems: "center",
gap: spacing.m,
paddingVertical: 14,
paddingHorizontal: spacing.l,
borderRadius: borderRadius.sm,
borderWidth: 1,
backgroundColor: colors.bgInput,
},
phraseBtnText: {
fontSize: fontSize.md,
fontWeight: "600",
flex: 1,
},
}),
[colors],
);
@@ -311,6 +343,50 @@ export default function AlertsScreen() {
return (
<View style={styles.container}>
{/* Phrase selection Modal */}
<Modal
visible={showPhraseModal}
transparent
animationType="fade"
onRequestClose={() => setShowPhraseModal(false)}
>
<View style={styles.modalOverlay}>
<View style={[styles.modalContent, { borderColor: colors.danger + "40" }]}>
<View style={styles.modalIconCircle}>
<View style={styles.modalIconInner}>
<Ionicons name="warning" size={40} color={colors.white} />
</View>
</View>
<Text style={styles.modalTitle}>Type d'alerte</Text>
<Text style={styles.modalMessage}>
Sélectionnez la raison de l'alerte.
</Text>
<View style={{ width: "100%", gap: spacing.m, marginBottom: spacing.l }}>
{ALERT_PHRASES.map((p) => (
<TouchableOpacity
key={p.label}
style={[styles.phraseBtn, { borderColor: colors.danger }]}
onPress={() => handleSelectPhrase(p.label)}
activeOpacity={0.7}
>
<Ionicons name={p.icon} size={20} color={colors.danger} />
<Text style={[styles.phraseBtnText, { color: colors.textWhite }]}>
{p.label}
</Text>
</TouchableOpacity>
))}
</View>
<TouchableOpacity
style={styles.modalCancelBtn}
onPress={() => setShowPhraseModal(false)}
activeOpacity={0.7}
>
<Text style={styles.modalCancelText}>Annuler</Text>
</TouchableOpacity>
</View>
</View>
</Modal>
{/* Confirmation Modal */}
<Modal
visible={showConfirmModal}
@@ -342,6 +418,11 @@ export default function AlertsScreen() {
police. Cette action notifiera immédiatement
l'administration.
</Text>
{selectedPhrase ? (
<Text style={[styles.modalWarning, { color: colors.danger, marginBottom: spacing.m }]}>
{selectedPhrase}
</Text>
) : null}
<Text style={styles.modalWarning}>
Confirmez-vous le déclenchement ?
</Text>
@@ -417,7 +498,7 @@ export default function AlertsScreen() {
<View style={styles.triggerSection}>
<Button
title={triggering ? "Envoi..." : "Déclencher alerte police"}
onPress={() => setShowConfirmModal(true)}
onPress={() => setShowPhraseModal(true)}
disabled={triggering}
style={{ backgroundColor: colors.danger }}
/>