1 /////////////////////////////////////////////////////////////////////////////
4 // Author: Julian Smart
8 // Copyright: (c) Julian Smart
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
13 #pragma implementation "bitmap.h"
17 #define XtParent XTPARENT
22 #include "wx/palette.h"
23 #include "wx/bitmap.h"
26 #include "wx/control.h"
27 #include "wx/dcmemory.h"
31 #pragma message disable nosimpint
35 #pragma message enable nosimpint
38 #include "wx/motif/private.h"
44 IMPLEMENT_DYNAMIC_CLASS(wxBitmap
, wxGDIObject
)
45 IMPLEMENT_DYNAMIC_CLASS(wxMask
, wxObject
)
47 wxBitmapRefData::wxBitmapRefData()
57 m_pixmap
= (WXPixmap
) 0;
58 m_display
= (WXDisplay
*) 0;
60 m_freePixmap
= TRUE
; //TODO: necessary?
61 m_freeColors
= (unsigned long*) 0;
62 m_freeColorsCount
= 0;
64 // These 5 variables are for wxControl
65 m_insensPixmap
= (WXPixmap
) 0;
66 m_labelPixmap
= (WXPixmap
) 0;
67 m_armPixmap
= (WXPixmap
) 0;
68 m_image
= (WXImage
*) 0;
69 m_insensImage
= (WXImage
*) 0;
72 wxBitmapRefData::~wxBitmapRefData()
75 XmDestroyPixmap (DefaultScreenOfDisplay ((Display
*) m_display
), (Pixmap
) m_labelPixmap
);
78 XmDestroyPixmap (DefaultScreenOfDisplay ((Display
*) m_display
), (Pixmap
) m_armPixmap
);
81 XmDestroyPixmap (DefaultScreenOfDisplay ((Display
*) m_display
), (Pixmap
) m_insensPixmap
);
85 XmUninstallImage ((XImage
*) m_image
);
86 XtFree ((char *) (XImage
*) m_image
);
91 XmUninstallImage ((XImage
*) m_insensImage
);
92 delete[] ((XImage
*) m_insensImage
)->data
;
93 XtFree ((char *) (XImage
*) m_insensImage
);
95 if (m_pixmap
&& m_freePixmap
)
96 XFreePixmap ((Display
*) m_display
, (Pixmap
) m_pixmap
);
100 int screen
= DefaultScreen((Display
*) m_display
);
101 Colormap cmp
= DefaultColormap((Display
*) m_display
,screen
);
103 for(llp
= 0;llp
< m_freeColorsCount
;llp
++)
104 XFreeColors((Display
*) m_display
, cmp
, &m_freeColors
[llp
], 1, 0L);
113 wxList
wxBitmap::sm_handlers
;
115 #define M_BMPDATA ((wxBitmapRefData *)m_refData)
121 if ( wxTheBitmapList
)
122 wxTheBitmapList
->AddBitmap(this);
125 wxBitmap::~wxBitmap()
128 wxTheBitmapList
->DeleteObject(this);
131 wxBitmap::wxBitmap(const char bits
[], int width
, int height
, int depth
)
133 m_refData
= new wxBitmapRefData
;
135 (void) Create((void*) bits
, wxBITMAP_TYPE_XBM_DATA
, width
, height
, depth
);
137 if ( wxTheBitmapList
)
138 wxTheBitmapList
->AddBitmap(this);
141 wxBitmap::wxBitmap(int w
, int h
, int d
)
143 (void)Create(w
, h
, d
);
145 if ( wxTheBitmapList
)
146 wxTheBitmapList
->AddBitmap(this);
149 wxBitmap::wxBitmap(void *data
, long type
, int width
, int height
, int depth
)
151 (void) Create(data
, type
, width
, height
, depth
);
153 if ( wxTheBitmapList
)
154 wxTheBitmapList
->AddBitmap(this);
157 wxBitmap::wxBitmap(const wxString
& filename
, long type
)
159 LoadFile(filename
, (int)type
);
161 if ( wxTheBitmapList
)
162 wxTheBitmapList
->AddBitmap(this);
165 // Create from XPM data
166 static wxControl
* sg_Control
= NULL
;
167 wxBitmap::wxBitmap(char **data
, wxControl
* control
)
169 // Pass the control to the Create function using a global
170 sg_Control
= control
;
172 (void) Create((void *)data
, wxBITMAP_TYPE_XPM_DATA
, 0, 0, 0);
174 sg_Control
= (wxControl
*) NULL
;
177 bool wxBitmap::CreateFromXpm(const char **bits
)
179 wxCHECK_MSG( bits
, FALSE
, _T("NULL pointer in wxBitmap::CreateFromXpm") );
181 return Create(bits
, wxBITMAP_TYPE_XPM_DATA
, 0, 0, 0);
184 bool wxBitmap::Create(int w
, int h
, int d
)
188 m_refData
= new wxBitmapRefData
;
191 d
= wxDisplayDepth();
193 M_BITMAPDATA
->m_width
= w
;
194 M_BITMAPDATA
->m_height
= h
;
195 M_BITMAPDATA
->m_depth
= d
;
196 M_BITMAPDATA
->m_freePixmap
= TRUE
;
198 Display
*dpy
= (Display
*) wxGetDisplay();
200 M_BITMAPDATA
->m_display
= dpy
; /* MATTHEW: [4] Remember the display */
202 M_BITMAPDATA
->m_pixmap
= (WXPixmap
) XCreatePixmap (dpy
, RootWindow (dpy
, DefaultScreen (dpy
)),
205 M_BITMAPDATA
->m_ok
= (M_BITMAPDATA
->m_pixmap
!= (WXPixmap
) 0) ;
206 return M_BITMAPDATA
->m_ok
;
209 bool wxBitmap::LoadFile(const wxString
& filename
, long type
)
213 m_refData
= new wxBitmapRefData
;
215 wxBitmapHandler
*handler
= FindHandler(type
);
217 if ( handler
== NULL
) {
219 if (!image
.LoadFile( filename
, type
)) return FALSE
;
222 *this = image
.ConvertToBitmap();
228 return handler
->LoadFile(this, filename
, type
, -1, -1);
231 bool wxBitmap::Create(void *data
, long type
, int width
, int height
, int depth
)
235 m_refData
= new wxBitmapRefData
;
237 wxBitmapHandler
*handler
= FindHandler(type
);
239 if ( handler
== NULL
) {
240 wxLogWarning("no data bitmap handler for type %d defined.", type
);
245 return handler
->Create(this, data
, type
, width
, height
, depth
);
248 bool wxBitmap::SaveFile(const wxString
& filename
, int type
, const wxPalette
*palette
)
250 wxBitmapHandler
*handler
= FindHandler(type
);
252 if ( handler
== NULL
) { // try wxImage
253 wxImage
image( *this );
254 if (image
.Ok()) return image
.SaveFile( filename
, type
);
258 return handler
->SaveFile(this, filename
, type
, palette
);
261 void wxBitmap::SetWidth(int w
)
264 m_refData
= new wxBitmapRefData
;
266 M_BITMAPDATA
->m_width
= w
;
269 void wxBitmap::SetHeight(int h
)
272 m_refData
= new wxBitmapRefData
;
274 M_BITMAPDATA
->m_height
= h
;
277 void wxBitmap::SetDepth(int d
)
280 m_refData
= new wxBitmapRefData
;
282 M_BITMAPDATA
->m_depth
= d
;
285 void wxBitmap::SetQuality(int q
)
288 m_refData
= new wxBitmapRefData
;
290 M_BITMAPDATA
->m_quality
= q
;
293 void wxBitmap::SetOk(bool isOk
)
296 m_refData
= new wxBitmapRefData
;
298 M_BITMAPDATA
->m_ok
= isOk
;
301 void wxBitmap::SetPalette(const wxPalette
& palette
)
304 m_refData
= new wxBitmapRefData
;
306 M_BITMAPDATA
->m_bitmapPalette
= palette
;
309 void wxBitmap::SetMask(wxMask
*mask
)
312 m_refData
= new wxBitmapRefData
;
314 M_BITMAPDATA
->m_bitmapMask
= mask
;
317 wxBitmap
wxBitmap::GetSubBitmap( const wxRect
& rect
) const
320 (rect
.x
>= 0) && (rect
.y
>= 0) &&
321 (rect
.x
+rect
.width
<= M_BMPDATA
->m_width
) && (rect
.y
+rect
.height
<= M_BMPDATA
->m_height
),
322 wxNullBitmap
, wxT("invalid bitmap or bitmap region") );
324 wxBitmap
ret( rect
.width
, rect
.height
, 0 );
325 wxASSERT_MSG( ret
.Ok(), wxT("GetSubBitmap error") );
327 // The remaining still TODO
331 void wxBitmap::AddHandler(wxBitmapHandler
*handler
)
333 sm_handlers
.Append(handler
);
336 void wxBitmap::InsertHandler(wxBitmapHandler
*handler
)
338 sm_handlers
.Insert(handler
);
341 bool wxBitmap::RemoveHandler(const wxString
& name
)
343 wxBitmapHandler
*handler
= FindHandler(name
);
346 sm_handlers
.DeleteObject(handler
);
353 wxBitmapHandler
*wxBitmap::FindHandler(const wxString
& name
)
355 wxNode
*node
= sm_handlers
.First();
358 wxBitmapHandler
*handler
= (wxBitmapHandler
*)node
->Data();
359 if ( handler
->GetName() == name
)
366 wxBitmapHandler
*wxBitmap::FindHandler(const wxString
& extension
, long bitmapType
)
368 wxNode
*node
= sm_handlers
.First();
371 wxBitmapHandler
*handler
= (wxBitmapHandler
*)node
->Data();
372 if ( handler
->GetExtension() == extension
&&
373 (bitmapType
== -1 || handler
->GetType() == bitmapType
) )
380 wxBitmapHandler
*wxBitmap::FindHandler(long bitmapType
)
382 wxNode
*node
= sm_handlers
.First();
385 wxBitmapHandler
*handler
= (wxBitmapHandler
*)node
->Data();
386 if (handler
->GetType() == bitmapType
)
399 m_pixmap
= (WXPixmap
) 0;
402 // Construct a mask from a bitmap and a colour indicating
403 // the transparent area
404 wxMask::wxMask(const wxBitmap
& bitmap
, const wxColour
& colour
)
406 m_pixmap
= (WXPixmap
) 0;
408 Create(bitmap
, colour
);
411 // Construct a mask from a bitmap and a palette index indicating
412 // the transparent area
413 wxMask::wxMask(const wxBitmap
& bitmap
, int paletteIndex
)
415 m_pixmap
= (WXPixmap
) 0;
417 Create(bitmap
, paletteIndex
);
420 // Construct a mask from a mono bitmap (copies the bitmap).
421 wxMask::wxMask(const wxBitmap
& bitmap
)
423 m_pixmap
= (WXPixmap
) 0;
430 // TODO: this may be the wrong display
432 XFreePixmap ((Display
*) wxGetDisplay(), (Pixmap
) m_pixmap
);
435 // Create a mask from a mono bitmap (copies the bitmap).
436 bool wxMask::Create(const wxBitmap
& WXUNUSED(bitmap
))
442 // Create a mask from a bitmap and a palette index indicating
443 // the transparent area
444 bool wxMask::Create(const wxBitmap
& WXUNUSED(bitmap
), int WXUNUSED(paletteIndex
))
450 // Create a mask from a bitmap and a colour indicating
451 // the transparent area
452 bool wxMask::Create(const wxBitmap
& WXUNUSED(bitmap
), const wxColour
& WXUNUSED(colour
))
462 IMPLEMENT_DYNAMIC_CLASS(wxBitmapHandler
, wxObject
)
464 bool wxBitmapHandler::Create(wxBitmap
*WXUNUSED(bitmap
), void *WXUNUSED(data
), long WXUNUSED(type
),
465 int WXUNUSED(width
), int WXUNUSED(height
), int WXUNUSED(depth
))
470 bool wxBitmapHandler::LoadFile(wxBitmap
*WXUNUSED(bitmap
), const wxString
& WXUNUSED(name
), long WXUNUSED(type
),
471 int WXUNUSED(desiredWidth
), int WXUNUSED(desiredHeight
))
476 bool wxBitmapHandler::SaveFile(wxBitmap
*WXUNUSED(bitmap
), const wxString
& WXUNUSED(name
), int WXUNUSED(type
),
477 const wxPalette
*WXUNUSED(palette
))
486 class WXDLLEXPORT wxXBMFileHandler
: public wxBitmapHandler
488 DECLARE_DYNAMIC_CLASS(wxXBMFileHandler
)
490 inline wxXBMFileHandler()
494 m_type
= wxBITMAP_TYPE_XBM
;
497 virtual bool LoadFile(wxBitmap
*bitmap
, const wxString
& name
, long flags
,
498 int desiredWidth
, int desiredHeight
);
500 IMPLEMENT_DYNAMIC_CLASS(wxXBMFileHandler
, wxBitmapHandler
)
502 bool wxXBMFileHandler::LoadFile(wxBitmap
*bitmap
, const wxString
& name
, long WXUNUSED(flags
),
503 int WXUNUSED(desiredWidth
), int WXUNUSED(desiredHeight
))
505 M_BITMAPHANDLERDATA
->m_freePixmap
= TRUE
;
511 Display
*dpy
= (Display
*) wxGetDisplay();
512 M_BITMAPDATA
->m_display
= (WXDisplay
*) dpy
;
514 int value
= XReadBitmapFile (dpy
, RootWindow (dpy
, DefaultScreen (dpy
)),
515 (char*) (const char*) name
, &w
, &h
, &pixmap
, &hotX
, &hotY
);
516 M_BITMAPHANDLERDATA
->m_width
= w
;
517 M_BITMAPHANDLERDATA
->m_height
= h
;
518 M_BITMAPHANDLERDATA
->m_depth
= 1;
519 M_BITMAPHANDLERDATA
->m_pixmap
= (WXPixmap
) pixmap
;
521 if ((value
== BitmapFileInvalid
) ||
522 (value
== BitmapOpenFailed
) ||
523 (value
== BitmapNoMemory
))
525 M_BITMAPHANDLERDATA
->m_ok
= FALSE
;
526 M_BITMAPHANDLERDATA
->m_pixmap
= (WXPixmap
) 0;
529 M_BITMAPHANDLERDATA
->m_ok
= TRUE
;
531 return M_BITMAPHANDLERDATA
->m_ok
;
534 class WXDLLEXPORT wxXBMDataHandler
: public wxBitmapHandler
536 DECLARE_DYNAMIC_CLASS(wxXBMDataHandler
)
538 inline wxXBMDataHandler()
542 m_type
= wxBITMAP_TYPE_XBM_DATA
;
545 virtual bool Create(wxBitmap
*bitmap
, void *data
, long flags
, int width
, int height
, int depth
= 1);
547 IMPLEMENT_DYNAMIC_CLASS(wxXBMDataHandler
, wxBitmapHandler
)
549 bool wxXBMDataHandler::Create( wxBitmap
*bitmap
, void *data
, long WXUNUSED(flags
),
550 int width
, int height
, int WXUNUSED(depth
))
552 M_BITMAPHANDLERDATA
->m_width
= width
;
553 M_BITMAPHANDLERDATA
->m_height
= height
;
554 M_BITMAPHANDLERDATA
->m_depth
= 1;
555 M_BITMAPHANDLERDATA
->m_freePixmap
= TRUE
;
557 Display
*dpy
= (Display
*) wxGetDisplay();
558 M_BITMAPHANDLERDATA
->m_display
= (WXDisplay
*) dpy
;
560 M_BITMAPHANDLERDATA
->m_pixmap
= (WXPixmap
) XCreateBitmapFromData (dpy
, RootWindow (dpy
, DefaultScreen (dpy
)), (char*) data
, width
, height
);
561 M_BITMAPHANDLERDATA
->m_ok
= (M_BITMAPHANDLERDATA
->m_pixmap
!= (WXPixmap
) 0) ;
563 // code for wxControl. TODO: can we avoid doing this until we need it?
564 // E.g. have CreateButtonPixmaps which is called on demand.
565 XImage
* image
= (XImage
*) XtMalloc (sizeof (XImage
));
566 image
->width
= width
;
567 image
->height
= height
;
568 image
->data
= (char*) data
;
571 image
->format
= XYBitmap
;
572 image
->byte_order
= LSBFirst
;
573 image
->bitmap_unit
= 8;
574 image
->bitmap_bit_order
= LSBFirst
;
575 image
->bitmap_pad
= 8;
576 image
->bytes_per_line
= (width
+ 7) >> 3;
579 sprintf (tmp
, "Im%x", (unsigned int) image
);
580 XmInstallImage (image
, tmp
);
582 // Build our manually stipped pixmap.
584 int bpl
= (width
+ 7) / 8;
585 char *data1
= new char[height
* bpl
];
586 char* bits
= (char*) data
;
588 for (i
= 0; i
< height
; i
++)
590 int mask
= i
% 2 ? 0x55 : 0xaa;
592 for (j
= 0; j
< bpl
; j
++)
593 data1
[i
* bpl
+ j
] = bits
[i
* bpl
+ j
] & mask
;
595 XImage
* insensImage
= (XImage
*) XtMalloc (sizeof (XImage
));
596 insensImage
->width
= width
;
597 insensImage
->height
= height
;
598 insensImage
->data
= data1
;
599 insensImage
->depth
= 1;
600 insensImage
->xoffset
= 0;
601 insensImage
->format
= XYBitmap
;
602 insensImage
->byte_order
= LSBFirst
;
603 insensImage
->bitmap_unit
= 8;
604 insensImage
->bitmap_bit_order
= LSBFirst
;
605 insensImage
->bitmap_pad
= 8;
606 insensImage
->bytes_per_line
= bpl
;
608 sprintf (tmp
, "Not%x", (unsigned int)insensImage
);
609 XmInstallImage (insensImage
, tmp
);
611 M_BITMAPHANDLERDATA
->m_image
= (WXImage
*) image
;
612 M_BITMAPHANDLERDATA
->m_insensImage
= (WXImage
*) insensImage
;
618 class WXDLLEXPORT wxXPMFileHandler
: public wxBitmapHandler
620 DECLARE_DYNAMIC_CLASS(wxXPMFileHandler
)
622 inline wxXPMFileHandler()
626 m_type
= wxBITMAP_TYPE_XPM
;
629 virtual bool LoadFile(wxBitmap
*bitmap
, const wxString
& name
, long flags
,
630 int desiredWidth
, int desiredHeight
);
631 virtual bool SaveFile(wxBitmap
*bitmap
, const wxString
& name
, int type
, const wxPalette
*palette
= NULL
);
634 IMPLEMENT_DYNAMIC_CLASS(wxXPMFileHandler
, wxBitmapHandler
)
636 bool wxXPMFileHandler::LoadFile( wxBitmap
*bitmap
, const wxString
& name
, long WXUNUSED(flags
),
637 int WXUNUSED(desiredWidth
), int WXUNUSED(desiredHeight
) )
639 Display
*dpy
= (Display
*) wxGetDisplay();
640 M_BITMAPHANDLERDATA
->m_display
= (WXDisplay
*) dpy
;
642 XpmAttributes xpmAttr
;
646 M_BITMAPHANDLERDATA
->m_ok
= FALSE
;
647 xpmAttr
.valuemask
= XpmReturnInfos
| XpmCloseness
;
648 xpmAttr
.closeness
= 40000;
649 int errorStatus
= XpmReadFileToPixmap(dpy
,
650 RootWindow(dpy
, DefaultScreen(dpy
)), (char*) (const char*) name
,
651 &pixmap
, &mask
, &xpmAttr
);
653 if (errorStatus
== XpmSuccess
)
655 M_BITMAPHANDLERDATA
->m_pixmap
= (WXPixmap
) pixmap
;
658 M_BITMAPHANDLERDATA
->m_bitmapMask
= new wxMask
;
659 M_BITMAPHANDLERDATA
->m_bitmapMask
->SetPixmap((WXPixmap
) mask
);
662 unsigned int depthRet
;
664 unsigned int widthRet
, heightRet
, borderWidthRet
;
665 Window rootWindowRet
;
666 XGetGeometry(dpy
, pixmap
, &rootWindowRet
, &xRet
, &yRet
,
667 &widthRet
, &heightRet
, &borderWidthRet
, &depthRet
);
669 M_BITMAPHANDLERDATA
->m_width
= xpmAttr
.width
;
670 M_BITMAPHANDLERDATA
->m_height
= xpmAttr
.height
;
673 if ( xpmAttr.npixels > 2 )
675 M_BITMAPHANDLERDATA->m_depth = 8; // TODO: next time not just a guess :-) ...
678 M_BITMAPHANDLERDATA->m_depth = 1; // mono
682 M_BITMAPHANDLERDATA
->m_depth
= depthRet
;
684 M_BITMAPHANDLERDATA
->m_numColors
= xpmAttr
.npixels
;
686 XpmFreeAttributes(&xpmAttr
);
688 M_BITMAPHANDLERDATA
->m_ok
= TRUE
;
692 // XpmDebugError(errorStatus, name);
693 M_BITMAPHANDLERDATA
->m_ok
= FALSE
;
698 bool wxXPMFileHandler::SaveFile( wxBitmap
*bitmap
, const wxString
& name
, int WXUNUSED(type
),
699 const wxPalette
*WXUNUSED(palette
))
701 if (M_BITMAPHANDLERDATA
->m_ok
&& M_BITMAPHANDLERDATA
->m_pixmap
)
703 Display
*dpy
= (Display
*) M_BITMAPHANDLERDATA
->m_display
;
704 int errorStatus
= XpmWriteFileFromPixmap(dpy
, (char*) (const char*) name
,
705 (Pixmap
) M_BITMAPHANDLERDATA
->m_pixmap
,
706 (M_BITMAPHANDLERDATA
->m_bitmapMask
? (Pixmap
) M_BITMAPHANDLERDATA
->m_bitmapMask
->GetPixmap() : (Pixmap
) 0),
707 (XpmAttributes
*) NULL
);
708 if (errorStatus
== XpmSuccess
)
717 class WXDLLEXPORT wxXPMDataHandler
: public wxBitmapHandler
719 DECLARE_DYNAMIC_CLASS(wxXPMDataHandler
)
721 inline wxXPMDataHandler()
725 m_type
= wxBITMAP_TYPE_XPM_DATA
;
728 virtual bool Create(wxBitmap
*bitmap
, void *data
, long flags
, int width
, int height
, int depth
= 1);
730 IMPLEMENT_DYNAMIC_CLASS(wxXPMDataHandler
, wxBitmapHandler
)
732 bool wxXPMDataHandler::Create( wxBitmap
*bitmap
, void *data
, long WXUNUSED(flags
),
733 int width
, int height
, int WXUNUSED(depth
))
735 M_BITMAPHANDLERDATA
->m_width
= width
;
736 M_BITMAPHANDLERDATA
->m_height
= height
;
737 M_BITMAPHANDLERDATA
->m_depth
= 1;
738 M_BITMAPHANDLERDATA
->m_freePixmap
= TRUE
;
740 Display
*dpy
= (Display
*) wxGetDisplay();
741 M_BITMAPHANDLERDATA
->m_display
= (WXDisplay
*) dpy
;
743 XpmAttributes xpmAttr
;
745 xpmAttr
.valuemask
= XpmReturnInfos
; /* nothing yet, but get infos back */
747 XpmColorSymbol symbolicColors
[4];
748 if (sg_Control
&& sg_Control
->GetMainWidget())
750 symbolicColors
[0].name
= "foreground";
751 symbolicColors
[0].value
= NULL
;
752 symbolicColors
[1].name
= "background";
753 symbolicColors
[1].value
= NULL
;
754 XtVaGetValues((Widget
) sg_Control
->GetMainWidget(),
755 XmNforeground
, &symbolicColors
[0].pixel
,
756 XmNbackground
, &symbolicColors
[1].pixel
,NULL
);
757 xpmAttr
.numsymbols
= 2;
758 xpmAttr
.colorsymbols
= symbolicColors
;
759 xpmAttr
.valuemask
|= XpmColorSymbols
; // add flag
764 int ErrorStatus
= XpmCreatePixmapFromData(dpy
, RootWindow(dpy
, DefaultScreen(dpy
)),
765 (char**) data
, &pixmap
, &mask
, &xpmAttr
);
766 if (ErrorStatus
== XpmSuccess
)
769 M_BITMAPHANDLERDATA
->m_width
= xpmAttr
.width
;
770 M_BITMAPHANDLERDATA
->m_height
= xpmAttr
.height
;
772 unsigned int depthRet
;
774 unsigned int widthRet
, heightRet
, borderWidthRet
;
775 Window rootWindowRet
;
776 XGetGeometry(dpy
, pixmap
, &rootWindowRet
, &xRet
, &yRet
,
777 &widthRet
, &heightRet
, &borderWidthRet
, &depthRet
);
780 if ( xpmAttr.npixels > 2 )
782 M_BITMAPHANDLERDATA->m_depth = 8; // next time not just a guess :-) ...
785 M_BITMAPHANDLERDATA->m_depth = 1; // mono
789 M_BITMAPHANDLERDATA
->m_depth
= depthRet
;
791 M_BITMAPHANDLERDATA
->m_numColors
= xpmAttr
.npixels
;
792 XpmFreeAttributes(&xpmAttr
);
793 M_BITMAPHANDLERDATA
->m_ok
= TRUE
;
794 M_BITMAPHANDLERDATA
->m_pixmap
= (WXPixmap
) pixmap
;
797 M_BITMAPHANDLERDATA
->m_bitmapMask
= new wxMask
;
798 M_BITMAPHANDLERDATA
->m_bitmapMask
->SetPixmap((WXPixmap
) mask
);
803 // XpmDebugError(ErrorStatus, NULL);
804 M_BITMAPHANDLERDATA
->m_ok
= FALSE
;
806 return M_BITMAPHANDLERDATA
->m_ok
;
809 #endif // wxHAVE_LIB_XPM
811 void wxBitmap::CleanUpHandlers()
813 wxNode
*node
= sm_handlers
.First();
816 wxBitmapHandler
*handler
= (wxBitmapHandler
*)node
->Data();
817 wxNode
*next
= node
->Next();
824 void wxBitmap::InitStandardHandlers()
826 // Initialize all standard bitmap or derived class handlers here.
827 AddHandler(new wxXBMFileHandler
);
828 AddHandler(new wxXBMDataHandler
);
830 // XPM is considered standard for Motif, although it can be omitted if
831 // libXpm is not installed
833 AddHandler(new wxXPMFileHandler
);
834 AddHandler(new wxXPMDataHandler
);
835 #endif // wxHAVE_LIB_XPM
838 WXPixmap
wxBitmap::GetLabelPixmap (WXWidget w
)
840 if (M_BITMAPDATA
->m_image
== (WXPixmap
) 0)
841 return M_BITMAPDATA
->m_pixmap
;
843 Display
*dpy
= (Display
*) M_BITMAPDATA
->m_display
;
848 if (labelPixmap) return labelPixmap;
849 things can be wrong, because colors can have been changed.
853 XmDestroyPixmap(DefaultScreenOfDisplay(dpy),labelPixmap) ;
854 we got BadDrawable if the pixmap is referenced by multiples widgets
858 So, before doing thing really clean, I just do nothing; if the pixmap is
859 referenced by many widgets, Motif performs caching functions.
860 And if pixmap is referenced with multiples colors, we just have some
861 memory leaks... I hope we can deal with them...
863 // Must be destroyed, because colours can have been changed!
864 if (M_BITMAPDATA
->m_labelPixmap
)
865 XmDestroyPixmap (DefaultScreenOfDisplay (dpy
), M_BITMAPDATA
->m_labelPixmap
);
869 sprintf (tmp
, "Im%x", (unsigned int) M_BITMAPDATA
->m_image
);
872 Widget widget
= (Widget
) w
;
874 while (XmIsGadget ( widget
))
875 widget
= XtParent (widget
);
876 XtVaGetValues (widget
, XmNbackground
, &bg
, XmNforeground
, &fg
, NULL
);
878 M_BITMAPDATA
->m_labelPixmap
= (WXPixmap
) XmGetPixmap (DefaultScreenOfDisplay (dpy
), tmp
, fg
, bg
);
880 return M_BITMAPDATA
->m_labelPixmap
;
883 WXPixmap
wxBitmap::GetArmPixmap (WXWidget w
)
885 if (M_BITMAPDATA
->m_image
== (WXPixmap
) 0)
886 return M_BITMAPDATA
->m_pixmap
;
888 Display
*dpy
= (Display
*) M_BITMAPDATA
->m_display
;
890 // See GetLabelPixmap () comment
892 // Must be destroyed, because colours can have been changed!
893 if (M_BITMAPDATA
->m_armPixmap
)
894 XmDestroyPixmap (DefaultScreenOfDisplay (dpy
), M_BITMAPDATA
->m_armPixmap
);
898 sprintf (tmp
, "Im%x", (unsigned int) M_BITMAPDATA
->m_image
);
901 Widget widget
= (Widget
) w
;
903 XtVaGetValues (widget
, XmNarmColor
, &bg
, NULL
);
904 while (XmIsGadget (widget
))
905 widget
= XtParent (widget
);
906 XtVaGetValues (widget
, XmNforeground
, &fg
, NULL
);
908 M_BITMAPDATA
->m_armPixmap
= (WXPixmap
) XmGetPixmap (DefaultScreenOfDisplay (dpy
), tmp
, fg
, bg
);
910 return M_BITMAPDATA
->m_armPixmap
;
913 WXPixmap
wxBitmap::GetInsensPixmap (WXWidget w
)
915 Display
*dpy
= (Display
*) M_BITMAPDATA
->m_display
;
917 if (M_BITMAPDATA
->m_insensPixmap
)
918 return M_BITMAPDATA
->m_insensPixmap
;
922 M_BITMAPDATA
->m_insensPixmap
= (WXPixmap
) XCreateInsensitivePixmap(dpy
, (Pixmap
) M_BITMAPDATA
->m_pixmap
);
923 if (M_BITMAPDATA
->m_insensPixmap
)
924 return M_BITMAPDATA
->m_insensPixmap
;
926 return M_BITMAPDATA
->m_pixmap
;
929 if (M_BITMAPDATA
->m_insensImage
== (WXPixmap
) 0)
930 return M_BITMAPDATA
->m_pixmap
;
933 See
GetLabelPixmap () comment
934 // Must be destroyed, because colours can have been changed!
935 if (M_BITMAPDATA
->m_insensPixmap
)
936 XmDestroyPixmap (DefaultScreenOfDisplay (dpy
), (Pixmap
) M_BITMAPDATA
->m_insensPixmap
);
940 sprintf (tmp
, "Not%x", (unsigned int) M_BITMAPDATA
->m_insensImage
);
943 Widget widget
= (Widget
) w
;
945 while (XmIsGadget (widget
))
946 widget
= XtParent (widget
);
947 XtVaGetValues (widget
, XmNbackground
, &bg
, XmNforeground
, &fg
, NULL
);
949 M_BITMAPDATA
->m_insensPixmap
= (WXPixmap
) XmGetPixmap (DefaultScreenOfDisplay (dpy
), tmp
, fg
, bg
);
951 return M_BITMAPDATA
->m_insensPixmap
;
954 // We may need this sometime...
956 /****************************************************************************
959 XCreateInsensitivePixmap - create a grayed-out copy of a pixmap
962 Pixmap XCreateInsensitivePixmap( Display *display, Pixmap pixmap )
965 This function creates a grayed-out copy of the argument pixmap, suitable
966 for use as a XmLabel's XmNlabelInsensitivePixmap resource.
969 The return value is the new Pixmap id or zero on error. Errors include
970 a NULL display argument or an invalid Pixmap argument.
973 If one of the XLib functions fail, it will produce a X error. The
974 default X error handler prints a diagnostic and calls exit().
977 XCopyArea(3), XCreateBitmapFromData(3), XCreateGC(3), XCreatePixmap(3),
978 XFillRectangle(3), exit(2)
981 John R Veregge - john@puente.jpl.nasa.gov
982 Advanced Engineering and Prototyping Group (AEG)
983 Information Systems Technology Section (395)
984 Jet Propulsion Lab - Calif Institute of Technology
986 *****************************************************************************/
989 XCreateInsensitivePixmap( Display
*display
, Pixmap pixmap
)
992 static char stipple_data
[] =
994 0x55, 0x55, 0xAA, 0xAA, 0x55, 0x55, 0xAA, 0xAA,
995 0x55, 0x55, 0xAA, 0xAA, 0x55, 0x55, 0xAA, 0xAA,
996 0x55, 0x55, 0xAA, 0xAA, 0x55, 0x55, 0xAA, 0xAA,
997 0x55, 0x55, 0xAA, 0xAA, 0x55, 0x55, 0xAA, 0xAA
1000 Pixmap ipixmap
, stipple
;
1001 unsigned width
, height
, depth
;
1003 Window window
; /* These return values */
1004 unsigned border
; /* from XGetGeometry() */
1005 int x
, y
; /* are not needed. */
1009 if ( NULL
== display
|| 0 == pixmap
)
1012 if ( 0 == XGetGeometry( display
, pixmap
, &window
, &x
, &y
,
1013 &width
, &height
, &border
, &depth
)
1015 return ipixmap
; /* BadDrawable: probably an invalid pixmap */
1017 /* Get the stipple pixmap to be used to 'gray-out' the argument pixmap.
1019 stipple
= XCreateBitmapFromData( display
, pixmap
, stipple_data
, 16, 16 );
1022 gc
= XCreateGC( display
, pixmap
, (XtGCMask
)0, (XGCValues
*)NULL
);
1025 /* Create an identical copy of the argument pixmap.
1027 ipixmap
= XCreatePixmap( display
, pixmap
, width
, height
, depth
);
1030 /* Copy the argument pixmap into the new pixmap.
1032 XCopyArea( display
, pixmap
, ipixmap
,
1033 gc
, 0, 0, width
, height
, 0, 0 );
1035 /* Refill the new pixmap using the stipple algorithm/pixmap.
1037 XSetStipple( display
, gc
, stipple
);
1038 XSetFillStyle( display
, gc
, FillStippled
);
1039 XFillRectangle( display
, ipixmap
, gc
, 0, 0, width
, height
);
1041 XFreeGC( display
, gc
);
1043 XFreePixmap( display
, stipple
);
1048 // Creates a bitmap with transparent areas drawn in
1049 // the given colour.
1050 wxBitmap
wxCreateMaskedBitmap(const wxBitmap
& bitmap
, wxColour
& colour
)
1052 wxBitmap
newBitmap(bitmap
.GetWidth(),
1057 srcDC
.SelectObject(bitmap
);
1058 destDC
.SelectObject(newBitmap
);
1060 wxBrush
brush(colour
, wxSOLID
);
1061 destDC
.SetOptimization(FALSE
);
1062 destDC
.SetBackground(brush
);
1064 destDC
.Blit(0, 0, bitmap
.GetWidth(), bitmap
.GetHeight(), & srcDC
, 0, 0, wxCOPY
, TRUE
);