u
This commit is contained in:
@@ -868,6 +868,7 @@ class ManifestForm extends PureComponent {
|
|||||||
|
|
||||||
handleRemoveAllLines() {
|
handleRemoveAllLines() {
|
||||||
this.setState((prev) => {
|
this.setState((prev) => {
|
||||||
|
let nextLines = [];
|
||||||
if (this.props.kind === 'order') {
|
if (this.props.kind === 'order') {
|
||||||
const shippedSkus = new Set();
|
const shippedSkus = new Set();
|
||||||
for (const sh of prev.shipments || []) {
|
for (const sh of prev.shipments || []) {
|
||||||
@@ -876,7 +877,7 @@ class ManifestForm extends PureComponent {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (shippedSkus.size > 0) {
|
if (shippedSkus.size > 0) {
|
||||||
const remaining = prev.lines.filter((l) => {
|
const remaining = (prev.lines || []).filter((l) => {
|
||||||
const raw = l.sku != null ? String(l.sku).trim().toLowerCase() : '';
|
const raw = l.sku != null ? String(l.sku).trim().toLowerCase() : '';
|
||||||
return shippedSkus.has(raw);
|
return shippedSkus.has(raw);
|
||||||
});
|
});
|
||||||
@@ -885,10 +886,10 @@ class ManifestForm extends PureComponent {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
enqueueSnackbar('Nicht ausgelieferte Positionen wurden entfernt.', { variant: 'info' });
|
enqueueSnackbar('Nicht ausgelieferte Positionen wurden entfernt.', { variant: 'info' });
|
||||||
return { lines: remaining, isDirty: true };
|
nextLines = remaining;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return { lines: [], isDirty: true };
|
return { lines: nextLines, isDirty: true };
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1181,7 +1182,7 @@ class ManifestForm extends PureComponent {
|
|||||||
{
|
{
|
||||||
kind: cfg.kind,
|
kind: cfg.kind,
|
||||||
partyField: cfg.partyField,
|
partyField: cfg.partyField,
|
||||||
requireAtLeastOne: true,
|
requireAtLeastOne: !isEdit,
|
||||||
externalNumber: cfg.externalNumber,
|
externalNumber: cfg.externalNumber,
|
||||||
isUpdate: isEdit,
|
isUpdate: isEdit,
|
||||||
mode,
|
mode,
|
||||||
@@ -1334,7 +1335,7 @@ class ManifestForm extends PureComponent {
|
|||||||
isDirty={this.state.isDirty}
|
isDirty={this.state.isDirty}
|
||||||
dirtyFields={this.state.dirtyFields}
|
dirtyFields={this.state.dirtyFields}
|
||||||
dirtySummary={this.state.dirtySummary}
|
dirtySummary={this.state.dirtySummary}
|
||||||
onRestore={this.props.mode === 'edit' && this.state.isDirty ? this.handleRestore : undefined}
|
onRestore={this.props.mode === 'edit' ? this.handleRestore : undefined}
|
||||||
onPdfUpload={kind === 'delivery' ? this.handlePdfUpload : undefined}
|
onPdfUpload={kind === 'delivery' ? this.handlePdfUpload : undefined}
|
||||||
onPdfDelete={this.handleAttachmentDelete}
|
onPdfDelete={this.handleAttachmentDelete}
|
||||||
onPdfCreate={kind === 'quote' || kind === 'order' ? this.handleCreatePdf : undefined}
|
onPdfCreate={kind === 'quote' || kind === 'order' ? this.handleCreatePdf : undefined}
|
||||||
|
|||||||
@@ -481,27 +481,45 @@ class ManifestHeader extends PureComponent {
|
|||||||
>
|
>
|
||||||
{saving ? 'Speichern…' : 'Speichern'}
|
{saving ? 'Speichern…' : 'Speichern'}
|
||||||
</Button>
|
</Button>
|
||||||
{isDirty && onRestore && (
|
{(() => {
|
||||||
<Button
|
const canRestore = Boolean(onRestore && isDirty && !saving && !orderCreating);
|
||||||
variant="outlined"
|
return (
|
||||||
color="warning"
|
<Button
|
||||||
size="small"
|
variant="outlined"
|
||||||
startIcon={<RestoreIcon />}
|
color={canRestore ? 'warning' : 'inherit'}
|
||||||
disabled={saving || orderCreating}
|
size="small"
|
||||||
onClick={onRestore}
|
startIcon={<RestoreIcon />}
|
||||||
sx={{
|
disabled={!canRestore}
|
||||||
height: 34,
|
onClick={canRestore ? onRestore : undefined}
|
||||||
fontWeight: 700,
|
title={
|
||||||
fontSize: '0.8rem',
|
canRestore
|
||||||
whiteSpace: 'nowrap',
|
? 'Änderungen verwerfen und ursprünglichen Stand wiederherstellen'
|
||||||
textTransform: 'none',
|
: 'Keine Änderungen zum Wiederherstellen'
|
||||||
borderWidth: 1.5,
|
}
|
||||||
'&:hover': { borderWidth: 1.5 },
|
sx={{
|
||||||
}}
|
height: 34,
|
||||||
>
|
width: '100%',
|
||||||
Wiederherstellen
|
fontWeight: 700,
|
||||||
</Button>
|
fontSize: '0.8rem',
|
||||||
)}
|
whiteSpace: 'nowrap',
|
||||||
|
textTransform: 'none',
|
||||||
|
borderWidth: 1.5,
|
||||||
|
'&:hover': { borderWidth: 1.5 },
|
||||||
|
...(!canRestore && {
|
||||||
|
borderColor: 'action.disabled',
|
||||||
|
color: 'text.disabled',
|
||||||
|
'&.Mui-disabled': {
|
||||||
|
borderColor: 'action.disabled',
|
||||||
|
color: 'text.disabled',
|
||||||
|
borderWidth: 1.5,
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
Wiederherstellen
|
||||||
|
</Button>
|
||||||
|
);
|
||||||
|
})()}
|
||||||
{docId != null && kind === 'delivery' && onOpenBookDialog && Boolean(ledgerSummary && (ledgerSummary.totalPositions > 0 || ledgerSummary.lines?.length > 0 || ledgerSummary.hasTrackStock)) && (
|
{docId != null && kind === 'delivery' && onOpenBookDialog && Boolean(ledgerSummary && (ledgerSummary.totalPositions > 0 || ledgerSummary.lines?.length > 0 || ledgerSummary.hasTrackStock)) && (
|
||||||
<Button
|
<Button
|
||||||
variant={ledgerSummary?.status === 'booked' ? 'outlined' : 'contained'}
|
variant={ledgerSummary?.status === 'booked' ? 'outlined' : 'contained'}
|
||||||
@@ -561,27 +579,56 @@ class ManifestHeader extends PureComponent {
|
|||||||
{orderCreating ? 'Wird erstellt…' : 'Bestellung erstellen'}
|
{orderCreating ? 'Wird erstellt…' : 'Bestellung erstellen'}
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
{(kind === 'quote' || kind === 'order' || kind === 'delivery') && onPdfCreate && docId != null && Boolean(number) && (
|
{(kind === 'quote' || kind === 'order' || kind === 'delivery') && (() => {
|
||||||
<Button
|
const canCreatePdf = Boolean(
|
||||||
type="button"
|
onPdfCreate &&
|
||||||
variant="outlined"
|
docId != null &&
|
||||||
startIcon={pdfCreating ? <CircularProgress size={16} color="inherit" /> : <PictureAsPdfIcon />}
|
Boolean(number) &&
|
||||||
disabled={saving || pdfCreating || orderCreating}
|
!saving &&
|
||||||
onClick={onPdfCreate}
|
!pdfCreating &&
|
||||||
title="PDF erstellen"
|
!orderCreating
|
||||||
sx={{
|
);
|
||||||
whiteSpace: 'nowrap',
|
return (
|
||||||
height: 40,
|
<Button
|
||||||
width: '100%',
|
type="button"
|
||||||
px: 1.5,
|
variant="outlined"
|
||||||
boxSizing: 'border-box',
|
color={canCreatePdf ? 'primary' : 'inherit'}
|
||||||
fontWeight: 600,
|
startIcon={pdfCreating ? <CircularProgress size={16} color="inherit" /> : <PictureAsPdfIcon />}
|
||||||
fontSize: '0.875rem',
|
disabled={!canCreatePdf}
|
||||||
}}
|
onClick={canCreatePdf ? onPdfCreate : undefined}
|
||||||
>
|
title={
|
||||||
{pdfCreating ? 'Wird erstellt…' : 'PDF erstellen'}
|
pdfCreating
|
||||||
</Button>
|
? 'PDF wird erstellt…'
|
||||||
)}
|
: canCreatePdf
|
||||||
|
? 'PDF erstellen'
|
||||||
|
: docId == null
|
||||||
|
? 'PDF kann erst nach dem Speichern erstellt werden'
|
||||||
|
: !number
|
||||||
|
? 'Dokumentnummer erforderlich für PDF'
|
||||||
|
: 'PDF erstellen'
|
||||||
|
}
|
||||||
|
sx={{
|
||||||
|
whiteSpace: 'nowrap',
|
||||||
|
height: 40,
|
||||||
|
width: '100%',
|
||||||
|
px: 1.5,
|
||||||
|
boxSizing: 'border-box',
|
||||||
|
fontWeight: 600,
|
||||||
|
fontSize: '0.875rem',
|
||||||
|
...(!canCreatePdf && {
|
||||||
|
borderColor: 'action.disabled',
|
||||||
|
color: 'text.disabled',
|
||||||
|
'&.Mui-disabled': {
|
||||||
|
borderColor: 'action.disabled',
|
||||||
|
color: 'text.disabled',
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{pdfCreating ? 'Wird erstellt…' : 'PDF erstellen'}
|
||||||
|
</Button>
|
||||||
|
);
|
||||||
|
})()}
|
||||||
{onPdfUpload ? (
|
{onPdfUpload ? (
|
||||||
<FileDropzone
|
<FileDropzone
|
||||||
accept="application/pdf,.pdf,text/plain,.txt,text/csv,.csv"
|
accept="application/pdf,.pdf,text/plain,.txt,text/csv,.csv"
|
||||||
|
|||||||
@@ -199,22 +199,42 @@ class ManifestLines extends PureComponent {
|
|||||||
);
|
);
|
||||||
})()}
|
})()}
|
||||||
{(() => {
|
{(() => {
|
||||||
const hasShippedLines = kind === 'order' && Array.isArray(shipments) && shipments.some((sh) => (sh.lines?.length || 0) > 0);
|
const shippedSkus = new Set();
|
||||||
const hasLedgeredLines = kind === 'delivery' && Array.isArray(lines) && lines.some((line) => {
|
if (kind === 'order' && Array.isArray(shipments)) {
|
||||||
const ledgerLine = line?.id != null ? ledgerLinesById?.[line.id] : null;
|
for (const sh of shipments) {
|
||||||
return Boolean(
|
for (const sl of sh.lines || []) {
|
||||||
ledgerLine?.isBooked ||
|
if (sl.sku) shippedSkus.add(String(sl.sku).trim().toLowerCase());
|
||||||
(ledgerLine && ledgerLine.targetAmount > 0 && ledgerLine.remainingAmount <= 0) ||
|
}
|
||||||
(ledgerLine && ledgerLine.bookedAmount > 0) ||
|
}
|
||||||
line?.isBooked ||
|
}
|
||||||
line?.is_booked
|
const allLinesShipped =
|
||||||
);
|
kind === 'order' &&
|
||||||
});
|
shippedSkus.size > 0 &&
|
||||||
const disabled = saving || !lines || lines.length === 0 || hasShippedLines || hasLedgeredLines;
|
Array.isArray(lines) &&
|
||||||
const title = hasLedgeredLines
|
lines.length > 0 &&
|
||||||
? 'Lieferung enthält bereits im Ledger verbuchte Positionen'
|
lines.every((l) => {
|
||||||
: hasShippedLines
|
const raw = l?.sku != null ? String(l.sku).trim().toLowerCase() : '';
|
||||||
? 'Auftrag enthält bereits ausgelieferte Positionen'
|
return raw && shippedSkus.has(raw);
|
||||||
|
});
|
||||||
|
const allLinesLedgered =
|
||||||
|
kind === 'delivery' &&
|
||||||
|
Array.isArray(lines) &&
|
||||||
|
lines.length > 0 &&
|
||||||
|
lines.every((line) => {
|
||||||
|
const ledgerLine = line?.id != null ? ledgerLinesById?.[line.id] : null;
|
||||||
|
return Boolean(
|
||||||
|
ledgerLine?.isBooked ||
|
||||||
|
(ledgerLine && ledgerLine.targetAmount > 0 && ledgerLine.remainingAmount <= 0) ||
|
||||||
|
(ledgerLine && ledgerLine.bookedAmount > 0) ||
|
||||||
|
line?.isBooked ||
|
||||||
|
line?.is_booked
|
||||||
|
);
|
||||||
|
});
|
||||||
|
const disabled = saving || !lines || lines.length === 0 || allLinesShipped || allLinesLedgered;
|
||||||
|
const title = allLinesLedgered
|
||||||
|
? 'Alle Positionen der Lieferung sind bereits im Ledger verbucht'
|
||||||
|
: allLinesShipped
|
||||||
|
? 'Alle Positionen des Auftrags sind bereits ausgeliefert'
|
||||||
: 'Alle Zeilen entfernen';
|
: 'Alle Zeilen entfernen';
|
||||||
return (
|
return (
|
||||||
<Button
|
<Button
|
||||||
|
|||||||
@@ -160,6 +160,7 @@ class LieferungNeuPage extends PureComponent {
|
|||||||
this.handleRemoveLine = this.handleRemoveLine.bind(this);
|
this.handleRemoveLine = this.handleRemoveLine.bind(this);
|
||||||
this.handleMoveLine = this.handleMoveLine.bind(this);
|
this.handleMoveLine = this.handleMoveLine.bind(this);
|
||||||
this.handleRemoveAllLines = this.handleRemoveAllLines.bind(this);
|
this.handleRemoveAllLines = this.handleRemoveAllLines.bind(this);
|
||||||
|
this.handleRestore = this.handleRestore.bind(this);
|
||||||
this.handleSave = this.handleSave.bind(this);
|
this.handleSave = this.handleSave.bind(this);
|
||||||
this.handlePdfUpload = this.handlePdfUpload.bind(this);
|
this.handlePdfUpload = this.handlePdfUpload.bind(this);
|
||||||
this.handlePdfRescan = this.handlePdfRescan.bind(this);
|
this.handlePdfRescan = this.handlePdfRescan.bind(this);
|
||||||
@@ -686,6 +687,24 @@ class LieferungNeuPage extends PureComponent {
|
|||||||
|
|
||||||
handleRemoveAllLines() {
|
handleRemoveAllLines() {
|
||||||
this.automat.actions.clearLineitems();
|
this.automat.actions.clearLineitems();
|
||||||
|
this.setState({ lines: [] });
|
||||||
|
}
|
||||||
|
|
||||||
|
handleRestore() {
|
||||||
|
if (!this._initialDoc) return;
|
||||||
|
const base = this._initialDoc;
|
||||||
|
this.automat.actions.setDate(base.date);
|
||||||
|
if (base.partyId != null) {
|
||||||
|
this.automat.actions.setDeliveryEntity(base.partyId);
|
||||||
|
}
|
||||||
|
this.automat.actions.setExternalNumber(base.externalNumber || '');
|
||||||
|
const restoredLines = (base.lines || []).map((l) => ({ ...l }));
|
||||||
|
this.automat.actions.setLineitems(restoredLines);
|
||||||
|
this.automat.actions.setAttachments([...(base.attachments || [])]);
|
||||||
|
this.setState({
|
||||||
|
lines: restoredLines,
|
||||||
|
});
|
||||||
|
enqueueSnackbar('Änderungen verworfen und ursprünglicher Stand wiederhergestellt.', { variant: 'info' });
|
||||||
}
|
}
|
||||||
|
|
||||||
async handlePdfUpload(file) {
|
async handlePdfUpload(file) {
|
||||||
@@ -1331,6 +1350,7 @@ class LieferungNeuPage extends PureComponent {
|
|||||||
onNumberChange={this.handleNumberChange}
|
onNumberChange={this.handleNumberChange}
|
||||||
onExternalNumberChange={this.handleExternalNumberChange}
|
onExternalNumberChange={this.handleExternalNumberChange}
|
||||||
docId={this.props.docId}
|
docId={this.props.docId}
|
||||||
|
onRestore={isEdit ? this.handleRestore : undefined}
|
||||||
ledgerSummary={this.state.ledgerSummary}
|
ledgerSummary={this.state.ledgerSummary}
|
||||||
onOpenBookDialog={this.handleOpenBookDialog}
|
onOpenBookDialog={this.handleOpenBookDialog}
|
||||||
/>
|
/>
|
||||||
|
|||||||
Reference in New Issue
Block a user