📄 tkbitmap.c
字号:
/* * tkBitmap.c -- * * This file maintains a database of read-only bitmaps for the Tk * toolkit. This allows bitmaps to be shared between widgets and * also avoids interactions with the X server. * * Copyright (c) 1990-1994 The Regents of the University of California. * Copyright (c) 1994-1996 Sun Microsystems, Inc. * * See the file "license.terms" for information on usage and redistribution * of this file, and for a DISCLAIMER OF ALL WARRANTIES. * * SCCS: @(#) tkBitmap.c 1.45 97/07/24 17:27:38 */#include "tkPort.h"#include "tkInt.h"/* * The includes below are for pre-defined bitmaps. * * Platform-specific issue: Windows complains when the bitmaps are * included, because an array of characters is being initialized with * integers as elements. For lint purposes, the following pragmas * temporarily turn off that warning message. */#if defined(__WIN32__) || defined(_WIN32)#pragma warning (disable : 4305)#endif#include "error.bmp"#include "gray12.bmp"#include "gray25.bmp"#include "gray50.bmp"#include "gray75.bmp"#include "hourglass.bmp"#include "info.bmp"#include "questhead.bmp"#include "question.bmp"#include "warning.bmp"#if defined(__WIN32__) || defined(_WIN32)#pragma warning (default : 4305)#endif/* * One of the following data structures exists for each bitmap that is * currently in use. Each structure is indexed with both "idTable" and * "nameTable". */typedef struct { Pixmap bitmap; /* X identifier for bitmap. None means this * bitmap was created by Tk_DefineBitmap * and it isn't currently in use. */ int width, height; /* Dimensions of bitmap. */ Display *display; /* Display for which bitmap is valid. */ int refCount; /* Number of active uses of bitmap. */ Tcl_HashEntry *hashPtr; /* Entry in nameTable for this structure * (needed when deleting). */} TkBitmap;/* * Hash table to map from a textual description of a bitmap to the * TkBitmap record for the bitmap, and key structure used in that * hash table: */static Tcl_HashTable nameTable;typedef struct { Tk_Uid name; /* Textual name for desired bitmap. */ Screen *screen; /* Screen on which bitmap will be used. */} NameKey;/* * Hash table that maps from <display + bitmap id> to the TkBitmap structure * for the bitmap. This table is used by Tk_FreeBitmap. */static Tcl_HashTable idTable;typedef struct { Display *display; /* Display for which bitmap was allocated. */ Pixmap pixmap; /* X identifier for pixmap. */} IdKey;/* * Hash table create by Tk_DefineBitmap to map from a name to a * collection of in-core data about a bitmap. The table is * indexed by the address of the data for the bitmap, and the entries * contain pointers to TkPredefBitmap structures. */Tcl_HashTable tkPredefBitmapTable;/* * Hash table used by Tk_GetBitmapFromData to map from a collection * of in-core data about a bitmap to a Tk_Uid giving an automatically- * generated name for the bitmap: */static Tcl_HashTable dataTable;typedef struct { char *source; /* Bitmap bits. */ int width, height; /* Dimensions of bitmap. */} DataKey;static int initialized = 0; /* 0 means static structures haven't been * initialized yet. *//* * Forward declarations for procedures defined in this file: */static void BitmapInit _ANSI_ARGS_((void));/* *---------------------------------------------------------------------- * * Tk_GetBitmap -- * * Given a string describing a bitmap, locate (or create if necessary) * a bitmap that fits the description. * * Results: * The return value is the X identifer for the desired bitmap * (i.e. a Pixmap with a single plane), unless string couldn't be * parsed correctly. In this case, None is returned and an error * message is left in interp->result. The caller should never * modify the bitmap that is returned, and should eventually call * Tk_FreeBitmap when the bitmap is no longer needed. * * Side effects: * The bitmap is added to an internal database with a reference count. * For each call to this procedure, there should eventually be a call * to Tk_FreeBitmap, so that the database can be cleaned up when bitmaps * aren't needed anymore. * *---------------------------------------------------------------------- */PixmapTk_GetBitmap(interp, tkwin, string) Tcl_Interp *interp; /* Interpreter to use for error reporting, * this may be NULL. */ Tk_Window tkwin; /* Window in which bitmap will be used. */ Tk_Uid string; /* Description of bitmap. See manual entry * for details on legal syntax. */{ NameKey nameKey; IdKey idKey; Tcl_HashEntry *nameHashPtr, *idHashPtr, *predefHashPtr; register TkBitmap *bitmapPtr; TkPredefBitmap *predefPtr; int new; Pixmap bitmap; int width, height; int dummy2; if (!initialized) { BitmapInit(); } nameKey.name = string; nameKey.screen = Tk_Screen(tkwin); nameHashPtr = Tcl_CreateHashEntry(&nameTable, (char *) &nameKey, &new); if (!new) { bitmapPtr = (TkBitmap *) Tcl_GetHashValue(nameHashPtr); bitmapPtr->refCount++; return bitmapPtr->bitmap; } /* * No suitable bitmap exists. Create a new bitmap from the * information contained in the string. If the string starts * with "@" then the rest of the string is a file name containing * the bitmap. Otherwise the string must refer to a bitmap * defined by a call to Tk_DefineBitmap. */ if (*string == '@') { Tcl_DString buffer; int result; if (Tcl_IsSafe(interp)) { Tcl_AppendResult(interp, "can't specify bitmap with '@' in a", " safe interpreter", (char *) NULL); goto error; } string = Tcl_TranslateFileName(interp, string + 1, &buffer); if (string == NULL) { goto error; } result = TkReadBitmapFile(Tk_Display(tkwin), RootWindowOfScreen(nameKey.screen), string, (unsigned int *) &width, (unsigned int *) &height, &bitmap, &dummy2, &dummy2); if (result != BitmapSuccess) { if (interp != NULL) { Tcl_AppendResult(interp, "error reading bitmap file \"", string, "\"", (char *) NULL); } Tcl_DStringFree(&buffer); goto error; } Tcl_DStringFree(&buffer); } else { predefHashPtr = Tcl_FindHashEntry(&tkPredefBitmapTable, string); if (predefHashPtr == NULL) { /* * The following platform specific call allows the user to * define bitmaps that may only exist during run time. If * it returns None nothing was found and we return the error. */ bitmap = TkpGetNativeAppBitmap(Tk_Display(tkwin), string, &width, &height); if (bitmap == None) { if (interp != NULL) { Tcl_AppendResult(interp, "bitmap \"", string, "\" not defined", (char *) NULL); } goto error; } } else { predefPtr = (TkPredefBitmap *) Tcl_GetHashValue(predefHashPtr); width = predefPtr->width; height = predefPtr->height; if (predefPtr->native) { bitmap = TkpCreateNativeBitmap(Tk_Display(tkwin), predefPtr->source); if (bitmap == None) { panic("native bitmap creation failed"); } } else { bitmap = XCreateBitmapFromData(Tk_Display(tkwin), RootWindowOfScreen(nameKey.screen), predefPtr->source, (unsigned) width, (unsigned) height); } } } /* * Add information about this bitmap to our database. */ bitmapPtr = (TkBitmap *) ckalloc(sizeof(TkBitmap)); bitmapPtr->bitmap = bitmap; bitmapPtr->width = width; bitmapPtr->height = height; bitmapPtr->display = Tk_Display(tkwin); bitmapPtr->refCount = 1; bitmapPtr->hashPtr = nameHashPtr; idKey.display = bitmapPtr->display; idKey.pixmap = bitmap; idHashPtr = Tcl_CreateHashEntry(&idTable, (char *) &idKey, &new); if (!new) { panic("bitmap already registered in Tk_GetBitmap"); } Tcl_SetHashValue(nameHashPtr, bitmapPtr); Tcl_SetHashValue(idHashPtr, bitmapPtr); return bitmapPtr->bitmap; error: Tcl_DeleteHashEntry(nameHashPtr); return None;}/* *---------------------------------------------------------------------- * * Tk_DefineBitmap -- * * This procedure associates a textual name with a binary bitmap * description, so that the name may be used to refer to the * bitmap in future calls to Tk_GetBitmap. * * Results: * A standard Tcl result. If an error occurs then TCL_ERROR is * returned and a message is left in interp->result. * * Side effects: * "Name" is entered into the bitmap table and may be used from * here on to refer to the given bitmap. * *---------------------------------------------------------------------- */intTk_DefineBitmap(interp, name, source, width, height) Tcl_Interp *interp; /* Interpreter to use for error reporting. */ Tk_Uid name; /* Name to use for bitmap. Must not already * be defined as a bitmap. */ char *source; /* Address of bits for bitmap. */ int width; /* Width of bitmap. */ int height; /* Height of bitmap. */{ int new; Tcl_HashEntry *predefHashPtr; TkPredefBitmap *predefPtr; if (!initialized) { BitmapInit(); } predefHashPtr = Tcl_CreateHashEntry(&tkPredefBitmapTable, name, &new); if (!new) { Tcl_AppendResult(interp, "bitmap \"", name, "\" is already defined", (char *) NULL); return TCL_ERROR; } predefPtr = (TkPredefBitmap *) ckalloc(sizeof(TkPredefBitmap)); predefPtr->source = source;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -