| 
									
										
										
										
											2022-05-16 01:30:33 +02:00
										 |  |  | import DOMPurify from "isomorphic-dompurify"; | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  | import { useFraction } from "./use-fraction"; | 
					
						
							| 
									
										
										
										
											2023-11-14 09:39:07 -06:00
										 |  |  | import { CreateIngredientFood, CreateIngredientUnit, IngredientFood, IngredientUnit, RecipeIngredient } from "~/lib/api/types/recipe"; | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  | const { frac } = useFraction(); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-10-07 14:23:47 -05:00
										 |  |  | export function sanitizeIngredientHTML(rawHtml: string) { | 
					
						
							| 
									
										
										
										
											2022-04-24 13:00:04 -08:00
										 |  |  |   return DOMPurify.sanitize(rawHtml, { | 
					
						
							| 
									
										
										
										
											2022-05-22 11:16:23 -08:00
										 |  |  |     USE_PROFILES: { html: true }, | 
					
						
							|  |  |  |     ALLOWED_TAGS: ["b", "q", "i", "strong", "sup"], | 
					
						
							| 
									
										
										
										
											2022-05-16 01:30:33 +02:00
										 |  |  |   }); | 
					
						
							| 
									
										
										
										
											2022-04-24 13:00:04 -08:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-11-14 09:39:07 -06:00
										 |  |  | function useFoodName(food: CreateIngredientFood | IngredientFood | undefined, usePlural: boolean) { | 
					
						
							|  |  |  |   if (!food) { | 
					
						
							|  |  |  |     return ""; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   return (usePlural ? food.pluralName || food.name : food.name) || ""; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | function useUnitName(unit: CreateIngredientUnit | IngredientUnit | undefined, usePlural: boolean) { | 
					
						
							|  |  |  |   if (!unit) { | 
					
						
							|  |  |  |     return ""; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   let returnVal = ""; | 
					
						
							|  |  |  |   if (unit.useAbbreviation) { | 
					
						
							|  |  |  |     returnVal = (usePlural ? unit.pluralAbbreviation || unit.abbreviation : unit.abbreviation) || ""; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   if (!returnVal) { | 
					
						
							|  |  |  |     returnVal = (usePlural ? unit.pluralName || unit.name : unit.name) || ""; | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   return returnVal; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-08-31 12:08:44 -05:00
										 |  |  | export function useParsedIngredientText(ingredient: RecipeIngredient, disableAmount: boolean, scale = 1, includeFormating = true) { | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  |   if (disableAmount) { | 
					
						
							| 
									
										
										
										
											2023-08-21 17:32:09 +02:00
										 |  |  |     return { | 
					
						
							|  |  |  |       name: ingredient.note ? sanitizeIngredientHTML(ingredient.note) : undefined, | 
					
						
							|  |  |  |       quantity: undefined, | 
					
						
							|  |  |  |       unit: undefined, | 
					
						
							|  |  |  |       note: undefined, | 
					
						
							|  |  |  |     }; | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   const { quantity, food, unit, note } = ingredient; | 
					
						
							| 
									
										
										
										
											2023-11-27 10:58:18 -06:00
										 |  |  |   const usePluralUnit = quantity !== undefined && (quantity * scale > 1 || quantity * scale === 0); | 
					
						
							|  |  |  |   const usePluralFood = (!quantity) || quantity * scale > 1 | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   let returnQty = ""; | 
					
						
							| 
									
										
										
										
											2022-05-22 11:16:23 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   // casting to number is required as sometimes quantity is a string
 | 
					
						
							|  |  |  |   if (quantity && Number(quantity) !== 0) { | 
					
						
							| 
									
										
										
										
											2024-05-12 14:15:26 -05:00
										 |  |  |     if (unit && !unit.fraction) { | 
					
						
							|  |  |  |       returnQty = (quantity * scale).toString(); | 
					
						
							|  |  |  |     } else { | 
					
						
							| 
									
										
										
										
											2022-01-09 07:15:23 +01:00
										 |  |  |       const fraction = frac(quantity * scale, 10, true); | 
					
						
							|  |  |  |       if (fraction[0] !== undefined && fraction[0] > 0) { | 
					
						
							|  |  |  |         returnQty += fraction[0]; | 
					
						
							|  |  |  |       } | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2022-01-09 07:15:23 +01:00
										 |  |  |       if (fraction[1] > 0) { | 
					
						
							| 
									
										
										
										
											2023-08-31 12:08:44 -05:00
										 |  |  |         returnQty += includeFormating ? | 
					
						
							| 
									
										
										
										
											2024-06-13 15:04:45 +02:00
										 |  |  |           `<sup>${fraction[1]}</sup><span>⁄</span><sub>${fraction[2]}</sub>` : | 
					
						
							| 
									
										
										
										
											2023-08-31 12:08:44 -05:00
										 |  |  |           ` ${fraction[1]}/${fraction[2]}`; | 
					
						
							| 
									
										
										
										
											2022-01-09 07:15:23 +01:00
										 |  |  |       } | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  |     } | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-11-14 09:39:07 -06:00
										 |  |  |   const unitName = useUnitName(unit, usePluralUnit); | 
					
						
							|  |  |  |   const foodName = useFoodName(food, usePluralFood); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-08-21 17:32:09 +02:00
										 |  |  |   return { | 
					
						
							|  |  |  |     quantity: returnQty ? sanitizeIngredientHTML(returnQty) : undefined, | 
					
						
							| 
									
										
										
										
											2023-11-14 09:39:07 -06:00
										 |  |  |     unit: unitName && quantity ? sanitizeIngredientHTML(unitName) : undefined, | 
					
						
							|  |  |  |     name: foodName ? sanitizeIngredientHTML(foodName) : undefined, | 
					
						
							| 
									
										
										
										
											2023-08-21 17:32:09 +02:00
										 |  |  |     note: note ? sanitizeIngredientHTML(note) : undefined, | 
					
						
							|  |  |  |   }; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-08-31 12:08:44 -05:00
										 |  |  | export function parseIngredientText(ingredient: RecipeIngredient, disableAmount: boolean, scale = 1, includeFormating = true): string { | 
					
						
							|  |  |  |   const { quantity, unit, name, note } = useParsedIngredientText(ingredient, disableAmount, scale, includeFormating); | 
					
						
							| 
									
										
										
										
											2023-08-21 17:32:09 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |   const text = `${quantity || ""} ${unit || ""} ${name || ""} ${note || ""}`.replace(/ {2,}/g, " ").trim(); | 
					
						
							| 
									
										
										
										
											2022-04-24 13:00:04 -08:00
										 |  |  |   return sanitizeIngredientHTML(text); | 
					
						
							| 
									
										
										
										
											2021-11-06 11:28:47 -08:00
										 |  |  | } |