Prezentációk exportálása XAML-be JavaScriptben
Áttekintés
Ez a cikk bemutatja, hogyan exportálhatók a PowerPoint‑prezentációk XAML formátumba az Aspose.Slides segítségével. Rövid bevezetést ad a XAML‑ról, megmutatja, hogyan menthető el egy prezentáció XAML‑ként alapértelmezett beállításokkal, és bemutatja, hogyan szabható testre az export a XamlOptions használatával, beleértve a rejtett diák exportálását is. A cikk néhány gyakori kérdésre is válaszol a helyettesítő betűtípusokkal, a XAML‑verem kompatibilitásával és a rejtett diák export viselkedésével kapcsolatban.
A XAML‑ról
A XAML egy XML‑alapú jelölőnyelv, amelyet felhasználói felületek leírására használnak olyan keretrendszerekben, mint a WPF (Windows Presentation Foundation), az UWP (Universal Windows Platform) és a Xamarin.Forms.
A XAML‑fájlokkal dolgozhat vizuális tervezőben, vagy közvetlenül szerkesztheti a jelölőnyelvet.
Prezentációk exportálása XAML‑ba alapértelmezett beállításokkal
Az alábbi JavaScript‑példa bemutatja, hogyan exportálható egy prezentáció XAML‑ba alapértelmezett beállításokkal:
const aspose = { slides: require("aspose.slides.via.java") };
const presentation = new aspose.slides.Presentation("input.pptx");
try {
const xamlOptions = new aspose.slides.XamlOptions();
presentation.save(xamlOptions);
} finally {
presentation.dispose();
}
Alapértelmezés szerint az exportált diák az input almappába kerülnek a folyamat aktuális munkakönyvtárában. A mappa automatikusan létrejön, és a szükséges képek is oda kerülnek.
A kimeneti mappa neve a forrásfájl neve kiterjesztés nélkül kerül meghatározásra. Az Aspose.Slides for Node.js via Java 26.8 esetén a input.pptx exportálása egy beágyazott útvonalat hoz létre, például input/input/Slide_1.xaml. A generált teljes útvonalakat meg kell őrizni a kimenet kezelése során. Az alapértelmezett kimenet a jelenlegi munkakönyvtárhoz relatív, nem feltétlenül a bemeneti fájl mellett.
Prezentációk exportálása XAML‑ba egyéni beállításokkal
Használja a IXamlOptions interfészt annak szabályozásához, hogy az Aspose.Slides hogyan exportálja a prezentációt XAML‑ba.
A kimenet egyedi helyre történő mentéséhez valósítsa meg a IXamlOutputSaver interfészt, és adja át a megvalósítás példányát a setOutputSaver metódusnak a XamlOptions objektumból.
A rejtett diák XAML‑kimenetbe való felvételéhez hívja meg a setExportHiddenSlides metódust true értékkel, ahogy az alábbi JavaScript‑példában látható:
const aspose = { slides: require("aspose.slides.via.java") };
const presentation = new aspose.slides.Presentation("input.pptx");
try {
const xamlOptions = new aspose.slides.XamlOptions();
xamlOptions.setExportHiddenSlides(true);
presentation.save(xamlOptions);
} finally {
presentation.dispose();
}
Az összes generált XAML‑eszköz elfogása
Az XAML‑exportálás minden exportált dia esetén XAML‑dokumentumot, valamint különálló képeket és támogató erőforrásokat hozhat létre. Rendeljen egy egyéni IXamlOutputSaver példányt a XamlOptions.setOutputSaver metódushoz, hogy ezeket az eszközöket a alapértelmezett fájlrendszer‑mentő helyett megkapja. Indítsa el az exportálást a XAML‑specifikus Presentation.save túlterheléssel, amely XAML‑beállításokat fogad.
Node.js‑ben valósítsa meg a Java interfészt a java.newProxy‑val a Aspose.Slides által használt java csomagból. Tartsa a proxyt elérhető állapotban, amíg az export be nem fejeződik.
A visszahívási életciklus megértése
Az exportáló külön-külön meghívja az IXamlOutputSaver.save metódust minden egyes generált eszközre:
pathazonosítja az eszközt, és tartalmazhat relatív könyvtárakat. Ezt az információt meg kell őrizni, mert a XAML relatív útvonalak segítségével hivatkozhat erőforrásokra.datatartalmazza az eszköz bájtjait. A képeket és egyéb bináris erőforrásokat nem szabad szövegként dekódolni.- A mentő feladata, hogy a visszaadása előtt megtartsa vagy perzisztálja az adatokat. A példák minden Java‑byte‑tömböt egy alkalmazás által birtokolt Node.js bufferbe másolnak.
- Az export sikeresnek tekinthető csak akkor, ha a prezentáció mentési művelete visszatér, és minden visszahívás sikeresen befejeződött. Ne nyeljen el tárolási hibákat, és ne indítson megfigyelés nélküli háttér‑írásokat. Ha a perzisztálás utólag történik, a teljes sikerességet csak akkor jelentse, ha ez a lépés is sikeres.
A XamlOptions.setExportHiddenSlides szintén érvényes egy egyéni mentőre. Az alapértelmezett beállítás, false, kizárja a rejtett dia XAML‑dokumentumait. true átadása felveszi őket, valamint minden exportáláshoz szükséges erőforrást. Az erőforrások száma a prezentációtól függ; ne feltételezze, hogy egy visszahívás dia‑onként vagy fix sorrendben történik.
Exportálás memóriába és az eszközök ellenőrzése
Ez a teljes példa betölti a input.pptx‑t, minden eszközt egy JavaScript‑térképre (név → buffer) gyűjt, és kiírja a nevét, típusát és bájtszámát. A megadott neveket pontosan megőrzi. Azonos nevek esetén a gyűjtemény érvénytelennek minősül, ahelyett, hogy csendben felülírná az eszközt. A példa ellenőrzi ezt, mielőtt a visszatérő értékeket felhasználná.
const aspose = { slides: require("aspose.slides.via.java") };
const java = require("java");
const artifacts = new Map();
let valid = true;
const saver = java.newProxy("com.aspose.slides.IXamlOutputSaver", {
save: function(path, data) {
const name = String(path);
if (artifacts.has(name)) {
valid = false;
console.error("Export rejected: duplicate artifact name: " + name);
return;
}
const retainedData = Buffer.from(data);
artifacts.set(name, retainedData);
}
});
const presentation = new aspose.slides.Presentation("input.pptx");
try {
const options = new aspose.slides.XamlOptions();
options.setOutputSaver(saver);
options.setExportHiddenSlides(true);
presentation.save(options);
} finally {
presentation.dispose();
}
if (!valid) {
console.error("Export rejected: the artifact collection is invalid.");
} else {
const inspectXamlText = false;
for (const [name, data] of artifacts) {
const isXaml = /\.xaml$/i.test(name);
const isImage = /\.(png|jpg|jpeg|gif|bmp|tif|tiff|svg)$/i.test(name);
const kind = isXaml ? "slide XAML" : isImage ? "image" : "supporting resource";
console.log(name + ": " + data.length + " bytes (" + kind + ")");
// Csak a XAML-t dekódolja, és csak akkor, ha szöveges vizsgálatra van szükség.
if (isXaml && inspectXamlText) {
console.log(data.toString("utf8"));
}
}
}
A kiterjesztés‑ellenőrzések hasznosak az ellenőrzéshez; őrizze meg az összes eszközt, beleértve a kevésbé ismert erőforrás‑típusokat is. A tárolás vagy továbbítás során ne módosítsa a bájtokat. Az UTF‑8 dekódolást csak akkor használja, ha a XAML‑szöveget kell feldolgozni.
Gyűjtött eszközök csomagolása ZIP‑archívumba
Ez a független példa összegyűjti az exportot, ellenőrzi a neveket, és az eredeti bájtokat egy Java‑híd segítségével ZIP‑archívumba írja. A ZIP memóriában áll elő, mielőtt lemezre kerülne. Egy egyedi archívumnév elválasztja a párhuzamos exportfeladatokat. A ZIP‑bejegyzések szereplő perjel („/”) karaktert használják, és megőrzik a relatív könyvtárakat. Nem megfelelő vagy normalizálás után ütköző nevek esetén az egész csomag elutasításra kerül, mielőtt írásra kerülne.
const aspose = { slides: require("aspose.slides.via.java") };
const java = require("java");
const artifacts = new Map();
let valid = true;
const saver = java.newProxy("com.aspose.slides.IXamlOutputSaver", {
save: function(path, data) {
const name = String(path);
if (artifacts.has(name)) {
valid = false;
console.error("Export rejected: duplicate artifact name: " + name);
return;
}
const retainedData = Buffer.from(data);
artifacts.set(name, retainedData);
}
});
const presentation = new aspose.slides.Presentation("input.pptx");
try {
const options = new aspose.slides.XamlOptions();
options.setOutputSaver(saver);
options.setExportHiddenSlides(false);
presentation.save(options);
} finally {
presentation.dispose();
}
const entries = new Map();
const entryNames = new Set();
for (const [name, data] of artifacts) {
const entryName = name.replace(/\\/g, "/");
const segments = entryName.split("/");
const unsafeName = entryName.startsWith("/") || entryName.includes(":") || segments.some(segment => segment.trim() === "" || segment === "." || segment === "..");
const comparisonName = entryName.toLowerCase();
if (unsafeName || entryNames.has(comparisonName)) {
valid = false;
console.error("Export rejected: unsafe or duplicate artifact name: " + name);
break;
}
entryNames.add(comparisonName);
entries.set(entryName, data);
}
if (!valid) {
console.error("Export rejected: the artifact collection is invalid.");
} else {
const fs = require("node:fs");
const crypto = require("node:crypto");
const archivePath = "xaml-" + crypto.randomUUID() + ".zip";
const output = java.newInstanceSync("java.io.ByteArrayOutputStream");
const archive = java.newInstanceSync("java.util.zip.ZipOutputStream", output);
try {
for (const [name, data] of entries) {
const entry = java.newInstanceSync("java.util.zip.ZipEntry", name);
archive.putNextEntry(entry);
const signedBytes = Array.from(data, value => value > 127 ? value - 256 : value);
const bytes = java.newArray("byte", signedBytes);
archive.write(bytes);
archive.closeEntry();
}
} finally {
archive.close();
}
// A zárás befejezi a ZIP könyvtárat, mielőtt az archívum mentésre kerül.
const archiveData = Buffer.from(output.toByteArray());
try {
fs.writeFileSync(archivePath, archiveData, { flag: "wx" });
console.log("Saved " + entries.size + " artifacts to " + archivePath);
} catch (error) {
console.error("Archive persistence failed: " + error.message);
}
}
A példa a ZipOutputStream osztályt használja egy helyi archívum írásához; az exportáló maga nem ír széttagolt XAML‑ vagy kép‑fájlokat. Távoli tároláshoz cserélje le az archívum‑írási lépést a gyűjtött bájt‑tömbök feltöltésére. Használjon egy export‑feladat‑azonosítót és a teljes relatív eszköznevet blob‑kulcsként, vagy tárolja a feladat‑azonosítót, a relatív nevet és a bináris adatot egy adatbázis‑sorban. A feladatot csak akkor tegye közzé, miután minden feltöltés befejeződött vagy a tranzakció elköteleződött. Ha a perzisztálás sikertelen, tisztítsa meg a részleges kimenetet.
Nagy prezentációk esetén egy egyéni mentő közvetlenül az alkalmazás‑tárolóba mentheti az egyes eszközöket, elkerülve a teljes export egy további példányának memóriában tartását. Tartsa minden visszahívást szinkronban az exportáló szemszögéből: csak akkor térjen vissza, amikor a célpont elfogadta a bájtokat, és engedje, hogy a hibák elérjék a hívót.
Erőforrásnevek megőrzése és hivatkozások ellenőrzése
- Normalizálja az útvonal‑elválasztókat, ha a célhely megköveteli, de őrizze meg a relatív könyvtárakat. Ne csak az alapnevet használja, hacsak nem biztos, hogy minden generált név egyedi, és a hivatkozások érvényesek maradnak.
- Alkalmazzon célspecifikus név‑validációt. Szétállomány‑írásnál utasítsa el a gyökér‑útvonalakat és a traversális szegmenseket, oldja fel a célhelyet abszolút úttá, és ellenőrizze, hogy az a kívánt exportkönyvtár alatt marad‑e, beleértve az útvonal‑elválasztót is a tartalmazási ellenőrzésben. Használjon alkalmazás‑vezérelt könyvtárat szimbolikus linkek nélkül, amelyek átirányíthatják az írásokat.
- Minden exportfeladathoz használjon külön mentőt és tárolási névtér‑kört. Ütközéseket detektáljon az elválasztó‑normalizálás után, és a célhely esetleges nagy‑/kisbetű‑érzékenységének szabályai szerint.
- Közzététel előtt parse-olja minden XAML‑dokumentumot XML‑ként, és ellenőrizze a fájl‑alapú erőforrás‑hivatkozásokat, például az
ImageSourcevagyImageSourceattribútumokat. Oldja fel minden relatív URI‑t a tartalmazó XAML‑eszköz könyvtára alapján, normalizálja a kapott tárolási nevet, és erősítse meg, hogy a megfelelő térkép‑kulcs, ZIP‑bejegyzés vagy tárolt objektum létezik. Kezelje külön a külső URI‑kat és a XAML‑kifejezéseket a relatív fájlnevektől.
Például, ha az input/Slide_1.xaml a images/image1.png‑re hivatkozik, a tárolt erőforrásnak input/images/image1.png néven kell elérhetőnek lennie. A image1.png csak tárolása megtöri a kapcsolatot. Objektumtárolás esetén őrizze meg ugyanazt a struktúrát a feladat‑előtag alatt, és tegye elérhetővé ezeket az URL‑eket a XAML‑fogyasztó számára. Nyissa meg a kész ZIP‑et az entry‑nevek és erőforrás‑bájtok ellenőrzéséhez, és töltsön be reprezentatív diákat a cél‑XAML környezetben, hogy megerősítse a képek helyes feloldását.
GYIK
Hogyan biztosítható a prediktív betűtípus, ha az eredeti betűtípus nem érhető el a gépen?
Hívja meg a setDefaultRegularFont metódust a XamlOptions objektumban – ez a fallback betűtípusként kerül felhasználásra az exportálás során, ha az eredeti hiányzik. Ez nem garantálja, hogy a generált XAML a fallback betűtípust használja, vagy hogy a betűtípus elérhető a célgépen. Győződjön meg róla, hogy a XAML által hivatkozott betűtípusok elérhetők abban a környezetben, ahol megjelenik.
Az exportált XAML csak WPF‑hez szánt, vagy más XAML‑veremekben is használható?
Az Aspose.Slides a WPF XAML‑t exportálja a nyilvános API‑ján keresztül. Más XAML‑veremekkel, például az UWP‑vel vagy a Xamarin.Forms‑szal való kompatibilitás nem garantált. Tesztelje a generált jelölőnyelvet a célkörnyezetben.
Támogatottak a rejtett diák, és hogyan akadályozható meg, hogy alapértelmezés szerint exportálódjanak?
Alapértelmezés szerint a rejtett diák nincsenek benne. Ezt a viselkedést a setExportHiddenSlides metódussal szabályozhatja a XamlOptions objektumban – tartsa letiltva, ha nem szeretné exportálni őket.