summaryrefslogtreecommitdiff
path: root/src/WNT/WNT_PixMap.cxx
blob: f003cbd81b4e5b2a2ad8204a29507f537e947e21 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
// File   WNT_PixMap.cxx
// Created  20 December 1999
// Author VKH
//    SZV/GG IMP100701 Add the "depth" field and method
//              to the pixmap object.

//-Copyright  MatraDatavision 1991,1992,1999

//-Version

// include windows.h first to have all definitions available
#include <windows.h>

#include <WNT_PixMap.ixx>

#include <WNT_Window.hxx>

extern int DumpBitmapToFile( Handle(WNT_GraphicDevice)&, HDC, HBITMAP, char* );

#include <WNT_GraphicDevice.hxx>

Standard_Integer WNT_PixMap::PreferedDepth(
  const Handle(Aspect_Window)& aWindow,
  const Standard_Integer aCDepth) const
{
  Standard_Integer theDepth = 32;
  if (aCDepth <= 1) theDepth = 1;
  else if (aCDepth <=  4) theDepth =  4;
  else if (aCDepth <=  8) theDepth =  8;
  else if (aCDepth <= 16) theDepth = 16;
  else if (aCDepth <= 24) theDepth = 24;

  return theDepth;
}

///////////////////////////////////////////////////////////////////////////////////////
WNT_PixMap::WNT_PixMap ( const Handle(Aspect_Window)& aWindow,
                         const Standard_Integer aWidth,
                         const Standard_Integer anHeight,
                         const Standard_Integer aCDepth ) :
Aspect_PixMap(aWidth, anHeight, PreferedDepth(aWindow, aCDepth))
{
  myWND = aWindow;

  const Handle(WNT_Window)& hWindow = Handle(WNT_Window)::DownCast(aWindow);
  HDC hdc = GetDC ( (HWND)(hWindow->HWindow()) );
  HDC hdcMem = CreateCompatibleDC ( hdc );
  ReleaseDC ( (HWND)(hWindow->HWindow()), hdc );
  myDC = hdcMem;

  Standard_Integer theNbColors = 0, theFormat = PFD_TYPE_RGBA;

#ifdef BUG  // Our OpenGl driver supports only RGB mode.
  //WIL001: Color table can not be initialized - do not use
  if (myDepth <= 8)
  {
    theNbColors = (1 << myDepth);
    theFormat = PFD_TYPE_COLORINDEX;
  }
#endif

  Standard_Integer sizeBmi = Standard_Integer(sizeof(BITMAPINFO)+sizeof(RGBQUAD)*theNbColors);
  PBITMAPINFO pBmi = (PBITMAPINFO)(new char[sizeBmi]);
  ZeroMemory (  pBmi, sizeBmi  );

  pBmi->bmiHeader.biSize          = sizeof (BITMAPINFOHEADER); //sizeBmi
  pBmi->bmiHeader.biWidth         = aWidth;
  pBmi->bmiHeader.biHeight        = anHeight;
  pBmi->bmiHeader.biPlanes        = 1;
  pBmi->bmiHeader.biBitCount      = (WORD)myDepth; //WIL001: was 24
  pBmi->bmiHeader.biCompression   = BI_RGB;

  LPVOID ppvBits;
  HBITMAP hBmp = CreateDIBSection ( hdcMem, pBmi, DIB_RGB_COLORS, &ppvBits, NULL, 0 );
  if ( !hBmp )
    Aspect_PixmapDefinitionError::Raise ( "CreateDIBSection" );
  SelectBitmap ( hdcMem, hBmp );
  myBitmap = hBmp;

  delete[] pBmi;

  if (myDepth > 1) {

    PIXELFORMATDESCRIPTOR pfd;
    ZeroMemory (  &pfd, sizeof (PIXELFORMATDESCRIPTOR)  );
    pfd.nSize           =  sizeof (PIXELFORMATDESCRIPTOR);
    pfd.nVersion        =  1;
    pfd.dwFlags         =  PFD_SUPPORT_OPENGL | PFD_DRAW_TO_BITMAP;
    pfd.iPixelType      =  (BYTE)theFormat; //WIL001: was PFD_TYPE_RGBA
    pfd.cColorBits      =  (BYTE)myDepth; //WIL001: was 24
    pfd.cDepthBits      =  24;//
    pfd.iLayerType      =  PFD_MAIN_PLANE;

    Standard_Integer iPf = ChoosePixelFormat(hdcMem, &pfd);
    if ( !iPf )
      Aspect_PixmapDefinitionError::Raise ( "ChoosePixelFormat" );

    if ( !DescribePixelFormat ( hdcMem, iPf, sizeof(PIXELFORMATDESCRIPTOR), &pfd ) )
      Aspect_PixmapDefinitionError::Raise ( "DescribePixelFormat" );

    if ( !SetPixelFormat(hdcMem, iPf, &pfd) )
      Aspect_PixmapDefinitionError::Raise ( "SetPixelFormat" );
  }
}

///////////////////////////////
void WNT_PixMap::Destroy ()
{
  if ( myDC     ) DeleteDC ( (HDC)myDC );
  if ( myBitmap ) DeleteObject ( (HBITMAP)myBitmap );
}

////////////////////////////////////////////////////////////
Standard_Boolean WNT_PixMap::Dump ( const Standard_CString aFilename,
                                   const Standard_Real aGammaValue ) const
{
  // *** gamma correction must be implemented also on WNT system ...
  const Handle(WNT_Window) hWindow = Handle(WNT_Window)::DownCast(myWND);

  Handle(WNT_GraphicDevice) dev =
    Handle ( WNT_GraphicDevice )::DownCast ( hWindow->MyGraphicDevice );
  if ( dev.IsNull() ) return Standard_False;
  //Aspect_PixmapError::Raise ( "WNT_GraphicDevice is NULL" );

  return DumpBitmapToFile ( dev, (HDC)myDC, (HBITMAP)myBitmap, (Standard_PCharacter)aFilename );
}

////////////////////////////////////////////////////////////
Standard_Address WNT_PixMap::PixmapID() const
{
  return myDC;
}

Quantity_Color WNT_PixMap::PixelColor (const Standard_Integer ,
                                       const Standard_Integer ) const
{
  Aspect_PixmapError::Raise ("PixelColor() method not implemented!");
  return Quantity_Color (0.0, 0.0, 0.0, Quantity_TOC_RGB);
}