Hi,
In our codebase, I have implemented the callback for image merging like this:
public void imageFieldMerging(ImageFieldMergingArgs ifma) throws Exception {
try {
// immagine richiesta
Object field = ifma.getFieldValue();
String path = "";
// array di byte come path
if (field instanceof byte[]) {
path = new String((byte[]) field, StandardCharsets.UTF_8);
}
// path come stringa semplice
else if (field != null) {
path = field.toString();
}
// se
if (
// non è valido
!Strings.isValid(path)
// o non esite
|| !Files.exists(path)
) {
// non proseguo
ifma.setImage(null);
return;
}
// dimensioni specificate nel documento (eventualmente non presenti)
double width = ifma.getImageWidth().getValue();
double height = ifma.getImageHeight().getValue();
// se le dimensioni non sono già specificate
if (width < 0 && height < 0) {
DocumentBuilder builder = new DocumentBuilder(ifma.getDocument());
builder.moveToMergeField(ifma.getDocumentFieldName(), false, false);
// se si trova in una cella di una tabella
Cell cell = (Cell) builder.getCurrentParagraph().getAncestor(NodeType.CELL);
if (cell != null) {
CellFormat format = cell.getCellFormat();
format.setLeftPadding(0.0);
format.setRightPadding(0.0);
format.setTopPadding(0.0);
format.setBottomPadding(0.0);
format.setWrapText(false);
format.setFitText(true);
// uso dimensioni cella
width = format.getWidth();
height = cell.getParentRow().getRowFormat().getHeight();
}
// se si trova in un textbox
Shape shape = (Shape) builder.getCurrentParagraph().getAncestor(NodeType.SHAPE);
if (shape != null && shape.getShapeType() == ShapeType.TEXT_BOX) {
TextBox tb = shape.getTextBox();
tb.setInternalMarginBottom(0.0);
tb.setInternalMarginTop(0.0);
tb.setInternalMarginLeft(0.0);
tb.setInternalMarginRight(0.0);
// uso dimensioni textbox
width = shape.getWidth();
height = shape.getHeight();
}
}
// se sono specificate misure massime
if (width > 0 || height > 0) {
// carico immagine
BufferedImage img = ImageIO.read(new File(path));
// ricavo fattore di scala
int imgw = img.getWidth();
int imgh = img.getHeight();
// distruggo immagine
img = null;
// calcolo fattore di scalatura
double scale = Math.max(imgw / width, imgh / height);
// inserisco l'immagine specificando le dimensioni
width = imgw / scale;
height = imgh / scale;
}
// immagine come path sul disco
ifma.setImageFileName(path);
// imposto le dimensioni
ifma.getImageWidth().setValue(width);
ifma.getImageHeight().setValue(height);
}
// se qualcosa va male
catch (Exception e) {
System.err.println(Strings.getTrace(e));
// in modalità debug
if (Util.DEBUG) {
// riporta errore
throw Util.error("Errore durante il caricamento di un'immagine", e);
}
// setta immagine a null
ifma.setImage(null);
}
}
The merge is done by passing in the full path to the image file on disk, and the code should verify if the path is valid (not null and not empty), and that the image actually exists on disk; if one of the checks fail, it should “abort” the insertion.
However, it seems that setting the image as null
does not work, what would the proper way be? I keep getting the exception:
Cannot load image from field 'foto'. The field contains data in unsupported format. Can't find file: /opt/agews64/data/upload/AGEWS626/5/6/5663370B-EEE4-4BDC-AFB9-C8B3BD4EE300
The file indeed does not exists, however the checks in the callback should catch this case and simply proceed without the image.