Tk Source Code

Check-in [3fc37e6b]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:fix the clipping in entries too
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | core-8-5-branch
Files: files | file ages | folders
SHA1: 3fc37e6b404bd4cd6f2c8128f6366f37527c7de1
User & Date: dkf 2012-06-11 09:32:22
Context
2012-06-11
10:20
make it build check-in: 00b9436f user: dkf tags: core-8-5-branch
09:33
fix the clipping in entries too check-in: bf81f828 user: dkf tags: trunk
09:32
fix the clipping in entries too check-in: 3fc37e6b user: dkf tags: core-8-5-branch
08:57
[Bug 3294450]: Do clipping of ttk text elements correctly. check-in: bd1d53d6 user: dkf tags: core-8-5-branch
Changes
Hide Diffs Unified Diffs Ignore Whitespace Patch

Changes to ChangeLog.

1
2
3

4
5
6
7
8
9
10
11
12
13
14
15
16
2012-06-11  Donal K. Fellows  <[email protected]>

	* generic/ttk/ttkLabel.c (TextDraw): [Bug 3294450]: Get the clipping

	of text in Ttk text elements (e.g., buttons, entries, etc.) correct.
	Stops a whole range of visual problems, including loss of the second
	and subsequent lines of a label when the first line doesn't entirely
	fit, and failing to draw the last character of an entry at all if it
	doesn't all exactly fit in the space available (a problem I've noticed
	in tkchat, and been very frustrated with).

2012-06-10  Jan Nijtmans  <[email protected]>

	* library/*.tcl:      [Bug 3534137]: $tcl_platform(platform) !=
	[tk windowingsystem]

2012-06-08  Jan Nijtmans  <[email protected]>



>
|
|
|
|
|
|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
2012-06-11  Donal K. Fellows  <[email protected]>

	* generic/ttk/ttkLabel.c (TextDraw): [Bug 3294450]: Get the clipping
	* generic/ttk/ttkEntry.c (EntryDisplay): of text in Ttk various text
	elements (e.g., buttons, entries, etc.) correct. Stops a whole range
	of visual problems, including loss of the second and subsequent lines
	of a label when the first line doesn't entirely fit, and failing to
	draw the last character of an entry at all if it doesn't all exactly
	fit in the space available (a problem I've noticed in tkchat, and been
	very frustrated with).

2012-06-10  Jan Nijtmans  <[email protected]>

	* library/*.tcl:      [Bug 3534137]: $tcl_platform(platform) !=
	[tk windowingsystem]

2012-06-08  Jan Nijtmans  <[email protected]>

Changes to generic/ttk/ttkEntry.c.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
/*
 * DERIVED FROM: tk/generic/tkEntry.c r1.35.
 *
 * Copyright (c) 1990-1994 The Regents of the University of California.
 * Copyright (c) 1994-1997 Sun Microsystems, Inc.
 * Copyright (c) 2000 Ajuba Solutions.
 * Copyright (c) 2002 ActiveState Corporation.
 * Copyright (c) 2004 Joe English
 */

#include <string.h>
#include <stdio.h>
#include <tk.h>
#include <X11/Xatom.h>

#include "ttkTheme.h"
#include "ttkWidget.h"

/*
 * Extra bits for core.flags:












|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
/*
 * DERIVED FROM: tk/generic/tkEntry.c r1.35.
 *
 * Copyright (c) 1990-1994 The Regents of the University of California.
 * Copyright (c) 1994-1997 Sun Microsystems, Inc.
 * Copyright (c) 2000 Ajuba Solutions.
 * Copyright (c) 2002 ActiveState Corporation.
 * Copyright (c) 2004 Joe English
 */

#include <string.h>
#include <stdio.h>
#include <tkInt.h>
#include <X11/Xatom.h>

#include "ttkTheme.h"
#include "ttkWidget.h"

/*
 * Extra bits for core.flags:
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144

1145
1146
1147
1148
1149
1150
1151
1152


1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168



1169
1170
1171

1172
1173
1174
1175
1176
1177
1178
	    leftIndex = maxLeftIndex;
	}

	/* Compute layoutX and rightIndex.
	 * rightIndex is set to one past the last fully-visible character.
	 */
	Tk_CharBbox(textLayout, leftIndex, &leftX, NULL, NULL, NULL);
	rightIndex = Tk_PointToChar(textLayout, leftX + textarea.width, 0);
	entryPtr->entry.layoutX = textarea.x - leftX;
    }

    TtkScrolled(entryPtr->entry.xscrollHandle,
	    leftIndex, rightIndex, entryPtr->entry.numChars);
}

/* EntryGetGC -- Helper routine.
 *      Get a GC using the specified foreground color and the entry's font.
 *      Result must be freed with Tk_FreeGC().
 */
