diff --git a/src/pages/nutrition/PictureSection.tsx b/src/pages/nutrition/PictureSection.tsx
index 18910ccdf..7ffc7f76d 100644
--- a/src/pages/nutrition/PictureSection.tsx
+++ b/src/pages/nutrition/PictureSection.tsx
@@ -1,4 +1,7 @@
import * as React from "react";
+import IconButton from "@mui/material/IconButton";
+import RotateRightIcon from "@mui/icons-material/RotateRight";
+import RotateLeftIcon from "@mui/icons-material/RotateLeft";
import { InsightType } from "./insight.types";
import { ProductType } from "./useRobotoffPredictions";
import { getImageId } from "./utils";
@@ -19,6 +22,11 @@ interface PictureSectionProps {
export default function PictureSection(props: PictureSectionProps) {
const { isLoading, insight, product, apiRef } = props;
+ const [rotationIndex, setRotationIndex] = React.useState(0);
+
+ React.useEffect(() => {
+ setRotationIndex(0);
+ }, [insight]);
if (isLoading) {
return
Loading ....
;
}
@@ -42,6 +50,12 @@ export default function PictureSection(props: PictureSectionProps) {
})
: "..."}
+ setRotationIndex((p) => p - 1)}>
+
+
+ setRotationIndex((p) => p + 1)}>
+
+
diff --git a/src/pages/nutrition/config.ts b/src/pages/nutrition/config.ts
index 9360ba960..c998769a5 100644
--- a/src/pages/nutrition/config.ts
+++ b/src/pages/nutrition/config.ts
@@ -1 +1,153 @@
export const UNITS = ["", "g", "mg", "µg"];
+
+export const OFF_NUTRIMENTS_TO_IGNORE = [
+ "serving",
+ "energy", // Already available with energy kj and kcal.
+ "fruits-vegetables-legumes-estimate-from-ingredients",
+ "fruits-vegetables-nuts-estimate-from-ingredients",
+ "nova-group",
+ "nutrition-score-fr",
+];
+export const NUTRIMENTS_ORDER = [
+ // Energy
+ "energy-kj",
+ "energy-kcal",
+
+ // Fat
+ "fat",
+ "saturated-fat",
+ "unsaturated-fat",
+ "monounsaturated-fat",
+ "polyunsaturated-fat",
+ "trans-fat",
+ "butyric-acid",
+ "caproic-acid",
+ "caprylic-acid",
+ "capric-acid",
+ "lauric-acid",
+ "myristic-acid",
+ "palmitic-acid",
+ "stearic-acid",
+ "arachidic-acid",
+ "behenic-acid",
+ "lignoceric-acid",
+ "cerotic-acid",
+ "montanic-acid",
+ "melissic-acid",
+
+ // Sucres
+ "carbohydrates",
+ "sugars",
+ "added-sugars",
+ "sucrose",
+ "glucose",
+ "fructose",
+ "lactose",
+ "maltose",
+ "maltodextrins",
+
+ "fiber",
+ "soluble-fiber",
+ "insoluble-fiber",
+
+ "proteins",
+ "casein",
+ "serum-proteins",
+
+ "salt",
+ "added-salt",
+ "sodium",
+
+ "cholesterol",
+
+ "alpha-linolenic-acid",
+ "eicosapentaenoic-acid",
+ "docosahexaenoic-acid",
+ "omega-3-fat",
+ "omega-6-fat",
+ "linoleic-acid",
+ "arachidonic-acid",
+ "gamma-linolenic-acid",
+ "dihomo-gamma-linolenic-acid",
+ "omega-9-fat",
+ "oleic-acid",
+ "elaidic-acid",
+ "gondoic-acid",
+ "mead-acid",
+ "erucic-acid",
+ "nervonic-acid",
+
+ "oligosaccharide",
+
+ "galactose",
+ "starch",
+ "Polydextrose",
+ "polyols",
+ "erythritol",
+
+ "nucleotides",
+ "alcohol",
+ "vitamin-a",
+ "beta-carotene",
+ "vitamin-d",
+ "vitamin-e",
+ "vitamin-k",
+ "vitamin-c",
+ "vitamin-b1",
+ "vitamin-b2",
+ "vitamin-pp",
+ "vitamin-b6",
+ "vitamin-b9",
+ "folates",
+ "vitamin-b12",
+ "biotin",
+ "pantothenic-acid",
+ "silica",
+ "bicarbonate",
+ "Sulphate",
+ "Nitrate",
+ "Hydrogencarbonate",
+ "Nitrite",
+ "potassium",
+ "chloride",
+ "calcium",
+ "phosphorus",
+ "iron",
+ "magnesium",
+ "zinc",
+ "copper",
+ "manganese",
+ "fluoride",
+ "selenium",
+ "chromium",
+ "molybdenum",
+ "iodine",
+ "caffeine",
+ "taurine",
+ "ph",
+ "collagen-meat-protein-ratio",
+ "cocoa",
+ "chlorophyl",
+ "glycemic-index",
+ "water-hardness",
+ "choline",
+ "phylloquinone",
+ "beta-glucan",
+ "inositol",
+ "carnitine",
+ "spermidine",
+ "water",
+ "acidity",
+ "dry-residue",
+ "beta-alanine",
+ "creatine",
+ "l-citrulline",
+ "l-glutamine",
+ "bcaa",
+ "l-valine",
+ "l-leucine",
+ "l-isoleucine",
+ "l-arginine",
+ "l-cysteine",
+ "l-Glutathione",
+];
diff --git a/src/pages/nutrition/index.tsx b/src/pages/nutrition/index.tsx
index 8b97c4b20..19a5228d1 100644
--- a/src/pages/nutrition/index.tsx
+++ b/src/pages/nutrition/index.tsx
@@ -15,6 +15,7 @@ import { ErrorBoundary } from "../taxonomyWalk/Error";
import LinksToProduct from "./LinksToProduct";
import { NutrimentCell } from "./NutrimentCell";
import PictureSection from "./PictureSection";
+import { NUTRIMENTS_ORDER } from "./config";
export default function Nutrition() {
const [partiallyFilled, setPartiallyFilled] = React.useState(false);
@@ -22,7 +23,8 @@ export default function Nutrition() {
const handlePartiallyFilled = (_, checked) => setPartiallyFilled(checked);
const handleDisplayOFFValue = (_, checked) => setDisplayOFFValue(checked);
- console.log({ partiallyFilled });
+ const [additionalIds, setAdditionalIds] = React.useState([]);
+
const { isLoading, insight, nextItem, count, product } =
useRobotoffPredictions(partiallyFilled);
@@ -32,6 +34,7 @@ export default function Nutrition() {
const apiRef = React.useRef();
React.useEffect(() => {
+ setAdditionalIds([]);
if (!insight || typeof insight === "string") {
setValues({});
return;
@@ -62,8 +65,15 @@ export default function Nutrition() {
}));
}, [insight]);
- const nutrimentsDetected = structurePredictions(values);
+ const nutrimentsDetected = React.useMemo(
+ () => structurePredictions(values, product, additionalIds),
+ [values, product, additionalIds],
+ );
+ const notUsedNutriments = React.useMemo(
+ () => NUTRIMENTS_ORDER.filter((id) => !nutrimentsDetected.includes(id)),
+ [nutrimentsDetected],
+ );
return (
@@ -195,6 +205,29 @@ export default function Nutrition() {
);
})}
+
+
+
+ |
+ |
+ |
+
diff --git a/src/pages/nutrition/utils.ts b/src/pages/nutrition/utils.ts
index c8ff42652..e4f919e78 100644
--- a/src/pages/nutrition/utils.ts
+++ b/src/pages/nutrition/utils.ts
@@ -1,5 +1,5 @@
import axios from "axios";
-import { UNITS } from "./config";
+import { OFF_NUTRIMENTS_TO_IGNORE, UNITS } from "./config";
import { NutrimentPrediction } from "./insight.types";
import { ROBOTOFF_API_URL } from "../../const";
@@ -15,6 +15,7 @@ export const NUTRIMENTS = {
fiber: "fiber",
proteins: "proteins",
salt: "salt",
+ sodium: "sodium",
};
export function isValidUnit(unit: string | null) {
@@ -23,21 +24,34 @@ export function isValidUnit(unit: string | null) {
export function structurePredictions(
predictions: Record>,
+ productValue?: { nutriments?: Record },
+ additionalIds?: string[],
) {
const nurimentsIds = Object.keys(NUTRIMENTS);
Object.keys(predictions).forEach((key) => {
- if (key === "serving_size") {
+ const id = key.split("_")[0]; // split 'energy-kj_100g' to only get 'energy-kj'
+
+ if (OFF_NUTRIMENTS_TO_IGNORE.includes(id)) {
return;
}
+ if (!nurimentsIds.includes(id)) {
+ nurimentsIds.push(id);
+ }
+ });
+
+ Object.keys(productValue?.nutriments ?? {}).forEach((key) => {
const id = key.split("_")[0]; // split 'energy-kj_100g' to only get 'energy-kj'
+ if (OFF_NUTRIMENTS_TO_IGNORE.includes(id)) {
+ return;
+ }
if (!nurimentsIds.includes(id)) {
nurimentsIds.push(id);
}
});
- return nurimentsIds;
+ return [...nurimentsIds, ...additionalIds];
}
interface PostRobotoffParams {