main
tsx 284 lines 6.99 KB
Raw
1 import { useState } from "react";
2 import CutCard from "../components/CutCard";
3 import BarbershopDetail from "../components/BarbershopDetail";
4 import haptics from "../utils/haptics";
5 import { openUrl } from "@tauri-apps/plugin-opener";
6 import { useLang } from "../context/LanguageContext";
7
8 interface Barbershop {
9 id: number;
10 name: { [key: string]: string };
11 address: { [key: string]: string };
12 rating: number;
13 reviewCount: number;
14 priceLevel: number;
15 distance: { [key: string]: string };
16 openNow: boolean;
17 phone: string;
18 types: string[];
19 imageUrl?: string;
20 }
21
22 // Barbershop locations in Hagersten, Stockholm area
23 const BARBERSHOPS: Barbershop[] = [
24 {
25 id: 1,
26 name: {
27 fa: "هگرستن استریت کات",
28 en: "Hägersten StreetCut",
29 sv: "Hägersten StreetCut",
30 },
31 address: {
32 fa: "هگرستنس گاتا 15، استکهلم",
33 en: "Hågerstensvägen 15, Stockholm",
34 sv: "Hågerstensvägen 15, Stockholm",
35 },
36 rating: 4.8,
37 reviewCount: 124,
38 priceLevel: 2,
39 distance: {
40 fa: "500 متر",
41 en: "500m",
42 sv: "500m",
43 },
44 openNow: true,
45 phone: "+46 8 123 4567",
46 types: ["Barbershop", "Hair Salon"],
47 },
48 {
49 id: 2,
50 name: {
51 fa: "آرایشگاه مردانه نورد",
52 en: "Barber Nord",
53 sv: "Barber Nord",
54 },
55 address: {
56 fa: "هگرستن تورگ 8، استکهلم",
57 en: "Hägerstens Torg 8, Stockholm",
58 sv: "Hägerstens Torg 8, Stockholm",
59 },
60 rating: 4.6,
61 reviewCount: 89,
62 priceLevel: 2,
63 distance: {
64 fa: "750 متر",
65 en: "750m",
66 sv: "750m",
67 },
68 openNow: true,
69 phone: "+46 8 234 5678",
70 types: ["Barbershop", "Beard Trimming"],
71 },
72 {
73 id: 3,
74 name: {
75 fa: "کلاسیک کات استوکهلم",
76 en: "Classic Cut Stockholm",
77 sv: "Classic Cut Stockholm",
78 },
79 address: {
80 fa: "لیلجهولمنس وگن 22، استکهلم",
81 en: "Liljeholmsvägen 22, Stockholm",
82 sv: "Liljeholmsvägen 22, Stockholm",
83 },
84 rating: 4.7,
85 reviewCount: 156,
86 priceLevel: 3,
87 distance: {
88 fa: "1.2 کیلومتر",
89 en: "1.2km",
90 sv: "1.2km",
91 },
92 openNow: true,
93 phone: "+46 8 345 6789",
94 types: ["Barbershop", "Hair Salon", "Grooming"],
95 },
96 {
97 id: 4,
98 name: {
99 fa: "آرایشگاه سوئدی",
100 en: "Swedish Barber House",
101 sv: "Svenska Barber House",
102 },
103 address: {
104 fa: "هگرستنس آله 45، استکهلم",
105 en: "Hägerstensåsens Allé 45, Stockholm",
106 sv: "Hägerstensåsens Allé 45, Stockholm",
107 },
108 rating: 4.5,
109 reviewCount: 72,
110 priceLevel: 2,
111 distance: {
112 fa: "900 متر",
113 en: "900m",
114 sv: "900m",
115 },
116 openNow: false,
117 phone: "+46 8 456 7890",
118 types: ["Barbershop", "Traditional Shave"],
119 },
120 {
121 id: 5,
122 name: {
123 fa: "استایل مستر",
124 en: "Style Master",
125 sv: "Style Master",
126 },
127 address: {
128 fa: "گران بری وگن 33، استکهلم",
129 en: "Granbergsvägen 33, Stockholm",
130 sv: "Granbergsvägen 33, Stockholm",
131 },
132 rating: 4.9,
133 reviewCount: 203,
134 priceLevel: 3,
135 distance: {
136 fa: "1.5 کیلومتر",
137 en: "1.5km",
138 sv: "1.5km",
139 },
140 openNow: true,
141 phone: "+46 8 567 8901",
142 types: ["Barbershop", "Hair Salon", "Styling"],
143 },
144 {
145 id: 6,
146 name: {
147 fa: "آرایشگاه مدرن هگرستن",
148 en: "Modern Barber Hagersten",
149 sv: "Modern Barber Hagersten",
150 },
151 address: {
152 fa: "هگرستنس گاتا 67، استکهلم",
153 en: "Hågerstensvägen 67, Stockholm",
154 sv: "Hågerstensvägen 67, Stockholm",
155 },
156 rating: 4.4,
157 reviewCount: 58,
158 priceLevel: 2,
159 distance: {
160 fa: "650 متر",
161 en: "650m",
162 sv: "650m",
163 },
164 openNow: true,
165 phone: "+46 8 678 9012",
166 types: ["Barbershop", "Modern Cuts"],
167 },
168 {
169 id: 7,
170 name: {
171 fa: "آرایشگاه کلاسیک",
172 en: "The Classic Barber",
173 sv: "Den Klassiska Frisören",
174 },
175 address: {
176 fa: "تیلوریس گاتا 12، استکهلم",
177 en: "Telefonvägen 12, Stockholm",
178 sv: "Telefonvägen 12, Stockholm",
179 },
180 rating: 4.8,
181 reviewCount: 145,
182 priceLevel: 2,
183 distance: {
184 fa: "1.8 کیلومتر",
185 en: "1.8km",
186 sv: "1.8km",
187 },
188 openNow: true,
189 phone: "+46 8 789 0123",
190 types: ["Barbershop", "Traditional Service"],
191 },
192 {
193 id: 8,
194 name: {
195 fa: "آرایشگاه سریع",
196 en: "Quick Cuts Barber",
197 sv: "Snabbklipp Frisör",
198 },
199 address: {
200 fa: "هگرستن تورگ 2، استکهلم",
201 en: "Hägerstens Torg 2, Stockholm",
202 sv: "Hägerstens Torg 2, Stockholm",
203 },
204 rating: 4.3,
205 reviewCount: 91,
206 priceLevel: 1,
207 distance: {
208 fa: "800 متر",
209 en: "800m",
210 sv: "800m",
211 },
212 openNow: false,
213 phone: "+46 8 890 1234",
214 types: ["Barbershop", "Walk-in"],
215 },
216 ];
217
218 export default function Cut() {
219 const [selectedShop, setSelectedShop] = useState<Barbershop | null>(null);
220 const { lang } = useLang();
221 const isRTL = lang === "fa";
222 const dir = isRTL ? "rtl" : "ltr";
223 const align = isRTL ? "text-right" : "text-left";
224
225 const handleDirections = async (shop: Barbershop) => {
226 const address = shop.address[lang];
227 // Try to open in native maps app using Tauri opener
228 try {
229 // For macOS, use maps:// URL scheme
230 // For other platforms, fall back to Google Maps URL
231 const mapsUrl = `maps://?q=${encodeURIComponent(address)}`;
232 const googleMapsUrl = `https://www.google.com/maps/search/?api=1&query=${encodeURIComponent(address)}`;
233
234 try {
235 await openUrl(mapsUrl);
236 } catch {
237 // If maps:// doesn't work, try Google Maps URL
238 await openUrl(googleMapsUrl);
239 }
240 } catch (error) {
241 console.error("Failed to open maps:", error);
242 }
243 };
244
245 return (
246 <section dir={dir} className={`pb-12 ` + align}>
247 <div className="grid gap-4">
248 {BARBERSHOPS.map((shop) => (
249 <CutCard
250 key={shop.id}
251 name={shop.name[lang]}
252 address={shop.address[lang]}
253 rating={shop.rating}
254 reviewCount={shop.reviewCount}
255 priceLevel={shop.priceLevel}
256 distance={shop.distance[lang]}
257 openNow={shop.openNow}
258 phone={shop.phone}
259 types={shop.types}
260 onViewDetails={async () => {
261 await haptics.cardTap();
262 setSelectedShop(shop);
263 }}
264 />
265 ))}
266 </div>
267
268 {/* Detail Modal */}
269 {selectedShop && (
270 <BarbershopDetail
271 shop={selectedShop}
272 onClose={async () => {
273 await haptics.buttonPress();
274 setSelectedShop(null);
275 }}
276 onDirections={async () => {
277 await haptics.buttonPress();
278 await handleDirections(selectedShop);
279 }}
280 />
281 )}
282 </section>
283 );
284 }