Nuances.vue 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. <template>
  2. <div class="min-h-screen bg-background">
  3. <Header />
  4. <main class="pt-24 sm:pt-32 pb-20">
  5. <div class="container mx-auto px-4">
  6. <!-- Hero Section -->
  7. <div class="text-center mb-16 animate-slide-up">
  8. <span class="text-primary font-display text-sm tracking-widest uppercase mb-4 block">{{ t("nuances.subtitle") }}</span>
  9. <h1 class="font-display text-4xl sm:text-5xl lg:text-6xl font-bold mb-6">
  10. {{ t("nuances.title") }}
  11. </h1>
  12. <p class="text-muted-foreground max-w-2xl mx-auto text-lg leading-relaxed">
  13. {{ t("nuances.description") }}
  14. </p>
  15. </div>
  16. <!-- Nuances Grid -->
  17. <div class="grid md:grid-cols-2 lg:grid-cols-3 gap-8 max-w-7xl mx-auto">
  18. <div
  19. v-for="(nuance, key) in nuances"
  20. :key="key"
  21. class="group bg-card border border-border/50 rounded-[2rem] overflow-hidden hover:border-primary/30 transition-all duration-500 shadow-sm hover:shadow-xl"
  22. >
  23. <!-- Visual Example -->
  24. <div class="aspect-video bg-muted overflow-hidden relative">
  25. <img
  26. v-if="nuance.image"
  27. :src="nuance.image"
  28. :alt="t(`nuances.items.${key}.title`)"
  29. loading="lazy"
  30. class="w-full h-full object-cover group-hover:scale-105 transition-transform duration-700"
  31. />
  32. <div v-else class="w-full h-full flex items-center justify-center bg-primary/5">
  33. <component :is="nuance.icon" class="w-12 h-12 text-primary/20" />
  34. </div>
  35. <div class="absolute inset-0 bg-gradient-to-t from-black/20 to-transparent opacity-0 group-hover:opacity-100 transition-opacity" />
  36. </div>
  37. <!-- Content -->
  38. <div class="p-8">
  39. <div class="flex items-center gap-3 mb-4">
  40. <div class="w-10 h-10 bg-primary/10 rounded-xl flex items-center justify-center text-primary group-hover:bg-primary group-hover:text-white transition-all duration-500">
  41. <component :is="nuance.icon" class="w-5 h-5" />
  42. </div>
  43. <h3 class="font-display text-xl font-bold">{{ t(`nuances.items.${key}.title`) }}</h3>
  44. </div>
  45. <p class="text-muted-foreground mb-6 text-sm leading-relaxed">
  46. {{ t(`nuances.items.${key}.description`) }}
  47. </p>
  48. <div class="pt-6 border-t border-border/50">
  49. <div class="flex items-start gap-3">
  50. <Info class="w-4 h-4 text-primary/40 mt-0.5" />
  51. <p class="text-xs text-muted-foreground/70 italic leading-relaxed">
  52. {{ t(`nuances.items.${key}.details`) }}
  53. </p>
  54. </div>
  55. </div>
  56. </div>
  57. </div>
  58. </div>
  59. <!-- AI Disclaimer -->
  60. <div class="mt-8 text-center animate-fade-in">
  61. <p class="text-[10px] uppercase tracking-widest text-muted-foreground/40 font-bold flex items-center justify-center gap-2">
  62. <Sparkles class="w-3 h-3" />
  63. {{ t("nuances.aiDisclaimer") }}
  64. </p>
  65. </div>
  66. <!-- Global Disclaimer -->
  67. <div class="mt-20 max-w-4xl mx-auto p-8 sm:p-12 bg-primary/5 rounded-[2.5rem] border border-primary/10 relative overflow-hidden group">
  68. <div class="relative z-10 flex flex-col md:flex-row items-center gap-8">
  69. <div class="w-20 h-20 bg-white rounded-3xl flex items-center justify-center shadow-lg group-hover:rotate-12 transition-transform duration-500">
  70. <ShieldCheck class="w-10 h-10 text-primary" />
  71. </div>
  72. <div class="text-center md:text-left">
  73. <h2 class="font-display text-2xl font-bold mb-3">{{ t("nuances.disclaimer.title") }}</h2>
  74. <p class="text-muted-foreground leading-relaxed">
  75. {{ t("nuances.disclaimer.text") }}
  76. </p>
  77. </div>
  78. </div>
  79. <!-- Decor -->
  80. <div class="absolute -top-12 -right-12 w-40 h-40 bg-primary/10 rounded-full blur-3xl" />
  81. </div>
  82. </div>
  83. </main>
  84. <Footer />
  85. </div>
  86. </template>
  87. <script setup lang="ts">
  88. import { useI18n } from "vue-i18n";
  89. import { computed } from "vue";
  90. import { useHead } from "@unhead/vue";
  91. import Header from "@/components/Header.vue";
  92. import Footer from "@/components/Footer.vue";
  93. import {
  94. Layers,
  95. Grid,
  96. Scaling,
  97. Spline,
  98. Triangle,
  99. Ruler,
  100. Palette,
  101. Zap,
  102. Info,
  103. ShieldCheck,
  104. Sparkles
  105. } from "lucide-vue-next";
  106. const { t } = useI18n();
  107. useHead({
  108. title: computed(() => t('nuances.title')),
  109. meta: [
  110. { name: 'description', content: computed(() => t('nuances.description')) }
  111. ]
  112. });
  113. const nuances = {
  114. anisotropy: {
  115. image: "/fdm_anisotropy.png",
  116. icon: Zap
  117. },
  118. layerStructure: {
  119. image: "/fdm_layer_lines_photo_1776031229473.webp",
  120. icon: Layers
  121. },
  122. supportMarks: {
  123. image: "/fdm_supports_photo_1776031246690.webp",
  124. icon: Scaling
  125. },
  126. zSeam: {
  127. image: "/fdm_zseam_photo_1776031258273.webp",
  128. icon: Spline
  129. },
  130. surfaceImperfections: {
  131. image: "/fdm_surface_photo_1776031404133.webp",
  132. icon: Grid
  133. },
  134. overhangs: {
  135. image: "/fdm_overhangs_photo_v2_1776032258991.webp",
  136. icon: Triangle
  137. },
  138. dimensionalTolerances: {
  139. image: "/fdm_tolerances_photo_1776031451173.webp",
  140. icon: Ruler
  141. },
  142. colorVariations: {
  143. image: "/fdm_color_photo_1776031463894.webp",
  144. icon: Palette
  145. },
  146. stringing: {
  147. image: "/fdm_stringing_photo_1776031432344.webp",
  148. icon: Zap
  149. }
  150. };
  151. </script>