diff --git a/DesktopEditor/doctrenderer/embed/ZipEmbed.cpp b/DesktopEditor/doctrenderer/embed/ZipEmbed.cpp index e2151d1f28..ef2a2fe5a4 100644 --- a/DesktopEditor/doctrenderer/embed/ZipEmbed.cpp +++ b/DesktopEditor/doctrenderer/embed/ZipEmbed.cpp @@ -258,3 +258,56 @@ JSSmart CZipEmbed::getImageType(JSSmart typedArray) oBuffer.Free(); return CJSContext::createInt(bIsImageFile ? oChecker.eFileType : 0); } + +JSSmart CZipEmbed::getImageBuffer(JSSmart filePath) +{ + if (!m_pFolder || !filePath->isString()) + return CJSContext::createNull(); + + std::wstring sFilePath = filePath->toStringW(); + IFolder::CBuffer* pBuffer; + if (!m_pFolder->read(sFilePath, pBuffer)) + return CJSContext::createNull(); + + size_t nBufferSize = (size_t)pBuffer->Size; + + CImageFileFormatChecker oChecker; + bool bIsImageFile = oChecker.isImageFile(pBuffer->Buffer, (DWORD)pBuffer->Size); + + if (!bIsImageFile) + { + RELEASEOBJECT(pBuffer); + return CJSContext::createNull(); + } + + if (oChecker.eFileType != _CXIMAGE_FORMAT_WMF && oChecker.eFileType != _CXIMAGE_FORMAT_EMF) + { + BYTE* pMemory = NSJSBase::NSAllocator::Alloc(nBufferSize); + memcpy(pMemory, pBuffer->Buffer, nBufferSize); + RELEASEOBJECT(pBuffer); + + JSSmart retObject = CJSContext::createObject(); + retObject->set("type", CJSContext::createInt(oChecker.eFileType)); + retObject->set("data", NSJSBase::CJSContext::createUint8Array(pMemory, (int)nBufferSize, false)); + return retObject->toValue(); + } + +#ifndef GRAPHICS_DISABLE_METAFILE + MetaFile::IMetaFile* pMetaFile = MetaFile::Create(NULL); + pMetaFile->LoadFromBuffer(pBuffer->Buffer, (unsigned int)pBuffer->Size); + std::wstring wsSvg = pMetaFile->ConvertToSvg(); + std::string sSvg = U_TO_UTF8(wsSvg); + pMetaFile->Release(); + RELEASEOBJECT(pBuffer); + + BYTE* pData = NSAllocator::Alloc(sSvg.length()); + memcpy(pData, sSvg.c_str(), sSvg.length()); + + JSSmart retObject = CJSContext::createObject(); + retObject->set("type", CJSContext::createInt(24)); + retObject->set("data", NSJSBase::CJSContext::createUint8Array(pData, sSvg.length(), false)); + return retObject->toValue(); +#else + return CJSContext::createNull(); +#endif +} diff --git a/DesktopEditor/doctrenderer/embed/ZipEmbed.h b/DesktopEditor/doctrenderer/embed/ZipEmbed.h index 35bb724ffb..02a4e86060 100644 --- a/DesktopEditor/doctrenderer/embed/ZipEmbed.h +++ b/DesktopEditor/doctrenderer/embed/ZipEmbed.h @@ -36,6 +36,7 @@ public: JSSmart encodeImageData(JSSmart typedArray, JSSmart w, JSSmart h, JSSmart stride, JSSmart format, JSSmart isRgba); JSSmart encodeImage(JSSmart typedArray, JSSmart format); JSSmart getImageType(JSSmart typedArray); + JSSmart getImageBuffer(JSSmart path); DECLARE_EMBED_METHODS }; diff --git a/DesktopEditor/doctrenderer/embed/jsc/jsc_ZipEmbed.mm b/DesktopEditor/doctrenderer/embed/jsc/jsc_ZipEmbed.mm index 1c831a0aab..2da39ec0bc 100644 --- a/DesktopEditor/doctrenderer/embed/jsc/jsc_ZipEmbed.mm +++ b/DesktopEditor/doctrenderer/embed/jsc/jsc_ZipEmbed.mm @@ -17,6 +17,7 @@ -(JSValue*) encodeImageData : (JSValue*)typedArray : (JSValue*)w : (JSValue*)h : (JSValue*)stride : (JSValue*)format : (JSValue*)isRgba; -(JSValue*) encodeImage : (JSValue*)typedArray : (JSValue*)format; -(JSValue*) getImageType : (JSValue*)typedArray; +-(JSValue*) getImageBuffer : (JSValue*)path; @end @interface CJSCZipEmbed : NSObject @@ -41,6 +42,7 @@ FUNCTION_WRAPPER_JS_2(decodeImage, decodeImage) FUNCTION_WRAPPER_JS_6(encodeImageData, encodeImageData) FUNCTION_WRAPPER_JS_2(encodeImage, encodeImage) FUNCTION_WRAPPER_JS_1(getImageType, getImageType) +FUNCTION_WRAPPER_JS_1(getImageBuffer, getImageBuffer) @end class CZipEmbedAdapter : public CJSEmbedObjectAdapterJSC diff --git a/DesktopEditor/doctrenderer/embed/v8/v8_ZipEmbed.cpp b/DesktopEditor/doctrenderer/embed/v8/v8_ZipEmbed.cpp index 7e6b00e67e..ffedb7a472 100644 --- a/DesktopEditor/doctrenderer/embed/v8/v8_ZipEmbed.cpp +++ b/DesktopEditor/doctrenderer/embed/v8/v8_ZipEmbed.cpp @@ -20,6 +20,7 @@ namespace NSZipEmbed FUNCTION_WRAPPER_V8_6(_encodeImageData, encodeImageData) FUNCTION_WRAPPER_V8_2(_encodeImage, encodeImage) FUNCTION_WRAPPER_V8_1(_getImageType, getImageType) + FUNCTION_WRAPPER_V8_1(_getImageBuffer, getImageBuffer) v8::Handle CreateTemplate(v8::Isolate* isolate) { @@ -39,6 +40,7 @@ namespace NSZipEmbed NSV8Objects::Template_Set(result, "encodeImageData", _encodeImageData); NSV8Objects::Template_Set(result, "encodeImage", _encodeImage); NSV8Objects::Template_Set(result, "getImageType", _getImageType); + NSV8Objects::Template_Set(result, "getImageBuffer", _getImageBuffer); return handle_scope.Escape(result); } diff --git a/DesktopEditor/fontengine/js/engine/module_js.js b/DesktopEditor/fontengine/js/engine/module_js.js index 982143a58d..93f4dc9572 100644 --- a/DesktopEditor/fontengine/js/engine/module_js.js +++ b/DesktopEditor/fontengine/js/engine/module_js.js @@ -531,6 +531,40 @@ ZLib.prototype.getImageAsSvg = function(path) return string; }; +/** + * Get image file raw data. this memory was copied and detach from archive. + * @returns {Uint8Array} + */ +ZLib.prototype.getImageBuffer = function(path) +{ + let result = { + type : 0, + data : null + }; + result.type = this.getImageType(path); + if (result.type != 10 && + result.type != 21) + { + let fileData = this.getFile(path); + result.data = new Uint8Array(fileData.length); + result.data.set(fileData); + return result; + } + + result.type = 24; + + let fileData = this.getFile(path); + let encodedData = Module["_Raster_Encode"](this.files[path].p + 4, fileData.length, 24); + let encodedSize = Module["_Raster_GetEncodedSize"](encodedData); + let encodedBuffer = Module["_Raster_GetEncodedBuffer"](encodedData); + + let fileDataEnc = new Uint8Array(Module["HEAP8"].buffer, encodedBuffer, encodedSize); + result.data = new Uint8Array(fileDataEnc.length); + result.data.set(fileDataEnc); + + Module["_Raster_DestroyEncodedData"](encodedData); + return result; +}; /** * Get image blob for browser * @returns {Blob}