⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tktextindex.c

📁 linux系统下的音频通信
💻 C
📖 第 1 页 / 共 2 页
字号:
/*  * tkTextIndex.c -- * *	This module provides procedures that manipulate indices for *	text widgets. * * Copyright (c) 1992-1994 The Regents of the University of California. * Copyright (c) 1994-1995 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: @(#) tkTextIndex.c 1.15 97/06/17 17:49:24 */#include "default.h"#include "tkPort.h"#include "tkInt.h"#include "tkText.h"/* * Index to use to select last character in line (very large integer): */#define LAST_CHAR 1000000/* * Forward declarations for procedures defined later in this file: */static char *		ForwBack _ANSI_ARGS_((char *string,			    TkTextIndex *indexPtr));static char *		StartEnd _ANSI_ARGS_(( char *string,			    TkTextIndex *indexPtr));/* *-------------------------------------------------------------- * * TkTextMakeIndex -- * *	Given a line index and a character index, look things up *	in the B-tree and fill in a TkTextIndex structure. * * Results: *	The structure at *indexPtr is filled in with information *	about the character at lineIndex and charIndex (or the *	closest existing character, if the specified one doesn't *	exist), and indexPtr is returned as result. * * Side effects: *	None. * *-------------------------------------------------------------- */TkTextIndex *TkTextMakeIndex(tree, lineIndex, charIndex, indexPtr)    TkTextBTree tree;		/* Tree that lineIndex and charIndex refer				 * to. */    int lineIndex;		/* Index of desired line (0 means first				 * line of text). */    int charIndex;		/* Index of desired character. */    TkTextIndex *indexPtr;	/* Structure to fill in. */{    register TkTextSegment *segPtr;    int index;    indexPtr->tree = tree;    if (lineIndex < 0) {	lineIndex = 0;	charIndex = 0;    }    if (charIndex < 0) {	charIndex = 0;    }    indexPtr->linePtr = TkBTreeFindLine(tree, lineIndex);    if (indexPtr->linePtr == NULL) {	indexPtr->linePtr = TkBTreeFindLine(tree, TkBTreeNumLines(tree));	charIndex = 0;    }    /*     * Verify that the index is within the range of the line.     * If not, just use the index of the last character in the line.     */    for (index = 0, segPtr = indexPtr->linePtr->segPtr; ;	    segPtr = segPtr->nextPtr) {	if (segPtr == NULL) {	    indexPtr->charIndex = index-1;	    break;	}	index += segPtr->size;	if (index > charIndex) {	    indexPtr->charIndex = charIndex;	    break;	}    }    return indexPtr;}/* *-------------------------------------------------------------- * * TkTextIndexToSeg -- * *	Given an index, this procedure returns the segment and *	offset within segment for the index. * * Results: *	The return value is a pointer to the segment referred to *	by indexPtr;  this will always be a segment with non-zero *	size.  The variable at *offsetPtr is set to hold the *	integer offset within the segment of the character *	given by indexPtr. * * Side effects: *	None. * *-------------------------------------------------------------- */TkTextSegment *TkTextIndexToSeg(indexPtr, offsetPtr)    TkTextIndex *indexPtr;		/* Text index. */    int *offsetPtr;			/* Where to store offset within					 * segment, or NULL if offset isn't					 * wanted. */{    register TkTextSegment *segPtr;    int offset;    for (offset = indexPtr->charIndex, segPtr = indexPtr->linePtr->segPtr;	    offset >= segPtr->size;	    offset -= segPtr->size, segPtr = segPtr->nextPtr) {	/* Empty loop body. */    }    if (offsetPtr != NULL) {	*offsetPtr = offset;    }    return segPtr;}/* *-------------------------------------------------------------- * * TkTextSegToOffset -- * *	Given a segment pointer and the line containing it, this *	procedure returns the offset of the segment within its *	line. * * Results: *	The return value is the offset (within its line) of the *	first character in segPtr. * * Side effects: *	None. * *-------------------------------------------------------------- */intTkTextSegToOffset(segPtr, linePtr)    TkTextSegment *segPtr;		/* Segment whose offset is desired. */    TkTextLine *linePtr;		/* Line containing segPtr. */{    TkTextSegment *segPtr2;    int offset;    offset = 0;    for (segPtr2 = linePtr->segPtr; segPtr2 != segPtr;	    segPtr2 = segPtr2->nextPtr) {	offset += segPtr2->size;    }    return offset;}/* *---------------------------------------------------------------------- * * TkTextGetIndex -- * *	Given a string, return the line and character indices that *	it describes. * * Results: *	The return value is a standard Tcl return result.  If *	TCL_OK is returned, then everything went well and the index *	at *indexPtr is filled in;  otherwise TCL_ERROR is returned *	and an error message is left in interp->result. * * Side effects: *	None. * *---------------------------------------------------------------------- */intTkTextGetIndex(interp, textPtr, string, indexPtr)    Tcl_Interp *interp;		/* Use this for error reporting. */    TkText *textPtr;		/* Information about text widget. */    char *string;		/* Textual description of position. */    TkTextIndex *indexPtr;	/* Index structure to fill in. */{    register char *p;    char *end, *endOfBase;    Tcl_HashEntry *hPtr;    TkTextTag *tagPtr;    TkTextSearch search;    TkTextIndex first, last;    int wantLast, result;    char c;    /*     *---------------------------------------------------------------------     * Stage 1: check to see if the index consists of nothing but a mark     * name.  We do this check now even though it's also done later, in     * order to allow mark names that include funny characters such as     * spaces or "+1c".     *---------------------------------------------------------------------     */    if (TkTextMarkNameToIndex(textPtr, string, indexPtr) == TCL_OK) {	return TCL_OK;    }    /*     *------------------------------------------------     * Stage 2: start again by parsing the base index.     *------------------------------------------------     */    indexPtr->tree = textPtr->tree;    /*     * First look for the form "tag.first" or "tag.last" where "tag"     * is the name of a valid tag.  Try to use up as much as possible     * of the string in this check (strrchr instead of strchr below).     * Doing the check now, and in this way, allows tag names to include     * funny characters like "@" or "+1c".     */    p = strrchr(string, '.');    if (p != NULL) {	if ((p[1] == 'f') && (strncmp(p+1, "first", 5) == 0)) {	    wantLast = 0;	    endOfBase = p+6;	} else if ((p[1] == 'l') && (strncmp(p+1, "last", 4) == 0)) {	    wantLast = 1;	    endOfBase = p+5;	} else {	    goto tryxy;	}	*p = 0;	hPtr = Tcl_FindHashEntry(&textPtr->tagTable, string);	*p = '.';	if (hPtr == NULL) {	    goto tryxy;	}	tagPtr = (TkTextTag *) Tcl_GetHashValue(hPtr);	TkTextMakeIndex(textPtr->tree, 0, 0, &first);	TkTextMakeIndex(textPtr->tree, TkBTreeNumLines(textPtr->tree), 0,		&last);	TkBTreeStartSearch(&first, &last, tagPtr, &search);	if (!TkBTreeCharTagged(&first, tagPtr) && !TkBTreeNextTag(&search)) {	    Tcl_AppendResult(interp,		    "text doesn't contain any characters tagged with \"",		    Tcl_GetHashKey(&textPtr->tagTable, hPtr), "\"",			    (char *) NULL);	    return TCL_ERROR;	}	*indexPtr = search.curIndex;	if (wantLast) {	    while (TkBTreeNextTag(&search)) {		*indexPtr = search.curIndex;	    }	}	goto gotBase;    }    tryxy:    if (string[0] == '@') {	/*	 * Find character at a given x,y location in the window.	 */	int x, y;	p = string+1;	x = strtol(p, &end, 0);	if ((end == p) || (*end != ',')) {	    goto error;	}	p = end+1;	y = strtol(p, &end, 0);	if (end == p) {	    goto error;	}	TkTextPixelIndex(textPtr, x, y, indexPtr);	endOfBase = end;	goto gotBase;     }    if (isdigit(UCHAR(string[0])) || (string[0] == '-')) {	int lineIndex, charIndex;	/*	 * Base is identified with line and character indices.	 */	lineIndex = strtol(string, &end, 0) - 1;	if ((end == string) || (*end != '.')) {	    goto error;	}	p = end+1;	if ((*p == 'e') && (strncmp(p, "end", 3) == 0)) {	    charIndex = LAST_CHAR;	    endOfBase = p+3;	} else {	    charIndex = strtol(p, &end, 0);	    if (end == p) {		goto error;	    }	    endOfBase = end;	}	TkTextMakeIndex(textPtr->tree, lineIndex, charIndex, indexPtr);	goto gotBase;    }    for (p = string; *p != 0; p++) {	if (isspace(UCHAR(*p)) || (*p == '+') || (*p == '-')) {	    break;	}    }    endOfBase = p;    if (string[0] == '.') {	/*	 * See if the base position is the name of an embedded window.	 */	c = *endOfBase;	*endOfBase = 0;	result = TkTextWindowIndex(textPtr, string, indexPtr);	*endOfBase = c;	if (result != 0) {	    goto gotBase;	}    }    if ((string[0] == 'e')	    && (strncmp(string, "end", (size_t) (endOfBase-string)) == 0)) {	/*	 * Base position is end of text.	 */	TkTextMakeIndex(textPtr->tree, TkBTreeNumLines(textPtr->tree),		0, indexPtr);	goto gotBase;    } else {	/*	 * See if the base position is the name of a mark.	 */	c = *endOfBase;	*endOfBase = 0;	result = TkTextMarkNameToIndex(textPtr, string, indexPtr);	*endOfBase = c;	if (result == TCL_OK) {	    goto gotBase;	}	/*	 * See if the base position is the name of an embedded image	 */	c = *endOfBase;	*endOfBase = 0;	result = TkTextImageIndex(textPtr, string, indexPtr);	*endOfBase = c;	if (result != 0) {	    goto gotBase;	}    }    goto error;    /*     *-------------------------------------------------------------------     * Stage 3: process zero or more modifiers.  Each modifier is either     * a keyword like "wordend" or "linestart", or it has the form     * "op count units" where op is + or -, count is a number, and units     * is "chars" or "lines".     *-------------------------------------------------------------------     */    gotBase:    p = endOfBase;    while (1) {	while (isspace(UCHAR(*p))) {	    p++;	}	if (*p == 0) {	    break;	}    	if ((*p == '+') || (*p == '-')) {	    p = ForwBack(p, indexPtr);	} else {	    p = StartEnd(p, indexPtr);	}	if (p == NULL) {	    goto error;	}    }    return TCL_OK;    error:    Tcl_AppendResult(interp, "bad text index \"", string, "\"",	    (char *) NULL);    return TCL_ERROR;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -