feat(realestate): 공고 카드 매칭 점수 + 매칭 결과 탭 강화
- 공고 카드에 매칭 점수 뱃지 표시 (70+녹색, 40+주황, 기본회색) - 상세 패널 헤더에 매칭 점수 + 자격 유형 태그 표시 - 매칭 결과 카드에 D-day + 접수일정 + 매칭 사유 표시 추가 Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -331,6 +331,15 @@ function AnnouncementCard({ item, isSelected, onClick, onBookmark }) {
|
||||
{HOUSE_TYPE_LABELS[item.house_secd]}
|
||||
</span>
|
||||
)}
|
||||
{item.match_score > 0 && (
|
||||
<span className="sub-badge" style={{
|
||||
color: item.match_score >= 70 ? '#34d399' : item.match_score >= 40 ? '#f59e0b' : '#94a3b8',
|
||||
background: item.match_score >= 70 ? 'rgba(52,211,153,0.1)' : item.match_score >= 40 ? 'rgba(245,158,11,0.1)' : 'rgba(148,163,184,0.1)',
|
||||
fontWeight: 700,
|
||||
}}>
|
||||
{item.match_score}점
|
||||
</span>
|
||||
)}
|
||||
</div>
|
||||
<button
|
||||
onClick={(e) => { e.stopPropagation(); onBookmark?.(item.id); }}
|
||||
@@ -404,6 +413,23 @@ function AnnouncementDetail({ item, onBookmark }) {
|
||||
</div>
|
||||
<h3 className="sub-detail__name">{item.house_nm}</h3>
|
||||
<p className="sub-detail__address">{item.address || item.region_name}</p>
|
||||
{item.match_score > 0 && (
|
||||
<div style={{ display: 'flex', alignItems: 'center', gap: 8, marginTop: 6 }}>
|
||||
<span style={{
|
||||
fontSize: 20, fontWeight: 700, fontFamily: 'var(--font-display)',
|
||||
color: item.match_score >= 70 ? '#34d399' : item.match_score >= 40 ? '#f59e0b' : '#94a3b8',
|
||||
}}>
|
||||
매칭 {item.match_score}점
|
||||
</span>
|
||||
{item.eligible_types?.length > 0 && (
|
||||
<div style={{ display: 'flex', gap: 4, flexWrap: 'wrap' }}>
|
||||
{(Array.isArray(item.eligible_types) ? item.eligible_types : []).map((t, i) => (
|
||||
<span key={i} className="sub-tag is-neutral" style={{ fontSize: 10 }}>{t}</span>
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
<div className="sub-detail__actions">
|
||||
<button
|
||||
@@ -811,6 +837,15 @@ function MatchesTab() {
|
||||
</div>
|
||||
<p className="sub-card__address" style={{ margin: 0 }}>
|
||||
{match.region_name || '-'}
|
||||
{match.receipt_start && (
|
||||
<span style={{ marginLeft: 8 }}>
|
||||
{fmt(match.receipt_start)} ~ {fmt(match.receipt_end)}
|
||||
{(() => {
|
||||
const dd = getDDays(match.receipt_start);
|
||||
return dd ? <span style={{ marginLeft: 6, fontWeight: 600, color: getDDayColor(match.receipt_start) }}>{dd}</span> : null;
|
||||
})()}
|
||||
</span>
|
||||
)}
|
||||
</p>
|
||||
{match.eligible_types && (
|
||||
<div style={{ display: 'flex', gap: 4, flexWrap: 'wrap' }}>
|
||||
@@ -824,9 +859,14 @@ function MatchesTab() {
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
<span style={{ fontSize: 11, color: 'var(--text-muted)' }}>
|
||||
매칭일: {fmtDateTime(match.created_at)}
|
||||
</span>
|
||||
{match.match_reasons?.length > 0 && (
|
||||
<div style={{ fontSize: 11, color: 'var(--text-muted)' }}>
|
||||
{(Array.isArray(match.match_reasons)
|
||||
? match.match_reasons
|
||||
: (() => { try { return JSON.parse(match.match_reasons); } catch { return []; } })()
|
||||
).join(' · ')}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
<div style={{ textAlign: 'center', flexShrink: 0 }}>
|
||||
<div style={{
|
||||
|
||||
Reference in New Issue
Block a user