feat: 찰떡지수 피드백 UI (우리/동네 궁합도)
CI / build (push) Successful in 27s

- FeedbackDialog: 잘 놀았어요/안 맞았어요 + BAD 사유 선택·추가입력
- 채팅 '산책 완료' 버튼 + 2시간 FEEDBACK_REQUEST 알림 → 피드백 팝업
- AffinityBadges: 동네 찰떡지수(전체), 우리 찰떡지수(매칭 쌍·유료 게이팅)
  스팟 메이트/AI 추천 카드 및 우리 강아지 프로필에 노출

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
sb
2026-07-11 23:55:16 +09:00
parent eb51201669
commit c8a8681a61
9 changed files with 344 additions and 3 deletions
+22
View File
@@ -55,6 +55,11 @@
<div class="text-caption text-grey-7">
{{ current.breed || '견종 미상' }}<span v-if="current.size"> · {{ sizeLabel(current.size) }}</span>
</div>
<div v-if="hoodScore" class="text-caption row items-center no-wrap q-mt-xs">
<q-icon name="groups" size="14px" color="teal" class="q-mr-xs" />
<span class="text-weight-medium text-teal-8">동네 찰떡지수 {{ hoodScore.percent }}%</span>
<span class="text-grey-6 q-ml-xs">({{ hoodScore.label }})</span>
</div>
</div>
<q-space />
<q-btn dense flat round color="grey-6" icon="delete_outline" @click="onDelete" />
@@ -140,6 +145,7 @@ import { computed, onMounted, reactive, ref, watch } from 'vue'
import { useQuasar } from 'quasar'
import { useAuthStore } from '@/stores/auth'
import { useDogsStore } from '@/stores/dogs'
import { affinityApi, type NeighborhoodScore } from '@/api/affinity'
import { ApiError } from '@/api/http'
const $q = useQuasar()
@@ -147,6 +153,22 @@ const auth = useAuthStore()
const dogs = useDogsStore()
const current = computed(() => dogs.currentDog)
// 내 강아지 동네 찰떡지수 (전체 노출 지표)
const hoodScore = ref<NeighborhoodScore | null>(null)
watch(
() => current.value?.id,
async (id) => {
hoodScore.value = null
if (id == null) return
try {
hoodScore.value = await affinityApi.neighborhood(id)
} catch {
hoodScore.value = null
}
},
{ immediate: true },
)
const selected = ref<Set<number>>(new Set())
const saving = ref(false)
const createOpen = ref(false)