Fix build pdf files

This commit is contained in:
Oleg Korshul
2024-09-11 01:09:50 +03:00
parent 8917390185
commit e345eff63a
11 changed files with 243 additions and 67 deletions

View File

@ -39,6 +39,7 @@
#include "embed/Default.h"
#include "embed/NativeControlEmbed.h"
#include "embed/GraphicsEmbed.h"
#include "embed/DrawingFileEmbed.h"
#include "./editors.h"
#include <iostream>
@ -232,10 +233,13 @@ namespace NSDoctRenderer
std::vector<std::wstring> m_arImagesInChanges;
IOfficeDrawingFile* m_pDrawingFile;
public:
CDoctRenderer_Private(const std::wstring& sAllFontsPath = L"") : CDoctRendererConfig()
{
LoadConfig(NSFile::GetProcessDirectory(), sAllFontsPath);
m_pDrawingFile = NULL;
}
~CDoctRenderer_Private()
{
@ -274,9 +278,9 @@ namespace NSDoctRenderer
std::cerr << sT << ": " << sE << std::endl;
}
static bool Doct_renderer_SaveFile(
CExecuteParams* pParams, NSNativeControl::CNativeControl* pNative, JSSmart<CJSContext> context, JSSmart<CJSValue>* args, std::wstring& strError, JSSmart<CJSObject>& api_js_maybe_null,
bool bIsPdfBase64 = false)
static bool Doct_renderer_SaveFile(CExecuteParams* pParams,
NSNativeControl::CNativeControl* pNative, JSSmart<CJSContext> context,
JSSmart<CJSValue>* args, std::wstring& strError, JSSmart<CJSObject>& api_js_maybe_null)
{
JSSmart<CJSTryCatch> try_catch = context->GetExceptions();
JSSmart<CJSObject> global_js = context->GetGlobal();
@ -446,23 +450,12 @@ namespace NSDoctRenderer
JSSmart<CJSTypedArray> typedArray = js_result2->toTypedArray();
NSJSBase::CJSDataBuffer oBuffer = typedArray->getData();
DWORD bufferSize = (pNative->m_nSaveBinaryLen == 0) ? (DWORD)oBuffer.Len : (DWORD)pNative->m_nSaveBinaryLen;
NSFile::CFileBinary oFile;
if (true == oFile.CreateFileW(pParams->m_strDstFilePath))
{
if (!bIsPdfBase64)
{
oFile.WriteFile(oBuffer.Data, (DWORD)pNative->m_nSaveBinaryLen);
}
else
{
char* pDataDst = NULL;
int nDataDst = 0;
if (NSFile::CBase64Converter::Encode(oBuffer.Data, pNative->m_nSaveBinaryLen, pDataDst, nDataDst))
{
oFile.WriteFile((BYTE*)pDataDst, (DWORD)nDataDst);
RELEASEARRAYOBJECTS(pDataDst);
}
}
oFile.WriteFile(oBuffer.Data, bufferSize);
oFile.CloseFile();
}
@ -601,6 +594,9 @@ namespace NSDoctRenderer
NSDoctRenderer::RunEditor(editorType, context, try_catch, this);
if (editorType == DoctRendererEditorType::PDF && m_pDrawingFile)
EmbedDrawingFile(context, m_pDrawingFile);
if (try_catch->Check())
{
strError = L"code=\"run\"";
@ -662,10 +658,15 @@ namespace NSDoctRenderer
if (!bIsWatermark)
{
CChangesWorker oWorkerLoader;
int nVersion = oWorkerLoader.OpenNative(pNative->GetFilePath());
int nVersion = 0;
if (editorType == DoctRendererEditorType::PDF)
nVersion = -1;
else
nVersion = oWorkerLoader.OpenNative(pNative->GetFilePath());
JSSmart<CJSValue> args_open[4];
args_open[0] = oWorkerLoader.GetDataFull()->toValue();
args_open[0] = (nVersion != -1) ? oWorkerLoader.GetDataFull()->toValue() : CJSContext::createUndefined();
args_open[1] = CJSContext::createInt(nVersion);
std::wstring sXlsx = NSFile::GetDirectoryName(pNative->GetFilePath()) + L"/Editor.xlsx";
args_open[2] = NSFile::CFileBinary::Exists(sXlsx) ? CJSContext::createString(sXlsx) : CJSContext::createUndefined();
@ -1103,6 +1104,18 @@ namespace NSDoctRenderer
}
#endif
}
void CDoctrenderer::SetAdditionalParam(const AdditionalParamType& type, void* data)
{
switch (type)
{
case AdditionalParamType::DRAWINGFILE:
m_pInternal->m_pDrawingFile = (IOfficeDrawingFile*)data;
break;
default:
break;
}
}
} // namespace NSDoctRenderer
bool Doct_renderer_SaveFile_ForBuilder(
@ -1114,5 +1127,5 @@ bool Doct_renderer_SaveFile_ForBuilder(
oParams.m_sJsonParams = jsonParams;
JSSmart<CJSObject> js_objectApi; // empty
return NSDoctRenderer::CDoctRenderer_Private::Doct_renderer_SaveFile(&oParams, pNative, context, args, strError, js_objectApi, false);
return NSDoctRenderer::CDoctRenderer_Private::Doct_renderer_SaveFile(&oParams, pNative, context, args, strError, js_objectApi);
}

View File

@ -55,6 +55,12 @@ namespace NSDoctRenderer
INVALID = 255
};
}
enum class AdditionalParamType
{
DRAWINGFILE = 0,
INVALID = 255
};
}
namespace NSDoctRenderer
@ -73,6 +79,8 @@ namespace NSDoctRenderer
void CreateCache(const std::wstring& sAllFontsPath, const std::wstring& sCacheDir);
void CreateSnapshots();
void SetAdditionalParam(const AdditionalParamType& type, void* data);
private:
CDoctRenderer_Private* m_pInternal;
};

View File

@ -53,6 +53,8 @@ private:
IOfficeDrawingFile* m_pFile;
int m_nType = -1;
bool m_bIsExternalFile;
public:
CDrawingFile(NSFonts::IApplicationFonts* pFonts)
{
@ -69,16 +71,41 @@ public:
m_pImageStorage = NULL;
m_pFile = NULL;
m_bIsExternalFile = false;
}
~CDrawingFile()
{
RELEASEOBJECT(m_pFile);
if (!m_bIsExternalFile)
RELEASEOBJECT(m_pFile);
RELEASEOBJECT(m_pTextRenderer);
RELEASEOBJECT(m_pFontManager);
RELEASEINTERFACE(m_pApplicationFonts);
RELEASEOBJECT(m_pImageStorage);
}
void SetInternalFile(IOfficeDrawingFile* pFile)
{
m_pFile = pFile;
if (!m_pFile)
return;
m_bIsExternalFile = true;
switch (m_pFile->GetType())
{
case odftPDF:
m_nType = 0;
break;
case odftDJVU:
m_nType = 1;
break;
case odftXPS:
m_nType = 2;
break;
default:
break;
}
}
public:
static void InitFontsGlobalStorage()
{

View File

@ -1,4 +1,5 @@
#include "DrawingFileEmbed.h"
#include "../drawingfile.h"
JSSmart<CJSValue> WasmMemoryToJS(BYTE* pWasmData)
{
@ -13,6 +14,15 @@ JSSmart<CJSValue> WasmMemoryToJS(BYTE* pWasmData)
return NSJSBase::CJSContext::createUint8Array(pWasmData + 4, nLen - 4, true);
}
CDrawingFileEmbed::CDrawingFileEmbed()
{
m_pFile = NULL;
}
CDrawingFileEmbed::~CDrawingFileEmbed()
{
RELEASEOBJECT(m_pFile);
}
JSSmart<CJSValue> CDrawingFileEmbed::OpenFile(JSSmart<CJSValue> sFile, JSSmart<CJSValue> sPassword)
{
bool bResult = m_pFile->OpenFile(sFile->toStringW(), sPassword->isString() ? sPassword->toStringW() : L"");
@ -136,7 +146,22 @@ JSSmart<CJSValue> CDrawingFileEmbed::FreeWasmData(JSSmart<CJSValue> typedArray)
if (!typedArray->isTypedArray())
return NULL;
BYTE* data = typedArray->toTypedArray()->getData().Data;
typedArray->toTypedArray()->Detach();
data -= 4; // sizeof int (length in NSWasm::Data)
free(data);
return NULL;
}
bool EmbedDrawingFile(JSSmart<NSJSBase::CJSContext>& context, IOfficeDrawingFile* pFile)
{
CJSContext::Embed<CDrawingFileEmbed>(false);
JSSmart<CJSObject> oNativeDrawingFile = CJSContext::createEmbedObject("CDrawingFileEmbed");
context->GetGlobal()->set("g_native_drawing_file", oNativeDrawingFile);
CDrawingFile* pDrFile = new CDrawingFile(pFile->GetFonts());
pDrFile->SetInternalFile(pFile);
((CDrawingFileEmbed*)oNativeDrawingFile->getNative())->m_pFile = pDrFile;
return true;
}

View File

@ -1,8 +1,10 @@
#ifndef _BUILD_DRAWING_EMBED_H_
#define _BUILD_DRAWING_EMBED_H_
#include "../drawingfile.h"
#include "../js_internal/js_base.h"
#include "../../graphics/pro/officedrawingfile.h"
class CDrawingFile;
using namespace NSJSBase;
class JS_DECL CDrawingFileEmbed : public CJSEmbedObject
@ -11,14 +13,8 @@ public:
CDrawingFile* m_pFile;
public:
CDrawingFileEmbed()
{
m_pFile = NULL;
}
~CDrawingFileEmbed()
{
RELEASEOBJECT(m_pFile);
}
CDrawingFileEmbed();
~CDrawingFileEmbed();
virtual void* getObject() override { return (void*)m_pFile; }
@ -57,4 +53,6 @@ public:
DECLARE_EMBED_METHODS
};
bool EmbedDrawingFile(JSSmart<NSJSBase::CJSContext>& context, IOfficeDrawingFile* pFile);
#endif // _BUILD_NATIVE_ZIP_EMBED_H_

