📄 pxcpngff.cpp
字号:
pSession->AddRef(); // Init the size retVal = pSession->InitSize(ulMaxNumPackets); if (SUCCEEDED(retVal)) { // Parse the image, putting buffers into the session object HXxSize rImageDim; retVal = ParseBuffer(pBuffer, pSession, rImageDim); if (SUCCEEDED(retVal)) { // Now we can reduce our size to the number of packets we actually have retVal = pSession->SetSize(pSession->GetNumPackets()); if (SUCCEEDED(retVal)) { // Add the session to the map retVal = m_pMapManager->AddEntry((void*) pSession, rulSessionHandle); if (SUCCEEDED(retVal)) { // AddRef the session since it's in the map pSession->AddRef(); // Create an IHXValues object IHXValues* pParam = NULL; retVal = m_pCommonClassFactory->CreateInstance(CLSID_IHXValues, (void**) &pParam); if (SUCCEEDED(retVal)) { // Set properties in the IHXValues pParam->SetPropertyULONG32("MaxPacketSize", pSession->GetMaxPacketSize()); pParam->SetPropertyULONG32("MinPacketSize", pSession->GetMinPacketSize()); pParam->SetPropertyULONG32("TotalBytes", pSession->GetTotalBytes()); pParam->SetPropertyULONG32("TotalReqBytes", pSession->GetTotalRequiredBytes()); pParam->SetPropertyULONG32("TotalNonReqBytes", pSession->GetTotalNonRequiredBytes()); pParam->SetPropertyULONG32("ImageWidth", (UINT32) rImageDim.cx); pParam->SetPropertyULONG32("ImageHeight", (UINT32) rImageDim.cy); // Set the outgoing parameters rulNumPackets = pSession->GetNumPackets(); HX_RELEASE(rpParam); rpParam = pParam; rpParam->AddRef(); } HX_RELEASE(pParam); } } } } } else { retVal = HXR_OUTOFMEMORY; } HX_RELEASE(pSession); } else { retVal = HXR_INVALID_PARAMETER; } return retVal;}STDMETHODIMP CRealPixPNGFileFormatCodec::GetImagePacket(UINT32 ulSessionHandle, UINT32 ulPacketNum, REF(IHXBuffer*) rpPacketBuffer, REF(IHXBuffer*) rpOpaquePacketData, REF(BOOL) rbRequired){ HX_RESULT retVal = HXR_FAIL; if (m_pMapManager) { PXParseSession* pSession = NULL; retVal = m_pMapManager->GetEntry(ulSessionHandle, (void**) &pSession); if (SUCCEEDED(retVal)) { // Get the packet from the session retVal = pSession->GetPacket(ulPacketNum, rpPacketBuffer, rpOpaquePacketData, rbRequired); } } return retVal;}STDMETHODIMP CRealPixPNGFileFormatCodec::ReleaseImage(UINT32 ulSessionHandle){ HX_RESULT retVal = HXR_FAIL; if (m_pMapManager) { PXParseSession* pSession = NULL; retVal = m_pMapManager->DeleteEntry(ulSessionHandle, (void**) &pSession); HX_RELEASE(pSession); } return retVal;}HX_RESULT STDAPICALLTYPE CRealPixPNGFileFormatCodec::HXCreateInstance(IUnknown** ppIUnknown){ HX_RESULT retVal = HXR_OK; if (ppIUnknown) { // Create file format codec CRealPixPNGFileFormatCodec* pCodec = new CRealPixPNGFileFormatCodec(); if (pCodec) { // QI for IUnknown retVal = pCodec->QueryInterface(IID_IUnknown, (void**) ppIUnknown); } else { retVal = HXR_OUTOFMEMORY; } if (FAILED(retVal)) { HX_DELETE(pCodec); } } else { retVal = HXR_FAIL; } return retVal;}HX_RESULT CRealPixPNGFileFormatCodec::ParseBuffer(IHXBuffer* pBuffer, PXParseSession* pSession, REF(HXxSize) rImageDim){ HX_RESULT retVal = HXR_OK; if (pBuffer && pSession) { UINT32 ulWidth = 0; UINT32 ulHeight = 0; if (PXPNGDecode::GetIHDRInfo(pBuffer, ulWidth, ulHeight)) { rImageDim.cx = (INT32) ulWidth; rImageDim.cy = (INT32) ulHeight; } // Find the beginning of the IDAT chunk UINT32 ulOffset = 0; UINT32 ulBytes = 0; BOOL bComplete = FALSE; BOOL bPresent = PXPNGDecode::IsChunkPresent(pBuffer, 0x49444154, // IDAT chunk ulOffset, ulBytes, bComplete); if (bPresent && bComplete) { UINT32 ulFirstBufferSize = 0; if (ulOffset + kMinIDATBytes > kDefaultPacketSize) { // Since the size of the all the chunks before the IDAT is // greater than the ideal packet size, then we'll just do // the minimum here. ulFirstBufferSize = ulOffset + kMinIDATBytes; } else { // Since the size of all the chunks before the IDAT is // LESS than the ideal packet size, we'll allow some of // the IDAT chunk into the first packet. ulFirstBufferSize = kDefaultPacketSize; if (ulFirstBufferSize > pBuffer->GetSize()) { ulFirstBufferSize = pBuffer->GetSize(); } } // Add the first packet buffer UINT32 ulNumBuffers = 1; // Add all the rest of the packets past the first ulNumBuffers += (pBuffer->GetSize() - ulFirstBufferSize + kDefaultPacketSize - 1) / kDefaultPacketSize; // Now run through and create the buffers UINT32 ulCurOffset = 0; UINT32 ulCurSize = ulFirstBufferSize; for (UINT32 i = 0; i < ulNumBuffers && SUCCEEDED(retVal); i++) { // Create a nested buffer CHXNestedBuffer* pNest = NULL; retVal = CHXNestedBuffer::CreateObject(&pNest); if (SUCCEEDED(retVal)) { // AddRef the object pNest->AddRef(); // Init the nested buffer retVal = pNest->Init(pBuffer, ulCurOffset, ulCurSize); if (SUCCEEDED(retVal)) { // QI for IHXBuffer IHXBuffer* pData = NULL; retVal = pNest->QueryInterface(IID_IHXBuffer, (void**) &pData); if (SUCCEEDED(retVal)) { // Update the current offset and size ulCurOffset += ulCurSize; ulCurSize = kDefaultPacketSize; if (ulCurOffset + ulCurSize > pBuffer->GetSize()) { ulCurSize = pBuffer->GetSize() - ulCurOffset; } // Create the opaque buffer IHXBuffer* pOpaque = NULL; retVal = m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer, (void**) &pOpaque); if (SUCCEEDED(retVal)) { // Set its size retVal = pOpaque->SetSize(4); if (SUCCEEDED(retVal)) { // Pack the opaque buffer with a seq num BYTE* pBuf = pOpaque->GetBuffer(); Pack32(pBuf, i); // Add the packet retVal = pSession->AddPacket(pData, pOpaque, (i ? FALSE : TRUE)); } } HX_RELEASE(pOpaque); } HX_RELEASE(pData); } } HX_RELEASE(pNest); } } else { retVal = HXR_OUTOFMEMORY; } } else { retVal = HXR_FAIL; } return retVal;}void CRealPixPNGFileFormatCodec::ReleaseAllSessions(){ if (m_pMapManager) { UINT32 ulHandle = 0; PXParseSession* pSession = NULL; HX_RESULT retVal = m_pMapManager->GetFirstEntry(ulHandle, (void**) &pSession); while (SUCCEEDED(retVal)) { HX_RELEASE(pSession); retVal = m_pMapManager->GetNextEntry(ulHandle, (void**) &pSession); } m_pMapManager->DeleteAllEntries(); }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -