-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathindex.html
More file actions
725 lines (684 loc) · 34.6 KB
/
Copy pathindex.html
File metadata and controls
725 lines (684 loc) · 34.6 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Beyond Kibble - Recipe & Tips Companion</title>
<script crossorigin src="https://unpkg.com/react@18/umd/react.production.min.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@18/umd/react-dom.production.min.js"></script>
<script src="https://unpkg.com/@babel/standalone/babel.min.js"></script>
<script src="https://cdn.tailwindcss.com"></script>
</head>
<body><!-- Amazon Promotion Banner -->
<div class="bg-gradient-to-r from-amber-600 to-amber-700 text-white text-center py-3 px-4 shadow-md no-print">
<a
href="https://www.amazon.com/dp/B0FTTJYRT8"
target="_blank"
rel="noopener noreferrer"
className="hover:underline font-semibold inline-flex items-center gap-2 text-sm md:text-base"
>
📚 Love these recipes? Get the complete <strong>Beyond Kibble: Abby's Story</strong> book on Amazon →
</a>
</div>
<div id="root"></div>
<script type="text/babel">
const { useState, useEffect } = React;
// Lucide icons as simple SVG components
const ChefHat = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<path d="M6 13.87A4 4 0 0 1 7.41 6a5.11 5.11 0 0 1 1.05-1.54 5 5 0 0 1 7.08 0A5.11 5.11 0 0 1 16.59 6 4 4 0 0 1 18 13.87V21H6Z"/>
<line x1="6" y1="17" x2="18" y2="17"/>
</svg>
);
const Clock = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<circle cx="12" cy="12" r="10"/>
<polyline points="12 6 12 12 16 14"/>
</svg>
);
const Leaf = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<path d="M11 20A7 7 0 0 1 9.8 6.1C15.5 5 17 4.48 19 2c1 2 2 4.18 2 8 0 5.5-4.78 10-10 10Z"/>
<path d="M2 21c0-3 1.85-5.36 5.08-6C9.5 14.52 12 13 13 12"/>
</svg>
);
const Heart = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<path d="M19 14c1.49-1.46 3-3.21 3-5.5A5.5 5.5 0 0 0 16.5 3c-1.76 0-3 .5-4.5 2-1.5-1.5-2.74-2-4.5-2A5.5 5.5 0 0 0 2 8.5c0 2.3 1.5 4.05 3 5.5l7 7Z"/>
</svg>
);
const Printer = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<polyline points="6 9 6 2 18 2 18 9"/>
<path d="M6 18H4a2 2 0 0 1-2-2v-5a2 2 0 0 1 2-2h16a2 2 0 0 1 2 2v5a2 2 0 0 1-2 2h-2"/>
<rect x="6" y="14" width="12" height="8"/>
</svg>
);
const BookOpen = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<path d="M2 3h6a4 4 0 0 1 4 4v14a3 3 0 0 0-3-3H2z"/>
<path d="M22 3h-6a4 4 0 0 0-4 4v14a3 3 0 0 1 3-3h7z"/>
</svg>
);
const ChevronLeft = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<polyline points="15 18 9 12 15 6"/>
</svg>
);
const ChevronRight = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<polyline points="9 18 15 12 9 6"/>
</svg>
);
const Globe = ({ className }) => (
<svg className={className} viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<circle cx="12" cy="12" r="10"/>
<line x1="2" y1="12" x2="22" y2="12"/>
<path d="M12 2a15.3 15.3 0 0 1 4 10 15.3 15.3 0 0 1-4 10 15.3 15.3 0 0 1-4-10 15.3 15.3 0 0 1 4-10z"/>
</svg>
);
const RecipeEbook = () => {
const [currentPage, setCurrentPage] = useState(0);
const [language, setLanguage] = useState('en');
// Load saved language preference
useEffect(() => {
const savedLang = localStorage.getItem('bk-language');
if (savedLang && (savedLang === 'en' || savedLang === 'nl')) {
setLanguage(savedLang);
}
}, []);
// Save language preference
const toggleLanguage = () => {
const newLang = language === 'en' ? 'nl' : 'en';
setLanguage(newLang);
localStorage.setItem('bk-language', newLang);
};
// Translations object
const t = {
en: {
appTitle: "Beyond Kibble Recipe Guide",
page: "Page",
of: "of",
print: "Print",
previous: "Previous",
next: "Next",
quickNav: "Quick Navigation:",
cover: "Cover",
introduction: "Introduction",
recipesStart: "Recipes Start",
conclusion: "Conclusion",
recipe: "Recipe",
ingredients: "Ingredients",
instructions: "Instructions",
elenaTips: "Elena's Tips",
},
nl: {
appTitle: "Beyond Kibble Receptengids",
page: "Pagina",
of: "van",
print: "Afdrukken",
previous: "Vorige",
next: "Volgende",
quickNav: "Snelle Navigatie:",
cover: "Omslag",
introduction: "Introductie",
recipesStart: "Recepten Begin",
conclusion: "Conclusie",
recipe: "Recept",
ingredients: "Ingrediënten",
instructions: "Instructies",
elenaTips: "Elena's Tips",
}
}[language];
const content = {
en: {
coverTitle: "Beyond Kibble",
coverSubtitle: "Recipe & Tips Companion",
coverLine1: "4 Complete Recipes (Demo)",
coverLine2: "Essential Tips & Guides",
coverLine3: "Your Practical Guide to Fresh Food for Labs",
coverAuthor: "By Elena Notte",
coverCompanion: 'Companion to "Beyond Kibble"',
introTitle: "Welcome to Your Recipe Companion",
introPara1: "Dear Reader,",
introPara2: "When I wrote \"Beyond Kibble,\" I knew that theory without practice would leave many of you standing in your kitchen, overwhelmed and uncertain. This companion e-book is the answer to that concern.",
introPara3: "Here you'll find complete recipes that Abby and I have tested and refined over three years. These aren't complicated chef creations - they're practical, affordable, and designed for real life.",
introPara4: "Each recipe includes prep time, difficulty level, complete ingredient lists, step-by-step instructions, and practical tips I've learned through experience.",
introPara5: "Remember: These recipes are starting points. Every Lab is unique. Pay attention to your dog's body, energy, and stool quality. Adjust portions and ingredients based on what you observe.",
introClosing: "With love and solidarity in the revolution,",
introSignature: "Elena Notte",
conclusionTitle: "Your Journey Begins Now",
conclusionPara1: "You've reached the end of this demo guide, but really, you're at the beginning of something transformative.",
conclusionPara2: "Three years ago, I stood in my kitchen exactly where you might be standing now - uncertain, overwhelmed, questioning whether I could really do this.",
conclusionPara3: "Today, Abby is thriving. Not managing symptoms. Not surviving on medications. Thriving.",
conclusionPara4: "This isn't just about food. This is about reclaiming your sovereignty. Trusting your judgment. Remembering that you are nature, your Lab is nature, and nature knows how to heal when given what it needs.",
conclusionClosing: "Welcome to the vitality revolution.",
conclusionSignature: "— Elena Notte, With Abby, always",
},
nl: {
coverTitle: "Beyond Kibble",
coverSubtitle: "Recepten & Tips Gids",
coverLine1: "4 Complete Recepten (Demo)",
coverLine2: "Essentiële Tips & Gidsen",
coverLine3: "Jouw Praktische Gids voor Vers Voer voor Labradors",
coverAuthor: "Door Elena Notte",
coverCompanion: 'Aanvulling op "Beyond Kibble"',
introTitle: "Welkom bij Je Recepten Gids",
introPara1: "Beste Lezer,",
introPara2: "Toen ik \"Beyond Kibble\" schreef, wist ik dat theorie zonder praktijk velen van jullie overweldigd en onzeker in de keuken zou laten staan. Dit aanvullende e-boek is het antwoord op die zorg.",
introPara3: "Hier vind je complete recepten die Abby en ik hebben getest en verfijnd over drie jaar. Dit zijn geen ingewikkelde chef-creaties - ze zijn praktisch, betaalbaar en ontworpen voor het echte leven.",
introPara4: "Elk recept bevat bereidingstijd, moeilijkheidsgraad, complete ingrediëntenlijsten, stap-voor-stap instructies en praktische tips die ik heb geleerd door ervaring.",
introPara5: "Onthoud: Deze recepten zijn startpunten. Elke Lab is uniek. Let op het lichaam, energie en ontlasting van je hond. Pas porties en ingrediënten aan op basis van wat je waarneemt.",
introClosing: "Met liefde en solidariteit in de revolutie,",
introSignature: "Elena Notte",
conclusionTitle: "Jouw Reis Begint Nu",
conclusionPara1: "Je hebt het einde van deze demo gids bereikt, maar eigenlijk sta je aan het begin van iets transformerends.",
conclusionPara2: "Drie jaar geleden stond ik in mijn keuken precies waar jij nu misschien staat - onzeker, overweldigd, me afvragend of ik dit echt kon.",
conclusionPara3: "Vandaag floreert Abby. Niet symptomen managen. Niet overleven op medicijnen. Floreren.",
conclusionPara4: "Dit gaat niet alleen over voedsel. Dit gaat over het terugvorderen van je soevereiniteit. Vertrouwen op je eigen oordeel. Onthouden dat jij natuur bent, je Lab natuur is, en de natuur weet hoe te genezen wanneer het krijgt wat het nodig heeft.",
conclusionClosing: "Welkom bij de vitaliteitsrevolutie.",
conclusionSignature: "— Elena Notte, Met Abby, altijd",
}
}[language];
const recipes = {
en: [
{
title: "Abby's Daily Base Recipe",
category: "Daily Meals",
prepTime: "45 min",
servings: "7 days (30kg Lab)",
difficulty: "Easy",
ingredients: [
"2kg chicken thighs (with bone and skin)",
"500g beef liver",
"1kg mixed vegetables (carrots, broccoli, spinach, pumpkin)",
"1 dozen eggs",
"2 tbsp coconut oil",
"Fish oil supplement"
],
instructions: [
"Place chicken thighs in large pot with water, bring to boil then simmer for 20 minutes",
"While chicken cooks, roughly chop vegetables",
"Steam vegetables for 10 minutes until tender",
"Remove cooked chicken, let cool slightly, then roughly chop (bones and all - they're soft and safe)",
"Dice beef liver into small pieces",
"Mix chicken, liver, and vegetables in large bowl",
"Add coconut oil and mix well",
"Portion into 7 containers (one per day)",
"Store 3-4 days worth in fridge, freeze the rest",
"Before serving: add fish oil pump and optional raw egg"
],
tips: [
"Cooked bones are soft and completely digestible - never use raw weight-bearing bones",
"Rotate proteins weekly: turkey, beef, fish, lamb",
"Vegetables should be 10-15% of total meal",
"Each portion should be roughly 650-700g for a 30kg Lab"
]
},
{
title: "Quick Turkey & Pumpkin Bowl",
category: "Daily Meals",
prepTime: "30 min",
servings: "5 days",
difficulty: "Easy",
ingredients: [
"1.5kg ground turkey",
"400g pumpkin puree",
"200g spinach (chopped)",
"3 raw eggs",
"1 tbsp apple cider vinegar",
"2 tbsp coconut oil"
],
instructions: [
"Brown ground turkey in large pan (no need to fully cook - will finish when mixed)",
"Add chopped spinach to pan, wilt for 2-3 minutes",
"Remove from heat, add pumpkin puree and mix well",
"Crack eggs into mixture while still warm (but not hot), mix thoroughly",
"Add coconut oil and apple cider vinegar",
"Divide into 5 portions",
"Can be served immediately or refrigerate for up to 4 days"
],
tips: [
"Turkey is lean - coconut oil adds needed fat",
"Pumpkin aids digestion and provides fiber",
"This is great for weight management",
"Raw eggs add biotin and extra protein"
]
},
{
title: "Salmon & Sweet Potato Feast",
category: "Daily Meals",
prepTime: "40 min",
servings: "4 days",
difficulty: "Easy",
ingredients: [
"1kg fresh salmon (skin on)",
"300g sweet potato",
"200g green beans",
"100g carrots",
"2 tbsp olive oil",
"1 tsp turmeric powder"
],
instructions: [
"Bake salmon at 180°C for 15-20 minutes until cooked through",
"Steam sweet potato cubes until tender (15 minutes)",
"Steam green beans and carrots (10 minutes)",
"Flake salmon (including skin) into large bowl",
"Mash sweet potato roughly",
"Mix all ingredients with olive oil and turmeric",
"Divide into 4 portions"
],
tips: [
"Salmon skin is rich in omega-3s - don't remove it",
"Sweet potato is higher in carbs - use for active Labs only",
"This recipe is excellent for skin and coat health",
"Can substitute with mackerel or sardines"
]
},
{
title: "Beef & Organ Meat Power Bowl",
category: "Daily Meals",
prepTime: "35 min",
servings: "6 days",
difficulty: "Medium",
ingredients: [
"1.5kg beef chunks (chuck or stew meat)",
"300g beef heart",
"200g beef liver",
"100g beef kidney",
"500g mixed vegetables (zucchini, broccoli, kale)",
"2 tbsp beef tallow or coconut oil"
],
instructions: [
"Cut all meats into bite-sized pieces",
"Brown beef chunks in large pot",
"Add heart and cook for 10 minutes",
"Add roughly chopped vegetables",
"Add enough water to barely cover, simmer for 15 minutes",
"Remove from heat, add diced liver and kidney (cook with residual heat only)",
"Mix in beef tallow",
"Portion into 6 containers"
],
tips: [
"Organ meats are incredibly nutrient-dense",
"Don't overcook liver - it becomes tough",
"This is vitamin and mineral rich - use weekly",
"The variety of organs provides complete nutrition"
]
}
],
nl: [
{
title: "Abby's Dagelijkse Basis Recept",
category: "Dagelijkse Maaltijden",
prepTime: "45 min",
servings: "7 dagen (30kg Lab)",
difficulty: "Makkelijk",
ingredients: [
"2kg kippendijen (met bot en vel)",
"500g runderlever",
"1kg gemengde groenten (wortels, broccoli, spinazie, pompoen)",
"1 dozijn eieren",
"2 el kokosolie",
"Visolie supplement"
],
instructions: [
"Doe kippendijen in grote pan met water, breng aan de kook en laat 20 minuten sudderen",
"Terwijl de kip kookt, hak de groenten grof",
"Stoom groenten 10 minuten tot ze zacht zijn",
"Haal gekookte kip eruit, laat iets afkoelen, hak dan grof (botten en al - ze zijn zacht en veilig)",
"Snijd runderlever in kleine stukjes",
"Meng kip, lever en groenten in grote kom",
"Voeg kokosolie toe en meng goed",
"Verdeel over 7 bakjes (één per dag)",
"Bewaar 3-4 dagen in koelkast, vries de rest in",
"Voor serveren: voeg visolie toe en optioneel een rauw ei"
],
tips: [
"Gekookte botten zijn zacht en volledig verteerbaar - gebruik nooit rauwe dragende botten",
"Roteer eiwitten wekelijks: kalkoen, rund, vis, lam",
"Groenten moeten 10-15% van de totale maaltijd zijn",
"Elke portie moet ongeveer 650-700g zijn voor een 30kg Lab"
]
},
{
title: "Snelle Kalkoen & Pompoen Bowl",
category: "Dagelijkse Maaltijden",
prepTime: "30 min",
servings: "5 dagen",
difficulty: "Makkelijk",
ingredients: [
"1,5kg kalkoenmince",
"400g pompoenpuree",
"200g spinazie (gehakt)",
"3 rauwe eieren",
"1 el appelazijn",
"2 el kokosolie"
],
instructions: [
"Bak kalkoenmince in grote pan (hoeft niet helemaal gaar - wordt af tijdens mengen)",
"Voeg gehakte spinazie toe aan pan, laat 2-3 minuten slinken",
"Haal van het vuur, voeg pompoenpuree toe en meng goed",
"Breek eieren in mengsel terwijl het nog warm is (maar niet heet), meng grondig",
"Voeg kokosolie en appelazijn toe",
"Verdeel in 5 porties",
"Kan direct geserveerd worden of tot 4 dagen in koelkast bewaren"
],
tips: [
"Kalkoen is mager - kokosolie voegt benodigde vet toe",
"Pompoen bevordert spijsvertering en levert vezels",
"Dit is geweldig voor gewichtsbeheersing",
"Rauwe eieren voegen biotine en extra eiwit toe"
]
},
{
title: "Zalm & Zoete Aardappel Feest",
category: "Dagelijkse Maaltijden",
prepTime: "40 min",
servings: "4 dagen",
difficulty: "Makkelijk",
ingredients: [
"1kg verse zalm (met vel)",
"300g zoete aardappel",
"200g sperziebonen",
"100g wortels",
"2 el olijfolie",
"1 tl kurkumapoeder"
],
instructions: [
"Bak zalm op 180°C voor 15-20 minuten tot gaar",
"Stoom zoete aardappelblokjes tot zacht (15 minuten)",
"Stoom sperziebonen en wortels (10 minuten)",
"Prak zalm (inclusief vel) in grote kom",
"Stamp zoete aardappel grof",
"Meng alle ingrediënten met olijfolie en kurkuma",
"Verdeel in 4 porties"
],
tips: [
"Zalmvel is rijk aan omega-3 - verwijder het niet",
"Zoete aardappel bevat meer koolhydraten - gebruik alleen voor actieve Labs",
"Dit recept is uitstekend voor huid- en vachtgezondheid",
"Kan vervangen worden door makreel of sardines"
]
},
{
title: "Rund & Orgaanvlees Power Bowl",
category: "Dagelijkse Maaltijden",
prepTime: "35 min",
servings: "6 dagen",
difficulty: "Gemiddeld",
ingredients: [
"1,5kg rundvleesstukken (sukade of stoofvlees)",
"300g runderhart",
"200g runderlever",
"100g rundernier",
"500g gemengde groenten (courgette, broccoli, boerenkool)",
"2 el rundervet of kokosolie"
],
instructions: [
"Snijd al het vlees in hapklare stukjes",
"Braad rundvleesstukken in grote pan",
"Voeg hart toe en kook 10 minuten",
"Voeg grof gehakte groenten toe",
"Voeg net genoeg water toe om te bedekken, laat 15 minuten sudderen",
"Haal van het vuur, voeg blokjes lever en nier toe (kook met restwarmte)",
"Meng rundervet erdoor",
"Verdeel in 6 bakjes"
],
tips: [
"Orgaanvlees is ongelooflijk voedingrijk",
"Kook lever niet te lang - het wordt taai",
"Dit is rijk aan vitaminen en mineralen - gebruik wekelijks",
"De variëteit aan organen zorgt voor complete voeding"
]
}
]
}[language];
const pages = [
{ type: 'cover', content: null },
{ type: 'intro', content: null },
...recipes.map(recipe => ({ type: 'recipe', content: recipe })),
{ type: 'conclusion', content: null }
];
const renderCover = () => (
<div className="h-full flex flex-col items-center justify-center p-8 bg-gradient-to-br from-amber-50 to-orange-50">
<ChefHat className="w-24 h-24 text-amber-600 mb-6" />
<h1 className="text-5xl font-bold text-gray-800 text-center mb-4">{content.coverTitle}</h1>
<h2 className="text-3xl text-amber-700 text-center mb-8">{content.coverSubtitle}</h2>
<div className="text-center text-gray-600 mb-8">
<p className="text-xl mb-2">{content.coverLine1}</p>
<p className="text-xl mb-2">{content.coverLine2}</p>
<p className="text-lg">{content.coverLine3}</p>
</div>
<div className="mt-8 text-center">
<p className="text-gray-500 italic">{content.coverAuthor}</p>
<p className="text-gray-500 mt-2">{content.coverCompanion}</p>
</div>
</div>
);
const renderIntro = () => (
<div className="h-full p-8 overflow-y-auto">
<h2 className="text-3xl font-bold text-amber-700 mb-6">{content.introTitle}</h2>
<div className="prose prose-lg">
<p className="mb-4">{content.introPara1}</p>
<p className="mb-4">{content.introPara2}</p>
<p className="mb-4">{content.introPara3}</p>
<p className="mb-4">{content.introPara4}</p>
<p className="mb-4">{content.introPara5}</p>
<p className="mt-8 italic">{content.introClosing}<br/>{content.introSignature}</p>
</div>
</div>
);
const renderRecipe = (recipe) => (
<div className="h-full p-8 overflow-y-auto">
<div className="mb-6">
<span className="inline-block px-3 py-1 bg-amber-100 text-amber-800 rounded-full text-sm font-semibold mb-3">
{recipe.category}
</span>
<h2 className="text-3xl font-bold text-gray-800 mb-4">{recipe.title}</h2>
<div className="flex gap-6 text-sm text-gray-600 mb-6">
<div className="flex items-center gap-2">
<Clock className="w-4 h-4" />
<span>{recipe.prepTime}</span>
</div>
<div className="flex items-center gap-2">
<ChefHat className="w-4 h-4" />
<span>{recipe.difficulty}</span>
</div>
<div className="flex items-center gap-2">
<Leaf className="w-4 h-4" />
<span>{recipe.servings}</span>
</div>
</div>
</div>
<div className="mb-6">
<h3 className="text-xl font-bold text-gray-800 mb-3">{t.ingredients}</h3>
<ul className="space-y-2">
{recipe.ingredients.map((ingredient, idx) => (
<li key={idx} className="flex items-start gap-2">
<span className="text-amber-600 mt-1">•</span>
<span>{ingredient}</span>
</li>
))}
</ul>
</div>
<div className="mb-6">
<h3 className="text-xl font-bold text-gray-800 mb-3">{t.instructions}</h3>
<ol className="space-y-3">
{recipe.instructions.map((instruction, idx) => (
<li key={idx} className="flex items-start gap-3">
<span className="flex-shrink-0 w-6 h-6 bg-amber-600 text-white rounded-full flex items-center justify-center text-sm font-bold">
{idx + 1}
</span>
<span className="pt-0.5">{instruction}</span>
</li>
))}
</ol>
</div>
<div className="bg-blue-50 p-6 rounded-lg">
<h3 className="text-lg font-bold text-blue-800 mb-3 flex items-center gap-2">
<Heart className="w-5 h-5" />
{t.elenaTips}
</h3>
<ul className="space-y-2">
{recipe.tips.map((tip, idx) => (
<li key={idx} className="flex items-start gap-2 text-sm">
<span className="text-blue-600 mt-1">✓</span>
<span>{tip}</span>
</li>
))}
</ul>
</div>
</div>
);
const renderConclusion = () => (
<div className="h-full p-8 overflow-y-auto">
<h2 className="text-3xl font-bold text-amber-700 mb-6">{content.conclusionTitle}</h2>
<div className="prose prose-lg">
<p className="mb-4">{content.conclusionPara1}</p>
<p className="mb-4">{content.conclusionPara2}</p>
<p className="mb-4">{content.conclusionPara3}</p>
<p className="mb-6">{content.conclusionPara4}</p>
<p className="mb-6 text-xl font-bold text-gray-800">{content.conclusionClosing}</p>
<div className="text-center mt-12 p-8 bg-gradient-to-br from-amber-50 to-orange-50 rounded-lg">
<Heart className="w-16 h-16 text-amber-600 mx-auto mb-4" />
<p className="text-gray-500 italic">{content.conclusionSignature}</p>
</div>
</div>
</div>
);
const currentPageData = pages[currentPage];
const nextPage = () => {
if (currentPage < pages.length - 1) {
setCurrentPage(currentPage + 1);
}
};
const prevPage = () => {
if (currentPage > 0) {
setCurrentPage(currentPage - 1);
}
};
return (
<div className="min-h-screen bg-gray-100 p-4">
<div className="max-w-4xl mx-auto">
{/* Header */}
<div className="bg-white rounded-t-lg shadow-lg p-4 flex justify-between items-center flex-wrap gap-2">
<div className="flex items-center gap-3">
<ChefHat className="w-8 h-8 text-amber-600" />
<div>
<h1 className="text-xl font-bold text-gray-800">{t.appTitle}</h1>
<p className="text-sm text-gray-500">
{t.page} {currentPage + 1} {t.of} {pages.length}
</p>
</div>
</div>
<div className="flex items-center gap-2">
{/* Language Switcher */}
<button
onClick={toggleLanguage}
className="flex items-center gap-2 px-3 py-2 bg-blue-100 text-blue-800 rounded-lg hover:bg-blue-200 transition-colors font-semibold"
title={language === 'en' ? 'Switch to Dutch / Schakel naar Nederlands' : 'Switch to English / Schakel naar Engels'}
>
<Globe className="w-4 h-4" />
<span className="uppercase font-bold">{language === 'en' ? 'NL' : 'EN'}</span>
</button>
<button
onClick={() => window.print()}
className="flex items-center gap-2 px-4 py-2 bg-amber-600 text-white rounded-lg hover:bg-amber-700 transition-colors"
>
<Printer className="w-4 h-4" />
{t.print}
</button>
</div>
</div>
{/* Book Page */}
<div className="bg-white shadow-lg" style={{ minHeight: '800px' }}>
{currentPageData.type === 'cover' && renderCover()}
{currentPageData.type === 'intro' && renderIntro()}
{currentPageData.type === 'recipe' && renderRecipe(currentPageData.content)}
{currentPageData.type === 'conclusion' && renderConclusion()}
</div>
{/* Navigation */}
<div className="bg-white rounded-b-lg shadow-lg p-4 flex justify-between items-center">
<button
onClick={prevPage}
disabled={currentPage === 0}
className={`flex items-center gap-2 px-4 py-2 rounded-lg transition-colors ${
currentPage === 0
? 'bg-gray-200 text-gray-400 cursor-not-allowed'
: 'bg-amber-600 text-white hover:bg-amber-700'
}`}
>
<ChevronLeft className="w-4 h-4" />
{t.previous}
</button>
<div className="text-sm text-gray-600">
{currentPageData.type === 'cover' && t.cover}
{currentPageData.type === 'intro' && t.introduction}
{currentPageData.type === 'recipe' && `${t.recipe}: ${currentPageData.content.title}`}
{currentPageData.type === 'conclusion' && t.conclusion}
</div>
<button
onClick={nextPage}
disabled={currentPage === pages.length - 1}
className={`flex items-center gap-2 px-4 py-2 rounded-lg transition-colors ${
currentPage === pages.length - 1
? 'bg-gray-200 text-gray-400 cursor-not-allowed'
: 'bg-amber-600 text-white hover:bg-amber-700'
}`}
>
{t.next}
<ChevronRight className="w-4 h-4" />
</button>
</div>
{/* Quick Navigation */}
<div className="mt-4 bg-white rounded-lg shadow-lg p-4">
<h3 className="font-bold text-gray-800 mb-3">{t.quickNav}</h3>
<div className="grid grid-cols-2 md:grid-cols-4 gap-2">
<button
onClick={() => setCurrentPage(0)}
className="text-left px-3 py-2 bg-amber-50 hover:bg-amber-100 rounded text-sm transition-colors"
>
📖 {t.cover}
</button>
<button
onClick={() => setCurrentPage(1)}
className="text-left px-3 py-2 bg-amber-50 hover:bg-amber-100 rounded text-sm transition-colors"
>
👋 {t.introduction}
</button>
<button
onClick={() => setCurrentPage(2)}
className="text-left px-3 py-2 bg-green-50 hover:bg-green-100 rounded text-sm transition-colors"
>
🍗 {t.recipesStart}
</button>
<button
onClick={() => setCurrentPage(pages.length - 1)}
className="text-left px-3 py-2 bg-blue-50 hover:bg-blue-100 rounded text-sm transition-colors"
>
💫 {t.conclusion}
</button>
</div>
</div>
</div>
</div>
);
};
ReactDOM.render(<RecipeEbook />, document.getElementById('root'));
</script>
</body><!-- Floating Amazon Button -->
<a
href="https://www.amazon.com/dp/B0FTTJYRT8"
target="_blank"
rel="noopener noreferrer"
class="no-print fixed bottom-6 right-6 bg-amber-600 text-white px-6 py-3 rounded-full shadow-2xl hover:bg-amber-700 hover:scale-105 transition-all duration-200 font-bold z-50 flex items-center gap-2"
>
📖 Buy the Book
</a>
```
---
## 🔗 **De Amazon link om te kopiëren:**
```
https://www.amazon.com/dp/B0FTTJYRT8
</html>