static GC EntryGetGC(Entry *entryPtr, Tcl_Obj *colorObj)
{
    Tk_Window tkwin = entryPtr->core.tkwin;
    Tk_Font font = Tk_GetFontFromObj(tkwin, entryPtr->entry.fontObj);
    XColor *colorPtr;
    unsigned long mask = 0ul;
    XGCValues gcValues;


    gcValues.line_width = 1; mask |= GCLineWidth;
    gcValues.font = Tk_FontId(font); mask |= GCFont;
    if (colorObj != 0 && (colorPtr=Tk_GetColorFromObj(tkwin,colorObj)) != 0) {
	gcValues.foreground = colorPtr->pixel;
	mask |= GCForeground;
    }
    return Tk_GetGC(entryPtr->core.tkwin, mask, &gcValues);


}

/* EntryDisplay --
 *	Redraws the contents of an entry window.
 */
static void EntryDisplay(void *clientData, Drawable d)
{
    Entry *entryPtr = clientData;
    Tk_Window tkwin = entryPtr->core.tkwin;
    int leftIndex = entryPtr->entry.xscroll.first,
	rightIndex = entryPtr->entry.xscroll.last,
	selFirst = entryPtr->entry.selectFirst,
	selLast = entryPtr->entry.selectLast;
    EntryStyleData es;
    GC gc;
    int showSelection, showCursor;




    EntryInitStyleData(entryPtr, &es);


    showCursor =
	   (entryPtr->core.flags & CURSOR_ON) != 0
	&& EntryEditable(entryPtr)
	&& entryPtr->entry.insertPos >= leftIndex
	&& entryPtr->entry.insertPos <= rightIndex
	;
    showSelection =







|











|






>







|
>
>
















>
>
>



>







1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
	    leftIndex = maxLeftIndex;
	}

	/* Compute layoutX and rightIndex.
	 * rightIndex is set to one past the last fully-visible character.
	 */
	Tk_CharBbox(textLayout, leftIndex, &leftX, NULL, NULL, NULL);
	rightIndex = Tk_PointToChar(textLayout, leftX + textarea.width, 0)+1;
	entryPtr->entry.layoutX = textarea.x - leftX;
    }

    TtkScrolled(entryPtr->entry.xscrollHandle,
	    leftIndex, rightIndex, entryPtr->entry.numChars);
}

/* EntryGetGC -- Helper routine.
 *      Get a GC using the specified foreground color and the entry's font.
 *      Result must be freed with Tk_FreeGC().
 */
static GC EntryGetGC(Entry *entryPtr, Tcl_Obj *colorObj, TkRegion clip)
{
    Tk_Window tkwin = entryPtr->core.tkwin;
    Tk_Font font = Tk_GetFontFromObj(tkwin, entryPtr->entry.fontObj);
    XColor *colorPtr;
    unsigned long mask = 0ul;
    XGCValues gcValues;
    GC gc;

    gcValues.line_width = 1; mask |= GCLineWidth;
    gcValues.font = Tk_FontId(font); mask |= GCFont;
    if (colorObj != 0 && (colorPtr=Tk_GetColorFromObj(tkwin,colorObj)) != 0) {
	gcValues.foreground = colorPtr->pixel;
	mask |= GCForeground;
    }
    gc = Tk_GetGC(entryPtr->core.tkwin, mask, &gcValues);
    TkSetRegion(Tk_Display(entryPtr->core.tkwin), gc, clip);
    return gc;
}

/* EntryDisplay --
 *	Redraws the contents of an entry window.
 */
