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

📄 miwideline.c

📁 远程桌面连接工具
💻 C
📖 第 1 页 / 共 4 页
字号:
/* $XConsortium: miwideline.c /main/58 1996/08/12 21:51:21 dpw $ *//*Copyright (c) 1988  X ConsortiumPermission is hereby granted, free of charge, to any person obtaininga copy of this software and associated documentation files (the"Software"), to deal in the Software without restriction, includingwithout limitation the rights to use, copy, modify, merge, publish,distribute, sublicense, and/or sell copies of the Software, and topermit persons to whom the Software is furnished to do so, subject tothe following conditions:The above copyright notice and this permission notice shall be includedin all copies or substantial portions of the Software.THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESSOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OFMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OROTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OROTHER DEALINGS IN THE SOFTWARE.Except as contained in this notice, the name of the X Consortium shallnot be used in advertising or otherwise to promote the sale, use orother dealings in this Software without prior written authorizationfrom the X Consortium.*//* $XFree86: xc/programs/Xserver/mi/miwideline.c,v 1.1.1.3.2.2 1998/02/01 22:08:22 robin Exp $ *//* Author:  Keith Packard, MIT X Consortium *//* * Mostly integer wideline code.  Uses a technique similar to * bresenham zero-width lines, except walks an X edge */#include <stdio.h>#ifdef _XOPEN_SOURCE#include <math.h>#else#define _XOPEN_SOURCE	/* to get prototype for hypot on some systems */#include <math.h>#undef _XOPEN_SOURCE#endif#include "X.h"#include "windowstr.h"#include "gcstruct.h"#include "miscstruct.h"#include "miwideline.h"#include "mi.h"#ifdef ICEILTEMPDECLICEILTEMPDECL#endifstatic void miLineArc();/* * spans-based polygon filler */voidmiFillPolyHelper (pDrawable, pGC, pixel, spanData, y, overall_height,		  left, right, left_count, right_count)    DrawablePtr	pDrawable;    GCPtr	pGC;    unsigned long   pixel;    SpanDataPtr	spanData;    int		y;			/* start y coordinate */    int		overall_height;		/* height of entire segment */    PolyEdgePtr	left, right;    int		left_count, right_count;{    register int left_x, left_e;    int	left_stepx;    int	left_signdx;    int	left_dy, left_dx;    register int right_x, right_e;    int	right_stepx;    int	right_signdx;    int	right_dy, right_dx;    int	height;    int	left_height, right_height;    register DDXPointPtr ppt;    DDXPointPtr pptInit;    register int *pwidth;    int *pwidthInit;    XID		oldPixel;    int		xorg;    Spans	spanRec;    left_height = 0;    right_height = 0;        if (!spanData)    {    	pptInit = (DDXPointPtr) ALLOCATE_LOCAL (overall_height * sizeof(*ppt));    	if (!pptInit)	    return;    	pwidthInit = (int *) ALLOCATE_LOCAL (overall_height * sizeof(*pwidth));    	if (!pwidthInit)    	{	    DEALLOCATE_LOCAL (pptInit);	    return;    	}	ppt = pptInit;	pwidth = pwidthInit;    	oldPixel = pGC->fgPixel;    	if (pixel != oldPixel)    	{    	    DoChangeGC (pGC, GCForeground, (XID *)&pixel, FALSE);    	    ValidateGC (pDrawable, pGC);    	}    }    else    {	spanRec.points = (DDXPointPtr) xalloc (overall_height * sizeof (*ppt));	if (!spanRec.points)	    return;	spanRec.widths = (int *) xalloc (overall_height * sizeof (int));	if (!spanRec.widths)	{	    xfree (spanRec.points);	    return;	}	ppt = spanRec.points;	pwidth = spanRec.widths;    }    xorg = 0;    if (pGC->miTranslate)    {	y += pDrawable->y;	xorg = pDrawable->x;    }    while ((left_count || left_height) &&	   (right_count || right_height))    {	MIPOLYRELOADLEFT	MIPOLYRELOADRIGHT	height = left_height;	if (height > right_height)	    height = right_height;	left_height -= height;	right_height -= height;	while (--height >= 0)	{	    if (right_x >= left_x)	    {		ppt->y = y;		ppt->x = left_x + xorg;		ppt++;		*pwidth++ = right_x - left_x + 1;	    }    	    y++;    		    MIPOLYSTEPLEFT	    MIPOLYSTEPRIGHT	}    }    if (!spanData)    {    	(*pGC->ops->FillSpans) (pDrawable, pGC, ppt - pptInit, pptInit, pwidthInit, TRUE);    	DEALLOCATE_LOCAL (pwidthInit);    	DEALLOCATE_LOCAL (pptInit);    	if (pixel != oldPixel)    	{	    DoChangeGC (pGC, GCForeground, &oldPixel, FALSE);	    ValidateGC (pDrawable, pGC);    	}    }    else    {	spanRec.count = ppt - spanRec.points;	AppendSpanGroup (pGC, pixel, &spanRec, spanData)    }}static voidmiFillRectPolyHelper (pDrawable, pGC, pixel, spanData, x, y, w, h)    DrawablePtr	pDrawable;    GCPtr	pGC;    unsigned long   pixel;    SpanDataPtr	spanData;    int		x, y, w, h;{    register DDXPointPtr ppt;    register int *pwidth;    XID		oldPixel;    Spans	spanRec;    xRectangle  rect;    if (!spanData)    {	rect.x = x;	rect.y = y;	rect.width = w;	rect.height = h;    	oldPixel = pGC->fgPixel;    	if (pixel != oldPixel)    	{    	    DoChangeGC (pGC, GCForeground, (XID *)&pixel, FALSE);    	    ValidateGC (pDrawable, pGC);    	}	(*pGC->ops->PolyFillRect) (pDrawable, pGC, 1, &rect);    	if (pixel != oldPixel)    	{	    DoChangeGC (pGC, GCForeground, &oldPixel, FALSE);	    ValidateGC (pDrawable, pGC);    	}    }    else    {	spanRec.points = (DDXPointPtr) xalloc (h * sizeof (*ppt));	if (!spanRec.points)	    return;	spanRec.widths = (int *) xalloc (h * sizeof (int));	if (!spanRec.widths)	{	    xfree (spanRec.points);	    return;	}	ppt = spanRec.points;	pwidth = spanRec.widths;    	if (pGC->miTranslate)    	{	    y += pDrawable->y;	    x += pDrawable->x;    	}	while (h--)	{	    ppt->x = x;	    ppt->y = y;	    ppt++;	    *pwidth++ = w;	    y++;	}	spanRec.count = ppt - spanRec.points;	AppendSpanGroup (pGC, pixel, &spanRec, spanData)    }}intmiPolyBuildEdge (x0, y0, k, dx, dy, xi, yi, left, edge)    double	x0, y0;    double	k;  /* x0 * dy - y0 * dx */    register int dx, dy;    int		xi, yi;    int		left;    register PolyEdgePtr edge;{    int	    x, y, e;    int	    xady;    if (dy < 0)    {	dy = -dy;	dx = -dx;	k = -k;    }#ifdef NOTDEF    {	double	realk, kerror;    	realk = x0 * dy - y0 * dx;    	kerror = Fabs (realk - k);    	if (kerror > .1)	    printf ("realk: %g k: %g\n", realk, k);    }#endif    y = ICEIL (y0);    xady = ICEIL (k) + y * dx;    if (xady <= 0)	x = - (-xady / dy) - 1;    else	x = (xady - 1) / dy;    e = xady - x * dy;    if (dx >= 0)    {	edge->signdx = 1;	edge->stepx = dx / dy;	edge->dx = dx % dy;    }    else    {	edge->signdx = -1;	edge->stepx = - (-dx / dy);	edge->dx = -dx % dy;	e = dy - e + 1;    }    edge->dy = dy;    edge->x = x + left + xi;    edge->e = e - dy;	/* bias to compare against 0 instead of dy */    return y + yi;}#define StepAround(v, incr, max) (((v) + (incr) < 0) ? (max - 1) : ((v) + (incr) == max) ? 0 : ((v) + (incr)))intmiPolyBuildPoly (vertices, slopes, count, xi, yi, left, right, pnleft, pnright, h)    register PolyVertexPtr vertices;    register PolySlopePtr  slopes;    int		    count;    int		    xi, yi;    PolyEdgePtr	    left, right;    int		    *pnleft, *pnright;    int		    *h;{    int	    top, bottom;    double  miny, maxy;    register int i;    int	    j;    int	    clockwise;    int	    slopeoff;    register int s;    register int nright, nleft;    int	    y, lasty, bottomy, topy;    /* find the top of the polygon */    maxy = miny = vertices[0].y;    bottom = top = 0;    for (i = 1; i < count; i++)    {	if (vertices[i].y < miny)	{	    top = i;	    miny = vertices[i].y;	}	if (vertices[i].y >= maxy)	{	    bottom = i;	    maxy = vertices[i].y;	}    }    clockwise = 1;    slopeoff = 0;    i = top;    j = StepAround (top, -1, count);    if (slopes[j].dy * slopes[i].dx > slopes[i].dy * slopes[j].dx)    {	clockwise = -1;	slopeoff = -1;    }    bottomy = ICEIL (maxy) + yi;    nright = 0;    s = StepAround (top, slopeoff, count);    i = top;    while (i != bottom)    {	if (slopes[s].dy != 0)	{	    y = miPolyBuildEdge (vertices[i].x, vertices[i].y,			slopes[s].k,			slopes[s].dx, slopes[s].dy,			xi, yi, 0,			&right[nright]);	    if (nright != 0)	    	right[nright-1].height = y - lasty;	    else	    	topy = y;	    nright++;	    lasty = y;	}	i = StepAround (i, clockwise, count);	s = StepAround (s, clockwise, count);    }    if (nright != 0)	right[nright-1].height = bottomy - lasty;    if (slopeoff == 0)	slopeoff = -1;    else	slopeoff = 0;    nleft = 0;    s = StepAround (top, slopeoff, count);    i = top;    while (i != bottom)    {	if (slopes[s].dy != 0)	{	    y = miPolyBuildEdge (vertices[i].x, vertices[i].y,			   slopes[s].k,		       	   slopes[s].dx,  slopes[s].dy, xi, yi, 1,		       	   &left[nleft]);    	    if (nleft != 0)	    	left[nleft-1].height = y - lasty;	    nleft++;	    lasty = y;	}	i = StepAround (i, -clockwise, count);	s = StepAround (s, -clockwise, count);    }    if (nleft != 0)	left[nleft-1].height = bottomy - lasty;    *pnleft = nleft;    *pnright = nright;    *h = bottomy - topy;    return topy;}static voidmiLineOnePoint (pDrawable, pGC, pixel, spanData, x, y)    DrawablePtr	    pDrawable;    GCPtr	    pGC;    unsigned long   pixel;    SpanDataPtr	    spanData;    int		    x, y;{    DDXPointRec pt;    int	    wid;    unsigned long	oldPixel;    MILINESETPIXEL (pDrawable, pGC, pixel, oldPixel);    if (pGC->fillStyle == FillSolid)    {	pt.x = x;	pt.y = y;	(*pGC->ops->PolyPoint) (pDrawable, pGC, CoordModeOrigin, 1, &pt);    }    else    {	wid = 1;	if (pGC->miTranslate) 	{	    x += pDrawable->x;	    y += pDrawable->y;	}	pt.x = x;	pt.y = y;	(*pGC->ops->FillSpans) (pDrawable, pGC, 1, &pt, &wid, TRUE);    }    MILINERESETPIXEL (pDrawable, pGC, pixel, oldPixel);}static voidmiLineJoin (pDrawable, pGC, pixel, spanData, pLeft, pRight)    DrawablePtr	    pDrawable;    GCPtr	    pGC;    unsigned long   pixel;    SpanDataPtr	    spanData;    register LineFacePtr pLeft, pRight;{    double	    mx, my;    double	    denom;    PolyVertexRec   vertices[4];    PolySlopeRec    slopes[4];    int		    edgecount;    PolyEdgeRec	    left[4], right[4];    int		    nleft, nright;    int		    y, height;    int		    swapslopes;    int		    joinStyle = pGC->joinStyle;    int		    lw = pGC->lineWidth;    if (lw == 1 && !spanData) {	/* Lines going in the same direction have no join */	if (pLeft->dx >= 0 == pRight->dx <= 0)	    return;	if (joinStyle != JoinRound) {    	    denom = - pLeft->dx * (double)pRight->dy + pRight->dx * (double)pLeft->dy;    	    if (denom == 0)	    	return;	/* no join to draw */	}	if (joinStyle != JoinMiter) {	    miLineOnePoint (pDrawable, pGC, pixel, spanData, pLeft->x, pLeft->y);	    return;	}    } else {    	if (joinStyle == JoinRound)    	{	    miLineArc(pDrawable, pGC, pixel, spanData,		      pLeft, pRight,		      (double)0.0, (double)0.0, TRUE);	    return;    	}    	denom = - pLeft->dx * (double)pRight->dy + pRight->dx * (double)pLeft->dy;    	if (denom == 0.0)	    return;	/* no join to draw */    }    swapslopes = 0;    if (denom > 0)    {	pLeft->xa = -pLeft->xa;	pLeft->ya = -pLeft->ya;	pLeft->dx = -pLeft->dx;	pLeft->dy = -pLeft->dy;    }    else    {	swapslopes = 1;	pRight->xa = -pRight->xa;	pRight->ya = -pRight->ya;	pRight->dx = -pRight->dx;	pRight->dy = -pRight->dy;    }    vertices[0].x = pRight->xa;    vertices[0].y = pRight->ya;    slopes[0].dx = -pRight->dy;    slopes[0].dy =  pRight->dx;    slopes[0].k = 0;    vertices[1].x = 0;    vertices[1].y = 0;    slopes[1].dx =  pLeft->dy;    slopes[1].dy = -pLeft->dx;    slopes[1].k = 0;    vertices[2].x = pLeft->xa;    vertices[2].y = pLeft->ya;    if (joinStyle == JoinMiter)    {    	my = (pLeft->dy  * (pRight->xa * pRight->dy - pRight->ya * pRight->dx) -              pRight->dy * (pLeft->xa  * pLeft->dy  - pLeft->ya  * pLeft->dx )) /	      denom;    	if (pLeft->dy != 0)    	{	    mx = pLeft->xa + (my - pLeft->ya) *			    (double) pLeft->dx / (double) pLeft->dy;    	}    	else    	{	    mx = pRight->xa + (my - pRight->ya) *			    (double) pRight->dx / (double) pRight->dy;    	}	/* check miter limit */	if ((mx * mx + my * my) * 4 > SQSECANT * lw * lw)	    joinStyle = JoinBevel;

⌨️ 快捷键说明

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