View File

@ -386,6 +386,14 @@ namespace NSJSBase
* Converts the typed array to a value.
*/
virtual JSSmart<CJSValue> toValue() = 0;
/**
* Detaches this ArrayBuffer and all its views (typed arrays).
* Detaching sets the byte length of the buffer and all typed arrays to zero,
* preventing JavaScript from ever accessing underlying backing store.
* ArrayBuffer should have been externalized.
*/
virtual void Detach() = 0;
};
/**

View File

@ -385,6 +385,11 @@ namespace NSJSBase
_value->value = value;
return _value;
}
virtual void Detach()
{
// None
}
};
class CJSFunctionJSC : public CJSValueJSCTemplate<CJSFunction>

View File

@ -705,6 +705,15 @@ namespace NSJSBase
_value->value = value;
return _value;
}
virtual void Detach()
{
#ifdef V8_ARRAY_BUFFER_USE_BACKING_STORE
value->Buffer()->Detach();
#else
value->Buffer()->Neuter();
#endif
}
};
class CJSFunctionV8 : public CJSValueV8Template<v8::Function, CJSFunction>

View File

@ -33,6 +33,7 @@ for item in content_native_files:
content_native += base.readFile(item)
content_native += "\n})(window, undefined);"
content_native = content_native.replace("//file_internal", base.readFile("./wasm/js/drawingfile_native.js"))
content_native = content_native.replace("//string_utf8", base.readFile("./../../../../Common/js/string_utf8.js"))
base.writeFile("./deploy/drawingfile_native.js", content_native)
base.cmd_in_dir("../../../../Common/js", "python", ["./min.py", "./../../DesktopEditor/graphics/pro/js/deploy/drawingfile_native.js", "WHITESPACE_ONLY"])

View File

@ -30,12 +30,16 @@
*
*/
//string_utf8
function CNativePointer()
{
this.ptr = null;
}
CNativePointer.prototype.free = function()
{
if (this.ptr)
g_native_drawing_file["FreeWasmData"](this.ptr);
this.ptr = null;
};
CNativePointer.prototype.getReader = function()
@ -65,120 +69,159 @@ CFile.prototype._getUint8ClampedArray = function(ptr, len)
// FILE
CFile.prototype._openFile = function(buffer, password)
{
// TODO:
let res = false;
if (!buffer)
res = -1 !== g_native_drawing_file["GetType"]();
if (res)
this.nativeFile = 1;
return res;
};
CFile.prototype._closeFile = function()
{
// TODO:
g_native_drawing_file["CloseFile"]();
this.nativeFile = 0;
};
CFile.prototype._getType = function()
{
// TODO:
return g_native_drawing_file["GetType"]();
};
CFile.prototype._getError = function()
{
// TODO:
return g_native_drawing_file["GetErrorCode"]();
};
// FONTS
CFile.prototype._isNeedCMap = function()
{
// TODO:
return g_native_drawing_file["IsNeedCMap"]();
};
CFile.prototype._setCMap = function(memoryBuffer)
{
// TODO:
// none
};
CFile.prototype._getFontByID = function(ID)
{
// TODO:
return null;
};
CFile.prototype._getInteractiveFormsFonts = function(type)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetInteractiveFormsFonts"](type);
return g_module_pointer;
};
// INFO DOCUMENT
CFile.prototype._getInfo = function()
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetInfo"]();
return g_module_pointer;
};
CFile.prototype._getStructure = function()
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetStructure"]();
return g_module_pointer;
};
CFile.prototype._getLinks = function(pageIndex)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetLinks"](pageIndex);
return g_module_pointer;
};
// WIDGETS & ANNOTATIONS
CFile.prototype._getInteractiveFormsInfo = function()
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetInteractiveFormsInfo"]();
return g_module_pointer;
};
CFile.prototype._getAnnotationsInfo = function(pageIndex)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetAnnotationsInfo"](pageIndex);
return g_module_pointer;
};
CFile.prototype._getButtonIcons = function(backgroundColor, pageIndex, isBase64, nWidget, nView)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetButtonIcons"](
backgroundColor === undefined ? 0xFFFFFF : backgroundColor,
pageIndex,
isBase64 ? 1 : 0,
nWidget === undefined ? -1 : nWidget,
nView);
return g_module_pointer;
};
CFile.prototype._getAnnotationsAP = function(width, height, backgroundColor, pageIndex, nAnnot, nView)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetAnnotationsAP"](
width,
height,
backgroundColor === undefined ? 0xFFFFFF : backgroundColor,
pageIndex,
nAnnot === undefined ? -1 : nAnnot,
nView);
return g_module_pointer;
};
CFile.prototype._getInteractiveFormsAP = function(width, height, backgroundColor, pageIndex, nWidget, nView, nButtonView)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["GetInteractiveFormsAP"](
width,
height,
backgroundColor === undefined ? 0xFFFFFF : backgroundColor,
pageIndex,
nWidget === undefined ? -1 : nWidget,
nView, nButtonView);
return g_module_pointer;
};
// SCAN PAGES
CFile.prototype._scanPage = function(page, mode)
{
// TODO:
g_module_pointer.ptr = g_native_drawing_file["ScanPage"](page, (mode === undefined) ? 0 : mode);
return g_module_pointer;
};
CFile.prototype._getImageBase64 = function(rId)
{
// TODO:
return g_native_drawing_file["GetImageBase64"](rId);
};
// TEXT
CFile.prototype._getGlyphs = function(pageIndex)
{
// TODO:
let res = {};
res.info = [0, 0, 0, 0];
res.result = [];
return res;
};
CFile.prototype._destroyTextInfo = function()
{
// TODO:
g_native_drawing_file["DestroyTextInfo"](rId);
};
// RASTER
CFile.prototype._getPixmap = function(pageIndex, width, height, backgroundColor)
{
// TODO:
return null;
};
// STATIC FUNCTIONS
CFile.prototype._InitializeFonts = function(basePath)
{
// none
};
CFile.prototype._CheckStreamId = function(data, status)
{
// none
};