static void EntryDisplay(void *clientData, Drawable d)
{
    Entry *entryPtr = clientData;
    Tk_Window tkwin = entryPtr->core.tkwin;
    int leftIndex = entryPtr->entry.xscroll.first,
	rightIndex = entryPtr->entry.xscroll.last,
	selFirst = entryPtr->entry.selectFirst,
	selLast = entryPtr->entry.selectLast;
    EntryStyleData es;
    GC gc;
    int showSelection, showCursor;
    Ttk_Box textarea;
    TkRegion clipRegion;
    XRectangle rect;

    EntryInitStyleData(entryPtr, &es);

    textarea = Ttk_ClientRegion(corePtr->layout, "textarea");
    showCursor =
	   (entryPtr->core.flags & CURSOR_ON) != 0
	&& EntryEditable(entryPtr)
	&& entryPtr->entry.insertPos >= leftIndex
	&& entryPtr->entry.insertPos <= rightIndex
	;
    showSelection =
1210
1211
1212
1213
1214
1215
1216










1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257

1258
1259
1260
1261
1262
1263
1264
		selStartX - borderWidth, entryPtr->entry.layoutY - borderWidth,
		selEndX - selStartX + 2*borderWidth,
		entryPtr->entry.layoutHeight + 2*borderWidth,
		borderWidth, TK_RELIEF_RAISED);
	}
    }











    /* Draw cursor:
     */
    if (showCursor) {
	int cursorX = EntryCharPosition(entryPtr, entryPtr->entry.insertPos),
	    cursorY = entryPtr->entry.layoutY,
	    cursorHeight = entryPtr->entry.layoutHeight,
	    cursorWidth = 1;

	Tcl_GetIntFromObj(NULL,es.insertWidthObj,&cursorWidth);
	if (cursorWidth <= 0) {
	    cursorWidth = 1;
	}

	/* @@@ should: maybe: SetCaretPos even when blinked off */
	Tk_SetCaretPos(tkwin, cursorX, cursorY, cursorHeight);

	gc = EntryGetGC(entryPtr, es.insertColorObj);
	XFillRectangle(Tk_Display(tkwin), d, gc,
	    cursorX-cursorWidth/2, cursorY, cursorWidth, cursorHeight);
	Tk_FreeGC(Tk_Display(tkwin), gc);
    }

    /* Draw the text:
     */
    gc = EntryGetGC(entryPtr, es.foregroundObj);
    Tk_DrawTextLayout(
	Tk_Display(tkwin), d, gc, entryPtr->entry.textLayout,
	entryPtr->entry.layoutX, entryPtr->entry.layoutY,
	leftIndex, rightIndex);
    Tk_FreeGC(Tk_Display(tkwin), gc);

    /* Overwrite the selected portion (if any) in the -selectforeground color:
     */
    if (showSelection) {
	gc = EntryGetGC(entryPtr, es.selForegroundObj);
	Tk_DrawTextLayout(
	    Tk_Display(tkwin), d, gc, entryPtr->entry.textLayout,
	    entryPtr->entry.layoutX, entryPtr->entry.layoutY,
	    selFirst, selLast);
	Tk_FreeGC(Tk_Display(tkwin), gc);
    }

}

/*------------------------------------------------------------------------
 * +++ Widget commands.
 */

/* EntryIndex --







>
>
>
>
>
>
>
>
>
>
















|







|









|






>







1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
		selStartX - borderWidth, entryPtr->entry.layoutY - borderWidth,
		selEndX - selStartX + 2*borderWidth,
		entryPtr->entry.layoutHeight + 2*borderWidth,
		borderWidth, TK_RELIEF_RAISED);
	}
    }

    /* Initialize the clip region:
     */

    rect.x = textarea.x;
    rect.y = textarea.y;
    rect.width = textarea.width;
    rect.height = textarea.height;
    clipRegion = TkCreateRegion();
    TkUnionRectWithRegion(&rect, clipRegion, clipRegion);

    /* Draw cursor:
     */
    if (showCursor) {
	int cursorX = EntryCharPosition(entryPtr, entryPtr->entry.insertPos),
	    cursorY = entryPtr->entry.layoutY,
	    cursorHeight = entryPtr->entry.layoutHeight,
	    cursorWidth = 1;

	Tcl_GetIntFromObj(NULL,es.insertWidthObj,&cursorWidth);
	if (cursorWidth <= 0) {
	    cursorWidth = 1;
	}

	/* @@@ should: maybe: SetCaretPos even when blinked off */
	Tk_SetCaretPos(tkwin, cursorX, cursorY, cursorHeight);

	gc = EntryGetGC(entryPtr, es.insertColorObj, clipRegion);
	XFillRectangle(Tk_Display(tkwin), d, gc,
	    cursorX-cursorWidth/2, cursorY, cursorWidth, cursorHeight);
	Tk_FreeGC(Tk_Display(tkwin), gc);
    }

    /* Draw the text:
     */
    gc = EntryGetGC(entryPtr, es.foregroundObj, clipRegion);
    Tk_DrawTextLayout(
	Tk_Display(tkwin), d, gc, entryPtr->entry.textLayout,
	entryPtr->entry.layoutX, entryPtr->entry.layoutY,
	leftIndex, rightIndex);
    Tk_FreeGC(Tk_Display(tkwin), gc);

    /* Overwrite the selected portion (if any) in the -selectforeground color:
     */
    if (showSelection) {
      gc = EntryGetGC(entryPtr, es.selForegroundObj, clipRegion);
	Tk_DrawTextLayout(
	    Tk_Display(tkwin), d, gc, entryPtr->entry.textLayout,
	    entryPtr->entry.layoutX, entryPtr->entry.layoutY,
	    selFirst, selLast);
	Tk_FreeGC(Tk_Display(tkwin), gc);
    }
    TkDestroyRegion(clipRegion);
}

/*------------------------------------------------------------------------
 * +++ Widget commands.
 */

/* EntryIndex --