mirror of
https://github.com/R0m1k3/Regisflow.git
synced 2026-10-22 14:48:19 +02:00
Add option to include and display a photo of the sales receipt
Implements `photoTicket` field in `Sale` and `FormData` types, adds UI elements in `NewSaleForm` and `SaleDetailsModal` components, and updates schema.ts. Replit-Commit-Author: Agent Replit-Commit-Session-Id: dec54137-d5a2-4406-8ad4-5f2f9fb110bf Replit-Commit-Screenshot-Url: https://storage.googleapis.com/screenshot-production-us-central1/0715008c-7244-40f4-befc-26c014852236/7df9e24f-d78b-4589-9a08-c70e02d6d7d9.jpg
This commit is contained in:
1 parent
e48337925c
commit
4f04428dea
5 files changed
+151
-38
No files matched your search
@@ -35,6 +35,7 @@ interface FormData {
|
||||
dateDelivrance: string;
|
||||
photoRecto?: string;
|
||||
photoVerso?: string;
|
||||
photoTicket?: string;
|
||||
}
|
||||
|
||||
export default function NewSaleForm() {
|
||||
@@ -75,6 +76,7 @@ export default function NewSaleForm() {
|
||||
dateDelivrance: '',
|
||||
photoRecto: '',
|
||||
photoVerso: '',
|
||||
photoTicket: '',
|
||||
}
|
||||
});
|
||||
|
||||
@@ -119,6 +121,7 @@ export default function NewSaleForm() {
|
||||
dateDelivrance: '',
|
||||
photoRecto: '',
|
||||
photoVerso: '',
|
||||
photoTicket: '',
|
||||
});
|
||||
},
|
||||
onError: (error: any) => {
|
||||
@@ -235,7 +238,13 @@ export default function NewSaleForm() {
|
||||
const photoData = await capturePhoto();
|
||||
console.log('Photo captured successfully, data length:', photoData.length);
|
||||
|
||||
form.setValue(currentPhotoType === 'recto' ? 'photoRecto' : 'photoVerso', photoData);
|
||||
if (currentPhotoType === 'recto') {
|
||||
form.setValue('photoRecto', photoData);
|
||||
} else if (currentPhotoType === 'verso') {
|
||||
form.setValue('photoVerso', photoData);
|
||||
} else if (currentPhotoType === 'ticket') {
|
||||
form.setValue('photoTicket', photoData);
|
||||
}
|
||||
|
||||
toast({
|
||||
title: "Photo capturée",
|
||||
@@ -255,7 +264,13 @@ export default function NewSaleForm() {
|
||||
};
|
||||
|
||||
const handleRemovePhoto = (photoType: PhotoType) => {
|
||||
form.setValue(photoType === 'recto' ? 'photoRecto' : 'photoVerso', '');
|
||||
if (photoType === 'recto') {
|
||||
form.setValue('photoRecto', '');
|
||||
} else if (photoType === 'verso') {
|
||||
form.setValue('photoVerso', '');
|
||||
} else if (photoType === 'ticket') {
|
||||
form.setValue('photoTicket', '');
|
||||
}
|
||||
toast({
|
||||
title: "Photo supprimée",
|
||||
description: `Photo ${photoType} supprimée`,
|
||||
@@ -288,7 +303,13 @@ export default function NewSaleForm() {
|
||||
const reader = new FileReader();
|
||||
reader.onload = (e) => {
|
||||
const result = e.target?.result as string;
|
||||
form.setValue(photoType === 'recto' ? 'photoRecto' : 'photoVerso', result);
|
||||
if (photoType === 'recto') {
|
||||
form.setValue('photoRecto', result);
|
||||
} else if (photoType === 'verso') {
|
||||
form.setValue('photoVerso', result);
|
||||
} else if (photoType === 'ticket') {
|
||||
form.setValue('photoTicket', result);
|
||||
}
|
||||
toast({
|
||||
title: "Photo ajoutée",
|
||||
description: `Photo ${photoType} ajoutée avec succès`,
|
||||
@@ -715,6 +736,63 @@ export default function NewSaleForm() {
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Photo Ticket de caisse */}
|
||||
<div className="mt-6 space-y-4">
|
||||
<div>
|
||||
<h4 className="text-sm font-medium text-gray-700">Photo du ticket de caisse</h4>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
<label className="text-sm font-medium text-gray-600">Photo Ticket</label>
|
||||
{form.watch('photoTicket') ? (
|
||||
<div className="relative">
|
||||
<img
|
||||
src={form.watch('photoTicket')}
|
||||
alt="Photo ticket"
|
||||
className="w-full h-32 object-cover rounded border"
|
||||
/>
|
||||
<Button
|
||||
type="button"
|
||||
variant="destructive"
|
||||
size="sm"
|
||||
className="absolute top-2 right-2"
|
||||
onClick={() => handleRemovePhoto('ticket')}
|
||||
>
|
||||
<Trash2 className="h-3 w-3" />
|
||||
</Button>
|
||||
</div>
|
||||
) : (
|
||||
<div className="space-y-2">
|
||||
<Button
|
||||
type="button"
|
||||
variant="outline"
|
||||
className="w-full h-24 border-dashed border-2"
|
||||
onClick={() => handlePhotoCapture('ticket')}
|
||||
>
|
||||
<Camera className="h-5 w-5 mr-2" />
|
||||
Prendre photo
|
||||
</Button>
|
||||
<div className="relative">
|
||||
<input
|
||||
type="file"
|
||||
accept="image/*"
|
||||
onChange={(e) => handleFileUpload('ticket', e)}
|
||||
className="absolute inset-0 w-full h-full opacity-0 cursor-pointer"
|
||||
/>
|
||||
<Button
|
||||
type="button"
|
||||
variant="outline"
|
||||
className="w-full h-8 text-xs"
|
||||
>
|
||||
<Upload className="h-3 w-3 mr-1" />
|
||||
Ou choisir un fichier
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Boutons d'action */}
|
||||
|
||||
Reference in new issue
Block a user