javascript - 将 SVG 导出为 PDF,组/图层完好无损
问题描述
我有一个看起来像这样的 SVG 对象:
每个内部<g>
元素都有<path>
s。
我想将此 SVG 导出为 PDF,以便组转换为图层(OCG),如下所示:
<ThroughCut>
<Path>
<Path>
<Path>
<Path>
<Graphics>
<Path>
<Path>
<Path>
<Path>
然而,我为此尝试过的任何工具都将所有对象放在同一层中,并且基本上会丢弃有关组的信息。
JavaScript 或 Python 中的解决方案是首选,但任何从 UNIX 机器上的命令行执行的都可以。
解决方案
我的其他解决方案虽然正确,但不会生成与 Adobe 标准兼容的 PDF(例如,Illustrator 不会将 OCG 视为合法图层——尽管奇怪的是,Acrobat 会)。
如果需要生成与 Adobe 标准兼容的 PDF ,并且可以在 Illustrator 中正确加载,另一种选择是使用 Illustrator 脚本 API。
这是一个脚本,可用于将加载的 SVG 文件转换为具有所需图层结构的 PDF。
/** Convert an open file in Illustrator to PDF, after removing the first layer.
* Useful for converting SVGs into PDFs, where it is desired that the first level
* `<g>` elements are converted to layers/OCGs in the exported PDF.
*/
// Select export destination
const destFolder = Folder.selectDialog( 'Select folder for PDF files.', '~' );
// Get the PDF options to be used
const options = getOptions();
// The SVG should have a single `Layer1` top layer...
const doc = app.activeDocument;
if (doc.layers.length == 1) {
// ... remove it
removeFirstLayer(doc)
// Create a file pointer for export...
var targetFile = getTargetFile(doc.name, '.pdf', destFolder);
// ... and save save `doc` in the file pointer.
doc.saveAs(targetFile, options);
}
/* --------- */
/* Utilities */
/* --------- */
function getOptions() {
// Create PDFSaveOptions object
var pdfSaveOpts = new PDFSaveOptions();
// Set PDFSaveOptions properties (toggle these comment/uncomment)
pdfSaveOpts.acrobatLayers = true;
pdfSaveOpts.colorBars = true;
pdfSaveOpts.colorCompression = CompressionQuality.AUTOMATICJPEGHIGH;
pdfSaveOpts.compressArt = true; //default
pdfSaveOpts.embedICCProfile = true;
pdfSaveOpts.enablePlainText = true;
pdfSaveOpts.generateThumbnails = true; // default
pdfSaveOpts.optimization = true;
pdfSaveOpts.pageInformation = true;
// pdfSaveOpts.viewAfterSaving = true;
return pdfSaveOpts;
}
function removeFirstLayer(doc) {
// Get the layer to be removed
var firstLayer = doc.layers[0];
// Convert groups into new layers
for (var i=firstLayer.groupItems.length-1; i>=0; i--) {
var group = firstLayer.groupItems[i];
var newLayer = firstLayer.layers.add();
newLayer.name = group.name;
for (var j=group.pageItems.length-1; j>=0; j--)
group.pageItems[j].move(newLayer, ElementPlacement.PLACEATBEGINNING);
}
// Move new layers to the document and remove `firstLayer`
for (var i=firstLayer.layers.length-1; i>=0; i--)
firstLayer.layers[i].move(firstLayer.parent, ElementPlacement.PLACEATBEGINNING);
firstLayer.remove();
}
function getTargetFile(docName, ext, destFolder) {
var newName = "";
// Add extension is none exists
if (docName.indexOf('.') < 0)
newName = docName + ext;
else
newName += docName.substring(0, docName.lastIndexOf('.')) + ext;
// Create file pointer
var myFile = new File(destFolder + '/' + newName);
// Check that file permissions are granted
if (myFile.open("w"))
myFile.close();
else
throw new Error('Access is denied');
return myFile;
}
将脚本放入以 结尾的文件中
.jsx
,然后放入Scripts
Illustrator 中的文件夹中。我的位于/Applications/Adobe Illustrator 2021/Presets/en_US/Scripts/svgToPDF.jsx
.重新启动 Illustrator
File
从>Scripts
>svgToPDF
菜单项执行脚本。
缺点
- 插画师要花钱。
- 您必须手动执行
SVG
->PDF
转换。可以使用 AppleScript 实现自动化,但它确实不是您希望在服务器上运行的东西。
推荐阅读
- ruby-on-rails - 在 Rails 中下载和重定向
- linux - libs 路径“/run/opengl-driver”如何注入到像 compton 这样的 Nix 二进制文件中
- typescript - 无法将参数传递给“forEach”
- nginx - 如何让nginx代理通过读取主机域映射
- three.js - MTLLoader 破坏了其他 3js 代码并且没有正确加载纹理
- javascript - 在 iOS 工作时,ReactNative Android 所有请求都失败
- javascript - 如何在 JavaScript 中显示 Object 的值?
- javascript - 自定义元素设置:构造函数与 connectedCallback
- html - 让页脚粘在页面底部并被内容推送
- macos - 如何在 Mac 中安排自动化工作流程