Create OfjsImage type

This commit is contained in:
Clémence Fernandez 2025-08-04 18:51:04 +02:00
parent b3d77cfdb9
commit 1c54f226cb
4 changed files with 47 additions and 11 deletions

View File

@ -1,5 +1,7 @@
import {traverse, Node, getAncestors, findCommonAncestor} from "../../DOMUtils.js";
import {closingIfMarker, eachClosingMarker, eachStartMarkerRegex, elseMarker, ifStartMarkerRegex, imageMarkerRegex, variableRegex} from './markers.js'
import {isOdfjsImage} from "../../shared.js"
/** @import {OdfjsImage} from "../../types.js" */
/**
* @typedef TextPlaceToFill
@ -557,7 +559,7 @@ function fillEachBlock(startNode, iterableExpression, itemExpression, endNode, c
/**
* @param {string} str
* @param {Compartement} compartment
* @returns {}
* @returns { {expression: string, odfjsImage: OdfjsImage | undefined} | undefined}
*/
function findImageMarker(str, compartment) {
const imageRexExp = new RegExp(imageMarkerRegex.source, 'g');
@ -570,14 +572,10 @@ function findImageMarker(str, compartment) {
const expression = match[1]
const value = compartment.evaluate(expression)
if (value instanceof ArrayBuffer) {
// TODO :
// - Rajouter un fichier image dans le odt avec le ArrayBuffer comme contenu (ou autre type)
// - Rajouter un suffixe/titre (donc peut-être changer l'api pour que photo ça soit un objet qui contienne arraybuffer et d'autres choses)
// - puis remplacer le texte par peut-être <draw:image et peut-être <draw:frame et peut être pas ici
return value
if (isOdfjsImage(value)) {
return { expression, odfjsImage: value}
} else {
// TODO: throws an exception
return { expression }
}
}
@ -790,9 +788,23 @@ export default function fillOdtElementTemplate(rootElements, compartment) {
currentNode.parentNode?.replaceChild(newTextNode, currentNode)
} else {
const imageMarker = findImageMarker(currentNode.data, compartment)
if (imageMarker){
console.log({imageMarker}, "dans le if")
if (imageMarker.odfjsImage) {
// TODO :
// - Rajouter un fichier image dans le odt avec le ArrayBuffer comme contenu (ou autre type)
// - Rajouter un suffixe/titre (donc peut-être changer l'api pour que photo ça soit un objet qui contienne arraybuffer et d'autres choses)
// - puis remplacer le texte par peut-être <draw:image et peut-être <draw:frame et peut être pas ici
// <draw:frame draw:style-name="fr1" draw:name="Image1" text:anchor-type="char"
// svg:width="7.28cm" svg:height="10.239cm" draw:z-index="0">
// <draw:image xlink:href="Pictures/100000000000016C00000200F498F14E.jpg"
// xlink:type="simple" xlink:show="embed" xlink:actuate="onLoad"
// draw:mime-type="image/jpeg" />
// </draw:frame>
} else {
throw new Error(`No valid OdfjsImage value has been found for expression: ${imageMarker.expression}`)
}
}

View File

@ -4,7 +4,7 @@ import { Uint8ArrayReader, ZipReader, TextWriter } from '@zip.js/zip.js';
import {parseXML} from './DOMUtils.js'
/** @import {Entry} from '@zip.js/zip.js'*/
/** @import {SheetName, SheetRawContent, SheetRowRawContent, SheetCellRawContent} from './types.js' */
/** @import {SheetName, SheetRawContent, SheetRowRawContent, SheetCellRawContent, OdfjsImage} from './types.js' */
// https://dom.spec.whatwg.org/#interface-node
@ -160,6 +160,22 @@ export function convertCellValue({value, type}) {
}
/**
* @param {unknown} value
* @returns {value is OdfjsImage}
*/
export function isOdfjsImage(value) {
if (typeof value === 'object' && value!==null
&& "content" in value && value.content instanceof ArrayBuffer
&& "fileName" in value && typeof value.fileName === 'string'
&& "mediaType" in value && typeof value.mediaType === 'string'
) {
return true
} else {
return false
}
}

View File

@ -10,4 +10,12 @@
/** @typedef {string} SheetName */
/**
* @typedef OdfjsImage
* @prop {ArrayBuffer} content
* @prop {string} fileName
* @prop {string} mediaType
*
*/
export {}

View File

@ -59,7 +59,7 @@ test('insert 2 images', async t => {
const photo1Buffer = (await readFile(photo1Path)).buffer
const photo2Buffer = (await readFile(photo2Path)).buffer
const photos = [photo1Buffer, photo2Buffer]
const photos = [{content: photo1Buffer, fileName: 'pitchou-1.png', mediaType: 'image/png'}, {content: photo2Buffer, fileName: 'pitchou-2.png', mediaType: 'image/png'}]
const data = {
title: 'Titre de mon projet',