📄 tkwindow.c
字号:
if (screenId >= ScreenCount(dispPtr->display)) { sprintf(interp->result, "bad screen number \"%d\"", screenId); return (TkDisplay *) NULL; } *screenPtr = screenId; return dispPtr;}/* *---------------------------------------------------------------------- * * TkGetDisplay -- * * Given an X display, TkGetDisplay returns the TkDisplay * structure for the display. * * Results: * The return value is a pointer to information about the display, * or NULL if the display did not have a TkDisplay structure. * * Side effects: * None. * *---------------------------------------------------------------------- */TkDisplay *TkGetDisplay(display) Display *display; /* X's display pointer */{ TkDisplay *dispPtr; for (dispPtr = tkDisplayList; dispPtr != NULL; dispPtr = dispPtr->nextPtr) { if (dispPtr->display == display) { break; } } return dispPtr;}/* *-------------------------------------------------------------- * * TkAllocWindow -- * * This procedure creates and initializes a TkWindow structure. * * Results: * The return value is a pointer to the new window. * * Side effects: * A new window structure is allocated and all its fields are * initialized. * *-------------------------------------------------------------- */TkWindow *TkAllocWindow(dispPtr, screenNum, parentPtr) TkDisplay *dispPtr; /* Display associated with new window. */ int screenNum; /* Index of screen for new window. */ TkWindow *parentPtr; /* Parent from which this window should * inherit visual information. NULL means * use screen defaults instead of * inheriting. */{ register TkWindow *winPtr; winPtr = (TkWindow *) ckalloc(sizeof(TkWindow)); winPtr->display = dispPtr->display; winPtr->dispPtr = dispPtr; winPtr->screenNum = screenNum; if ((parentPtr != NULL) && (parentPtr->display == winPtr->display) && (parentPtr->screenNum == winPtr->screenNum)) { winPtr->visual = parentPtr->visual; winPtr->depth = parentPtr->depth; } else { winPtr->visual = DefaultVisual(dispPtr->display, screenNum); winPtr->depth = DefaultDepth(dispPtr->display, screenNum); } winPtr->window = None; winPtr->childList = NULL; winPtr->lastChildPtr = NULL; winPtr->parentPtr = NULL; winPtr->nextPtr = NULL; winPtr->mainPtr = NULL; winPtr->pathName = NULL; winPtr->nameUid = NULL; winPtr->classUid = NULL; winPtr->changes = defChanges; winPtr->dirtyChanges = CWX|CWY|CWWidth|CWHeight|CWBorderWidth; winPtr->atts = defAtts; if ((parentPtr != NULL) && (parentPtr->display == winPtr->display) && (parentPtr->screenNum == winPtr->screenNum)) { winPtr->atts.colormap = parentPtr->atts.colormap; } else { winPtr->atts.colormap = DefaultColormap(dispPtr->display, screenNum); } winPtr->dirtyAtts = CWEventMask|CWColormap|CWBitGravity; winPtr->flags = 0; winPtr->handlerList = NULL;#ifdef TK_USE_INPUT_METHODS winPtr->inputContext = NULL;#endif /* TK_USE_INPUT_METHODS */ winPtr->tagPtr = NULL; winPtr->numTags = 0; winPtr->optionLevel = -1; winPtr->selHandlerList = NULL; winPtr->geomMgrPtr = NULL; winPtr->geomData = NULL; winPtr->reqWidth = winPtr->reqHeight = 1; winPtr->internalBorderWidth = 0; winPtr->wmInfoPtr = NULL; winPtr->classProcsPtr = NULL; winPtr->instanceData = NULL; winPtr->privatePtr = NULL; return winPtr;}/* *---------------------------------------------------------------------- * * NameWindow -- * * This procedure is invoked to give a window a name and insert * the window into the hierarchy associated with a particular * application. * * Results: * A standard Tcl return value. * * Side effects: * See above. * *---------------------------------------------------------------------- */static intNameWindow(interp, winPtr, parentPtr, name) Tcl_Interp *interp; /* Interpreter to use for error reporting. */ register TkWindow *winPtr; /* Window that is to be named and inserted. */ TkWindow *parentPtr; /* Pointer to logical parent for winPtr * (used for naming, options, etc.). */ char *name; /* Name for winPtr; must be unique among * parentPtr's children. */{#define FIXED_SIZE 200 char staticSpace[FIXED_SIZE]; char *pathName; int new; Tcl_HashEntry *hPtr; int length1, length2; /* * Setup all the stuff except name right away, then do the name stuff * last. This is so that if the name stuff fails, everything else * will be properly initialized (needed to destroy the window cleanly * after the naming failure). */ winPtr->parentPtr = parentPtr; winPtr->nextPtr = NULL; if (parentPtr->childList == NULL) { parentPtr->childList = winPtr; } else { parentPtr->lastChildPtr->nextPtr = winPtr; } parentPtr->lastChildPtr = winPtr; winPtr->mainPtr = parentPtr->mainPtr; winPtr->mainPtr->refCount++; winPtr->nameUid = Tk_GetUid(name); /* * Don't permit names that start with an upper-case letter: this * will just cause confusion with class names in the option database. */ if (isupper(UCHAR(name[0]))) { Tcl_AppendResult(interp, "window name starts with an upper-case letter: \"", name, "\"", (char *) NULL); return TCL_ERROR; } /* * To permit names of arbitrary length, must be prepared to malloc * a buffer to hold the new path name. To run fast in the common * case where names are short, use a fixed-size buffer on the * stack. */ length1 = strlen(parentPtr->pathName); length2 = strlen(name); if ((length1+length2+2) <= FIXED_SIZE) { pathName = staticSpace; } else { pathName = (char *) ckalloc((unsigned) (length1+length2+2)); } if (length1 == 1) { pathName[0] = '.'; strcpy(pathName+1, name); } else { strcpy(pathName, parentPtr->pathName); pathName[length1] = '.'; strcpy(pathName+length1+1, name); } hPtr = Tcl_CreateHashEntry(&parentPtr->mainPtr->nameTable, pathName, &new); if (pathName != staticSpace) { ckfree(pathName); } if (!new) { Tcl_AppendResult(interp, "window name \"", name, "\" already exists in parent", (char *) NULL); return TCL_ERROR; } Tcl_SetHashValue(hPtr, winPtr); winPtr->pathName = Tcl_GetHashKey(&parentPtr->mainPtr->nameTable, hPtr); return TCL_OK;}/* *---------------------------------------------------------------------- * * TkCreateMainWindow -- * * Make a new main window. A main window is a special kind of * top-level window used as the outermost window in an * application. * * Results: * The return value is a token for the new window, or NULL if * an error prevented the new window from being created. If * NULL is returned, an error message will be left in * interp->result. * * Side effects: * A new window structure is allocated locally; "interp" is * associated with the window and registered for "send" commands * under "baseName". BaseName may be extended with an instance * number in the form "#2" if necessary to make it globally * unique. Tk-related commands are bound into interp. * *---------------------------------------------------------------------- */Tk_WindowTkCreateMainWindow(interp, screenName, baseName) Tcl_Interp *interp; /* Interpreter to use for error reporting. */ char *screenName; /* Name of screen on which to create * window. Empty or NULL string means * use DISPLAY environment variable. */ char *baseName; /* Base name for application; usually of the * form "prog instance". */{ Tk_Window tkwin; int dummy; int isSafe; Tcl_HashEntry *hPtr; register TkMainInfo *mainPtr; register TkWindow *winPtr; register TkCmd *cmdPtr; /* * Panic if someone updated the TkWindow structure without * also updating the Tk_FakeWin structure (or vice versa). */ if (sizeof(TkWindow) != sizeof(Tk_FakeWin)) { panic("TkWindow and Tk_FakeWin are not the same size"); } /* * Create the basic TkWindow structure. */ tkwin = CreateTopLevelWindow(interp, (Tk_Window) NULL, baseName, screenName); if (tkwin == NULL) { return NULL; } /* * Create the TkMainInfo structure for this application, and set * up name-related information for the new window. */ winPtr = (TkWindow *) tkwin; mainPtr = (TkMainInfo *) ckalloc(sizeof(TkMainInfo)); mainPtr->winPtr = winPtr; mainPtr->refCount = 1; mainPtr->interp = interp; Tcl_InitHashTable(&mainPtr->nameTable, TCL_STRING_KEYS); TkBindInit(mainPtr); TkFontPkgInit(mainPtr); mainPtr->tlFocusPtr = NULL; mainPtr->displayFocusPtr = NULL; mainPtr->optionRootPtr = NULL; Tcl_InitHashTable(&mainPtr->imageTable, TCL_STRING_KEYS); mainPtr->strictMotif = 0; if (Tcl_LinkVar(interp, "tk_strictMotif", (char *) &mainPtr->strictMotif, TCL_LINK_BOOLEAN) != TCL_OK) { Tcl_ResetResult(interp); } mainPtr->nextPtr = tkMainWindowList; tkMainWindowList = mainPtr; winPtr->mainPtr = mainPtr; hPtr = Tcl_CreateHashEntry(&mainPtr->nameTable, ".", &dummy); Tcl_SetHashValue(hPtr, winPtr); winPtr->pathName = Tcl_GetHashKey(&mainPtr->nameTable, hPtr); /* * We have just created another Tk application; increment the refcount * on the display pointer. */ winPtr->dispPtr->refCount++; /* * Register the interpreter for "send" purposes. */ winPtr->nameUid = Tk_GetUid(Tk_SetAppName(tkwin, baseName)); /* * Bind in Tk's commands. */ isSafe = Tcl_IsSafe(interp); for (cmdPtr = commands; cmdPtr->name != NULL; cmdPtr++) { if ((cmdPtr->cmdProc == NULL) && (cmdPtr->objProc == NULL)) { panic("TkCreateMainWindow: builtin command with NULL string and object procs"); } if (cmdPtr->cmdProc != NULL) { Tcl_CreateCommand(interp, cmdPtr->name, cmdPtr->cmdProc, (ClientData) tkwin, (void (*) _ANSI_ARGS_((ClientData))) NULL); } else { Tcl_CreateObjCommand(interp, cmdPtr->name, cmdPtr->objProc, (ClientData) tkwin, NULL); } if (isSafe) { if (!(cmdPtr->isSafe)) { Tcl_HideCommand(interp, cmdPtr->name, cmdPtr->name); } } } /* * Set variables for the intepreter. */ Tcl_SetVar(interp, "tk_patchLevel", TK_PATCH_LEVEL, TCL_GLOBAL_ONLY); Tcl_SetVar(interp, "tk_version", TK_VERSION, TCL_GLOBAL_ONLY); numMainWindows++; return tkwin;}/* *-------------------------------------------------------------- * * Tk_CreateWindow -- * * Create a new internal or top-level window as a child of an * existing window. * * Results: * The return value is a token for the new window. This * is not the same as X's token for the window. If an error * occurred in creating the window (e.g. no such display or * screen), then an error message is left in interp->result and * NULL is returned. * * Side effects: * A new window structure is allocated locally. An X * window is not initially created, but will be created * the first time the window is mapped. * *-------------------------------------------------------------- */Tk_WindowTk_CreateWindow(interp, parent, name, screenName) Tcl_Interp *interp; /* Interpreter to use for error reporting. * Interp->result is assumed to be * initialized by the caller. */ Tk_Window parent; /* Token for parent of new window. */ char *name; /* Name for new window. Must be unique * among parent's children. */ char *screenName; /* If NULL, new window will be internal on * same screen as its parent. If non-NULL, * gives name of screen on which to create * new window; window will be a top-level * window. */{ TkWindow *parentPtr = (TkWindow *) parent; TkWindow *winPtr; if ((parentPtr != NULL) && (parentPtr->flags & TK_ALREADY_DEAD)) { Tcl_AppendResult(interp, "can't create window: parent has been destroyed", (char *) NULL); return NULL; } else if ((parentPtr != NULL) && (parentPtr->flags & TK_CONTAINER)) { Tcl_AppendResult(interp, "can't create window: its parent has -container = yes", (char *) NULL); return NULL; } if (screenName == NULL) { winPtr = TkAllocWindow(parentPtr->dispPtr, parentPtr->screenNum, parentPtr); if (NameWindow(interp, winPtr, parentPtr, name) != TCL_OK) { Tk_DestroyWindow((Tk_Window) winPtr); return NULL; } else { return (Tk_Window) winPtr; } } else { return CreateTopLevelWindow(interp, parent, name, screenName); }}/* *---------------------------------------------------------------------- * * Tk_CreateWindowFromPath -- * * This procedure is similar to Tk_CreateWindow except that * it uses a path name to create the window, rather than a * parent and a child name. * * Results: * The return value is a token for the new window. This * is not the same as X's token for the window. If an error * occurred in creating the window (e.g. no such display or * screen), then an error message is left in interp->result and * NULL is returned. * * Side effects: * A new window structure is allocated locally. An X * window is not initially created, but will be created
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -