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

📄 ttraster.c

📁 神龙卡开发原代码
💻 C
📖 第 1 页 / 共 5 页
字号:
    fresh  = ras.fresh;    result = Line_Up( RAS_VARS x1, -y1, x2, -y2, -maxy, -miny );    if ( fresh && !ras.fresh )      ras.cProfile->start = -ras.cProfile->start;    return result;  }/****************************************************************************//*                                                                          *//* Function:    Bezier_Up                                                   *//*                                                                          *//* Description: Computes thes x-coordinates of an ascending bezier arc      *//*              and stores them in the render pool.                         *//*                                                                          *//* Input:       None.  The arc is taken from the top of the Bezier stack.   *//*                                                                          *//* Returns:     SUCCESS on success.                                         *//*              FAILURE on Render Pool overflow.                            *//*                                                                          *//****************************************************************************/  static Bool  Bezier_Up( RAS_ARGS Long  miny, Long  maxy )  {    Long   y1, y2, e, e2, e0;    Short  f1;    TPoint*  arc;    TPoint*  start_arc;    PStorage top;    arc = ras.arc;    y1  = arc[2].y;    y2  = arc[0].y;    top = ras.top;    if ( y2 < miny || y1 > maxy )      goto Fin;    e2 = FLOOR( y2 );    if ( e2 > maxy )      e2 = maxy;    e0 = miny;    if ( y1 < miny )      e = miny;    else    {      e  = CEILING( y1 );      f1 = FRAC( y1 );      e0 = e;      if ( f1 == 0 )      {        if ( ras.joint )        {          top--;          ras.joint = FALSE;        }        *top++ = arc[2].x;        DEBUG_PSET;        e += ras.precision;      }    }    if ( ras.fresh )    {      ras.cProfile->start = TRUNC( e0 );      ras.fresh = FALSE;    }    if ( e2 < e )      goto Fin;    if ( ( top + TRUNC( e2 - e ) + 1 ) >= ras.maxBuff )    {      ras.top   = top;      ras.error = Raster_Err_Overflow;      return FAILURE;    }    start_arc = arc;    while ( arc >= start_arc && e <= e2 )    {      ras.joint = FALSE;      y2 = arc[0].y;      if ( y2 > e )      {        y1 = arc[2].y;        if ( y2 - y1 >= ras.precision_step )        {          Split_Bezier( arc );          arc += 2;        }        else        {          *top++ = arc[2].x + FMulDiv( arc[0].x - arc[2].x,                                       e - y1,                                       y2 - y1 );          DEBUG_PSET;          arc -= 2;          e   += ras.precision;        }      }      else      {        if ( y2 == e )        {          ras.joint  = TRUE;          *top++     = arc[0].x;          DEBUG_PSET;          e += ras.precision;        }        arc -= 2;      }    }  Fin:    ras.top  = top;    ras.arc -= 2;    return SUCCESS;  }/****************************************************************************//*                                                                          *//* Function:    Bezier_Down                                                 *//*                                                                          *//* Description: Computes the x-coordinates of a descending bezier arc       *//*              and stores them in the render pool.                         *//*                                                                          *//* Input:       None.  Arc is taken from the top of the Bezier stack.       *//*                                                                          *//* Returns:     SUCCESS on success.                                         *//*              FAILURE on Render Pool overflow.                            *//*                                                                          *//****************************************************************************/  static Bool  Bezier_Down( RAS_ARGS Long  miny, Long  maxy )  {    TPoint*  arc = ras.arc;    Bool     result, fresh;    arc[0].y = -arc[0].y;    arc[1].y = -arc[1].y;    arc[2].y = -arc[2].y;    fresh = ras.fresh;    result = Bezier_Up( RAS_VARS -maxy, -miny );    if ( fresh && !ras.fresh )      ras.cProfile->start = -ras.cProfile->start;    arc[0].y = -arc[0].y;    return result;  }/****************************************************************************//*                                                                          *//* Function:    Line_To                                                     *//*                                                                          *//* Description: Injects a new line segment and adjusts Profiles list.       *//*                                                                          *//* Input:       x, y : segment endpoint (start point in LastX,LastY)        *//*                                                                          *//* Returns:     SUCCESS on success.                                         *//*              FAILURE on Render Pool overflow or Incorrect Profile.       *//*                                                                          *//****************************************************************************/  static Bool  Line_To( RAS_ARGS Long  x, Long  y )  {    /* First, detect a change of direction */    switch ( ras.state )    {    case Unknown:      if ( y > ras.lastY )      {        if ( New_Profile( RAS_VARS  Ascending ) ) return FAILURE;      }      else      {        if ( y < ras.lastY )          if ( New_Profile( RAS_VARS  Descending ) ) return FAILURE;      }      break;    case Ascending:      if ( y < ras.lastY )      {        if ( End_Profile( RAS_VAR ) ||             New_Profile( RAS_VARS  Descending ) ) return FAILURE;      }      break;    case Descending:      if ( y > ras.lastY )      {        if ( End_Profile( RAS_VAR ) ||             New_Profile( RAS_VARS  Ascending ) ) return FAILURE;      }      break;    default:      ;    }    /* Then compute the lines */    switch ( ras.state )    {    case Ascending:      if ( Line_Up ( RAS_VARS  ras.lastX, ras.lastY,                     x, y, ras.minY, ras.maxY ) )        return FAILURE;      break;    case Descending:      if ( Line_Down( RAS_VARS ras.lastX, ras.lastY,                      x, y, ras.minY, ras.maxY ) )        return FAILURE;      break;    default:      ;    }    ras.lastX = x;    ras.lastY = y;    return SUCCESS;  }/****************************************************************************//*                                                                          *//* Function:    Bezier_To                                                   *//*                                                                          *//* Description: Injects a new bezier arc and adjusts the profile list.      *//*                                                                          *//* Input:       x,   y : arc endpoint (start point in LastX, LastY)         *//*              Cx, Cy : control point                                      *//*                                                                          *//* Returns:     SUCCESS on success.                                         *//*              FAILURE on Render Pool overflow or Incorrect Profile.       *//*                                                                          *//****************************************************************************/  static Bool  Bezier_To( RAS_ARGS Long  x,                                   Long  y,                                   Long  cx,                                   Long  cy )  {    Long     y1, y2, y3, x3;    TStates  state_bez;    Push_Bezier( RAS_VARS ras.lastX, ras.lastY, cx, cy, x, y );    do    {      y1 = ras.arc[2].y;      y2 = ras.arc[1].y;      y3 = ras.arc[0].y;      x3 = ras.arc[0].x;      /* first, categorize the bezier arc */      if ( y1 == y2 )      {        if ( y2 == y3 )          state_bez = Flat;        else if ( y2 > y3 )          state_bez = Descending;        else          state_bez = Ascending;      }      else if ( y1 > y2 )      {        if ( y2 >= y3 )          state_bez = Descending;        else          state_bez = Unknown;      }      else if ( y2 <= y3 )        state_bez = Ascending;      else        state_bez = Unknown;      /* split non-monotonic arcs, ignore flat ones, or */      /* computes the up and down ones                  */      switch ( state_bez )      {      case Flat:        ras.arc -= 2;        break;      case Unknown:        Split_Bezier( ras.arc );        ras.arc += 2;        break;      default:        /* detect a change of direction */        if ( ras.state != state_bez )        {          if ( ras.state != Unknown )            if ( End_Profile( RAS_VAR ) ) return FAILURE;          if ( New_Profile( RAS_VARS state_bez ) ) return FAILURE;        }        /* compute */        switch ( ras.state )        {        case Ascending:          if ( Bezier_Up ( RAS_VARS ras.minY, ras.maxY ) )            return FAILURE;          break;        case Descending:          if ( Bezier_Down( RAS_VARS ras.minY, ras.maxY ) )            return FAILURE;          break;        default:          ;        }      }    } while ( ras.arc >= ras.arcs );    ras.lastX = x3;    ras.lastY = y3;    return SUCCESS;  }/****************************************************************************//*                                                                          *//* Function:    Decompose_Curve                                             *//*                                                                          *//* Description: Scans the outline arays in order to emit individual         *//*              segments and beziers by calling Line_To() and Bezier_To().  *//*              It handles all weird cases, like when the first point       *//*              is off the curve, or when there are simply no 'on'          *//*              points in the contour!                                      *//*                                                                          *//* Input:       first, last    : indexes of first and last point in         *//*                               contour.                                   *//*                                                                          *//* Returns:     SUCCESS on success.                                         *//*              FAILURE on error.                                           *//*                                                                          *//****************************************************************************/#undef  SWAP_#define SWAP_(x,y)  { Long swap = x; x = y; y = swap; }  static Bool  Decompose_Curve( RAS_ARGS UShort  first,                                         UShort  last,                                         Bool    flipped )  {    Long   x,  y;   /* current point                */    Long   cx, cy;  /* current Bezier control point */    Long   mx, my;  /* current middle point         */    Long   x_first, y_first;  /* first point's coordinates */    Long   x_last,  y_last;   /* last point's coordinates  */    UShort  index;     /* current point's index */    Bool    on_curve;  /* current point's state */    x_first = SCALED( ras.coords[first].x );    y_first = SCALED( ras.coords[first].y );    if ( flipped ) SWAP_( x_first,y_first );    x_last  = SCALED( ras.coords[last].x );    y_last  = SCALED( ras.coords[last].y );    if ( flipped ) SWAP_( x_last,y_last );    ras.lastX = cx = x_first;    ras.lastY = cy = y_first;    on_curve = (ras.flags[first] & 1);    index    = first;    /* check first point to determine origin */    if ( !on_curve )    {      /* first point is off the curve.  Yes, this happens... */      if ( ras.flags[last] & 1 )      {        ras.lastX = x_last;  /* start at last point if it */        ras.lastY = y_last;  /* is on the curve           */      }      else      {        /* if both first and last points are off the curve, */        /* start at their middle and record its position    */        /* for closure                                      */

⌨️ 快捷键说明

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