mirror of
https://github.com/ONLYOFFICE/core.git
synced 2026-02-10 18:05:41 +08:00
Fix text color
This commit is contained in:
@ -520,6 +520,7 @@ namespace PdfWriter
|
||||
m_unShadingsCount = 0;
|
||||
m_pPatterns = NULL;
|
||||
m_unPatternsCount = 0;
|
||||
m_eType = fontUnknownType;
|
||||
}
|
||||
void CPage::SetWidth(double dValue)
|
||||
{
|
||||
@ -1281,26 +1282,24 @@ namespace PdfWriter
|
||||
}
|
||||
void CPage::WriteText(const BYTE* sText, unsigned int unLen)
|
||||
{
|
||||
EFontType eType = m_pFont ? m_pFont->GetFontType() : fontCIDType0;
|
||||
EFontType eType = m_eType != fontUnknownType ? m_eType : (m_pFont ? m_pFont->GetFontType() : fontCIDType0);
|
||||
if (fontCIDType0 == eType || fontCIDType0C == eType || fontCIDType0COT == eType || fontCIDType2 == eType || fontCIDType2OT == eType)
|
||||
{
|
||||
m_pStream->WriteChar('<');
|
||||
m_pStream->WriteBinary(sText, unLen, NULL);
|
||||
m_pStream->WriteChar('>');
|
||||
}
|
||||
else if (fontType1 == eType)
|
||||
else
|
||||
{
|
||||
unLen = unLen / 2;
|
||||
BYTE* sText2 = new BYTE[unLen];
|
||||
for (int i = 0; i < unLen; ++i)
|
||||
sText2[i] = sText[i * 2 + 1];
|
||||
m_pStream->WriteEscapeText(sText2, unLen);
|
||||
m_pStream->WriteChar('<');
|
||||
m_pStream->WriteBinary(sText2, unLen, NULL);
|
||||
m_pStream->WriteChar('>');
|
||||
RELEASEARRAYOBJECTS(sText2);
|
||||
}
|
||||
else
|
||||
{
|
||||
m_pStream->WriteEscapeText(sText, unLen);
|
||||
}
|
||||
}
|
||||
void CPage::DrawText(double dXpos, double dYpos, const BYTE* sText, unsigned int unLen)
|
||||
{
|
||||
@ -1448,6 +1447,10 @@ namespace PdfWriter
|
||||
m_pStream->WriteReal(dSize);
|
||||
m_pStream->WriteStr(" Tf\012");
|
||||
}
|
||||
void CPage::SetFontType(EFontType nType)
|
||||
{
|
||||
m_eType = nType;
|
||||
}
|
||||
void CPage::SetTextRenderingMode(ETextRenderingMode eMode)
|
||||
{
|
||||
// Operator : Tr
|
||||
|
||||
@ -174,6 +174,7 @@ namespace PdfWriter
|
||||
void SetHorizontalScaling(double dValue);
|
||||
void SetFontAndSize(CFontDict* pFont, double dSize);
|
||||
void SetFontKeyAndSize(const char* sKey, double dSize);
|
||||
void SetFontType(EFontType nType);
|
||||
void SetTextRenderingMode(ETextRenderingMode eMode);
|
||||
void SetTextMatrix(double dM11, double dM12, double dM21, double dM22, double dX, double dY);
|
||||
void DrawTextLine(const CTextLine* pTextLine);
|
||||
@ -228,6 +229,7 @@ namespace PdfWriter
|
||||
unsigned int m_unShadingsCount;
|
||||
CDictObject* m_pPatterns;
|
||||
unsigned int m_unPatternsCount;
|
||||
EFontType m_eType;
|
||||
};
|
||||
class CFakePage : public CObjectBase
|
||||
{
|
||||
|
||||
@ -379,7 +379,34 @@ void RedactOutputDev::clipToStrokePath(GfxState *pGState)
|
||||
//----- text drawing
|
||||
void RedactOutputDev::beginStringOp(GfxState *pGState)
|
||||
{
|
||||
int nDColor2Size;
|
||||
double* dColor = m_pRenderer->m_oBrush.GetDColor2(nDColor2Size);
|
||||
if (nDColor2Size == 1)
|
||||
m_pPage->SetFillG(dColor[0]);
|
||||
else if (nDColor2Size == 3)
|
||||
m_pPage->SetFillRGB(dColor[0], dColor[1], dColor[2]);
|
||||
else if (nDColor2Size == 4)
|
||||
m_pPage->SetFillCMYK(dColor[0], dColor[1], dColor[2], dColor[3]);
|
||||
|
||||
dColor = m_pRenderer->m_oPen.GetDColor2(nDColor2Size);
|
||||
if (nDColor2Size == 1)
|
||||
m_pPage->SetStrokeG(dColor[0]);
|
||||
else if (nDColor2Size == 3)
|
||||
m_pPage->SetStrokeRGB(dColor[0], dColor[1], dColor[2]);
|
||||
else if (nDColor2Size == 4)
|
||||
m_pPage->SetStrokeCMYK(dColor[0], dColor[1], dColor[2], dColor[3]);
|
||||
|
||||
CStream* pStream = m_pPage->GetStream();
|
||||
for (int i = 0; i < m_sStates.size(); ++i)
|
||||
{
|
||||
for (int j = 0; j < m_sStates[i].m_arrOp.size(); ++j)
|
||||
{
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].first.c_str());
|
||||
pStream->WriteChar(' ');
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].second.c_str());
|
||||
pStream->WriteStr("\012");
|
||||
}
|
||||
}
|
||||
}
|
||||
void RedactOutputDev::endStringOp(GfxState *pGState)
|
||||
{
|
||||
@ -454,7 +481,11 @@ void RedactOutputDev::drawChar(GfxState *pGState, double dX, double dY, double d
|
||||
double dShiftX = 0, dShiftY = 0;
|
||||
DoTransform(arrMatrix, &dShiftX, &dShiftY, true);
|
||||
|
||||
double dDiff = dX + dDx / 2.0;
|
||||
double startX, startY, endX, endY;
|
||||
pGState->transform(dX, dY, &startX, &startY);
|
||||
pGState->transform(dX + dDx, dY + dDy, &endX, &endY);
|
||||
double dCenterX = (startX + endX) / 2;
|
||||
double dCenterY = (startY + endY) / 2;
|
||||
for (int i = 0; i < m_arrQuadPoints.size(); i += 4)
|
||||
{
|
||||
double xMin = m_arrQuadPoints[i + 0];
|
||||
@ -462,8 +493,11 @@ void RedactOutputDev::drawChar(GfxState *pGState, double dX, double dY, double d
|
||||
double xMax = m_arrQuadPoints[i + 2];
|
||||
double yMax = m_arrQuadPoints[i + 3];
|
||||
|
||||
if (xMin < dDiff && dDiff < xMax && yMin < dY && dY < yMax)
|
||||
if (xMin < dCenterX && dCenterX < xMax && yMin < dCenterY && dCenterY < yMax)
|
||||
{
|
||||
m_pRenderer->put_FontSize(dOldSize);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
BYTE* pCodes = new BYTE[2];
|
||||
@ -475,9 +509,7 @@ void RedactOutputDev::drawChar(GfxState *pGState, double dX, double dY, double d
|
||||
CRendererTextCommand* pText = m_pRenderer->m_oCommandManager.AddText(pCodes, 2, dShiftX, dShiftY);
|
||||
pText->SetName(m_pRenderer->m_oFont.GetName());
|
||||
pText->SetSize(m_pRenderer->m_oFont.GetSize());
|
||||
int nDColor2Size;
|
||||
double* dColor2 = m_pRenderer->m_oBrush.GetDColor2(nDColor2Size);
|
||||
pText->SetDColor2(nDColor2Size, dColor2[0], dColor2[1], dColor2[2], dColor2[3]);
|
||||
pText->SetType((EFontType)pGState->getFont()->getType());
|
||||
pText->SetAlpha((BYTE)m_pRenderer->m_oBrush.GetAlpha1()); // TODO
|
||||
pText->SetCharSpace(m_pRenderer->m_oFont.GetCharSpace());
|
||||
pText->SetMode(m_pRenderer->m_oFont.GetRenderMode());
|
||||
@ -485,6 +517,8 @@ void RedactOutputDev::drawChar(GfxState *pGState, double dX, double dY, double d
|
||||
pText->SetWordSpace(m_pRenderer->m_oFont.GetWordSpace());
|
||||
pText->SetHorScaling(m_pRenderer->m_oFont.GetHorizontalScaling());
|
||||
pText->SetWidth(dDx);
|
||||
|
||||
m_pRenderer->put_FontSize(dOldSize);
|
||||
}
|
||||
GBool RedactOutputDev::beginType3Char(GfxState *pGState, double x, double y, double dx, double dy, CharCode code, Unicode *u, int uLen)
|
||||
{
|
||||
@ -527,13 +561,15 @@ void RedactOutputDev::setExtGState(const char* name)
|
||||
{
|
||||
if (m_sStates.empty())
|
||||
return;
|
||||
m_sStates.back().m_arrOp.push_back(std::make_pair("/" + std::string(name), "gs"));
|
||||
std::string sOp = "/" + std::string(name);
|
||||
m_sStates.back().m_arrOp.push_back(std::make_pair(sOp, "gs"));
|
||||
}
|
||||
void RedactOutputDev::setFillColorSpace(const char* name)
|
||||
{
|
||||
if (m_sStates.empty())
|
||||
return;
|
||||
m_sStates.back().m_arrOp.push_back(std::make_pair("/" + std::string(name), "cs"));
|
||||
std::string sOp = "/" + std::string(name);
|
||||
m_sStates.back().m_arrOp.push_back(std::make_pair(sOp, "cs"));
|
||||
}
|
||||
void RedactOutputDev::setFillColorN(Object* args, int numArgs)
|
||||
{
|
||||
@ -551,6 +587,34 @@ void RedactOutputDev::setFillColorN(Object* args, int numArgs)
|
||||
}
|
||||
m_sStates.back().m_arrOp.push_back(std::make_pair(sOp, "scn"));
|
||||
}
|
||||
void RedactOutputDev::setShading(GfxState *pGState, const char* name)
|
||||
{
|
||||
m_pRenderer->m_oCommandManager.Flush();
|
||||
|
||||
double dShiftX = 0, dShiftY = 0;
|
||||
DoTransform(pGState->getCTM(), &dShiftX, &dShiftY, true);
|
||||
|
||||
// TODO Нужно проверять Shading на отсечение?
|
||||
|
||||
m_pPage->GrSave();
|
||||
UpdateTransform();
|
||||
CStream* pStream = m_pPage->GetStream();
|
||||
for (int i = 0; i < m_sStates.size(); ++i)
|
||||
{
|
||||
for (int j = 0; j < m_sStates[i].m_arrOp.size(); ++j)
|
||||
{
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].first.c_str());
|
||||
pStream->WriteChar(' ');
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].second.c_str());
|
||||
pStream->WriteStr("\012");
|
||||
}
|
||||
}
|
||||
pStream->WriteEscapeName(name);
|
||||
pStream->WriteChar(' ');
|
||||
pStream->WriteStr("sh");
|
||||
pStream->WriteStr("\012");
|
||||
m_pPage->GrRestore();
|
||||
}
|
||||
//----- image drawing
|
||||
void RedactOutputDev::drawImageMask(GfxState *pGState, Object *pRef, Stream *pStream, int nWidth, int nHeight, GBool bInvert, GBool bInlineImage, GBool interpolate)
|
||||
{
|
||||
@ -659,54 +723,22 @@ void RedactOutputDev::drawImage(GfxState *pGState, Ref id, const char* name)
|
||||
DoTransform(pGState->getCTM(), &dShiftX, &dShiftY, true);
|
||||
|
||||
// TODO пока что исключается всё изображение
|
||||
Object oImage;
|
||||
if (!m_pXref->fetch(id.num, id.gen, &oImage)->isStream())
|
||||
{
|
||||
oImage.free();
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO нужно учитывать Matrix у формы
|
||||
Dict* pDict = oImage.streamGetDict();
|
||||
Object obj1;
|
||||
if (pDict->lookup("Width", &obj1)->isNull())
|
||||
{
|
||||
obj1.free();
|
||||
if (!pDict->lookup("W", &obj1)->isNum())
|
||||
{
|
||||
obj1.free(); oImage.free();
|
||||
return;
|
||||
}
|
||||
}
|
||||
double width = obj1.getNum();
|
||||
obj1.free();
|
||||
if (width <= 0)
|
||||
{
|
||||
oImage.free();
|
||||
return;
|
||||
}
|
||||
|
||||
if (pDict->lookup("Height", &obj1)->isNull())
|
||||
{
|
||||
obj1.free();
|
||||
if (!pDict->lookup("H", &obj1)->isNum())
|
||||
{
|
||||
obj1.free(); oImage.free();
|
||||
return;
|
||||
}
|
||||
}
|
||||
double height = obj1.getNum();
|
||||
obj1.free();
|
||||
if (height <= 0)
|
||||
{
|
||||
oImage.free();
|
||||
return;
|
||||
}
|
||||
|
||||
double dXmin = 0, dYmin = 0, dXmax = width, dYmax = height;
|
||||
double dXmin = 0, dYmin = 0, dXmax = 1, dYmax = 1;
|
||||
Transform(m_arrMatrix, dXmin, dYmin, &dXmin, &dYmin);
|
||||
Transform(m_arrMatrix, dXmax, dYmax, &dXmax, &dYmax);
|
||||
|
||||
for (int i = 0; i < m_arrQuadPoints.size(); i += 4)
|
||||
{
|
||||
double xMin = m_arrQuadPoints[i + 0];
|
||||
double yMin = m_arrQuadPoints[i + 1];
|
||||
double xMax = m_arrQuadPoints[i + 2];
|
||||
double yMax = m_arrQuadPoints[i + 3];
|
||||
|
||||
if (!(dXmax < xMin || dXmin > xMax || dYmax < yMin || dYmin > yMax))
|
||||
return;
|
||||
}
|
||||
|
||||
m_pPage->GrSave();
|
||||
UpdateTransform();
|
||||
CStream* pStream = m_pPage->GetStream();
|
||||
@ -720,22 +752,6 @@ void RedactOutputDev::drawImage(GfxState *pGState, Ref id, const char* name)
|
||||
pStream->WriteStr("\012");
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0; i < m_arrQuadPoints.size(); i += 4)
|
||||
{
|
||||
double xMin = m_arrQuadPoints[i + 0];
|
||||
double yMin = m_arrQuadPoints[i + 1];
|
||||
double xMax = m_arrQuadPoints[i + 2];
|
||||
double yMax = m_arrQuadPoints[i + 3];
|
||||
|
||||
if (!(dXmax < xMin || dXmin > xMax || dYmax < yMin || dYmin > yMax))
|
||||
{
|
||||
m_pPage->GrRestore();
|
||||
return;
|
||||
}
|
||||
}
|
||||
oImage.free();
|
||||
|
||||
m_pPage->ExecuteXObject(name);
|
||||
m_pPage->GrRestore();
|
||||
}
|
||||
@ -1416,9 +1432,10 @@ void RedactOutputDev::DrawPath(const LONG& lType)
|
||||
{
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].first.c_str());
|
||||
pStream->WriteChar(' ');
|
||||
pStream->WriteStr(m_sStates[i].m_arrOp[j].second.c_str());
|
||||
std::string sOp = m_sStates[i].m_arrOp[j].second;
|
||||
pStream->WriteStr(sOp.c_str());
|
||||
pStream->WriteStr("\012");
|
||||
if (m_sStates[i].m_arrOp[j].second == "cs")
|
||||
if (sOp == "cs" || sOp == "sc" || sOp == "scn")
|
||||
bCS = true;
|
||||
}
|
||||
}
|
||||
|
||||
@ -157,6 +157,7 @@ namespace PdfWriter
|
||||
virtual void setExtGState(const char* name) override;
|
||||
virtual void setFillColorSpace(const char* name) override;
|
||||
virtual void setFillColorN(Object* args, int numArgs) override;
|
||||
virtual void setShading(GfxState *state, const char* name) override;
|
||||
//----- image drawing
|
||||
virtual void drawImageMask(GfxState *pGState, Object *pRef, Stream *pStream, int nWidth, int nHeight, GBool bInvert, GBool bInlineImage, GBool interpolate) override;
|
||||
virtual void setSoftMaskFromImageMask(GfxState *pGState, Object *pRef, Stream *pStream, int nWidth, int nHeight, GBool bInvert, GBool bInlineImage, GBool interpolate) override;
|
||||
|
||||
@ -35,6 +35,7 @@
|
||||
#include "Pages.h"
|
||||
#include "FontCidTT.h"
|
||||
#include "../PdfWriter.h"
|
||||
#include "Streams.h"
|
||||
|
||||
//----------------------------------------------------------------------------------------
|
||||
//
|
||||
@ -120,6 +121,7 @@ void CCommandManager::Flush()
|
||||
{
|
||||
std::string sKey = U_TO_UTF8(sTextName);
|
||||
pPage->SetFontKeyAndSize(sKey.c_str(), dTextSize);
|
||||
pPage->SetFontType(pText->GetFontType());
|
||||
}
|
||||
}
|
||||
|
||||
@ -132,6 +134,7 @@ void CCommandManager::Flush()
|
||||
oTextLine.Flush(pPage);
|
||||
nColorSize = nColorSize2;
|
||||
dColor[0] = dColor2[0];
|
||||
pPage->SetFillG(dColor[0]);
|
||||
pPage->SetStrokeG(dColor[0]);
|
||||
}
|
||||
else if (nColorSize2 == 3 && (nColorSize != nColorSize2 || dColor[0] != dColor2[0] || dColor[1] != dColor2[1] || dColor[2] != dColor2[2]))
|
||||
@ -141,6 +144,7 @@ void CCommandManager::Flush()
|
||||
dColor[0] = dColor2[0];
|
||||
dColor[1] = dColor2[1];
|
||||
dColor[2] = dColor2[2];
|
||||
pPage->SetFillRGB(dColor[0], dColor[1], dColor[2]);
|
||||
pPage->SetStrokeRGB(dColor[0], dColor[1], dColor[2]);
|
||||
}
|
||||
else if (nColorSize2 == 4 && (nColorSize != nColorSize2 || dColor[0] != dColor2[0] || dColor[1] != dColor2[1] || dColor[2] != dColor2[2] || dColor[3] != dColor2[3]))
|
||||
@ -151,6 +155,7 @@ void CCommandManager::Flush()
|
||||
dColor[1] = dColor2[1];
|
||||
dColor[2] = dColor2[2];
|
||||
dColor[3] = dColor2[3];
|
||||
pPage->SetFillCMYK(dColor[0], dColor[1], dColor[2], dColor[3]);
|
||||
pPage->SetStrokeCMYK(dColor[0], dColor[1], dColor[2], dColor[3]);
|
||||
}
|
||||
}
|
||||
|
||||
@ -73,6 +73,7 @@ public:
|
||||
m_dY = dY;
|
||||
m_pFont = NULL;
|
||||
m_dSize = -1;
|
||||
m_nType = PdfWriter::EFontType::fontUnknownType;
|
||||
m_lColor = 0;
|
||||
m_nAlpha = 255;
|
||||
m_dCharSpace = 0;
|
||||
@ -121,6 +122,10 @@ public:
|
||||
{
|
||||
m_dSize = dSize;
|
||||
}
|
||||
inline void SetType(PdfWriter::EFontType oType)
|
||||
{
|
||||
m_nType = oType;
|
||||
}
|
||||
inline void SetColor(const LONG& lColor)
|
||||
{
|
||||
m_lColor = lColor;
|
||||
@ -185,6 +190,10 @@ public:
|
||||
{
|
||||
return m_dSize;
|
||||
}
|
||||
inline PdfWriter::EFontType GetFontType() const
|
||||
{
|
||||
return m_nType;
|
||||
}
|
||||
inline LONG GetColor() const
|
||||
{
|
||||
return m_lColor;
|
||||
@ -250,6 +259,7 @@ private:
|
||||
bool m_bNeedDoItalic;
|
||||
bool m_bNeedDoBold;
|
||||
double m_dSize;
|
||||
PdfWriter::EFontType m_nType;
|
||||
LONG m_lColor;
|
||||
BYTE m_nAlpha;
|
||||
double m_dCharSpace;
|
||||
@ -1634,7 +1644,7 @@ private:
|
||||
private:
|
||||
CPdfWriter* m_pRenderer;
|
||||
std::vector<CRendererCommandBase*> m_vCommands;
|
||||
CTransform m_oTransform;
|
||||
CTransform m_oTransform;
|
||||
};
|
||||
struct TDestinationInfo
|
||||
{
|
||||
|
||||
@ -2370,6 +2370,12 @@ void Gfx::opShFill(Object args[], int numArgs) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (out->useNameOp())
|
||||
{
|
||||
out->setShading(state, args[0].getName());
|
||||
return;
|
||||
}
|
||||
|
||||
// save current graphics state
|
||||
savedState = saveStateStack();
|
||||
|
||||
|
||||
@ -194,6 +194,7 @@ public:
|
||||
virtual void setExtGState(const char* name) {}
|
||||
virtual void setFillColorSpace(const char* name) {}
|
||||
virtual void setFillColorN(Object* args, int numArgs) {}
|
||||
virtual void setShading(GfxState *state, const char* name) {}
|
||||
|
||||
//----- image drawing
|
||||
virtual void drawImageMask(GfxState *state, Object *ref, Stream *str,
|
||||
|
||||
Reference in New Issue
Block a user