void TkDrawInsetFocusHighlight( Tk_Window tkwin, /* Window whose focus highlight ring is to be * drawn. */ GC gc, /* Graphics context to use for drawing the * highlight ring. */ int width, /* Width of the highlight ring, in pixels. */ Drawable drawable, /* Where to draw the ring (typically a pixmap * for double buffering). */ int padding) /* Width of padding outside of widget. */ { XRectangle rects[4]; rects[0].x = padding; rects[0].y = padding; rects[0].width = Tk_Width(tkwin) - (2 * padding); rects[0].height = width; rects[1].x = padding; rects[1].y = Tk_Height(tkwin) - width - padding; rects[1].width = Tk_Width(tkwin) - (2 * padding); rects[1].height = width; rects[2].x = padding; rects[2].y = width + padding; rects[2].width = width; rects[2].height = Tk_Height(tkwin) - 2*width - 2*padding; rects[3].x = Tk_Width(tkwin) - width - padding; rects[3].y = rects[2].y; rects[3].width = width; rects[3].height = rects[2].height; XFillRectangles(Tk_Display(tkwin), drawable, gc, rects, 4); }
void callGraphDisplay::rethink_nominal_centerx() { // using Tk_Width(theTkWindow) as the available screen width, and // using root->myEntireWidthAsDrawn(consts) as the amount of screen real // estate used, this routine rethinks this->nominal_centerx. const int horizSpaceUsedByTree = rootPtr->entire_width(consts); // If the entire tree fits, then set center-x to window-width / 2. // Otherwise, set center-x to used-width / 2; if (horizSpaceUsedByTree <= Tk_Width(consts.theTkWindow)) nominal_centerx = Tk_Width(consts.theTkWindow) / 2; else nominal_centerx = horizSpaceUsedByTree / 2; }
int C_StretchBoxProc(ClientData cl, Tcl_Interp *interp, int argc, char **argv) { double x2,y2,xtemp2,ytemp2; Pixmap pm; XRectangle theClientArea; Tk_Window tkwin; WindowType theWindow = theWindowArray[atoi(argv[1])]; tkwin = theWindow->tkwin; theClientArea.x = 0; theClientArea.y = 0; theClientArea.width = Tk_Width(tkwin); theClientArea.height = Tk_Height(tkwin); XSetClipRectangles(theDisplay, theWindow->xwingc, 0, 0, &theClientArea, 1, Unsorted); pm = XCreatePixmap(theDisplay, Tk_WindowId(tkwin), Tk_Width(tkwin), Tk_Height(tkwin), Tk_Depth(tkwin)); XCopyArea(theDisplay, theWindow->pixmap_buffer, pm, theWindow->xwingc, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 0, 0); x2 = atof(argv[2]); y2 = atof(argv[3]); if (Is_X_Log(theWindow)) { xtemp2 = theWindow->c1 * log10(max(x2, DBL_MIN)) + theWindow->d1; } else { xtemp2 = theWindow->c1 * x2 + theWindow->d1; } if (Is_Y_Log(theWindow)) { ytemp2 = theWindow->c2 * log10(max(y2, DBL_MIN)) + theWindow->d2; } else { ytemp2 = theWindow->c2 * y2 + theWindow->d2; } XSetForeground(theDisplay, theWindow->xwingc, theWhitePixel); XDrawRectangle(theDisplay, pm, theWindow->xwingc, min(xtemp1,xtemp2), min(ytemp1,ytemp2), fabs(xtemp2 - xtemp1), fabs(ytemp2 - ytemp1)); XCopyArea(theDisplay, pm, Tk_WindowId(tkwin), theWindow->xwingc, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 0, 0); XFlush(theDisplay); XFreePixmap(theDisplay, pm); return TCL_OK; }
void callGraphDisplay::resize(bool currentlyDisplayedAbstraction) { const int newWindowWidth = Tk_Width(consts.theTkWindow); // const int newWindowHeight = Tk_Height(consts.theTkWindow); [not used] consts.resize(); // reallocates offscreen pixmap; rethinks //listboxHeightWhereSBappears' // Loop through EVERY listbox (gasp) and rethink whether or not it needs // a scrollbar and (possibly) change listBoxActualHeight... // _Must_ go _after_ the consts.resize() (void)rootPtr->rethinkListboxAfterResize(consts); // Now the more conventional resize code: rootPtr->rethinkAfterResize(consts, newWindowWidth); rethink_nominal_centerx(); // must go _after_ the rootPtr->rethinkAfterResize() if (currentlyDisplayedAbstraction) { // We have changed axis width and/or height. Let's inform tcl, so it may // rethink the scrollbar ranges. resizeScrollbars(); // Now, let's update our own stored horiz & vert scrollbar offset values adjustHorizSBOffset(); // obtain FirstPix from the actual tk scrollbar adjustVertSBOffset (); // obtain FirstPix from the actual tk scrollbar } }
int TkScaleValueToPixel( register TkScale *scalePtr, /* Information about widget. */ double value) /* Reading of the widget. */ { int y, pixelRange; double valueRange; valueRange = scalePtr->toValue - scalePtr->fromValue; pixelRange = ((scalePtr->orient == ORIENT_VERTICAL) ? Tk_Height(scalePtr->tkwin) : Tk_Width(scalePtr->tkwin)) - scalePtr->sliderLength - 2*scalePtr->inset - 2*scalePtr->borderWidth; if (valueRange == 0) { y = 0; } else { y = (int) ((value - scalePtr->fromValue) * pixelRange / valueRange + 0.5); if (y < 0) { y = 0; } else if (y > pixelRange) { y = pixelRange; } } y += scalePtr->sliderLength/2 + scalePtr->inset + scalePtr->borderWidth; return y; }
/* ** Map any control that should be visible according to the ** current scroll position. At the same time, if any controls that ** should not be visible are mapped, unmap them. After this routine ** finishes, all <INPUT> controls should be in their proper places ** regardless of where they might have been before. ** ** Return the number of controls that are currently visible. */ int HtmlMapControls(HtmlWidget *htmlPtr){ HtmlElement *p; /* For looping over all controls */ int x, y, w, h; /* Part of the virtual canvas that is visible */ int cnt = 0; /* Number of visible controls */ x = htmlPtr->xOffset; y = htmlPtr->yOffset; w = Tk_Width(htmlPtr->clipwin); h = Tk_Height(htmlPtr->clipwin); for(p=htmlPtr->firstInput; p; p=p->input.pNext){ if( p->input.tkwin==0 ) continue; if( p->input.y < y+h && p->input.y + p->input.h > y && p->input.x < x+w && p->input.x + p->input.w > x ){ /* The control should be visible. Make is so if it isn't already */ Tk_MoveResizeWindow(p->input.tkwin, p->input.x - x, p->input.y - y, p->input.w, p->input.h); if( !Tk_IsMapped(p->input.tkwin) ){ Tk_MapWindow(p->input.tkwin); } cnt++; }else{ /* This control should not be visible. Unmap it. */ if( Tk_IsMapped(p->input.tkwin) ){ Tk_UnmapWindow(p->input.tkwin); } } } return cnt; }
/* PlacePanes -- * Places slave panes based on sash positions. */ static void PlacePanes(Paned *pw) { int horizontal = pw->paned.orient == TTK_ORIENT_HORIZONTAL; int width = Tk_Width(pw->core.tkwin), height = Tk_Height(pw->core.tkwin); int sashThickness = pw->paned.sashThickness; int pos = 0; int index; for (index = 0; index < Ttk_NumberSlaves(pw->paned.mgr); ++index) { Pane *pane = Ttk_SlaveData(pw->paned.mgr, index); int size = pane->sashPos - pos; if (size > 0) { if (horizontal) { Ttk_PlaceSlave(pw->paned.mgr, index, pos, 0, size, height); } else { Ttk_PlaceSlave(pw->paned.mgr, index, 0, pos, width, size); } } else { Ttk_UnmapSlave(pw->paned.mgr, index); } pos = pane->sashPos + sashThickness; } }
static void ContainerEventProc( ClientData clientData, /* Token for container window. */ XEvent *eventPtr) /* ResizeRequest event. */ { Container *containerPtr = (Container *)clientData; Tk_Window tkwin = (Tk_Window)containerPtr->parentPtr; if (eventPtr->type == ConfigureNotify) { /* * Resize the embedded window, if there is any. */ if (containerPtr->embeddedHWnd) { SetWindowPos(containerPtr->embeddedHWnd, NULL, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), SWP_NOZORDER); } } else if (eventPtr->type == DestroyNotify) { /* * The container is gone, remove it from the list. */ EmbedWindowDeleted(containerPtr->parentPtr); } }
static void EmbedStructureProc( ClientData clientData, /* Token for container window. */ XEvent *eventPtr) /* ResizeRequest event. */ { Container *containerPtr = clientData; Tk_ErrorHandler errHandler; if (eventPtr->type == ConfigureNotify) { if (containerPtr->embedded != None) { /* * Ignore errors, since the embedded application could have * deleted its window. */ errHandler = Tk_CreateErrorHandler(eventPtr->xfocus.display, -1, -1, -1, NULL, NULL); Tk_MoveResizeWindow((Tk_Window) containerPtr->embeddedPtr, 0, 0, (unsigned) Tk_Width((Tk_Window) containerPtr->parentPtr), (unsigned) Tk_Height((Tk_Window)containerPtr->parentPtr)); Tk_DeleteErrorHandler(errHandler); } } else if (eventPtr->type == DestroyNotify) { EmbedWindowDeleted(containerPtr->parentPtr); } }
static void DisplayHorizontalValue( register TkScale *scalePtr, /* Information about widget in which to * display value. */ Drawable drawable, /* Pixmap or window in which to draw the * value. */ double value, /* X-coordinate of number to display, * specified in application coords, not in * pixels (we'll compute pixels). */ int top) /* Y-coordinate of top edge of text, specified * in pixels. */ { register Tk_Window tkwin = scalePtr->tkwin; int x, y, length, width; char valueString[PRINT_CHARS]; Tk_FontMetrics fm; x = TkScaleValueToPixel(scalePtr, value); Tk_GetFontMetrics(scalePtr->tkfont, &fm); y = top + fm.ascent; sprintf(valueString, scalePtr->format, value); length = (int) strlen(valueString); width = Tk_TextWidth(scalePtr->tkfont, valueString, length); /* * Adjust the x-coordinate if necessary to keep the text entirely inside * the window. */ x -= (width)/2; if (x < (scalePtr->inset + SPACING)) { x = scalePtr->inset + SPACING; } /* * Check the right border so use starting point +text width for the check. */ if (x + width >= (Tk_Width(tkwin) - scalePtr->inset)) { x = Tk_Width(tkwin) - scalePtr->inset - SPACING - width; } Tk_DrawChars(scalePtr->display, drawable, scalePtr->textGC, scalePtr->tkfont, valueString, length, x, y); }
void callGraphDisplay::draw(bool doubleBuffer, bool xsynchronize // are we debugging? ) const { Drawable theDrawable = (doubleBuffer && !xsynchronize) ? consts.offscreenPixmap : Tk_WindowId(consts.theTkWindow); if (doubleBuffer || xsynchronize) // clear the offscreen pixmap before drawing onto it XFillRectangle(consts.display, theDrawable, consts.erasingGC, 0, // x-offset relative to drawable 0, // y-offset relative to drawable Tk_Width(consts.theTkWindow), Tk_Height(consts.theTkWindow) ); const int overallWindowBorderPix = 0; if (rootPtr) rootPtr->draw(consts.theTkWindow, consts, theDrawable, nominal_centerx + horizScrollBarOffset, // relative (not absolute) coord overallWindowBorderPix + vertScrollBarOffset, // relative (not absolute) coord false, // not root only false // not listbox only ); if (doubleBuffer && !xsynchronize) { // copy from offscreen pixmap onto the 'real' window XCopyArea(consts.display, theDrawable, // source pixmap Tk_WindowId(consts.theTkWindow), // dest pixmap consts.listboxCopyAreaGC, 0, 0, // source x,y pix Tk_Width(consts.theTkWindow), Tk_Height(consts.theTkWindow), 0, 0 // dest x,y offset pix ); } }
void callGraphDisplay::resizeScrollbars() { pdstring commandStr = pdstring("resize1Scrollbar ") + horizSBName + " " + pdstring(rootPtr->entire_width(consts)) + " " + pdstring(Tk_Width(consts.theTkWindow)); myTclEval(interp, commandStr); commandStr = pdstring("resize1Scrollbar ") + vertSBName + " " + pdstring(rootPtr->entire_height(consts)) + " " + pdstring(Tk_Height(consts.theTkWindow)); myTclEval(interp, commandStr); }
void TkpDrawFrame( Tk_Window tkwin, Tk_3DBorder border, int highlightWidth, int borderWidth, int relief) { Tk_Fill3DRectangle(tkwin, Tk_WindowId(tkwin), border, highlightWidth, highlightWidth, Tk_Width(tkwin) - 2 * highlightWidth, Tk_Height(tkwin) - 2 * highlightWidth, borderWidth, relief); }
static void ImageDraw( ImageElement *image, Tk_Window tkwin,Drawable d,Ttk_Box b,Ttk_State state) { int width = image->width, height = image->height; /* Clip width and height to remain within window bounds: */ if (b.x + width > Tk_Width(tkwin)) { width = Tk_Width(tkwin) - b.x; } if (b.y + height > Tk_Height(tkwin)) { height = Tk_Height(tkwin) - b.y; } if (height <= 0 || width <= 0) { /* Completely clipped - bail out. */ return; } Tk_RedrawImage(image->tkimg, 0,0, width, height, d, b.x, b.y); /* If we're disabled there's no state-specific 'disabled' image, * stipple the image. * @@@ Possibly: Don't do disabled-stippling at all; * @@@ it's ugly and out of fashion. * Do not stipple at all under Aqua, just draw the image: it shows up * as a white rectangle otherwise. */ if (state & TTK_STATE_DISABLED) { if (TtkSelectImage(image->imageSpec, 0ul) == image->tkimg) { #ifndef MAC_OSX_TK StippleOver(image, tkwin, d, b.x,b.y); #endif } } }
static void BackgroundElementDraw( void *clientData, void *elementRecord, Tk_Window tkwin, Drawable d, Ttk_Box b, unsigned state) { if (qApp == NULL) NULL_Q_APP; NULL_PROXY_WIDGET(TileQt_QWidget_Widget); Tcl_MutexLock(&tileqtMutex); int width = Tk_Width(tkwin), height = Tk_Height(tkwin); QPixmap pixmap(width, height); QPainter painter(&pixmap); TILEQT_PAINT_BACKGROUND(width, height); TileQt_CopyQtPixmapOnToDrawable(pixmap, d, tkwin, 0, 0, width, height, 0, 0); Tcl_MutexUnlock(&tileqtMutex); }
/* *-------------------------------------------------------------- * * ButtonBackgroundDrawCB -- * * This function draws the background that * lies under checkboxes and radiobuttons. * * Results: * None. * * Side effects: * The background gets updated to the current color. * *-------------------------------------------------------------- */ static void ButtonBackgroundDrawCB ( const HIRect * btnbounds, MacButton *ptr, SInt16 depth, Boolean isColorDev) { MacButton* mbPtr = (MacButton*)ptr; TkButton* butPtr = (TkButton*)mbPtr; Tk_Window tkwin = butPtr->tkwin; Pixmap pixmap; int usehlborder = 0; if (tkwin == NULL || !Tk_IsMapped(tkwin)) { return; } pixmap = (Pixmap)Tk_WindowId(tkwin); if (butPtr->type != TYPE_LABEL) { switch (mbPtr->btnkind) { case kThemeSmallBevelButton: case kThemeBevelButton: case kThemeRoundedBevelButton: case kThemePushButton: usehlborder = 1; break; } } if (usehlborder) { Tk_Fill3DRectangle(tkwin, pixmap, butPtr->highlightBorder, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 0, TK_RELIEF_FLAT); } else { Tk_Fill3DRectangle(tkwin, pixmap, butPtr->normalBorder, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 0, TK_RELIEF_FLAT); } }
/* SashLayout -- * Place the sash sublayout after the specified pane, * in preparation for drawing. */ static Ttk_Layout SashLayout(Paned *pw, int index) { Pane *pane = Ttk_SlaveData(pw->paned.mgr, index); int thickness = pw->paned.sashThickness, height = Tk_Height(pw->core.tkwin), width = Tk_Width(pw->core.tkwin), sashPos = pane->sashPos; Ttk_PlaceLayout( pw->paned.sashLayout, pw->core.state, pw->paned.orient == TTK_ORIENT_HORIZONTAL ? Ttk_MakeBox(sashPos, 0, thickness, height) : Ttk_MakeBox(0, sashPos, width, thickness)); return pw->paned.sashLayout; }
/* Post-configuration hook. */ static int PanedPostConfigure(Tcl_Interp *interp, void *clientData, int mask) { Paned *pw = clientData; if (mask & GEOMETRY_CHANGED) { /* User has changed -width or -height. * Recalculate sash positions based on requested size. */ Tk_Window tkwin = pw->core.tkwin; PlaceSashes(pw, pw->paned.width > 0 ? pw->paned.width : Tk_Width(tkwin), pw->paned.height > 0 ? pw->paned.height : Tk_Height(tkwin)); } return TCL_OK; }
int TkpScaleElement( TkScale *scalePtr, /* Widget record for scale. */ int x, int y) /* Coordinates within scalePtr's window. */ { int sliderFirst; if (scalePtr->orient == ORIENT_VERTICAL) { if ((x < scalePtr->vertTroughX) || (x >= (scalePtr->vertTroughX + 2*scalePtr->borderWidth + scalePtr->width))) { return OTHER; } if ((y < scalePtr->inset) || (y >= (Tk_Height(scalePtr->tkwin) - scalePtr->inset))) { return OTHER; } sliderFirst = TkScaleValueToPixel(scalePtr, scalePtr->value) - scalePtr->sliderLength/2; if (y < sliderFirst) { return TROUGH1; } if (y < (sliderFirst+scalePtr->sliderLength)) { return SLIDER; } return TROUGH2; } if ((y < scalePtr->horizTroughY) || (y >= (scalePtr->horizTroughY + 2*scalePtr->borderWidth + scalePtr->width))) { return OTHER; } if ((x < scalePtr->inset) || (x >= (Tk_Width(scalePtr->tkwin) - scalePtr->inset))) { return OTHER; } sliderFirst = TkScaleValueToPixel(scalePtr, scalePtr->value) - scalePtr->sliderLength/2; if (x < sliderFirst) { return TROUGH1; } if (x < (sliderFirst+scalePtr->sliderLength)) { return SLIDER; } return TROUGH2; }
static PyObject * getintattr(TkWinObject * self, char * name) { int value; if (*name == 'w' && strcmp(name, "width") == 0) value = Tk_Width(self->tkwin); else if (*name == 'h' && strcmp(name, "height") == 0) value = Tk_Height(self->tkwin); else if (*name == 'x' && name[1] == '\0') value = Tk_X(self->tkwin); else if (*name == 'y' && name[1] == '\0') value = Tk_Y(self->tkwin); else if (*name == 'd' && strcmp(name, "depth") == 0) value = Tk_Depth(self->tkwin); else return NULL; return PyInt_FromLong(value); }
static int WinItemToPostscript( Tcl_Interp *interp, /* Leave Postscript or error message here. */ Tk_Canvas canvas, /* Information about overall canvas. */ Tk_Item *itemPtr, /* Item for which Postscript is wanted. */ int prepass) /* 1 means this is a prepass to collect font * information; 0 means final Postscript is * being created. */ { WindowItem *winItemPtr = (WindowItem *) itemPtr; double x, y; int width, height; Tk_Window tkwin = winItemPtr->tkwin; if (prepass || winItemPtr->tkwin == NULL) { return TCL_OK; } width = Tk_Width(tkwin); height = Tk_Height(tkwin); /* * Compute the coordinates of the lower-left corner of the window, taking * into account the anchor position for the window. */ x = winItemPtr->x; y = Tk_CanvasPsY(canvas, winItemPtr->y); switch (winItemPtr->anchor) { case TK_ANCHOR_NW: y -= height; break; case TK_ANCHOR_N: x -= width/2.0; y -= height; break; case TK_ANCHOR_NE: x -= width; y -= height; break; case TK_ANCHOR_E: x -= width; y -= height/2.0; break; case TK_ANCHOR_SE: x -= width; break; case TK_ANCHOR_S: x -= width/2.0; break; case TK_ANCHOR_SW: break; case TK_ANCHOR_W: y -= height/2.0; break; case TK_ANCHOR_CENTER: x -= width/2.0; y -= height/2.0; break; } return CanvasPsWindow(interp, tkwin, canvas, x, y, width, height); }
static PyObject * tkwin_CreatePixmap(TkWinObject * self, PyObject * args) { Tk_Window tkwin = self->tkwin; Display *display = Tk_Display(self->tkwin); int width, height; int depth; Pixmap pixmap; Drawable d; display = Tk_Display(tkwin); width = Tk_Width(tkwin); height = Tk_Height(tkwin); depth = Tk_Depth(tkwin); if (!PyArg_ParseTuple(args, "|iii", &width, &height, &depth)) return NULL; d = RootWindowOfScreen(Tk_Screen(tkwin)); pixmap = XCreatePixmap(display, d, width, height, depth); return PaxPixmap_FromPixmap(display, pixmap, 1); }
int Configure (ClientData, Tcl_Interp *interp, int, char **argv) { if (view.m_started) { Tk_Window win; Tcl_Eval(interp, "set f $CVLkDemo::curframe"); win = Tk_NameToWindow(interp, interp->result, Tk_MainWindow(interp)); Tk_MapWindow(win); int w = Tk_Width(win); int h = Tk_Height(win); cvcamSetProperty(0, CVCAM_RNDWIDTH, (void*)&w); cvcamSetProperty(0, CVCAM_RNDHEIGHT, (void*)&h); view.SetSize(w,h); } return TCL_OK; }
double TkScalePixelToValue( register TkScale *scalePtr, /* Information about widget. */ int x, int y) /* Coordinates of point within window. */ { double value, pixelRange; if (scalePtr->orient == ORIENT_VERTICAL) { pixelRange = Tk_Height(scalePtr->tkwin) - scalePtr->sliderLength - 2*scalePtr->inset - 2*scalePtr->borderWidth; value = y; } else { pixelRange = Tk_Width(scalePtr->tkwin) - scalePtr->sliderLength - 2*scalePtr->inset - 2*scalePtr->borderWidth; value = x; } if (pixelRange <= 0) { /* * Not enough room for the slider to actually slide: just return the * scale's current value. */ return scalePtr->value; } value -= scalePtr->sliderLength/2 + scalePtr->inset + scalePtr->borderWidth; value /= pixelRange; if (value < 0) { value = 0; } if (value > 1) { value = 1; } value = scalePtr->fromValue + value * (scalePtr->toValue - scalePtr->fromValue); return TkRoundToResolution(scalePtr, value); }
void TkpDisplayMenuButton( ClientData clientData) /* Information about widget. */ { MacMenuButton *mbPtr = (MacMenuButton *)clientData; TkMenuButton *butPtr = (TkMenuButton *) clientData; Tk_Window tkwin = butPtr->tkwin; Pixmap pixmap; DrawParams* dpPtr = &mbPtr->drawParams; butPtr->flags &= ~REDRAW_PENDING; if ((butPtr->tkwin == NULL) || !Tk_IsMapped(tkwin)) { return; } pixmap = (Pixmap) Tk_WindowId(tkwin); TkMacOSXComputeMenuButtonDrawParams(butPtr, dpPtr); /* * set up clipping region. Make sure the we are using the port * for this button, or we will set the wrong window's clip. */ TkMacOSXSetUpClippingRgn(pixmap); /* Draw the native portion of the buttons. */ TkMacOSXDrawMenuButton(mbPtr, dpPtr->gc, pixmap); /* Draw highlight border, if needed. */ if (butPtr->highlightWidth < 3) { if ((butPtr->flags & GOT_FOCUS)) { Tk_Draw3DRectangle(tkwin, pixmap, butPtr->normalBorder, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), butPtr->highlightWidth, TK_RELIEF_SOLID); } } }
void TkpDisplayButton( ClientData clientData) /* Information about widget. */ { register TkButton *butPtr = (TkButton *) clientData; GC gc; Tk_3DBorder border; Pixmap pixmap; int x = 0; /* Initialization only needed to stop compiler * warning. */ int y, relief; Tk_Window tkwin = butPtr->tkwin; int width, height, fullWidth, fullHeight; int textXOffset, textYOffset; int haveImage = 0, haveText = 0; int offset; /* 1 means this is a button widget, so we * offset the text to make the button appear * to move up and down as the relief * changes. */ int imageWidth, imageHeight; int imageXOffset = 0, imageYOffset = 0; /* image information that will be used to * restrict disabled pixmap as well */ butPtr->flags &= ~REDRAW_PENDING; if ((butPtr->tkwin == NULL) || !Tk_IsMapped(tkwin)) { return; } border = butPtr->normalBorder; if ((butPtr->state == STATE_DISABLED) && (butPtr->disabledFg != NULL)) { gc = butPtr->disabledGC; } else if ((butPtr->state == STATE_ACTIVE) && !Tk_StrictMotif(butPtr->tkwin)) { gc = butPtr->activeTextGC; border = butPtr->activeBorder; } else { gc = butPtr->normalTextGC; } if ((butPtr->flags & SELECTED) && (butPtr->state != STATE_ACTIVE) && (butPtr->selectBorder != NULL) && !butPtr->indicatorOn) { border = butPtr->selectBorder; } /* * Override the relief specified for the button if this is a checkbutton * or radiobutton and there's no indicator. The new relief is as follows: * If the button is select --> "sunken" * If relief==overrelief --> relief * Otherwise --> overrelief * * The effect we are trying to achieve is as follows: * * value mouse-over? --> relief * ------- ------------ -------- * off no flat * off yes raised * on no sunken * on yes sunken * * This is accomplished by configuring the checkbutton or radiobutton like * this: * * -indicatoron 0 -overrelief raised -offrelief flat * * Bindings (see library/button.tcl) will copy the -overrelief into * -relief on mouseover. Hence, we can tell if we are in mouse-over by * comparing relief against overRelief. This is an aweful kludge, but it * gives use the desired behavior while keeping the code backwards * compatible. */ relief = butPtr->relief; if ((butPtr->type >= TYPE_CHECK_BUTTON) && !butPtr->indicatorOn) { if (butPtr->flags & SELECTED) { relief = TK_RELIEF_SUNKEN; } else if (butPtr->overRelief != relief) { relief = butPtr->offRelief; } } offset = (butPtr->type == TYPE_BUTTON) && !Tk_StrictMotif(butPtr->tkwin); /* * In order to avoid screen flashes, this function redraws the button in a * pixmap, then copies the pixmap to the screen in a single operation. * This means that there's no point in time where the on-screen image has * been cleared. */ pixmap = Tk_GetPixmap(butPtr->display, Tk_WindowId(tkwin), Tk_Width(tkwin), Tk_Height(tkwin), Tk_Depth(tkwin)); Tk_Fill3DRectangle(tkwin, pixmap, border, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 0, TK_RELIEF_FLAT); /* * Display image or bitmap or text for button. */ if (butPtr->image != NULL) { Tk_SizeOfImage(butPtr->image, &width, &height); haveImage = 1; } else if (butPtr->bitmap != None) { Tk_SizeOfBitmap(butPtr->display, butPtr->bitmap, &width, &height); haveImage = 1; } imageWidth = width; imageHeight = height; haveText = (butPtr->textWidth != 0 && butPtr->textHeight != 0); if (butPtr->compound != COMPOUND_NONE && haveImage && haveText) { textXOffset = 0; textYOffset = 0; fullWidth = 0; fullHeight = 0; switch ((enum compound) butPtr->compound) { case COMPOUND_TOP: case COMPOUND_BOTTOM: /* * Image is above or below text. */ if (butPtr->compound == COMPOUND_TOP) { textYOffset = height + butPtr->padY; } else { imageYOffset = butPtr->textHeight + butPtr->padY; } fullHeight = height + butPtr->textHeight + butPtr->padY; fullWidth = (width > butPtr->textWidth ? width : butPtr->textWidth); textXOffset = (fullWidth - butPtr->textWidth)/2; imageXOffset = (fullWidth - width)/2; break; case COMPOUND_LEFT: case COMPOUND_RIGHT: /* * Image is left or right of text. */ if (butPtr->compound == COMPOUND_LEFT) { textXOffset = width + butPtr->padX; } else { imageXOffset = butPtr->textWidth + butPtr->padX; } fullWidth = butPtr->textWidth + butPtr->padX + width; fullHeight = (height > butPtr->textHeight ? height : butPtr->textHeight); textYOffset = (fullHeight - butPtr->textHeight)/2; imageYOffset = (fullHeight - height)/2; break; case COMPOUND_CENTER: /* * Image and text are superimposed. */ fullWidth = (width > butPtr->textWidth ? width : butPtr->textWidth); fullHeight = (height > butPtr->textHeight ? height : butPtr->textHeight); textXOffset = (fullWidth - butPtr->textWidth)/2; imageXOffset = (fullWidth - width)/2; textYOffset = (fullHeight - butPtr->textHeight)/2; imageYOffset = (fullHeight - height)/2; break; case COMPOUND_NONE: break; } TkComputeAnchor(butPtr->anchor, tkwin, butPtr->padX, butPtr->padY, butPtr->indicatorSpace + fullWidth, fullHeight, &x, &y); x += butPtr->indicatorSpace; x += offset; y += offset; if (relief == TK_RELIEF_RAISED) { x -= offset; y -= offset; } else if (relief == TK_RELIEF_SUNKEN) { x += offset; y += offset; } imageXOffset += x; imageYOffset += y; if (butPtr->image != NULL) { /* * Do boundary clipping, so that Tk_RedrawImage is passed valid * coordinates. [Bug 979239] */ if (imageXOffset < 0) { imageXOffset = 0; } if (imageYOffset < 0) { imageYOffset = 0; } if (width > Tk_Width(tkwin)) { width = Tk_Width(tkwin); } if (height > Tk_Height(tkwin)) { height = Tk_Height(tkwin); } if ((width + imageXOffset) > Tk_Width(tkwin)) { imageXOffset = Tk_Width(tkwin) - width; } if ((height + imageYOffset) > Tk_Height(tkwin)) { imageYOffset = Tk_Height(tkwin) - height; } if ((butPtr->selectImage != NULL) && (butPtr->flags & SELECTED)) { Tk_RedrawImage(butPtr->selectImage, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } else if ((butPtr->tristateImage != NULL) && (butPtr->flags & TRISTATED)) { Tk_RedrawImage(butPtr->tristateImage, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } else { Tk_RedrawImage(butPtr->image, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } } else { XSetClipOrigin(butPtr->display, gc, imageXOffset, imageYOffset); XCopyPlane(butPtr->display, butPtr->bitmap, pixmap, gc, 0, 0, (unsigned int) width, (unsigned int) height, imageXOffset, imageYOffset, 1); XSetClipOrigin(butPtr->display, gc, 0, 0); } Tk_DrawTextLayout(butPtr->display, pixmap, gc, butPtr->textLayout, x + textXOffset, y + textYOffset, 0, -1); Tk_UnderlineTextLayout(butPtr->display, pixmap, gc, butPtr->textLayout, x + textXOffset, y + textYOffset, butPtr->underline); y += fullHeight/2; } else { if (haveImage) { TkComputeAnchor(butPtr->anchor, tkwin, 0, 0, butPtr->indicatorSpace + width, height, &x, &y); x += butPtr->indicatorSpace; x += offset; y += offset; if (relief == TK_RELIEF_RAISED) { x -= offset; y -= offset; } else if (relief == TK_RELIEF_SUNKEN) { x += offset; y += offset; } imageXOffset += x; imageYOffset += y; if (butPtr->image != NULL) { /* * Do boundary clipping, so that Tk_RedrawImage is passed * valid coordinates. [Bug 979239] */ if (imageXOffset < 0) { imageXOffset = 0; } if (imageYOffset < 0) { imageYOffset = 0; } if (width > Tk_Width(tkwin)) { width = Tk_Width(tkwin); } if (height > Tk_Height(tkwin)) { height = Tk_Height(tkwin); } if ((width + imageXOffset) > Tk_Width(tkwin)) { imageXOffset = Tk_Width(tkwin) - width; } if ((height + imageYOffset) > Tk_Height(tkwin)) { imageYOffset = Tk_Height(tkwin) - height; } if ((butPtr->selectImage != NULL) && (butPtr->flags & SELECTED)) { Tk_RedrawImage(butPtr->selectImage, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } else if ((butPtr->tristateImage != NULL) && (butPtr->flags & TRISTATED)) { Tk_RedrawImage(butPtr->tristateImage, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } else { Tk_RedrawImage(butPtr->image, 0, 0, width, height, pixmap, imageXOffset, imageYOffset); } } else { XSetClipOrigin(butPtr->display, gc, x, y); XCopyPlane(butPtr->display, butPtr->bitmap, pixmap, gc, 0, 0, (unsigned int) width, (unsigned int) height, x, y, 1); XSetClipOrigin(butPtr->display, gc, 0, 0); } y += height/2; } else { TkComputeAnchor(butPtr->anchor, tkwin, butPtr->padX, butPtr->padY, butPtr->indicatorSpace + butPtr->textWidth, butPtr->textHeight, &x, &y); x += butPtr->indicatorSpace; x += offset; y += offset; if (relief == TK_RELIEF_RAISED) { x -= offset; y -= offset; } else if (relief == TK_RELIEF_SUNKEN) { x += offset; y += offset; } Tk_DrawTextLayout(butPtr->display, pixmap, gc, butPtr->textLayout, x, y, 0, -1); Tk_UnderlineTextLayout(butPtr->display, pixmap, gc, butPtr->textLayout, x, y, butPtr->underline); y += butPtr->textHeight/2; } } /* * Draw the indicator for check buttons and radio buttons. At this point, * x and y refer to the top-left corner of the text or image or bitmap. */ if ((butPtr->type == TYPE_CHECK_BUTTON) && butPtr->indicatorOn) { if (butPtr->indicatorDiameter > 2*butPtr->borderWidth) { TkBorder *selBorder = (TkBorder *) butPtr->selectBorder; XColor *selColor = NULL; if (selBorder != NULL) { selColor = selBorder->bgColorPtr; } x -= butPtr->indicatorSpace/2; y = Tk_Height(tkwin)/2; TkpDrawCheckIndicator(tkwin, butPtr->display, pixmap, x, y, border, butPtr->normalFg, selColor, butPtr->disabledFg, ((butPtr->flags & SELECTED) ? 1 : (butPtr->flags & TRISTATED) ? 2 : 0), (butPtr->state == STATE_DISABLED), CHECK_BUTTON); } } else if ((butPtr->type == TYPE_RADIO_BUTTON) && butPtr->indicatorOn) { if (butPtr->indicatorDiameter > 2*butPtr->borderWidth) { TkBorder *selBorder = (TkBorder *) butPtr->selectBorder; XColor *selColor = NULL; if (selBorder != NULL) { selColor = selBorder->bgColorPtr; } x -= butPtr->indicatorSpace/2; y = Tk_Height(tkwin)/2; TkpDrawCheckIndicator(tkwin, butPtr->display, pixmap, x, y, border, butPtr->normalFg, selColor, butPtr->disabledFg, ((butPtr->flags & SELECTED) ? 1 : (butPtr->flags & TRISTATED) ? 2 : 0), (butPtr->state == STATE_DISABLED), RADIO_BUTTON); } } /* * If the button is disabled with a stipple rather than a special * foreground color, generate the stippled effect. If the widget is * selected and we use a different background color when selected, must * temporarily modify the GC so the stippling is the right color. */ if ((butPtr->state == STATE_DISABLED) && ((butPtr->disabledFg == NULL) || (butPtr->image != NULL))) { if ((butPtr->flags & SELECTED) && !butPtr->indicatorOn && (butPtr->selectBorder != NULL)) { XSetForeground(butPtr->display, butPtr->stippleGC, Tk_3DBorderColor(butPtr->selectBorder)->pixel); } /* * Stipple the whole button if no disabledFg was specified, otherwise * restrict stippling only to displayed image */ if (butPtr->disabledFg == NULL) { XFillRectangle(butPtr->display, pixmap, butPtr->stippleGC, 0, 0, (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin)); } else { XFillRectangle(butPtr->display, pixmap, butPtr->stippleGC, imageXOffset, imageYOffset, (unsigned) imageWidth, (unsigned) imageHeight); } if ((butPtr->flags & SELECTED) && !butPtr->indicatorOn && (butPtr->selectBorder != NULL)) { XSetForeground(butPtr->display, butPtr->stippleGC, Tk_3DBorderColor(butPtr->normalBorder)->pixel); } } /* * Draw the border and traversal highlight last. This way, if the button's * contents overflow they'll be covered up by the border. This code is * complicated by the possible combinations of focus highlight and default * rings. We draw the focus and highlight rings using the highlight border * and highlight foreground color. */ if (relief != TK_RELIEF_FLAT) { int inset = butPtr->highlightWidth; if (butPtr->defaultState == DEFAULT_ACTIVE) { /* * Draw the default ring with 2 pixels of space between the * default ring and the button and the default ring and the focus * ring. Note that we need to explicitly draw the space in the * highlightBorder color to ensure that we overwrite any overflow * text and/or a different button background color. */ Tk_Draw3DRectangle(tkwin, pixmap, butPtr->highlightBorder, inset, inset, Tk_Width(tkwin) - 2*inset, Tk_Height(tkwin) - 2*inset, 2, TK_RELIEF_FLAT); inset += 2; Tk_Draw3DRectangle(tkwin, pixmap, butPtr->highlightBorder, inset, inset, Tk_Width(tkwin) - 2*inset, Tk_Height(tkwin) - 2*inset, 1, TK_RELIEF_SUNKEN); inset++; Tk_Draw3DRectangle(tkwin, pixmap, butPtr->highlightBorder, inset, inset, Tk_Width(tkwin) - 2*inset, Tk_Height(tkwin) - 2*inset, 2, TK_RELIEF_FLAT); inset += 2; } else if (butPtr->defaultState == DEFAULT_NORMAL) { /* * Leave room for the default ring and write over any text or * background color. */ Tk_Draw3DRectangle(tkwin, pixmap, butPtr->highlightBorder, 0, 0, Tk_Width(tkwin), Tk_Height(tkwin), 5, TK_RELIEF_FLAT); inset += 5; } /* * Draw the button border. */ Tk_Draw3DRectangle(tkwin, pixmap, border, inset, inset, Tk_Width(tkwin) - 2*inset, Tk_Height(tkwin) - 2*inset, butPtr->borderWidth, relief); } if (butPtr->highlightWidth > 0) { GC gc; if (butPtr->flags & GOT_FOCUS) { gc = Tk_GCForColor(butPtr->highlightColorPtr, pixmap); } else { gc = Tk_GCForColor(Tk_3DBorderColor(butPtr->highlightBorder), pixmap); } /* * Make sure the focus ring shrink-wraps the actual button, not the * padding space left for a default ring. */ if (butPtr->defaultState == DEFAULT_NORMAL) { TkDrawInsetFocusHighlight(tkwin, gc, butPtr->highlightWidth, pixmap, 5); } else { Tk_DrawFocusHighlight(tkwin, gc, butPtr->highlightWidth, pixmap); } } /* * Copy the information from the off-screen pixmap onto the screen, then * delete the pixmap. */ XCopyArea(butPtr->display, pixmap, Tk_WindowId(tkwin), butPtr->copyGC, 0, 0, (unsigned) Tk_Width(tkwin), (unsigned) Tk_Height(tkwin), 0, 0); Tk_FreePixmap(butPtr->display, pixmap); }
void TkpDisplayScale( ClientData clientData) /* Widget record for scale. */ { TkScale *scalePtr = (TkScale *) clientData; Tk_Window tkwin = scalePtr->tkwin; Tcl_Interp *interp = scalePtr->interp; Pixmap pixmap; int result; char string[PRINT_CHARS]; XRectangle drawnArea; Tcl_DString buf; scalePtr->flags &= ~REDRAW_PENDING; if ((scalePtr->tkwin == NULL) || !Tk_IsMapped(scalePtr->tkwin)) { goto done; } /* * Invoke the scale's command if needed. */ Tcl_Preserve(scalePtr); if ((scalePtr->flags & INVOKE_COMMAND) && (scalePtr->command != NULL)) { Tcl_Preserve(interp); sprintf(string, scalePtr->format, scalePtr->value); Tcl_DStringInit(&buf); Tcl_DStringAppend(&buf, scalePtr->command, -1); Tcl_DStringAppend(&buf, " ", -1); Tcl_DStringAppend(&buf, string, -1); result = Tcl_EvalEx(interp, Tcl_DStringValue(&buf), -1, 0); Tcl_DStringFree(&buf); if (result != TCL_OK) { Tcl_AddErrorInfo(interp, "\n (command executed by scale)"); Tcl_BackgroundException(interp, result); } Tcl_Release(interp); } scalePtr->flags &= ~INVOKE_COMMAND; if (scalePtr->flags & SCALE_DELETED) { Tcl_Release(scalePtr); return; } Tcl_Release(scalePtr); #ifndef TK_NO_DOUBLE_BUFFERING /* * In order to avoid screen flashes, this function redraws the scale in a * pixmap, then copies the pixmap to the screen in a single operation. * This means that there's no point in time where the on-sreen image has * been cleared. */ pixmap = Tk_GetPixmap(scalePtr->display, Tk_WindowId(tkwin), Tk_Width(tkwin), Tk_Height(tkwin), Tk_Depth(tkwin)); #else pixmap = Tk_WindowId(tkwin); #endif /* TK_NO_DOUBLE_BUFFERING */ drawnArea.x = 0; drawnArea.y = 0; drawnArea.width = Tk_Width(tkwin); drawnArea.height = Tk_Height(tkwin); /* * Much of the redisplay is done totally differently for horizontal and * vertical scales. Handle the part that's different. */ if (scalePtr->orient == ORIENT_VERTICAL) { DisplayVerticalScale(scalePtr, pixmap, &drawnArea); } else { DisplayHorizontalScale(scalePtr, pixmap, &drawnArea); } /* * Now handle the part of redisplay that is the same for horizontal and * vertical scales: border and traversal highlight. */ if (scalePtr->flags & REDRAW_OTHER) { if (scalePtr->relief != TK_RELIEF_FLAT) { Tk_Draw3DRectangle(tkwin, pixmap, scalePtr->bgBorder, scalePtr->highlightWidth, scalePtr->highlightWidth, Tk_Width(tkwin) - 2*scalePtr->highlightWidth, Tk_Height(tkwin) - 2*scalePtr->highlightWidth, scalePtr->borderWidth, scalePtr->relief); } if (scalePtr->highlightWidth != 0) { GC gc; if (scalePtr->flags & GOT_FOCUS) { gc = Tk_GCForColor(scalePtr->highlightColorPtr, pixmap); } else { gc = Tk_GCForColor( Tk_3DBorderColor(scalePtr->highlightBorder), pixmap); } Tk_DrawFocusHighlight(tkwin, gc, scalePtr->highlightWidth, pixmap); } } #ifndef TK_NO_DOUBLE_BUFFERING /* * Copy the information from the off-screen pixmap onto the screen, then * delete the pixmap. */ XCopyArea(scalePtr->display, pixmap, Tk_WindowId(tkwin), scalePtr->copyGC, drawnArea.x, drawnArea.y, drawnArea.width, drawnArea.height, drawnArea.x, drawnArea.y); Tk_FreePixmap(scalePtr->display, pixmap); #endif /* TK_NO_DOUBLE_BUFFERING */ done: scalePtr->flags &= ~REDRAW_ALL; }
static void DisplayHorizontalScale( TkScale *scalePtr, /* Widget record for scale. */ Drawable drawable, /* Where to display scale (window or * pixmap). */ XRectangle *drawnAreaPtr) /* Initally contains area of window; if only a * part of the scale is redrawn, gets modified * to reflect the part of the window that was * redrawn. */ { register Tk_Window tkwin = scalePtr->tkwin; int x, y, width, height, shadowWidth; double tickValue, tickInterval = scalePtr->tickInterval; Tk_3DBorder sliderBorder; /* * Display the information from bottom to top across the window. */ if (!(scalePtr->flags & REDRAW_OTHER)) { drawnAreaPtr->x = scalePtr->inset; drawnAreaPtr->y = scalePtr->horizValueY; drawnAreaPtr->width -= 2*scalePtr->inset; drawnAreaPtr->height = scalePtr->horizTroughY + scalePtr->width + 2*scalePtr->borderWidth - scalePtr->horizValueY; } Tk_Fill3DRectangle(tkwin, drawable, scalePtr->bgBorder, drawnAreaPtr->x, drawnAreaPtr->y, drawnAreaPtr->width, drawnAreaPtr->height, 0, TK_RELIEF_FLAT); if (scalePtr->flags & REDRAW_OTHER) { /* * Display the tick marks. */ if (tickInterval != 0) { char valueString[PRINT_CHARS]; double ticks, maxTicks; /* * Ensure that we will only draw enough of the tick values such * that they don't overlap. We base this off the width that * fromValue would take. Not exact, but better than no constraint. */ ticks = fabs((scalePtr->toValue - scalePtr->fromValue) / tickInterval); sprintf(valueString, scalePtr->format, scalePtr->fromValue); maxTicks = (double) Tk_Width(tkwin) / (double) Tk_TextWidth(scalePtr->tkfont, valueString, -1); if (ticks > maxTicks) { tickInterval *= (ticks / maxTicks); } for (tickValue = scalePtr->fromValue; ; tickValue += tickInterval) { /* * The TkRoundToResolution call gets rid of accumulated * round-off errors, if any. */ tickValue = TkRoundToResolution(scalePtr, tickValue); if (scalePtr->toValue >= scalePtr->fromValue) { if (tickValue > scalePtr->toValue) { break; } } else { if (tickValue < scalePtr->toValue) { break; } } DisplayHorizontalValue(scalePtr, drawable, tickValue, scalePtr->horizTickY); } } } /* * Display the value, if it is desired. */ if (scalePtr->showValue) { DisplayHorizontalValue(scalePtr, drawable, scalePtr->value, scalePtr->horizValueY); } /* * Display the trough and the slider. */ y = scalePtr->horizTroughY; Tk_Draw3DRectangle(tkwin, drawable, scalePtr->bgBorder, scalePtr->inset, y, Tk_Width(tkwin) - 2*scalePtr->inset, scalePtr->width + 2*scalePtr->borderWidth, scalePtr->borderWidth, TK_RELIEF_SUNKEN); XFillRectangle(scalePtr->display, drawable, scalePtr->troughGC, scalePtr->inset + scalePtr->borderWidth, y + scalePtr->borderWidth, (unsigned) (Tk_Width(tkwin) - 2*scalePtr->inset - 2*scalePtr->borderWidth), (unsigned) scalePtr->width); if (scalePtr->state == STATE_ACTIVE) { sliderBorder = scalePtr->activeBorder; } else { sliderBorder = scalePtr->bgBorder; } width = scalePtr->sliderLength/2; height = scalePtr->width; x = TkScaleValueToPixel(scalePtr, scalePtr->value) - width; y += scalePtr->borderWidth; shadowWidth = scalePtr->borderWidth/2; if (shadowWidth == 0) { shadowWidth = 1; } Tk_Draw3DRectangle(tkwin, drawable, sliderBorder, x, y, 2*width, height, shadowWidth, scalePtr->sliderRelief); x += shadowWidth; y += shadowWidth; width -= shadowWidth; height -= 2*shadowWidth; Tk_Fill3DRectangle(tkwin, drawable, sliderBorder, x, y, width, height, shadowWidth, scalePtr->sliderRelief); Tk_Fill3DRectangle(tkwin, drawable, sliderBorder, x+width, y, width, height, shadowWidth, scalePtr->sliderRelief); /* * Draw the label at the top of the scale. */ if ((scalePtr->flags & REDRAW_OTHER) && (scalePtr->labelLength != 0)) { Tk_FontMetrics fm; Tk_GetFontMetrics(scalePtr->tkfont, &fm); Tk_DrawChars(scalePtr->display, drawable, scalePtr->textGC, scalePtr->tkfont, scalePtr->label, scalePtr->labelLength, scalePtr->inset + fm.ascent/2, scalePtr->horizLabelY + fm.ascent); } }
void TkpDisplayMenuButton( ClientData clientData) /* Information about widget. */ { TkMenuButton *butPtr = (TkMenuButton *) clientData; Tk_Window tkwin = butPtr->tkwin; TkWindow * winPtr; Pixmap pixmap; MacMenuButton * mbPtr = (MacMenuButton *) butPtr; GWorldPtr dstPort; CGrafPtr saveWorld; GDHandle saveDevice; int hasImageOrBitmap = 0; int width, height; int err; ControlButtonGraphicAlignment theAlignment; Rect paneRect, cntrRect; butPtr->flags &= ~REDRAW_PENDING; if ((butPtr->tkwin == NULL) || !Tk_IsMapped(tkwin)) { return; } pixmap = ( Pixmap )Tk_WindowId(tkwin); GetGWorld(&saveWorld, &saveDevice); dstPort = TkMacOSXGetDrawablePort(Tk_WindowId(tkwin)); SetGWorld(dstPort, NULL); TkMacOSXSetUpClippingRgn(Tk_WindowId(tkwin)); winPtr=(TkWindow *)butPtr->tkwin; paneRect.left=winPtr->privatePtr->xOff; paneRect.top=winPtr->privatePtr->yOff; paneRect.right=paneRect.left+Tk_Width(butPtr->tkwin)-1; paneRect.bottom=paneRect.top+Tk_Height(butPtr->tkwin)-1; cntrRect=paneRect; cntrRect.left+=butPtr->inset; cntrRect.top+=butPtr->inset; cntrRect.right-=butPtr->inset; cntrRect.bottom-=butPtr->inset; if (mbPtr->userPane) { MenuButtonControlParams params; bzero(¶ms, sizeof(params)); ComputeMenuButtonControlParams(butPtr, ¶ms ); if (bcmp(¶ms,&mbPtr->params,sizeof(params))) { if (mbPtr->userPane) { DisposeControl(mbPtr->userPane); mbPtr->userPane = NULL; mbPtr->control = NULL; } } } if (!mbPtr->userPane) { if (MenuButtonInitControl(mbPtr,&paneRect,&cntrRect ) ) { fprintf(stderr,"Init Control failed\n" ); return; } } SetControlBounds(mbPtr->userPane,&paneRect); SetControlBounds(mbPtr->control,&cntrRect); /* * We need to cache the title and its style */ if (!(mbPtr->flags&2)) { ControlTitleParams titleParams; int titleChanged; int styleChanged; ComputeControlTitleParams(butPtr,&titleParams); CompareControlTitleParams(&titleParams,&mbPtr->titleParams, &titleChanged,&styleChanged); if (titleChanged) { CFStringRef cf; cf = CFStringCreateWithCString(NULL, titleParams.title, kCFStringEncodingUTF8); if (hasImageOrBitmap) { SetControlTitleWithCFString(mbPtr->control, cf); } else { SetMenuItemTextWithCFString(mbPtr->menuRef, 1, cf); } CFRelease(cf); bcopy(titleParams.title,mbPtr->titleParams.title,titleParams.len+1); mbPtr->titleParams.len = titleParams.len; } if ((titleChanged||styleChanged) && titleParams .len) { if (hasImageOrBitmap) { if ((err=SetControlFontStyle(mbPtr->control,&titleParams.style))!=noErr) { fprintf(stderr,"SetControlFontStyle failed %d\n", err); return; } } bcopy(&titleParams.style,&mbPtr->titleParams.style,sizeof(titleParams.style)); } } if (butPtr->image != None) { Tk_SizeOfImage(butPtr->image, &width, &height); hasImageOrBitmap = 1; } else if (butPtr->bitmap != None) { Tk_SizeOfBitmap(butPtr->display, butPtr->bitmap, &width, &height); hasImageOrBitmap = 1; } if (hasImageOrBitmap) { mbPtr->picParams.srcRect.right = width; mbPtr->picParams.srcRect.bottom = height; /* Set the flag to circumvent clipping and bounds problems with OS 10.0.4 */ tkPictureIsOpen = 1; if (!(mbPtr->bevelButtonContent.u.picture = OpenCPicture(&mbPtr->picParams)) ) { fprintf(stderr,"OpenCPicture failed\n"); } /* * TO DO - There is one case where XCopyPlane calls CopyDeepMask, * which does not get recorded in the picture. So the bitmap code * will fail in that case. */ if (butPtr->image != NULL) { Tk_RedrawImage(butPtr->image, 0, 0, width, height, pixmap, 0, 0); } else { XCopyPlane(butPtr->display, butPtr->bitmap, pixmap, NULL, 0, 0, (unsigned int) width, (unsigned int) height, 0, 0, 1); } ClosePicture(); tkPictureIsOpen = 0; if ( (err=SetControlData(mbPtr->control, kControlButtonPart, kControlBevelButtonContentTag, sizeof(ControlButtonContentInfo), (char *) &mbPtr->bevelButtonContent)) != noErr ) { fprintf(stderr,"SetControlData BevelButtonContent failed, %d\n", err ); } switch (butPtr->anchor) { case TK_ANCHOR_N: theAlignment = kControlBevelButtonAlignTop; break; case TK_ANCHOR_NE: theAlignment = kControlBevelButtonAlignTopRight; break; case TK_ANCHOR_E: theAlignment = kControlBevelButtonAlignRight; break; case TK_ANCHOR_SE: theAlignment = kControlBevelButtonAlignBottomRight; break; case TK_ANCHOR_S: theAlignment = kControlBevelButtonAlignBottom; break; case TK_ANCHOR_SW: theAlignment = kControlBevelButtonAlignBottomLeft; break; case TK_ANCHOR_W: theAlignment = kControlBevelButtonAlignLeft; break; case TK_ANCHOR_NW: theAlignment = kControlBevelButtonAlignTopLeft; break; case TK_ANCHOR_CENTER: theAlignment = kControlBevelButtonAlignCenter; break; } if ((err=SetControlData(mbPtr->control, kControlButtonPart, kControlBevelButtonGraphicAlignTag, sizeof(ControlButtonGraphicAlignment), (char *) &theAlignment)) != noErr ) { fprintf(stderr,"SetControlData BevelButtonGraphicAlign failed, %d\n", err ); } } if (butPtr->flags & GOT_FOCUS) { HiliteControl(mbPtr->control,kControlButtonPart); } else { HiliteControl(mbPtr->control,kControlNoPart); } UpdateControlColors(mbPtr); if (mbPtr->flags&2) { ShowControl(mbPtr->control); ShowControl(mbPtr->userPane); mbPtr->flags ^= 2; } else { Draw1Control(mbPtr->userPane); SetControlVisibility(mbPtr->control, true, true); } if (hasImageOrBitmap) { KillPicture(mbPtr->bevelButtonContent.u.picture); } SetGWorld(saveWorld, saveDevice); }
void TkpDisplayScrollbar( ClientData clientData) /* Information about window. */ { register TkScrollbar *scrollPtr = (TkScrollbar *) clientData; register MacScrollbar *macScrollPtr = (MacScrollbar *) clientData; register Tk_Window tkwin = scrollPtr->tkwin; MacDrawable *macDraw; CGrafPtr saveWorld; GDHandle saveDevice; GWorldPtr destPort; WindowRef windowRef; if ((scrollPtr->tkwin == NULL) || !Tk_IsMapped(tkwin)) { goto done; } /* * Draw the focus or any 3D relief we may have. */ if (scrollPtr->highlightWidth != 0) { GC fgGC, bgGC; bgGC = Tk_GCForColor(scrollPtr->highlightBgColorPtr, Tk_WindowId(tkwin)); if (scrollPtr->flags & GOT_FOCUS) { fgGC = Tk_GCForColor(scrollPtr->highlightColorPtr, Tk_WindowId(tkwin)); TkpDrawHighlightBorder(tkwin, fgGC, bgGC, scrollPtr->highlightWidth, Tk_WindowId(tkwin)); } else { TkpDrawHighlightBorder(tkwin, bgGC, bgGC, scrollPtr->highlightWidth, Tk_WindowId(tkwin)); } } Tk_Draw3DRectangle(tkwin, Tk_WindowId(tkwin), scrollPtr->bgBorder, scrollPtr->highlightWidth, scrollPtr->highlightWidth, Tk_Width(tkwin) - 2*scrollPtr->highlightWidth, Tk_Height(tkwin) - 2*scrollPtr->highlightWidth, scrollPtr->borderWidth, scrollPtr->relief); /* * Set up port for drawing Macintosh control. */ macDraw = (MacDrawable *) Tk_WindowId(tkwin); destPort = TkMacGetDrawablePort(Tk_WindowId(tkwin)); GetGWorld(&saveWorld, &saveDevice); SetGWorld(destPort, NULL); TkMacSetUpClippingRgn(Tk_WindowId(tkwin)); if (macScrollPtr->sbHandle == NULL) { Rect r; WindowRef frontNonFloating; r.left = r.top = 0; r.right = r.bottom = 1; macScrollPtr->sbHandle = NewControl((WindowRef) destPort, &r, "\p", false, (short) 500, 0, 1000, scrollBarProc, (SInt32) scrollPtr); /* * If we are foremost than make us active. */ if (TkMacHaveAppearance() >= 0x110) { frontNonFloating = FrontNonFloatingWindow(); } else { frontNonFloating = FrontWindow(); } if ((WindowPtr) destPort == FrontWindow() || TkpIsWindowFloating((WindowPtr) destPort)) { macScrollPtr->macFlags |= ACTIVE; } } /* * Update the control values before we draw. */ windowRef = (**macScrollPtr->sbHandle).contrlOwner; UpdateControlValues(macScrollPtr); if (macScrollPtr->macFlags & ACTIVE) { Draw1Control(macScrollPtr->sbHandle); if (macScrollPtr->macFlags & DRAW_GROW) { DrawGrowIcon(windowRef); } } else { (**macScrollPtr->sbHandle).contrlHilite = 255; Draw1Control(macScrollPtr->sbHandle); if (macScrollPtr->macFlags & DRAW_GROW) { DrawGrowIcon(windowRef); Tk_Fill3DRectangle(tkwin, Tk_WindowId(tkwin), scrollPtr->bgBorder, Tk_Width(tkwin) - 13, Tk_Height(tkwin) - 13, Tk_Width(tkwin), Tk_Height(tkwin), 0, TK_RELIEF_FLAT); } } SetGWorld(saveWorld, saveDevice); done: scrollPtr->flags &= ~REDRAW_PENDING; }