diff --git a/client/src/components/production-board-kanban-card/production-board-kanban-card-color-legend.component.jsx b/client/src/components/production-board-kanban-card/production-board-kanban-card-color-legend.component.jsx
index f9bec96f0..abae21de0 100644
--- a/client/src/components/production-board-kanban-card/production-board-kanban-card-color-legend.component.jsx
+++ b/client/src/components/production-board-kanban-card/production-board-kanban-card-color-legend.component.jsx
@@ -22,7 +22,7 @@ const CardColorLegend = ({ bodyshop }) => {
});
return (
-
+
{t("production.labels.legend")}
- data
- .reduce(
- (acc, val) =>
- acc + (val.labhrs?.aggregate?.sum?.mod_lb_hrs || 0) + (val.larhrs?.aggregate?.sum?.mod_lb_hrs || 0),
- 0
- )
- .toFixed(1),
- [data]
- );
-
- const totalLAB = useMemo(
- () => data.reduce((acc, val) => acc + (val.labhrs?.aggregate?.sum?.mod_lb_hrs || 0), 0).toFixed(1),
- [data]
- );
-
- const totalLAR = useMemo(
- () => data.reduce((acc, val) => acc + (val.larhrs?.aggregate?.sum?.mod_lb_hrs || 0), 0).toFixed(1),
- [data]
- );
-
const cardSettings = useMemo(
() =>
associationSettings?.kanban_settings && Object.keys(associationSettings.kanban_settings).length > 0
@@ -215,7 +193,17 @@ function ProductionBoardKanbanComponent({ data, bodyshop, refetch, insertAuditTr
orientation: false,
cardSize: "small",
model_info: true,
- kiosk: false
+ kiosk: false,
+ totalHrs: true,
+ totalAmountInProduction: false,
+ totalLAB: true,
+ totalLAR: true,
+ jobsInProduction: true,
+ totalHrsOnBoard: false,
+ totalLABOnBoard: false,
+ totalLAROnBoard: false,
+ jobsOnBoard: false,
+ totalAmountOnBoard: true
},
[associationSettings]
);
@@ -234,14 +222,8 @@ function ProductionBoardKanbanComponent({ data, bodyshop, refetch, insertAuditTr
-
-
-
-
-
- }
+ title={cardSettings.cardcolor && }
+ style={{ paddingInline: 0, paddingBlock: 0 }}
extra={
}
/>
- {cardSettings.cardcolor && }
-
+
);
}
diff --git a/client/src/components/production-board-kanban/production-board-kanban.container.jsx b/client/src/components/production-board-kanban/production-board-kanban.container.jsx
index e6502b178..d4834cc94 100644
--- a/client/src/components/production-board-kanban/production-board-kanban.container.jsx
+++ b/client/src/components/production-board-kanban/production-board-kanban.container.jsx
@@ -2,10 +2,7 @@ import React, { useEffect, useMemo } from "react";
import { useQuery, useSubscription } from "@apollo/client";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
-import {
- QUERY_JOBS_IN_PRODUCTION_WITH_STATUSES,
- SUBSCRIPTION_JOBS_IN_PRODUCTION_WITH_STATUSES
-} from "../../graphql/jobs.queries";
+import { QUERY_JOBS_IN_PRODUCTION, SUBSCRIPTION_JOBS_IN_PRODUCTION } from "../../graphql/jobs.queries";
import { QUERY_KANBAN_SETTINGS } from "../../graphql/user.queries";
import { selectBodyshop, selectCurrentUser } from "../../redux/user/user.selectors";
import ProductionBoardKanbanComponent from "./production-board-kanban.component";
@@ -24,16 +21,14 @@ function ProductionBoardKanbanContainer({ bodyshop, currentUser }) {
[bodyshop.md_ro_statuses.production_statuses, bodyshop.md_ro_statuses.additional_board_statuses]
);
- const { refetch, loading, data } = useQuery(QUERY_JOBS_IN_PRODUCTION_WITH_STATUSES, {
- variables: { statuses: combinedStatuses },
+ const { refetch, loading, data } = useQuery(QUERY_JOBS_IN_PRODUCTION, {
pollInterval: 3600000,
fetchPolicy: "network-only",
nextFetchPolicy: "network-only",
onError: (error) => console.error(`Error fetching jobs in production: ${error.message}`)
});
- const { data: updatedJobs } = useSubscription(SUBSCRIPTION_JOBS_IN_PRODUCTION_WITH_STATUSES, {
- variables: { statuses: combinedStatuses },
+ const { data: updatedJobs } = useSubscription(SUBSCRIPTION_JOBS_IN_PRODUCTION, {
onError: (error) => console.error(`Error subscribing to jobs in production: ${error.message}`)
});
diff --git a/client/src/components/production-board-kanban/production-board-kanban.settings.component.jsx b/client/src/components/production-board-kanban/production-board-kanban.settings.component.jsx
index d84b19882..39d60fa14 100644
--- a/client/src/components/production-board-kanban/production-board-kanban.settings.component.jsx
+++ b/client/src/components/production-board-kanban/production-board-kanban.settings.component.jsx
@@ -1,3 +1,4 @@
+// ProductionBoardKanbanSettings.jsx
import { useMutation } from "@apollo/client";
import { Button, Card, Checkbox, Col, Form, notification, Popover, Radio, Row } from "antd";
import React, { useEffect, useState } from "react";
@@ -121,6 +122,22 @@ export default function ProductionBoardKanbanSettings({ associationSettings, par
].map((item) => renderCheckboxItem(item, `production.labels.${item}`))}
+
+
+ {[
+ { name: "totalHrs", label: "total_hours_in_production" },
+ { name: "totalLAB", label: "total_lab_in_production" },
+ { name: "totalLAR", label: "total_lar_in_production" },
+ { name: "totalAmountInProduction", label: "total_amount_in_production" },
+ { name: "jobsInProduction", label: "jobs_in_production" },
+ { name: "totalHrsOnBoard", label: "total_hours_on_board" },
+ { name: "totalLABOnBoard", label: "total_lab_on_board" },
+ { name: "totalLAROnBoard", label: "total_lar_on_board" },
+ { name: "jobsOnBoard", label: "total_jobs_on_board" },
+ { name: "totalAmountOnBoard", label: "total_amount_on_board" }
+ ].map((item) => renderCheckboxItem(item.name, `production.settings.statistics.${item.label}`))}
+
+
>
);
diff --git a/client/src/components/production-board-kanban/production-board-kanban.statistics.jsx b/client/src/components/production-board-kanban/production-board-kanban.statistics.jsx
new file mode 100644
index 000000000..7ce4591d2
--- /dev/null
+++ b/client/src/components/production-board-kanban/production-board-kanban.statistics.jsx
@@ -0,0 +1,145 @@
+import React, { useMemo } from "react";
+import { Statistic, Card } from "antd";
+import { useTranslation } from "react-i18next";
+
+const ProductionStatistics = ({ data, cardSettings, reducerData }) => {
+ const { t } = useTranslation();
+
+ const calculateTotal = (items, key, subKey) => {
+ return items.reduce((acc, item) => acc + (item[key]?.aggregate?.sum?.[subKey] || 0), 0);
+ };
+
+ const calculateTotalAmount = (items, key) => {
+ return items.reduce((acc, item) => acc + (item[key]?.totals?.subtotal?.amount || 0), 0);
+ };
+
+ const calculateReducerTotal = (lanes, key, subKey) => {
+ return lanes.reduce((acc, lane) => {
+ return (
+ acc + lane.cards.reduce((laneAcc, card) => laneAcc + (card.metadata[key]?.aggregate?.sum?.[subKey] || 0), 0)
+ );
+ }, 0);
+ };
+
+ const calculateReducerTotalAmount = (lanes, key) => {
+ return lanes.reduce((acc, lane) => {
+ return (
+ acc + lane.cards.reduce((laneAcc, card) => laneAcc + (card.metadata[key]?.totals?.subtotal?.amount || 0), 0)
+ );
+ }, 0);
+ };
+
+ const formatValue = (value, type) => {
+ if (type === "Jobs") {
+ return value.toFixed(0);
+ }
+ if (type === "Hrs") {
+ return value.toFixed(2);
+ }
+ return value;
+ };
+
+ const totalHrs = useMemo(() => {
+ if (!cardSettings.totalHrs) return null;
+ const total = calculateTotal(data, "labhrs", "mod_lb_hrs") + calculateTotal(data, "larhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [data, cardSettings.totalHrs]);
+
+ const totalLAB = useMemo(() => {
+ if (!cardSettings.totalLAB) return null;
+ const total = calculateTotal(data, "labhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [data, cardSettings.totalLAB]);
+
+ const totalLAR = useMemo(() => {
+ if (!cardSettings.totalLAR) return null;
+ const total = calculateTotal(data, "larhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [data, cardSettings.totalLAR]);
+
+ const jobsInProduction = useMemo(
+ () => (cardSettings.jobsInProduction ? data.length : null),
+ [data, cardSettings.jobsInProduction]
+ );
+
+ const totalAmountInProduction = useMemo(() => {
+ if (!cardSettings.totalAmountInProduction) return null;
+ const total = calculateTotalAmount(data, "job_totals");
+ return parseFloat(total.toFixed(2));
+ }, [data, cardSettings.totalAmountInProduction]);
+
+ const totalHrsOnBoard = useMemo(() => {
+ if (!reducerData || !cardSettings.totalHrsOnBoard) return null;
+ const total =
+ calculateReducerTotal(reducerData.lanes, "labhrs", "mod_lb_hrs") +
+ calculateReducerTotal(reducerData.lanes, "larhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [reducerData, cardSettings.totalHrsOnBoard]);
+
+ const totalLABOnBoard = useMemo(() => {
+ if (!reducerData || !cardSettings.totalLABOnBoard) return null;
+ const total = calculateReducerTotal(reducerData.lanes, "labhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [reducerData, cardSettings.totalLABOnBoard]);
+
+ const totalLAROnBoard = useMemo(() => {
+ if (!reducerData || !cardSettings.totalLAROnBoard) return null;
+ const total = calculateReducerTotal(reducerData.lanes, "larhrs", "mod_lb_hrs");
+ return parseFloat(total.toFixed(2));
+ }, [reducerData, cardSettings.totalLAROnBoard]);
+
+ const jobsOnBoard = useMemo(
+ () =>
+ reducerData && cardSettings.jobsOnBoard
+ ? reducerData.lanes.reduce((acc, lane) => acc + lane.cards.length, 0)
+ : null,
+ [reducerData, cardSettings.jobsOnBoard]
+ );
+
+ const totalAmountOnBoard = useMemo(() => {
+ if (!reducerData || !cardSettings.totalAmountOnBoard) return null;
+ const total = calculateReducerTotalAmount(reducerData.lanes, "job_totals");
+ return parseFloat(total.toFixed(2));
+ }, [reducerData, cardSettings.totalAmountOnBoard]);
+
+ const statistics = [
+ { value: totalHrs, title: t("total_hours_in_production"), suffix: t("production.statistics.hours") },
+ {
+ value: totalAmountInProduction,
+ title: t("total_amount_in_production"),
+ prefix: t("production.statistics.currency_symbol")
+ },
+ { value: totalLAB, title: t("total_lab_in_production"), suffix: t("production.statistics.hours") },
+ { value: totalLAR, title: t("total_lar_in_production"), suffix: t("production.statistics.hours") },
+ { value: jobsInProduction, title: t("jobs_in_production"), suffix: "Jobs" },
+ { value: totalHrsOnBoard, title: t("total_hours_on_board"), suffix: t("production.statistics.hours") },
+ {
+ value: totalAmountOnBoard,
+ title: t("total_amount_on_board"),
+ prefix: t("production.statistics.currency_symbol")
+ },
+ { value: totalLABOnBoard, title: t("total_lab_on_board"), suffix: t("production.statistics.hours") },
+ { value: totalLAROnBoard, title: t("total_lar_on_board"), suffix: t("production.statistics.hours") },
+ { value: jobsOnBoard, title: t("total_jobs_on_board"), suffix: "Jobs" }
+ ];
+
+ return (
+
+ {statistics.map(
+ (stat, index) =>
+ stat.value !== null && (
+
+
+
+ )
+ )}
+
+ );
+};
+
+export default ProductionStatistics;
diff --git a/client/src/components/production-board-kanban/trello-board/controllers/BoardContainer.jsx b/client/src/components/production-board-kanban/trello-board/controllers/BoardContainer.jsx
index e59d92aec..96879b0b6 100644
--- a/client/src/components/production-board-kanban/trello-board/controllers/BoardContainer.jsx
+++ b/client/src/components/production-board-kanban/trello-board/controllers/BoardContainer.jsx
@@ -7,6 +7,7 @@ import Lane from "./Lane";
import { PopoverWrapper } from "react-popopo";
import * as actions from "../../../../redux/trello/trello.actions.js";
import { BoardWrapper } from "../styles/Base.js";
+import ProductionStatistics from "../../production-board-kanban.statistics.jsx";
const useDragMap = () => {
const dragMapRef = useRef(new Map());
@@ -30,7 +31,8 @@ const BoardContainer = ({
orientation = "horizontal",
cardSettings = {},
eventBusHandle,
- reducerData
+ reducerData,
+ queryData
}) => {
const [isDragging, setIsDragging] = useState(false);
const [isProcessing, setIsProcessing] = useState(false);
@@ -124,33 +126,36 @@ const BoardContainer = ({
);
return (
-
-
-
- {currentReducerData.lanes.map((lane, index) => (
-
- ))}
-
-
-
+
+
+
+
+
+ {currentReducerData.lanes.map((lane, index) => (
+
+ ))}
+
+
+
+
);
};
diff --git a/client/src/graphql/jobs.queries.js b/client/src/graphql/jobs.queries.js
index 89dc8a726..51ff6927c 100644
--- a/client/src/graphql/jobs.queries.js
+++ b/client/src/graphql/jobs.queries.js
@@ -292,82 +292,6 @@ export const QUERY_EXACT_JOBS_IN_PRODUCTION = gql`
}
`;
-export const QUERY_JOBS_IN_PRODUCTION = gql`
- query QUERY_JOBS_IN_PRODUCTION {
- jobs(where: { inproduction: { _eq: true } }) {
- id
- updated_at
- comment
- status
- category
- iouparent
- ro_number
- ownerid
- ownr_fn
- ownr_ln
- ownr_co_nm
- v_model_yr
- v_model_desc
- clm_no
- v_make_desc
- v_color
- vehicleid
- plate_no
- actual_in
- scheduled_completion
- scheduled_delivery
- date_last_contacted
- date_next_contact
- ins_co_nm
- clm_total
- ownr_ph1
- ownr_ph2
- special_coverage_policy
- owner_owing
- production_vars
- kanbanparent
- alt_transport
- employee_body
- employee_refinish
- employee_prep
- employee_csr
- est_ct_fn
- est_ct_ln
- suspended
- date_repairstarted
- joblines_status {
- part_type
- status
- count
- }
- labhrs: joblines_aggregate(where: { _and: [{ mod_lbr_ty: { _neq: "LAR" } }, { removed: { _eq: false } }] }) {
- aggregate {
- sum {
- mod_lb_hrs
- }
- }
- }
- larhrs: joblines_aggregate(where: { _and: [{ mod_lbr_ty: { _eq: "LAR" } }, { removed: { _eq: false } }] }) {
- aggregate {
- sum {
- mod_lb_hrs
- }
- }
- }
- subletLines: joblines(
- where: { _and: { part_type: { _in: ["PAS", "PASL"] }, removed: { _eq: false } } }
- order_by: { line_no: asc }
- ) {
- id
- line_desc
- sublet_ignored
- sublet_completed
- jobid
- }
- }
- }
-`;
-
export const QUERY_LBR_HRS_BY_PK = gql`
query QUERY_LBR_HRS_BY_PK($id: uuid!) {
jobs_by_pk(id: $id) {
@@ -2529,9 +2453,18 @@ export const QUERY_PARTS_QUEUE_CARD_DETAILS = gql`
}
`;
-export const QUERY_JOBS_IN_PRODUCTION_WITH_STATUSES = gql`
- query QUERY_JOBS_IN_PRODUCTION($statuses: [String!]) {
- jobs(where: { inproduction: { _eq: true }, status: { _in: $statuses } }) {
+export const SUBSCRIPTION_JOBS_IN_PRODUCTION = gql`
+ subscription SUBSCRIPTION_JOBS_IN_PRODUCTION {
+ jobs(where: { inproduction: { _eq: true } }) {
+ id
+ updated_at
+ }
+ }
+`;
+
+export const QUERY_JOBS_IN_PRODUCTION = gql`
+ query QUERY_JOBS_IN_PRODUCTION {
+ jobs(where: { inproduction: { _eq: true } }) {
id
updated_at
comment
@@ -2571,6 +2504,7 @@ export const QUERY_JOBS_IN_PRODUCTION_WITH_STATUSES = gql`
est_ct_fn
est_ct_ln
suspended
+ job_totals
date_repairstarted
joblines_status {
part_type
@@ -2604,21 +2538,3 @@ export const QUERY_JOBS_IN_PRODUCTION_WITH_STATUSES = gql`
}
}
`;
-
-export const SUBSCRIPTION_JOBS_IN_PRODUCTION_WITH_STATUSES = gql`
- subscription SUBSCRIPTION_JOBS_IN_PRODUCTION($statuses: [String!]) {
- jobs(where: { inproduction: { _eq: true }, status: { _in: $statuses } }) {
- id
- updated_at
- }
- }
-`;
-
-export const SUBSCRIPTION_JOBS_IN_PRODUCTION = gql`
- subscription SUBSCRIPTION_JOBS_IN_PRODUCTION {
- jobs(where: { inproduction: { _eq: true } }) {
- id
- updated_at
- }
- }
-`;
diff --git a/client/src/translations/en_us/common.json b/client/src/translations/en_us/common.json
index 4f19ee1e5..c68f3ea15 100644
--- a/client/src/translations/en_us/common.json
+++ b/client/src/translations/en_us/common.json
@@ -2733,11 +2733,19 @@
"settings": {
"layout": "Layout",
"information": "Information",
+ "statistics_title": "Statistics",
"board_settings": "Board Settings",
- "tabs": {
- "card": "Card",
- "board": "Board",
- "lane": "Lane"
+ "statistics": {
+ "total_hours_in_production": "Hours in Production",
+ "total_lab_in_production": "Body Hours in Production",
+ "total_lar_in_production": "Refinish Hours in Production",
+ "total_amount_in_production": "Dollars in Production",
+ "jobs_in_production": "Jobs in Production",
+ "total_hours_on_board": "Hours on Board",
+ "total_lab_on_board": "Body Hours on Board",
+ "total_lar_on_board": "Refinish Hours on Board",
+ "total_amount_on_board": "Dollars on Board",
+ "total_jobs_on_board": "Jobs on Board"
}
},
"actions": {
@@ -2811,7 +2819,21 @@
},
"successes": {
"removed": "Job removed from production."
- }
+ },
+ "statistics": {
+ "total_hours_in_production": "Hours in Production",
+ "total_lab_in_production": "Body Hours in Production",
+ "total_lar_in_production": "Refinish Hours in Production",
+ "total_amount_in_production": "Dollars in Production",
+ "jobs_in_production": "Jobs in Production",
+ "total_hours_on_board": "Hours on Board",
+ "total_lab_on_board": "Body Hours on Board",
+ "total_lar_on_board": "Refinish Hours on Board",
+ "total_amount_on_board": "Dollars on Board",
+ "total_jobs_on_board": "Jobs on Board",
+ "hours": "Hours",
+ "currency_symbol": "$"
+ }
},
"profile": {
"errors": {
diff --git a/client/src/translations/es/common.json b/client/src/translations/es/common.json
index a80e7a054..d82de7862 100644
--- a/client/src/translations/es/common.json
+++ b/client/src/translations/es/common.json
@@ -2722,27 +2722,52 @@
"purchases_by_vendor_summary": ""
}
},
- "production": {
- "actions": {
- "addcolumns": "",
- "bodypriority-clear": "",
- "bodypriority-set": "",
- "detailpriority-clear": "",
- "detailpriority-set": "",
- "paintpriority-clear": "",
- "paintpriority-set": "",
- "remove": "",
- "removecolumn": "",
- "saveconfig": "",
- "suspend": "",
- "unsuspend": ""
- },
- "errors": {
- "boardupdate": "",
- "removing": "",
- "settings": ""
- },
- "labels": {
+ "production": {
+ "options": {
+ "small": "",
+ "medium": "",
+ "large": "",
+ "vertical": "",
+ "horizontal": ""
+ },
+ "settings": {
+ "layout": "",
+ "information": "",
+ "statistics_title": "",
+ "board_settings": "",
+ "statistics": {
+ "total_hours_in_production": "",
+ "total_lab_in_production": "",
+ "total_lar_in_production": "",
+ "total_amount_in_production": "",
+ "jobs_in_production": "",
+ "total_hours_on_board": "",
+ "total_lab_on_board": "",
+ "total_lar_on_board": "",
+ "total_amount_on_board": "",
+ "total_jobs_on_board": ""
+ }
+ },
+ "actions": {
+ "addcolumns": "",
+ "bodypriority-clear": "",
+ "bodypriority-set": "",
+ "detailpriority-clear": "",
+ "detailpriority-set": "",
+ "paintpriority-clear": "",
+ "paintpriority-set": "",
+ "remove": "",
+ "removecolumn": "",
+ "saveconfig": "",
+ "suspend": "",
+ "unsuspend": ""
+ },
+ "errors": {
+ "boardupdate": "",
+ "removing": "",
+ "settings": ""
+ },
+ "labels": {
"kiosk_mode": "",
"on": "",
"off": "",
@@ -2754,48 +2779,62 @@
"card_size": "",
"model_info": "",
"actual_in": "",
- "alert": "",
- "alertoff": "",
- "alerton": "",
- "ats": "",
- "bodyhours": "",
- "bodypriority": "",
- "bodyshop": {
- "labels": {
- "qbo_departmentid": "",
- "qbo_usa": ""
- }
- },
- "cardcolor": "",
- "cardsettings": "",
- "clm_no": "",
- "comment": "",
- "compact": "",
- "detailpriority": "",
- "employeeassignments": "",
- "employeesearch": "",
- "ins_co_nm": "",
- "jobdetail": "",
- "laborhrs": "",
- "legend": "",
- "note": "",
- "ownr_nm": "",
- "paintpriority": "",
- "partsstatus": "",
- "production_note": "",
- "refinishhours": "",
- "scheduled_completion": "",
- "selectview": "",
- "stickyheader": "",
- "sublets": "",
- "totalhours": "",
- "touchtime": "",
- "viewname": ""
- },
- "successes": {
- "removed": ""
- }
- },
+ "alert": "",
+ "alertoff": "",
+ "alerton": "",
+ "ats": "",
+ "bodyhours": "",
+ "bodypriority": "",
+ "bodyshop": {
+ "labels": {
+ "qbo_departmentid": "",
+ "qbo_usa": ""
+ }
+ },
+ "cardcolor": "",
+ "cardsettings": "",
+ "clm_no": "",
+ "comment": "",
+ "compact": "",
+ "detailpriority": "",
+ "employeeassignments": "",
+ "employeesearch": "",
+ "ins_co_nm": "",
+ "jobdetail": "",
+ "laborhrs": "",
+ "legend": "",
+ "note": "",
+ "ownr_nm": "",
+ "paintpriority": "",
+ "partsstatus": "",
+ "production_note": "",
+ "refinishhours": "",
+ "scheduled_completion": "",
+ "selectview": "",
+ "stickyheader": "",
+ "sublets": "",
+ "totalhours": "",
+ "touchtime": "",
+ "viewname": ""
+ },
+ "successes": {
+ "removed": ""
+ },
+ "statistics": {
+ "total_hours_in_production": "",
+ "total_lab_in_production": "",
+ "total_lar_in_production": "",
+ "total_amount_in_production": "",
+ "jobs_in_production": "",
+ "total_hours_on_board": "",
+ "total_lab_on_board": "",
+ "total_lar_on_board": "",
+ "total_amount_on_board": "",
+ "total_jobs_on_board": "",
+ "hours": "",
+ "currency_symbol": ""
+ }
+ },
"profile": {
"errors": {
"state": "Error al leer el estado de la página. Porfavor refresca."
diff --git a/client/src/translations/fr/common.json b/client/src/translations/fr/common.json
index 8d8c801ea..bf553724e 100644
--- a/client/src/translations/fr/common.json
+++ b/client/src/translations/fr/common.json
@@ -2722,72 +2722,119 @@
"purchases_by_vendor_summary": ""
}
},
- "production": {
- "actions": {
- "addcolumns": "",
- "bodypriority-clear": "",
- "bodypriority-set": "",
- "detailpriority-clear": "",
- "detailpriority-set": "",
- "paintpriority-clear": "",
- "paintpriority-set": "",
- "remove": "",
- "removecolumn": "",
- "saveconfig": "",
- "suspend": "",
- "unsuspend": ""
- },
- "errors": {
- "boardupdate": "",
- "removing": "",
- "settings": ""
- },
- "labels": {
+ "production": {
+ "options": {
+ "small": "",
+ "medium": "",
+ "large": "",
+ "vertical": "",
+ "horizontal": ""
+ },
+ "settings": {
+ "layout": "",
+ "information": "",
+ "statistics_title": "",
+ "board_settings": "",
+ "statistics": {
+ "total_hours_in_production": "",
+ "total_lab_in_production": "",
+ "total_lar_in_production": "",
+ "total_amount_in_production": "",
+ "jobs_in_production": "",
+ "total_hours_on_board": "",
+ "total_lab_on_board": "",
+ "total_lar_on_board": "",
+ "total_amount_on_board": "",
+ "total_jobs_on_board": ""
+ }
+ },
+ "actions": {
+ "addcolumns": "",
+ "bodypriority-clear": "",
+ "bodypriority-set": "",
+ "detailpriority-clear": "",
+ "detailpriority-set": "",
+ "paintpriority-clear": "",
+ "paintpriority-set": "",
+ "remove": "",
+ "removecolumn": "",
+ "saveconfig": "",
+ "suspend": "",
+ "unsuspend": ""
+ },
+ "errors": {
+ "boardupdate": "",
+ "removing": "",
+ "settings": ""
+ },
+ "labels": {
"kiosk_mode": "",
+ "on": "",
+ "off": "",
+ "wide": "",
+ "tall": "",
+ "vertical": "",
+ "horizontal": "",
+ "orientation": "",
+ "card_size": "",
"model_info": "",
"actual_in": "",
- "alert": "",
- "alertoff": "",
- "alerton": "",
- "ats": "",
- "bodyhours": "",
- "bodypriority": "",
- "bodyshop": {
- "labels": {
- "qbo_departmentid": "",
- "qbo_usa": ""
- }
- },
- "cardcolor": "",
- "cardsettings": "",
- "clm_no": "",
- "comment": "",
- "compact": "",
- "detailpriority": "",
- "employeeassignments": "",
- "employeesearch": "",
- "ins_co_nm": "",
- "jobdetail": "",
- "laborhrs": "",
- "legend": "",
- "note": "",
- "ownr_nm": "",
- "paintpriority": "",
- "partsstatus": "",
- "production_note": "",
- "refinishhours": "",
- "scheduled_completion": "",
- "selectview": "",
- "stickyheader": "",
- "sublets": "",
- "totalhours": "",
- "touchtime": "",
- "viewname": ""
- },
- "successes": {
- "removed": ""
- }
- },
+ "alert": "",
+ "alertoff": "",
+ "alerton": "",
+ "ats": "",
+ "bodyhours": "",
+ "bodypriority": "",
+ "bodyshop": {
+ "labels": {
+ "qbo_departmentid": "",
+ "qbo_usa": ""
+ }
+ },
+ "cardcolor": "",
+ "cardsettings": "",
+ "clm_no": "",
+ "comment": "",
+ "compact": "",
+ "detailpriority": "",
+ "employeeassignments": "",
+ "employeesearch": "",
+ "ins_co_nm": "",
+ "jobdetail": "",
+ "laborhrs": "",
+ "legend": "",
+ "note": "",
+ "ownr_nm": "",
+ "paintpriority": "",
+ "partsstatus": "",
+ "production_note": "",
+ "refinishhours": "",
+ "scheduled_completion": "",
+ "selectview": "",
+ "stickyheader": "",
+ "sublets": "",
+ "totalhours": "",
+ "touchtime": "",
+ "viewname": ""
+ },
+ "successes": {
+ "removed": ""
+ },
+ "statistics": {
+ "total_hours_in_production": "",
+ "total_lab_in_production": "",
+ "total_lar_in_production": "",
+ "total_amount_in_production": "",
+ "jobs_in_production": "",
+ "total_hours_on_board": "",
+ "total_lab_on_board": "",
+ "total_lar_on_board": "",
+ "total_amount_on_board": "",
+ "total_jobs_on_board": "",
+ "hours": "",
+ "currency_symbol": ""
+ }
+ },
"profile": {
"errors": {
"state": "Erreur lors de la lecture de l'état de la page. Rafraichissez, s'il vous plait."