1// Copyright 2014 PDFium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6 7#include "../../include/pdfwindow/PDFWindow.h" 8#include "../../include/pdfwindow/PWL_Wnd.h" 9#include "../../include/pdfwindow/PWL_Icon.h" 10#include "../../include/pdfwindow/PWL_Utils.h" 11 12/* ------------------------------- CPWL_Image ---------------------------------- */ 13 14CPWL_Image::CPWL_Image() : m_pPDFStream(NULL) 15{ 16} 17 18CPWL_Image::~CPWL_Image() 19{ 20} 21 22CFX_ByteString CPWL_Image::GetImageAppStream() 23{ 24 CFX_ByteTextBuf sAppStream; 25 26 CFX_ByteString sAlias = this->GetImageAlias(); 27 CPDF_Rect rcPlate = GetClientRect(); 28 CPDF_Matrix mt; 29 mt.SetReverse(GetImageMatrix()); 30 31 FX_FLOAT fHScale = 1.0f; 32 FX_FLOAT fVScale = 1.0f; 33 GetScale(fHScale,fVScale); 34 35 FX_FLOAT fx = 0.0f; 36 FX_FLOAT fy = 0.0f; 37 GetImageOffset(fx,fy); 38 39 if (m_pPDFStream && sAlias.GetLength()>0) 40 { 41 sAppStream << "q\n"; 42 sAppStream << rcPlate.left << " " << rcPlate.bottom << " " 43 << rcPlate.right - rcPlate.left << " " << rcPlate.top - rcPlate.bottom << " re W n\n"; 44 45 sAppStream << fHScale << " 0 0 " << fVScale << " " << rcPlate.left + fx << " " << rcPlate.bottom + fy << " cm\n"; 46 sAppStream << mt.GetA() << " " << mt.GetB() << " " << mt.GetC() << " " << mt.GetD() << " " << mt.GetE() << " " << mt.GetF() << " cm\n"; 47 48 sAppStream << "0 g 0 G 1 w /" << sAlias << " Do\n" << "Q\n"; 49 } 50 51 return sAppStream.GetByteString(); 52} 53 54void CPWL_Image::SetPDFStream(CPDF_Stream * pStream) 55{ 56 m_pPDFStream = pStream; 57} 58 59CPDF_Stream * CPWL_Image::GetPDFStream() 60{ 61 return this->m_pPDFStream; 62} 63 64void CPWL_Image::GetImageSize(FX_FLOAT & fWidth,FX_FLOAT & fHeight) 65{ 66 fWidth = 0.0f; 67 fHeight = 0.0f; 68 69 if (m_pPDFStream) 70 { 71 if (CPDF_Dictionary * pDict = m_pPDFStream->GetDict()) 72 { 73 CPDF_Rect rect = pDict->GetRect("BBox"); 74 75 fWidth = rect.right - rect.left; 76 fHeight = rect.top - rect.bottom; 77 } 78 } 79} 80 81CPDF_Matrix CPWL_Image::GetImageMatrix() 82{ 83 if (m_pPDFStream) 84 { 85 if (CPDF_Dictionary * pDict = m_pPDFStream->GetDict()) 86 { 87 return pDict->GetMatrix("Matrix"); 88 } 89 } 90 91 return CPDF_Matrix(); 92} 93 94CFX_ByteString CPWL_Image::GetImageAlias() 95{ 96 if (m_sImageAlias.IsEmpty()) 97 { 98 if (m_pPDFStream) 99 { 100 if (CPDF_Dictionary * pDict = m_pPDFStream->GetDict()) 101 { 102 return pDict->GetString("Name"); 103 } 104 } 105 } 106 else 107 return m_sImageAlias; 108 109 return CFX_ByteString(); 110} 111 112void CPWL_Image::SetImageAlias(FX_LPCSTR sImageAlias) 113{ 114 m_sImageAlias = sImageAlias; 115} 116 117void CPWL_Image::GetScale(FX_FLOAT & fHScale,FX_FLOAT & fVScale) 118{ 119 fHScale = 1.0f; 120 fVScale = 1.0f; 121} 122 123 124void CPWL_Image::GetImageOffset(FX_FLOAT & x,FX_FLOAT & y) 125{ 126 x = 0.0f; 127 y = 0.0f; 128} 129 130/* ------------------------------- CPWL_Icon ---------------------------------- */ 131 132CPWL_Icon::CPWL_Icon() : m_pIconFit(NULL) 133{ 134} 135 136CPWL_Icon::~CPWL_Icon() 137{ 138} 139 140FX_INT32 CPWL_Icon::GetScaleMethod() 141{ 142 if (m_pIconFit) 143 return m_pIconFit->GetScaleMethod(); 144 145 return 0; 146} 147 148FX_BOOL CPWL_Icon::IsProportionalScale() 149{ 150 if (m_pIconFit) 151 return m_pIconFit->IsProportionalScale(); 152 153 return FALSE; 154} 155 156void CPWL_Icon::GetIconPosition(FX_FLOAT & fLeft, FX_FLOAT & fBottom) 157{ 158 if (m_pIconFit) 159 { 160 //m_pIconFit->GetIconPosition(fLeft,fBottom); 161 fLeft = 0.0f; 162 fBottom = 0.0f; 163 CPDF_Array* pA = m_pIconFit->m_pDict ? m_pIconFit->m_pDict->GetArray("A") : NULL; 164 if (pA != NULL) 165 { 166 FX_DWORD dwCount = pA->GetCount(); 167 if (dwCount > 0) fLeft = pA->GetNumber(0); 168 if (dwCount > 1) fBottom = pA->GetNumber(1); 169 } 170 } 171 else 172 { 173 fLeft = 0.0f; 174 fBottom = 0.0f; 175 } 176} 177 178FX_BOOL CPWL_Icon::GetFittingBounds() 179{ 180 if (m_pIconFit) 181 return m_pIconFit->GetFittingBounds(); 182 183 return FALSE; 184} 185 186void CPWL_Icon::GetScale(FX_FLOAT & fHScale,FX_FLOAT & fVScale) 187{ 188 fHScale = 1.0f; 189 fVScale = 1.0f; 190 191 if (m_pPDFStream) 192 { 193 FX_FLOAT fImageWidth,fImageHeight; 194 FX_FLOAT fPlateWidth,fPlateHeight; 195 196 CPDF_Rect rcPlate = this->GetClientRect(); 197 fPlateWidth = rcPlate.right - rcPlate.left; 198 fPlateHeight = rcPlate.top - rcPlate.bottom; 199 200 GetImageSize(fImageWidth,fImageHeight); 201 202 FX_INT32 nScaleMethod = this->GetScaleMethod(); 203 204 /* 205 enum ScaleMethod 206 { 207 Always = 0, //A, Always scale 208 Bigger, //B, Scale only when the icon is bigger than the annotation rectangle 209 Smaller, //S, Scale only when the icon is smaller then the annotation rectangle 210 Never //N, Never scale 211 }; 212 */ 213 214 switch (nScaleMethod) 215 { 216 default: 217 case 0: 218 fHScale = fPlateWidth / PWL_MAX(fImageWidth,1.0f); 219 fVScale = fPlateHeight / PWL_MAX(fImageHeight,1.0f); 220 break; 221 case 1: 222 if (fPlateWidth < fImageWidth) 223 fHScale = fPlateWidth / PWL_MAX(fImageWidth,1.0f); 224 if (fPlateHeight < fImageHeight) 225 fVScale = fPlateHeight / PWL_MAX(fImageHeight,1.0f); 226 break; 227 case 2: 228 if (fPlateWidth > fImageWidth) 229 fHScale = fPlateWidth / PWL_MAX(fImageWidth,1.0f); 230 if (fPlateHeight > fImageHeight) 231 fVScale = fPlateHeight / PWL_MAX(fImageHeight,1.0f); 232 break; 233 case 3: 234 break; 235 } 236 237 FX_FLOAT fMinScale; 238 if (IsProportionalScale()) 239 { 240 fMinScale = PWL_MIN(fHScale,fVScale); 241 fHScale = fMinScale; 242 fVScale = fMinScale; 243 } 244 } 245} 246 247void CPWL_Icon::GetImageOffset(FX_FLOAT & x,FX_FLOAT & y) 248{ 249 FX_FLOAT fLeft,fBottom; 250 251 this->GetIconPosition(fLeft,fBottom); 252 x = 0.0f; 253 y = 0.0f; 254 255 FX_FLOAT fImageWidth,fImageHeight; 256 GetImageSize(fImageWidth,fImageHeight); 257 258 FX_FLOAT fHScale,fVScale; 259 GetScale(fHScale,fVScale); 260 261 FX_FLOAT fImageFactWidth = fImageWidth * fHScale; 262 FX_FLOAT fImageFactHeight = fImageHeight * fVScale; 263 264 FX_FLOAT fPlateWidth,fPlateHeight; 265 CPDF_Rect rcPlate = this->GetClientRect(); 266 fPlateWidth = rcPlate.right - rcPlate.left; 267 fPlateHeight = rcPlate.top - rcPlate.bottom; 268 269 x = (fPlateWidth - fImageFactWidth) * fLeft; 270 y = (fPlateHeight - fImageFactHeight) * fBottom; 271} 272 273