Erweiterungen

This commit is contained in:
2026-02-13 16:38:57 +01:00
parent ceffef2332
commit d5cf0f53ba
5 changed files with 348 additions and 45 deletions

View File

@@ -89,7 +89,8 @@ window.initProfileInvoiceGenerator = function() {
el.color || '#333333',
el.width || 100,
el.height || 30,
el.isStatic || false
el.isStatic || false,
el.variable || null
);
}
}
@@ -102,8 +103,10 @@ window.initProfileInvoiceGenerator = function() {
// Draw function
function draw() {
console.log('draw() called, elements:', elements.length);
var w = canvas.width;
var h = canvas.height;
console.log('Canvas size:', w, 'x', h);
// Clear background
ctx.fillStyle = '#e8e8e8';
@@ -141,7 +144,9 @@ window.initProfileInvoiceGenerator = function() {
}
// Draw elements
console.log('Drawing', elements.length, 'elements');
elements.forEach(function(el) {
console.log('Drawing element:', el.id, 'at', el.x, el.y, 'text:', el.text);
drawElement(el);
});
@@ -236,9 +241,6 @@ window.initProfileInvoiceGenerator = function() {
}
} else {
// Text elements
ctx.font = (el.fontStyle || '') + ' ' + fontSize + 'px Arial';
ctx.fillStyle = el.color || '#333333';
var lines = (el.text || '').split('\n');
var lineHeight = fontSize * 1.2;
var totalTextHeight = lines.length * lineHeight;
@@ -249,11 +251,17 @@ window.initProfileInvoiceGenerator = function() {
// Draw background highlight for static elements
if (el.isStatic) {
var textWidth = ctx.measureText(el.text || '').width + (10 * zoomFactor);
ctx.fillStyle = 'rgba(25, 118, 210, 0.1)'; // Light blue background
// Different background colors: green for customer, blue for masterdata
if (el.isCustomer) {
ctx.fillStyle = 'rgba(46, 204, 113, 0.15)'; // Light green for customer
} else {
ctx.fillStyle = 'rgba(25, 118, 210, 0.1)'; // Light blue for masterdata
}
ctx.fillRect(x - (3 * zoomFactor), y - (2 * zoomFactor), Math.max(w, textWidth), h);
}
ctx.fillStyle = el.color || '#333333';
// Always use black text for static elements, otherwise use element color
ctx.fillStyle = el.isStatic ? '#000000' : (el.color || '#333333');
ctx.font = (el.fontStyle || '') + ' ' + fontSize + 'px Arial';
ctx.textBaseline = 'top';
@@ -612,7 +620,7 @@ window.initProfileInvoiceGenerator = function() {
});
// Add element function
window.addProfileElement = function(type, label, dropX, dropY, isStatic, staticText) {
window.addProfileElement = function(type, label, dropX, dropY, isStatic, staticText, variable, isCustomer) {
elementCounter++;
var id = 'element-' + elementCounter;
@@ -633,7 +641,9 @@ window.initProfileInvoiceGenerator = function() {
height: 30,
fontSize: 14,
color: '#333333',
isStatic: isStatic || false
isStatic: isStatic || false,
variable: variable || null,
isCustomer: isCustomer || false
};
// Helper function to calculate height based on font size and lines
@@ -642,10 +652,10 @@ window.initProfileInvoiceGenerator = function() {
return Math.round(lineCount * lineHeight + 6);
}
// Handle static elements (user data)
// Handle static elements (user data or customer data)
if (isStatic && staticText) {
el.text = staticText;
el.color = '#1976d2'; // Blue color for static elements
el.color = '#000000'; // Black text for static elements
el.fontStyle = 'bold';
el.height = calculateHeight(el.fontSize, 1);
} else {
@@ -843,10 +853,22 @@ window.initProfileInvoiceGenerator = function() {
saveState();
// Convert pixel values to percentages for storage
var elementsWithPercent = elements.map(function(el) {
// For static elements with variables, handle text storage differently:
// - masterdata variables: text is resolved from user data, don't store
// - customer variables: store the placeholder text from canvas
var textToStore = el.text;
if (el.isStatic && el.variable) {
if (el.variable.startsWith('masterdata.')) {
// Don't store the text for masterdata variables - will be resolved from user data
textToStore = null;
}
// For customer variables, keep the text (placeholder) as is
}
return {
id: el.id,
type: el.type,
text: el.text,
text: textToStore,
xPercent: toPercentX(el.x),
yPercent: toPercentY(el.y),
widthPercent: toPercentX(el.width),
@@ -855,6 +877,8 @@ window.initProfileInvoiceGenerator = function() {
fontStyle: el.fontStyle,
color: el.color,
isStatic: el.isStatic,
isCustomer: el.isCustomer,
variable: el.variable,
imageData: el.imageData
};
});
@@ -899,27 +923,37 @@ window.initProfileInvoiceGenerator = function() {
var templateLabel = e.dataTransfer.getData('template-label');
var isStatic = e.dataTransfer.getData('is-static') === 'true';
var staticText = e.dataTransfer.getData('static-text');
var variable = e.dataTransfer.getData('variable');
var isCustomer = e.dataTransfer.getData('is-customer') === 'true';
if (templateType && window.addProfileElement) {
var rect = container.getBoundingClientRect();
var x = e.clientX - rect.left;
var y = e.clientY - rect.top;
window.addProfileElement(templateType, templateLabel, x, y, isStatic, staticText);
window.addProfileElement(templateType, templateLabel, x, y, isStatic, staticText, variable, isCustomer);
}
});
}
// Load template function
// Load template function - defined INSIDE initProfileInvoiceGenerator to access closure variables
window.loadProfileTemplate = function(templateData) {
try {
var data = JSON.parse(templateData);
console.log('loadProfileTemplate called with data:', JSON.stringify(templateData).substring(0, 200));
var data = (typeof templateData === 'string') ? JSON.parse(templateData) : templateData;
if (data.elements && Array.isArray(data.elements)) {
// Clear existing elements
elements = [];
console.log('Loading ' + data.elements.length + ' elements');
console.log('Current elements array before clear:', elements.length);
// Clear existing elements - use length = 0 to keep the same array reference
elements.length = 0;
selectedElement = null;
console.log('Elements array after clear:', elements.length);
// Master data mapping - these should be filled from user data
var masterdata = window.masterdataValues || {};
// Load new elements
data.elements.forEach(function(el) {
console.log('Loading element:', el.id, 'type:', el.type, 'variable:', el.variable);
// Ensure element has an ID
if (!el.id) {
elementCounter++;
@@ -940,7 +974,69 @@ window.initProfileInvoiceGenerator = function() {
el.height = fromPercentY(el.heightPercent);
}
// Handle elements with variables
if (el.variable) {
el.isStatic = true;
if (el.variable.startsWith('customer.')) {
el.isCustomer = true;
// Customer variables - use saved text if available, otherwise use placeholder
if (!el.text || el.text.trim() === '') {
el.text = '[' + el.variable.replace('customer.', '') + ']';
}
// If text is already set (from saved template), keep it
} else if (el.variable.startsWith('masterdata.')) {
// Masterdata variables - use actual value from masterdata or placeholder
var value = masterdata[el.variable];
if (value && value.trim() !== '') {
el.text = value;
} else {
el.text = '[' + el.variable.replace('masterdata.', '') + ']';
}
}
}
// Legacy: If text contains a variable placeholder {{variable}}|Display Text, extract it
else if (el.text && el.text.startsWith('{{')) {
var pipeIndex = el.text.indexOf('|');
if (pipeIndex > -1) {
// Format: {{variable}}|Display Text
var placeholderPart = el.text.substring(0, pipeIndex);
var displayText = el.text.substring(pipeIndex + 1);
if (placeholderPart.startsWith('{{') && placeholderPart.endsWith('}}')) {
var varName = placeholderPart.substring(2, placeholderPart.length - 2);
el.variable = varName;
if (varName.startsWith('masterdata.')) {
el.isStatic = true;
// Use masterdata value or fallback to display text
var value = masterdata[varName];
el.text = (value && value.trim() !== '') ? value : displayText;
} else if (varName.startsWith('customer.')) {
el.isStatic = true;
el.isCustomer = true;
// Use saved text if available, otherwise use placeholder
if (!el.text || el.text.trim() === '' || el.text.startsWith('{{')) {
el.text = '[' + varName.replace('customer.', '') + ']';
}
}
}
} else if (el.text.endsWith('}}')) {
// Legacy format: {{variable}} without display text
var varName = el.text.substring(2, el.text.length - 2);
el.variable = varName;
if (varName.startsWith('masterdata.')) {
el.isStatic = true;
var value = masterdata[varName];
el.text = (value && value.trim() !== '') ? value : '[' + varName.replace('masterdata.', '') + ']';
} else if (varName.startsWith('customer.')) {
el.isStatic = true;
el.isCustomer = true;
el.text = '[' + varName.replace('customer.', '') + ']';
}
}
}
console.log('Element processed:', el.id, 'x:', el.x, 'y:', el.y, 'text:', el.text);
elements.push(el);
console.log('Element pushed, elements count now:', elements.length);
});
// Update counter to be higher than any loaded element
@@ -956,9 +1052,14 @@ window.initProfileInvoiceGenerator = function() {
// Save to global state
saveState();
console.log('Calling draw(), elements count:', elements.length);
console.log('Canvas dimensions:', canvas.width, 'x', canvas.height);
draw();
console.log('draw() completed');
notifyElementDeselected();
console.log('Template loaded with ' + elements.length + ' elements');
} else {
console.log('No elements array found in template data');
}
} catch (e) {
console.error('Error loading template:', e);