Home | History | Annotate | Download | only in pdfwindow
      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 "fpdfsdk/include/pdfwindow/PWL_Icon.h"
      8 #include "fpdfsdk/include/pdfwindow/PWL_Utils.h"
      9 #include "fpdfsdk/include/pdfwindow/PWL_Wnd.h"
     10 
     11 CPWL_Image::CPWL_Image() : m_pPDFStream(NULL) {}
     12 
     13 CPWL_Image::~CPWL_Image() {}
     14 
     15 CFX_ByteString CPWL_Image::GetImageAppStream() {
     16   CFX_ByteTextBuf sAppStream;
     17 
     18   CFX_ByteString sAlias = GetImageAlias();
     19   CPDF_Rect rcPlate = GetClientRect();
     20   CFX_Matrix mt;
     21   mt.SetReverse(GetImageMatrix());
     22 
     23   FX_FLOAT fHScale = 1.0f;
     24   FX_FLOAT fVScale = 1.0f;
     25   GetScale(fHScale, fVScale);
     26 
     27   FX_FLOAT fx = 0.0f;
     28   FX_FLOAT fy = 0.0f;
     29   GetImageOffset(fx, fy);
     30 
     31   if (m_pPDFStream && sAlias.GetLength() > 0) {
     32     sAppStream << "q\n";
     33     sAppStream << rcPlate.left << " " << rcPlate.bottom << " "
     34                << rcPlate.right - rcPlate.left << " "
     35                << rcPlate.top - rcPlate.bottom << " re W n\n";
     36 
     37     sAppStream << fHScale << " 0 0 " << fVScale << " " << rcPlate.left + fx
     38                << " " << rcPlate.bottom + fy << " cm\n";
     39     sAppStream << mt.GetA() << " " << mt.GetB() << " " << mt.GetC() << " "
     40                << mt.GetD() << " " << mt.GetE() << " " << mt.GetF() << " cm\n";
     41 
     42     sAppStream << "0 g 0 G 1 w /" << sAlias << " Do\n"
     43                << "Q\n";
     44   }
     45 
     46   return sAppStream.GetByteString();
     47 }
     48 
     49 void CPWL_Image::SetPDFStream(CPDF_Stream* pStream) {
     50   m_pPDFStream = pStream;
     51 }
     52 
     53 CPDF_Stream* CPWL_Image::GetPDFStream() {
     54   return m_pPDFStream;
     55 }
     56 
     57 void CPWL_Image::GetImageSize(FX_FLOAT& fWidth, FX_FLOAT& fHeight) {
     58   fWidth = 0.0f;
     59   fHeight = 0.0f;
     60 
     61   if (m_pPDFStream) {
     62     if (CPDF_Dictionary* pDict = m_pPDFStream->GetDict()) {
     63       CPDF_Rect rect = pDict->GetRect("BBox");
     64 
     65       fWidth = rect.right - rect.left;
     66       fHeight = rect.top - rect.bottom;
     67     }
     68   }
     69 }
     70 
     71 CFX_Matrix CPWL_Image::GetImageMatrix() {
     72   if (m_pPDFStream) {
     73     if (CPDF_Dictionary* pDict = m_pPDFStream->GetDict()) {
     74       return pDict->GetMatrix("Matrix");
     75     }
     76   }
     77 
     78   return CFX_Matrix();
     79 }
     80 
     81 CFX_ByteString CPWL_Image::GetImageAlias() {
     82   if (!m_sImageAlias.IsEmpty())
     83     return m_sImageAlias;
     84 
     85   if (m_pPDFStream) {
     86     if (CPDF_Dictionary* pDict = m_pPDFStream->GetDict()) {
     87       return pDict->GetString("Name");
     88     }
     89   }
     90 
     91   return CFX_ByteString();
     92 }
     93 
     94 void CPWL_Image::SetImageAlias(const FX_CHAR* sImageAlias) {
     95   m_sImageAlias = sImageAlias;
     96 }
     97 
     98 void CPWL_Image::GetScale(FX_FLOAT& fHScale, FX_FLOAT& fVScale) {
     99   fHScale = 1.0f;
    100   fVScale = 1.0f;
    101 }
    102 
    103 void CPWL_Image::GetImageOffset(FX_FLOAT& x, FX_FLOAT& y) {
    104   x = 0.0f;
    105   y = 0.0f;
    106 }
    107 
    108 CPWL_Icon::CPWL_Icon() : m_pIconFit(NULL) {}
    109 
    110 CPWL_Icon::~CPWL_Icon() {}
    111 
    112 int32_t CPWL_Icon::GetScaleMethod() {
    113   if (m_pIconFit)
    114     return m_pIconFit->GetScaleMethod();
    115 
    116   return 0;
    117 }
    118 
    119 FX_BOOL CPWL_Icon::IsProportionalScale() {
    120   if (m_pIconFit)
    121     return m_pIconFit->IsProportionalScale();
    122 
    123   return FALSE;
    124 }
    125 
    126 void CPWL_Icon::GetIconPosition(FX_FLOAT& fLeft, FX_FLOAT& fBottom) {
    127   if (m_pIconFit) {
    128     fLeft = 0.0f;
    129     fBottom = 0.0f;
    130     CPDF_Array* pA =
    131         m_pIconFit->m_pDict ? m_pIconFit->m_pDict->GetArray("A") : NULL;
    132     if (pA) {
    133       FX_DWORD dwCount = pA->GetCount();
    134       if (dwCount > 0)
    135         fLeft = pA->GetNumber(0);
    136       if (dwCount > 1)
    137         fBottom = pA->GetNumber(1);
    138     }
    139   } else {
    140     fLeft = 0.0f;
    141     fBottom = 0.0f;
    142   }
    143 }
    144 
    145 FX_BOOL CPWL_Icon::GetFittingBounds() {
    146   if (m_pIconFit)
    147     return m_pIconFit->GetFittingBounds();
    148 
    149   return FALSE;
    150 }
    151 
    152 void CPWL_Icon::GetScale(FX_FLOAT& fHScale, FX_FLOAT& fVScale) {
    153   fHScale = 1.0f;
    154   fVScale = 1.0f;
    155 
    156   if (m_pPDFStream) {
    157     FX_FLOAT fImageWidth, fImageHeight;
    158     FX_FLOAT fPlateWidth, fPlateHeight;
    159 
    160     CPDF_Rect rcPlate = GetClientRect();
    161     fPlateWidth = rcPlate.right - rcPlate.left;
    162     fPlateHeight = rcPlate.top - rcPlate.bottom;
    163 
    164     GetImageSize(fImageWidth, fImageHeight);
    165 
    166     int32_t nScaleMethod = GetScaleMethod();
    167 
    168     switch (nScaleMethod) {
    169       default:
    170       case 0:
    171         fHScale = fPlateWidth / PWL_MAX(fImageWidth, 1.0f);
    172         fVScale = fPlateHeight / PWL_MAX(fImageHeight, 1.0f);
    173         break;
    174       case 1:
    175         if (fPlateWidth < fImageWidth)
    176           fHScale = fPlateWidth / PWL_MAX(fImageWidth, 1.0f);
    177         if (fPlateHeight < fImageHeight)
    178           fVScale = fPlateHeight / PWL_MAX(fImageHeight, 1.0f);
    179         break;
    180       case 2:
    181         if (fPlateWidth > fImageWidth)
    182           fHScale = fPlateWidth / PWL_MAX(fImageWidth, 1.0f);
    183         if (fPlateHeight > fImageHeight)
    184           fVScale = fPlateHeight / PWL_MAX(fImageHeight, 1.0f);
    185         break;
    186       case 3:
    187         break;
    188     }
    189 
    190     FX_FLOAT fMinScale;
    191     if (IsProportionalScale()) {
    192       fMinScale = PWL_MIN(fHScale, fVScale);
    193       fHScale = fMinScale;
    194       fVScale = fMinScale;
    195     }
    196   }
    197 }
    198 
    199 void CPWL_Icon::GetImageOffset(FX_FLOAT& x, FX_FLOAT& y) {
    200   FX_FLOAT fLeft, fBottom;
    201 
    202   GetIconPosition(fLeft, fBottom);
    203   x = 0.0f;
    204   y = 0.0f;
    205 
    206   FX_FLOAT fImageWidth, fImageHeight;
    207   GetImageSize(fImageWidth, fImageHeight);
    208 
    209   FX_FLOAT fHScale, fVScale;
    210   GetScale(fHScale, fVScale);
    211 
    212   FX_FLOAT fImageFactWidth = fImageWidth * fHScale;
    213   FX_FLOAT fImageFactHeight = fImageHeight * fVScale;
    214 
    215   FX_FLOAT fPlateWidth, fPlateHeight;
    216   CPDF_Rect rcPlate = GetClientRect();
    217   fPlateWidth = rcPlate.right - rcPlate.left;
    218   fPlateHeight = rcPlate.top - rcPlate.bottom;
    219 
    220   x = (fPlateWidth - fImageFactWidth) * fLeft;
    221   y = (fPlateHeight - fImageFactHeight) * fBottom;
    222 }
    223