View File

@ -651,6 +651,33 @@ namespace NExtractTools
return nRes;
}
bool applyCompiledChangesPdf(CPdfFile* pFile, const std::wstring& sCompiledChangesPath, CConvertFromBinParams& oConvertParams)
{
bool bRes = false;
NSFile::CFileBinary oFile;
if (oFile.OpenFile(sCompiledChangesPath))
{
char signature[4];
if (oFile.ReadFile((BYTE*)signature, 4))
{
if ('%' == signature[0] && 'P' == signature[1] && 'D' == signature[2] && 'F' == signature[3])
{
DWORD dwChangesSize = (DWORD)(oFile.GetFileSize() - 4);
BYTE* pChangesData = NULL;
if (oFile.ReadFile(pChangesData, dwChangesSize))
{
bRes = (S_OK == pFile->AddToPdfFromBinary(pChangesData, (unsigned int)dwChangesSize, &oConvertParams));
RELEASEARRAYOBJECTS(pChangesData);
}
}
}
oFile.CloseFile();
}
return bRes;
}
bool applyChangesPdf(const std::wstring& sFrom, const std::wstring& sTo,
NSFonts::IApplicationFonts* pApplicationFonts,
InputParams& params, ConvertParams& convertParams,
@ -676,6 +703,34 @@ namespace NExtractTools
oConvertParams.m_sInternalMediaDirectory = NSFile::GetDirectoryName(sFrom);
oConvertParams.m_sMediaDirectory = oConvertParams.m_sInternalMediaDirectory;
bool bIsCompiledChanges = false;
if (changes.size() > 0)
{
bIsCompiledChanges = applyCompiledChangesPdf(&oPdfResult, changes[0], oConvertParams);
if (!bIsCompiledChanges)
{
NSDoctRenderer::CDoctrenderer oDoctRenderer(NULL != params.m_sAllFontsPath ? *params.m_sAllFontsPath : L"");
std::wstring sPdfFileCompiledChanges = NSFile::CFileBinary::CreateTempFileWithUniqueName(convertParams.m_sTempDir, L"PDF_");
if (NSFile::CFileBinary::Exists(sPdfFileCompiledChanges))
NSFile::CFileBinary::Remove(sPdfFileCompiledChanges);
std::wstring sXml = getDoctXml(NSDoctRenderer::DoctRendererFormat::PDF,
NSDoctRenderer::DoctRendererFormat::PDF,
sFrom, sPdfFileCompiledChanges,
oConvertParams.m_sInternalMediaDirectory, convertParams.m_sThemesDir,
-1, L"", params);
std::wstring sResult = L"";
oDoctRenderer.SetAdditionalParam(NSDoctRenderer::AdditionalParamType::DRAWINGFILE, (void*)&oPdfResult);
oDoctRenderer.Execute(sXml, sResult);
if (NSFile::CFileBinary::Exists(sPdfFileCompiledChanges))
bIsCompiledChanges = applyCompiledChangesPdf(&oPdfResult, sPdfFileCompiledChanges, oConvertParams);
}
}
if (!sResultDirectory.empty() && !params.getDontSaveAdditional())
{
//apply and zip changes
@ -689,9 +744,6 @@ namespace NExtractTools
//add changes to zip
std::wstring sFilename = NSSystemPath::GetFileName(*i);
oFolderWithChanges.write(sFilename, pChangesData, dwChangesSize);
//apply changes
oPdfResult.AddToPdfFromBinary(pChangesData, (unsigned int)dwChangesSize, &oConvertParams);
RELEASEARRAYOBJECTS(pChangesData);
}
}
//add images
@ -717,19 +769,6 @@ namespace NExtractTools
oFile.CloseFile();
RELEASEOBJECT(pBuffer);
}
else
{
for (std::vector<std::wstring>::const_iterator i = changes.begin(); i != changes.end(); i++)
{
BYTE* pChangesData = NULL;
DWORD dwChangesSize = 0;
if (NSFile::CFileBinary::ReadAllBytes(*i, &pChangesData, dwChangesSize))
{
oPdfResult.AddToPdfFromBinary(pChangesData, (unsigned int)dwChangesSize, &oConvertParams);
RELEASEARRAYOBJECTS(pChangesData);
}
}
}
oPdfResult.Close();
return true;