Code format
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
import { useState, useEffect } from 'react';
|
||||
import { useState } from 'react';
|
||||
import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { Textarea } from '@/components/ui/textarea';
|
||||
@@ -208,11 +208,11 @@ const BatchTransactionForm: React.FC<BatchTransactionFormProps> = ({ onClose, on
|
||||
);
|
||||
|
||||
return (
|
||||
<div
|
||||
<div
|
||||
className="fixed inset-0 bg-black/50 flex items-center justify-center p-4 z-50"
|
||||
onClick={onClose}
|
||||
>
|
||||
<Card
|
||||
<Card
|
||||
className="bg-gray-900 border-gray-700 text-white w-full max-w-4xl max-h-[90vh] overflow-y-auto"
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
|
@@ -202,7 +202,7 @@ interface PriceDisplayProps {
|
||||
const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
const { copying, copyToClipboard } = useClipboard();
|
||||
const [salesTax, setSalesTax] = useState(() => parseFloat(localStorage.getItem('salesTax') || '0') / 100);
|
||||
|
||||
|
||||
// Listen for storage changes to update tax rate
|
||||
useEffect(() => {
|
||||
const handleStorageChange = () => {
|
||||
@@ -218,35 +218,35 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
const factor = Math.pow(10, digits - 1 - magnitude);
|
||||
return Math.round(num * factor) / factor;
|
||||
};
|
||||
|
||||
|
||||
// Calculate total costs and income
|
||||
const totalCosts = job.expenditures?.reduce((sum, tx) => sum + tx.totalPrice, 0) || 0;
|
||||
const totalIncome = job.income?.reduce((sum, tx) => sum + tx.totalPrice, 0) || 0;
|
||||
const itemsSold = job.income?.reduce((sum, tx) => sum + tx.quantity, 0) || 0;
|
||||
const itemsRemaining = (job.produced || 0) - itemsSold;
|
||||
|
||||
|
||||
// Original calculations (based on full revenue and costs)
|
||||
const targetPricePerUnit = job.projectedRevenue / job.produced;
|
||||
const targetPriceWithTax = roundToSignificantDigits(targetPricePerUnit * (1 + salesTax));
|
||||
|
||||
|
||||
const breakEvenPricePerUnit = totalCosts / job.produced;
|
||||
const breakEvenPriceWithTax = roundToSignificantDigits(breakEvenPricePerUnit * (1 + salesTax));
|
||||
|
||||
|
||||
// Adjusted calculations (based on remaining revenue and uncovered costs)
|
||||
const remainingRevenue = job.projectedRevenue - totalIncome;
|
||||
const uncoveredCosts = totalCosts - totalIncome;
|
||||
|
||||
|
||||
const adjustedTargetPricePerUnit = itemsRemaining > 0 ? remainingRevenue / itemsRemaining : 0;
|
||||
const adjustedTargetPriceWithTax = roundToSignificantDigits(adjustedTargetPricePerUnit * (1 + salesTax));
|
||||
|
||||
|
||||
const adjustedBreakEvenPricePerUnit = itemsRemaining > 0 ? Math.max(0, uncoveredCosts / itemsRemaining) : 0;
|
||||
const adjustedBreakEvenPriceWithTax = roundToSignificantDigits(adjustedBreakEvenPricePerUnit * (1 + salesTax));
|
||||
|
||||
|
||||
const handleCopyTargetPrice = async (e: React.MouseEvent) => {
|
||||
e.stopPropagation();
|
||||
await copyToClipboard(
|
||||
targetPriceWithTax.toString(),
|
||||
'targetPrice',
|
||||
targetPriceWithTax.toString(),
|
||||
'targetPrice',
|
||||
'Target price copied to clipboard'
|
||||
);
|
||||
};
|
||||
@@ -254,8 +254,8 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
const handleCopyBreakEvenPrice = async (e: React.MouseEvent) => {
|
||||
e.stopPropagation();
|
||||
await copyToClipboard(
|
||||
breakEvenPriceWithTax.toString(),
|
||||
'breakEvenPrice',
|
||||
breakEvenPriceWithTax.toString(),
|
||||
'breakEvenPrice',
|
||||
'Break-even price copied to clipboard'
|
||||
);
|
||||
};
|
||||
@@ -263,8 +263,8 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
const handleCopyAdjustedTargetPrice = async (e: React.MouseEvent) => {
|
||||
e.stopPropagation();
|
||||
await copyToClipboard(
|
||||
adjustedTargetPriceWithTax.toString(),
|
||||
'adjustedTargetPrice',
|
||||
adjustedTargetPriceWithTax.toString(),
|
||||
'adjustedTargetPrice',
|
||||
'Adjusted target price copied to clipboard'
|
||||
);
|
||||
};
|
||||
@@ -272,8 +272,8 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
const handleCopyAdjustedBreakEvenPrice = async (e: React.MouseEvent) => {
|
||||
e.stopPropagation();
|
||||
await copyToClipboard(
|
||||
adjustedBreakEvenPriceWithTax.toString(),
|
||||
'adjustedBreakEvenPrice',
|
||||
adjustedBreakEvenPriceWithTax.toString(),
|
||||
'adjustedBreakEvenPrice',
|
||||
'Adjusted break-even price copied to clipboard'
|
||||
);
|
||||
};
|
||||
@@ -290,7 +290,7 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
<DollarSign className="w-4 h-4" />
|
||||
<span>Break-even{taxSuffix}:</span>
|
||||
</div>
|
||||
|
||||
|
||||
<div className="flex items-center gap-1 text-lg">
|
||||
<span
|
||||
className="cursor-pointer hover:text-blue-400 transition-colors inline-flex items-center gap-1 text-white"
|
||||
@@ -322,7 +322,7 @@ const PriceDisplay: React.FC<PriceDisplayProps> = ({ job }) => {
|
||||
<DollarSign className="w-4 h-4" />
|
||||
<span>Adjusted Break-even{taxSuffix}:</span>
|
||||
</div>
|
||||
|
||||
|
||||
<div className="flex items-center gap-1 text-lg">
|
||||
<span
|
||||
className="cursor-pointer hover:text-blue-400 transition-colors inline-flex items-center gap-1 text-white"
|
||||
|
@@ -31,10 +31,10 @@ const JobCardMetrics: React.FC<JobCardMetricsProps> = ({ job }) => {
|
||||
// Calculate performance metrics - Simple price per unit comparison
|
||||
const itemsSold = sortedIncome.reduce((sum, tx) => sum + tx.quantity, 0);
|
||||
const produced = job.produced || 0;
|
||||
|
||||
|
||||
// Only show performance if we have produced items and sold items
|
||||
const showPerformanceIndicator = produced > 0 && itemsSold > 0 && job.projectedRevenue > 0;
|
||||
|
||||
|
||||
let performancePercentage = 0;
|
||||
if (showPerformanceIndicator) {
|
||||
const expectedPPU = job.projectedRevenue / produced;
|
||||
@@ -108,12 +108,11 @@ const JobCardMetrics: React.FC<JobCardMetricsProps> = ({ job }) => {
|
||||
{formatISK(job.projectedCost)}
|
||||
</span>
|
||||
)}</div>
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${
|
||||
totalExpenditure <= job.projectedCost
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${totalExpenditure <= job.projectedCost
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
: 'bg-red-900/50 text-red-400'
|
||||
}`}
|
||||
}`}
|
||||
title={`Cost efficiency: ${((totalExpenditure / job.projectedCost) * 100).toFixed(1)}% of projected cost`}
|
||||
>
|
||||
{totalExpenditure <= job.projectedCost ? '✅' : '⚠️'} {((totalExpenditure / job.projectedCost) * 100).toFixed(0)}%
|
||||
@@ -151,25 +150,23 @@ const JobCardMetrics: React.FC<JobCardMetricsProps> = ({ job }) => {
|
||||
</span>
|
||||
)}</div>
|
||||
<div className="flex justify-center gap-2">
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${
|
||||
totalIncome >= job.projectedRevenue
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${totalIncome >= job.projectedRevenue
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
: 'bg-yellow-900/50 text-yellow-400'
|
||||
}`}
|
||||
}`}
|
||||
title={`Revenue progress: ${((totalIncome / job.projectedRevenue) * 100).toFixed(1)}% of projected revenue`}
|
||||
>
|
||||
{totalIncome >= job.projectedRevenue ? '🎯' : '📊'} {((totalIncome / job.projectedRevenue) * 100).toFixed(0)}%
|
||||
</div>
|
||||
{showPerformanceIndicator && (
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${
|
||||
performancePercentage >= 100
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
: performancePercentage >= 90
|
||||
? 'bg-yellow-900/50 text-yellow-400'
|
||||
<div
|
||||
className={`text-xs font-medium px-2 py-0.5 rounded-full inline-block ${performancePercentage >= 100
|
||||
? 'bg-green-900/50 text-green-400'
|
||||
: performancePercentage >= 90
|
||||
? 'bg-yellow-900/50 text-yellow-400'
|
||||
: 'bg-red-900/50 text-red-400'
|
||||
}`}
|
||||
}`}
|
||||
title={`Price performance: ${formatISK(totalIncome / itemsSold)}/unit vs ${formatISK(job.projectedRevenue / produced)}/unit expected (${performancePercentage.toFixed(1)}%)`}
|
||||
>
|
||||
{performancePercentage >= 100 ? '📈' : performancePercentage >= 90 ? '⚠️' : '📉'} {performancePercentage.toFixed(0)}%
|
||||
|
Reference in New Issue
Block a user