From 7acca7516ab66ecbea898bbe3ab63c7f3ec7a030 Mon Sep 17 00:00:00 2001 From: dkf Date: Thu, 13 Jun 2002 09:46:38 +0000 Subject: Refixed cursor handling on Windows, and added tests to enforce it. --- ChangeLog | 9 +++++++ tests/cursor.test | 72 ++++++++++++++++++++++++++++++++++++------------------ win/tkWinCursor.c | 73 ++++++++++++++++++++++++++++++++----------------------- 3 files changed, 100 insertions(+), 54 deletions(-) diff --git a/ChangeLog b/ChangeLog index 98ff4a8..98a263c 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,12 @@ +2002-06-13 Donal K. Fellows + + * tests/cursor.test (cursor-2.[34]): Tests added to ensure that + cursor specs really are well-behaved lists. Also some general + clean-up... + * win/tkWinCursor.c (TkGetCursorByName): Undone Jeff's back-off + and fixed things so that they should work now. Cursor specs are + lists first and foremost. + 2002-06-12 Mo DeJong * changes: Clearly label wm transient changes as diff --git a/tests/cursor.test b/tests/cursor.test index 2d818c3..35a1d84 100644 --- a/tests/cursor.test +++ b/tests/cursor.test @@ -6,23 +6,19 @@ # Copyright (c) 1998-1999 by Scriptics Corporation. # All rights reserved. # -# RCS: @(#) $Id: cursor.test,v 1.3 2001/04/04 06:40:14 hobbs Exp $ +# RCS: @(#) $Id: cursor.test,v 1.4 2002/06/13 09:46:39 dkf Exp $ if {[lsearch [namespace children] ::tcltest] == -1} { source [file join [pwd] [file dirname [info script]] defs.tcl] } -if {[info commands testcursor] != "testcursor"} { - puts "testcursor command not available; skipping tests" - ::tcltest::cleanupTests - return -} +set ::tcltest::testConfig(testcursor) [llength [info commands testcursor]] eval destroy [winfo children .] wm geometry . {} raise . -test cursor-1.1 {Tk_AllocCursorFromObj - converting internal reps} { +test cursor-1.1 {Tk_AllocCursorFromObj - converting internal reps} {testcursor} { set x watch lindex $x 0 destroy .b1 @@ -30,7 +26,7 @@ test cursor-1.1 {Tk_AllocCursorFromObj - converting internal reps} { lindex $x 0 testcursor watch } {{1 0}} -test cursor-1.2 {Tk_AllocCursorFromObj - discard stale cursor} { +test cursor-1.2 {Tk_AllocCursorFromObj - discard stale cursor} {testcursor} { set x watch destroy .b1 .b2 button .b1 -cursor $x @@ -40,7 +36,7 @@ test cursor-1.2 {Tk_AllocCursorFromObj - discard stale cursor} { button .b2 -cursor $x lappend result [testcursor watch] } {{} {{1 1}}} -test cursor-1.3 {Tk_AllocCursorFromObj - reuse existing cursor} { +test cursor-1.3 {Tk_AllocCursorFromObj - reuse existing cursor} {testcursor} { set x watch destroy .b1 .b2 button .b1 -cursor $x @@ -59,8 +55,49 @@ test cursor-2.2 {Tk_GetCursor procedure} { destroy .b1 list [catch {button .b1 -cursor @xyzzy} msg] $msg } {1 {bad cursor spec "@xyzzy"}} +# Next two tests need a helper file with a very specific name and +# controlled format. +set wincur(data_octal) { + 000 000 002 000 001 000 040 040 000 000 007 000 007 000 060 001 + 000 000 026 000 000 000 050 000 000 000 040 000 000 000 100 000 + 000 000 001 000 001 000 000 000 000 000 000 000 000 000 000 000 + 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 + 000 000 377 377 377 000 000 000 000 000 000 000 000 000 000 000 + 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 + 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 + 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 000 + 000 000 000 000 000 000 000 000 000 000 160 016 000 000 170 036 + 000 000 174 076 000 000 076 174 000 000 037 370 000 000 017 360 + 000 000 007 340 000 000 007 340 000 000 017 360 000 000 037 370 + 000 000 076 174 000 000 174 076 000 000 170 036 000 000 160 016 + 000 000 000 000 000 000 377 377 377 377 377 377 377 377 377 377 + 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 + 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 + 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 377 + 377 377 377 377 377 377 017 360 377 377 007 340 377 377 003 300 + 377 377 001 200 377 377 200 001 377 377 300 003 377 377 340 007 + 377 377 360 017 377 377 360 017 377 377 340 007 377 377 300 003 + 377 377 200 001 377 377 001 200 377 377 003 300 377 377 007 340 + 377 377 017 360 377 377 +} +set wincur(data_binary) {} +foreach wincur(num) $wincur(data_octal) { + append wincur(data_binary) [binary format c 0$wincur(num)] +} +set wincur(dir) [::tcltest::makeDirectory {dir with spaces}] +set wincur(file) [::tcltest::makeFile $curdata "test file.cur" $wincur(dir)] +test cursor-2.3 {Tk_GetCursor procedure: cursor specs are lists} {pcOnly} { + destroy .b1 + button .b1 -cursor [list @$wincur(file)] +} {.b1} +test cursor-2.4 {Tk_GetCursor procedure: cursor specs are lists} {pcOnly} { + destroy .b1 + button .b1 -cursor @[regsub -all {[][ \\{}""$#]} $wincur(file) {\\&}] +} {.b1} +::tcltest::removeDirectory $wincur(dir) +unset wincur -test cursor-3.1 {Tk_FreeCursorFromObj - reference counts} { +test cursor-3.1 {Tk_FreeCursorFromObj - reference counts} {testcursor} { set x heart destroy .b1 .b2 .b3 button .b1 -cursor $x @@ -76,7 +113,7 @@ test cursor-3.1 {Tk_FreeCursorFromObj - reference counts} { lappend result [testcursor heart] } {{{3 1}} {{2 1}} {{1 1}} {}} -test cursor-4.1 {FreeCursorObjProc} { +test cursor-4.1 {FreeCursorObjProc} {testcursor} { destroy .b set x [format heart] button .b -cursor $x @@ -101,16 +138,3 @@ destroy .t # cleanup ::tcltest::cleanupTests return - - - - - - - - - - - - - diff --git a/win/tkWinCursor.c b/win/tkWinCursor.c index a5d60db..608dd5e 100644 --- a/win/tkWinCursor.c +++ b/win/tkWinCursor.c @@ -8,7 +8,7 @@ * See the file "license.terms" for information on usage and redistribution * of this file, and for a DISCLAIMER OF ALL WARRANTIES. * - * RCS: @(#) $Id: tkWinCursor.c,v 1.8 2002/06/12 23:39:14 hobbs Exp $ + * RCS: @(#) $Id: tkWinCursor.c,v 1.9 2002/06/13 09:46:39 dkf Exp $ */ #include "tkWinInt.h" @@ -87,63 +87,76 @@ TkGetCursorByName(interp, tkwin, string) { struct CursorName *namePtr; TkWinCursor *cursorPtr; + int argc; + CONST char **argv = NULL; /* - * Check for the cursor in the system cursor set. + * All cursor names are valid lists of one element (for + * Unix-compatability), even unadorned system cursor names. */ - for (namePtr = cursorNames; namePtr->name != NULL; namePtr++) { - if (strcmp(namePtr->name, string) == 0) { - break; - } + if (Tcl_SplitList(interp, string, &argc, &argv) != TCL_OK) { + return NULL; + } + if (argc != 1) { + goto badCursorSpec; } cursorPtr = (TkWinCursor *) ckalloc(sizeof(TkWinCursor)); cursorPtr->info.cursor = (Tk_Cursor) cursorPtr; cursorPtr->winCursor = NULL; - if (namePtr->name != NULL) { - cursorPtr->winCursor = LoadCursor(NULL, namePtr->id); - cursorPtr->system = 1; - } - if (cursorPtr->winCursor == NULL) { - cursorPtr->winCursor = LoadCursor(Tk_GetHINSTANCE(), string); - cursorPtr->system = 0; - } - if (string[0] == '@') { - int argc; - CONST char **argv = NULL; - if (Tcl_SplitList(interp, string, &argc, &argv) != TCL_OK) { - return NULL; - } + cursorPtr->system = 0; + + if (argv[0][0] == '@') { /* * Check for system cursor of type @, where only - * the name is allowed. This accepts either: + * the name is allowed. This accepts any of: * -cursor @/winnt/cursors/globe.ani * -cursor @C:/Winnt/cursors/E_arrow.cur * -cursor {@C:/Program\ Files/Cursors/bart.ani} + * -cursor {{@C:/Program Files/Cursors/bart.ani}} + * -cursor [list @[file join "C:/Program Files" Cursors bart.ani]] */ - if ((argc != 1) || (argv[0][0] != '@')) { - ckfree((char *) argv); - goto badCursorSpec; - } + if (Tcl_IsSafe(interp)) { Tcl_AppendResult(interp, "can't get cursor from a file in", " a safe interpreter", (char *) NULL); ckfree((char *) argv); - ckfree((char *)cursorPtr); + ckfree((char *) cursorPtr); return NULL; } cursorPtr->winCursor = LoadCursorFromFile(&(argv[0][1])); - cursorPtr->system = 0; - ckfree((char *) argv); + } else { + /* + * Check for the cursor in the system cursor set. + */ + for (namePtr = cursorNames; namePtr->name != NULL; namePtr++) { + if (strcmp(namePtr->name, argv[0]) == 0) { + cursorPtr->winCursor = LoadCursor(NULL, namePtr->id); + break; + } + } + + if (cursorPtr->winCursor == NULL) { + /* + * Hmm, it is not in the system cursor set. Check to see + * if it is one of our application resources. + */ + cursorPtr->winCursor = LoadCursor(Tk_GetHINSTANCE(), argv[0]); + } else { + cursorPtr->system = 1; + } } + if (cursorPtr->winCursor == NULL) { - badCursorSpec: - ckfree((char *)cursorPtr); + ckfree((char *) cursorPtr); + badCursorSpec: + ckfree((char *) argv); Tcl_AppendResult(interp, "bad cursor spec \"", string, "\"", (char *) NULL); return NULL; } else { + ckfree((char *) argv); return (TkCursor *) cursorPtr; } } -- cgit v0.12