// @(#)root/gui:$Name: $:$Id: TGPicture.cxx,v 1.24 2005/06/26 23:37:27 rdm Exp $
// Author: Fons Rademakers 01/01/98
/*************************************************************************
* Copyright (C) 1995-2000, Rene Brun and Fons Rademakers. *
* All rights reserved. *
* *
* For the licensing terms see $ROOTSYS/LICENSE. *
* For the list of contributors see $ROOTSYS/README/CREDITS. *
*************************************************************************/
/**************************************************************************
This source is based on Xclass95, a Win95-looking GUI toolkit.
Copyright (C) 1996, 1997 David Barth, Ricky Ralston, Hector Peraza.
Xclass95 is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
**************************************************************************/
//////////////////////////////////////////////////////////////////////////
// //
// TGPicture & TGPicturePool //
// //
// The TGPicture class implements pictures and icons used in the //
// different GUI elements and widgets. The TGPicturePool class //
// implements a TGPicture cache. TGPictures are created, managed and //
// destroyed by the TGPicturePool. //
// //
//////////////////////////////////////////////////////////////////////////
#include "TGPicture.h"
#include "TGResourcePool.h"
#include "THashTable.h"
#include "TSystem.h"
#include "TGWindow.h"
#include "TVirtualX.h"
#include "TImage.h"
TGGC *TGSelectedPicture::fgSelectedGC = 0;
ClassImp(TGPicture)
ClassImp(TGSelectedPicture)
ClassImp(TGPicturePool)
//______________________________________________________________________________
const TGPicture *TGPicturePool::GetPicture(const char *name)
{
// Get a picture from the picture pool. Picture must be freed using
// TGPicturePool::FreePicture(). If picture is not found 0 is returned.
if (!fPicList)
fPicList = new THashTable(50);
TString pname = name;
pname.Strip();
TString ext = strrchr(pname, '.');
ext.ToLower();
if (ext.Length()) { // ".xpm", ".gif" etc
char *pxname = gSystem->ExpandPathName(gSystem->UnixPathName(pname));
pname = pxname;
delete [] pxname;
}
TGPicture *pic = (TGPicture *)fPicList->FindObject(pname);
if (pic && !pic->IsScaled()) {
if (pic->fPic == kNone)
return 0;
pic->AddReference();
return pic;
}
char *picnam = gSystem->Which(fPath, pname, kReadPermission);
if (!picnam) {
pic = new TGPicture(pname);
pic->fAttributes.fColormap = fClient->GetDefaultColormap();
pic->fAttributes.fCloseness = 40000; // Allow for "similar" colors
pic->fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
fPicList->Add(pic);
return 0;
}
TImage *img = TImage::Open(picnam);
if (!img) {
pic = new TGPicture(pname);
pic->fAttributes.fColormap = fClient->GetDefaultColormap();
pic->fAttributes.fCloseness = 40000; // Allow for "similar" colors
pic->fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
fPicList->Add(pic);
delete [] picnam;
return 0;
}
pic = new TGPicture(pname, img->GetPixmap(), img->GetMask());
delete [] picnam;
delete img;
fPicList->Add(pic);
return pic;
}
//______________________________________________________________________________
const TGPicture *TGPicturePool::GetPicture(const char *name,
UInt_t new_width, UInt_t new_height)
{
// Get picture with specified size from pool (picture will be scaled if
// necessary). Picture must be freed using TGPicturePool::FreePicture(). If
// picture is not found 0 is returned.
if (!fPicList)
fPicList = new THashTable(50);
TString pname = name;
pname.Strip();
TString ext = strrchr(pname, '.');
ext.ToLower();
if (ext.Length()) { // ".xpm", ".gif" etc
char *pxname = gSystem->ExpandPathName(gSystem->UnixPathName(pname));
pname = pxname;
delete [] pxname;
}
const char *hname = TGPicture::HashName(pname, new_width, new_height);
TGPicture *pic = (TGPicture *)fPicList->FindObject(hname);
if (pic && pic->GetWidth() == new_width && pic->GetHeight() == new_height) {
if (pic->fPic == kNone)
return 0;
pic->AddReference();
return pic;
}
char *picnam = gSystem->Which(fPath, pname, kReadPermission);
if (!picnam) {
pic = new TGPicture(hname, kTRUE);
pic->fAttributes.fColormap = fClient->GetDefaultColormap();
pic->fAttributes.fCloseness = 40000; // Allow for "similar" colors
pic->fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
pic->fAttributes.fWidth = new_width;
pic->fAttributes.fHeight = new_height;
fPicList->Add(pic);
return 0;
}
TImage *img = TImage::Open(picnam);
if (!img) {
pic = new TGPicture(hname, kTRUE);
pic->fAttributes.fColormap = fClient->GetDefaultColormap();
pic->fAttributes.fCloseness = 40000; // Allow for "similar" colors
pic->fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
pic->fAttributes.fWidth = new_width;
pic->fAttributes.fHeight = new_height;
fPicList->Add(pic);
delete [] picnam;
return 0;
}
img->Scale(new_width, new_height);
pic = new TGPicture(hname, img->GetPixmap(), img->GetMask());
delete [] picnam;
delete img;
fPicList->Add(pic);
return pic;
}
//______________________________________________________________________________
const TGPicture *TGPicturePool::GetPicture(const char *name, Pixmap_t pxmap,
Pixmap_t mask)
{
// Get picture with specified pixmap and mask from pool.
// Picture must be freed using TGPicturePool::FreePicture().
// If picture is not found 0 is returned.
if (!fPicList)
fPicList = new THashTable(50);
Int_t xy;
UInt_t w, h;
gVirtualX->GetWindowSize(pxmap, xy, xy, w, h);
const char *hname = TGPicture::HashName(name, w, h);
TGPicture *pic = (TGPicture *)fPicList->FindObject(hname);
if (pic) {
pic->AddReference();
return pic;
}
pic = new TGPicture(hname, pxmap, mask);
fPicList->Add(pic);
return pic;
}
//______________________________________________________________________________
const TGPicture *TGPicturePool::GetPicture(const char *name, char **xpm)
{
// Create picture from XPM data.
// Picture must be freed using TGPicturePool::FreePicture().
// If picture creation failed 0 is returned.
UInt_t w, h;
if (!xpm || !*xpm) {
return 0;
}
if (!fPicList) {
fPicList = new THashTable(50);
}
char *ptr = xpm[0];
while (isspace((int)*ptr)) ++ptr;
w = atoi(ptr);
while (isspace((int)*ptr)) ++ptr;
h = atoi(ptr);
const char *hname = TGPicture::HashName(name, w, h);
TGPicture *pic = (TGPicture *)fPicList->FindObject(hname);
if (pic) {
pic->AddReference();
return pic;
}
TImage *img = TImage::Open(xpm);
if (!img) {
pic = new TGPicture(hname, kTRUE);
pic->fAttributes.fColormap = fClient->GetDefaultColormap();
pic->fAttributes.fCloseness = 40000; // Allow for "similar" colors
pic->fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
pic->fAttributes.fWidth = w;
pic->fAttributes.fHeight = h;
fPicList->Add(pic);
return 0;
}
pic = new TGPicture(hname, img->GetPixmap(), img->GetMask());
delete img;
return pic;
}
//______________________________________________________________________________
void TGPicturePool::FreePicture(const TGPicture *fpic)
{
// Remove picture from cache if nobody is using it anymore.
if (!fPicList) return;
TGPicture *pic = (TGPicture *)fPicList->FindObject(fpic);
if (pic) {
if (pic->RemoveReference() == 0) {
fPicList->Remove(pic);
delete pic;
}
}
}
//______________________________________________________________________________
TGPicturePool::~TGPicturePool()
{
// Delete picture cache.
if (fPicList) {
fPicList->Delete();
delete fPicList;
}
}
//______________________________________________________________________________
void TGPicturePool::Print(Option_t *) const
{
// List all pictures in the pool.
if (fPicList)
fPicList->Print();
else
Info("Print", "no pictures in picture pool");
}
//______________________________________________________________________________
TGPicture::TGPicture(const char *name, Pixmap_t pxmap, Pixmap_t mask)
{
// ctor. Important: both pixmaps pxmap and mask must be unique (not shared)
fName = name;
fScaled = kFALSE;
fPic = pxmap;
fMask = mask;
Int_t xy;
fAttributes.fColormap = gClient->GetDefaultColormap();
fAttributes.fCloseness = 40000; // Allow for "similar" colors
fAttributes.fMask = kPASize | kPAColormap | kPACloseness;
fAttributes.fPixels = 0;
gVirtualX->GetWindowSize(fPic, xy, xy, fAttributes.fWidth, fAttributes.fHeight);
SetRefCount(1);
}
//______________________________________________________________________________
void TGPicture::Draw(Handle_t id, GContext_t gc, Int_t x, Int_t y) const
{
// Draw a picture.
GCValues_t gcv;
gcv.fMask = kGCClipMask | kGCClipXOrigin | kGCClipYOrigin;
gcv.fClipMask = fMask;
gcv.fClipXOrigin = x;
gcv.fClipYOrigin = y;
gVirtualX->ChangeGC(gc, &gcv);
gVirtualX->CopyArea(fPic, id, gc, 0, 0, fAttributes.fWidth, fAttributes.fHeight,
x, y);
gcv.fMask = kGCClipMask;
gcv.fClipMask = kNone;
gVirtualX->ChangeGC(gc, &gcv);
}
//______________________________________________________________________________
TGPicture::~TGPicture()
{
// Delete picture object.
if (fPic != kNone)
gVirtualX->DeletePixmap(fPic);
if (fMask != kNone)
gVirtualX->DeletePixmap(fMask);
if (fAttributes.fPixels)
delete [] fAttributes.fPixels;
}
//______________________________________________________________________________
const char *TGPicture::HashName(const char *name, Int_t width, Int_t height)
{
// Static function returning a unique name used to look up a picture.
// The unique name has the form "name__widthxheight".
static TString hashName;
hashName.Form("%s__%dx%d", name, width, height);
return hashName.Data();
}
//______________________________________________________________________________
void TGPicture::Print(Option_t *) const
{
// Print picture info.
Printf("TGPicture: %s,%sref cnt = %u %d", GetName(),
fScaled ? " scaled, " : " ", References(), fPic);
}
//______________________________________________________________________________
TGSelectedPicture::TGSelectedPicture(const TGClient *client, const TGPicture *p) :
TGPicture("")
{
// Create a "selected" looking picture based on the original TGPicture.
GCValues_t gcv;
UInt_t w, h;
fClient = client;
Window_t root = fClient->GetDefaultRoot()->GetId();
w = p->GetWidth();
h = p->GetHeight();
fPic = gVirtualX->CreatePixmap(root, w, h);
fMask = p->GetMask();
fAttributes.fWidth = w;
fAttributes.fHeight = h;
gVirtualX->CopyArea(p->GetPicture(), fPic, GetSelectedGC()(), 0, 0, w, h, 0, 0);
gcv.fMask = kGCClipMask | kGCClipXOrigin | kGCClipYOrigin;
gcv.fClipMask = p->GetMask();
gcv.fClipXOrigin = 0;
gcv.fClipYOrigin = 0;
GetSelectedGC().SetAttributes(&gcv);
gVirtualX->FillRectangle(fPic, GetSelectedGC()(), 0, 0, w, h);
GetSelectedGC().SetClipMask(kNone);
}
//______________________________________________________________________________
TGSelectedPicture::~TGSelectedPicture()
{
// Delete selected picture.
// fMask was borrowed so should not be deleted by ~TGPicture.
fMask = kNone;
}
//______________________________________________________________________________
TGGC &TGSelectedPicture::GetSelectedGC()
{
if (!fgSelectedGC) {
fgSelectedGC = new TGGC(*gClient->GetResourcePool()->GetFrameGC());
fgSelectedGC->SetForeground(gClient->GetResourcePool()->GetSelectedBgndColor());
fgSelectedGC->SetBackground(gClient->GetResourcePool()->GetBlackColor());
fgSelectedGC->SetFillStyle(kFillStippled);
fgSelectedGC->SetStipple(gClient->GetResourcePool()->GetCheckeredBitmap());
}
return *fgSelectedGC;
}
ROOT page - Class index - Class Hierarchy - Top of the page
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.