import { useState } from 'react' import { Alert, Box, Button, Chip, CircularProgress, IconButton, Tab, Tabs, Typography, } from '@mui/material' import { Edit2, Save, X } from 'lucide-react' import type { UpdatePropertyInput } from '../../domain/property' import { usePropertyById, useUpdateProperty } from '../../hooks/useProperties' import { PropertyDetailSkeleton } from './PropertyDetailSkeleton' import { useToastStore } from '../../stores/toastStore' import { getAssetTypeColor, getAssetTypeLabel, getAvailabilityChipColor, getAvailabilityLabel, } from './propertyHelpers' import { PropertyDetailOverview } from './PropertyDetailOverview' import { MatchabilityTabPanel } from './MatchabilityTabPanel' import { PropertyMarketSignalsTab } from './PropertyMarketSignalsTab' interface PropertyDetailViewProps { propertyId: string onClose?: () => void hideTabs?: Array<'Matchability' | 'Marktsignale'> } const ALL_TABS = ['Übersicht', 'Matchability', 'Marktsignale'] as const export function PropertyDetailView({ propertyId, onClose, hideTabs = [] }: PropertyDetailViewProps) { const TABS = ALL_TABS.filter(t => !hideTabs.includes(t as 'Matchability' | 'Marktsignale')) const [tab, setTab] = useState(0) const [editing, setEditing] = useState(false) const [draft, setDraft] = useState({}) const { data: property, isLoading } = usePropertyById(propertyId) const updateProperty = useUpdateProperty() const showToast = useToastStore(s => s.showToast) const saving = updateProperty.isPending function startEdit() { setDraft({}) setEditing(true) } function saveEdit() { if (!property) return updateProperty.mutate( { id: property.id, input: draft }, { onSuccess: () => { setEditing(false) setDraft({}) showToast('Objekt gespeichert.', 'success') }, onError: () => { showToast('Fehler beim Speichern.', 'error') }, }, ) } if (isLoading) return if (!property) { return ( Objekt nicht gefunden. ) } const isLowQuality = property.dataQuality.score < 0.6 const hasCriticalGaps = property.dataQuality.missingCriticalFields.length > 0 return ( {/* Header */} {tab === 0 && !editing && ( )} {tab === 0 && editing && ( <> )} {onClose && ( )} {property.title} {property.address.street} {property.address.houseNumber}, {property.address.postalCode} {property.address.city} {isLowQuality && ( Niedrige Datenqualität ({Math.round(property.dataQuality.score * 100)}%) — Angaben können unvollständig sein. )} {hasCriticalGaps && !isLowQuality && ( Kritische Felder fehlen: {property.dataQuality.missingCriticalFields.slice(0, 3).join(', ')} )} {/* Photo */} {property.images?.[0] && ( {property.title} )} {/* Tabs */} setTab(v)} sx={{ borderBottom: '1px solid #e2e8f0', flexShrink: 0, '& .MuiTab-root': { textTransform: 'none', fontSize: '0.8rem', minWidth: 'auto', px: 2 }, }} > {TABS.map(label => ( ))} {/* Tab content */} {TABS[tab] === 'Übersicht' && ( )} {TABS[tab] === 'Matchability' && } {TABS[tab] === 'Marktsignale' && } ) }