roundedBoxRgba function

bool roundedBoxRgba(
  1. Pointer<SdlRenderer> renderer,
  2. double x1,
  3. double y1,
  4. double x2,
  5. double y2,
  6. double rad,
  7. int r,
  8. int g,
  9. int b,
  10. int a, {
  11. int blendMode = SDL_BLENDMODE_BLEND,
})

Implementation

bool roundedBoxRgba(
  Pointer<SdlRenderer> renderer,
  double x1,
  double y1,
  double x2,
  double y2,
  double rad,
  int r,
  int g,
  int b,
  int a, {
  int blendMode = SDL_BLENDMODE_BLEND,
}) {
  var result = true;
  var x10 = x1;
  var y10 = y1;
  var x20 = x2;
  var y20 = y2;
  var rad0 = rad;
  double w;
  double h;
  double r2;
  double tmp;
  double cx = 0;
  var cy = rad0;
  double ocx = 0xffff;
  double ocy = 0xffff;
  var df = 1 - rad0;
  double dE = 3;
  var dSe = -2 * rad0 + 5;
  double xpcx;
  double xmcx;
  double xpcy;
  double xmcy;
  double ypcy;
  double ymcy;
  double ypcx;
  double ymcx;
  double x;
  double y;
  double dx;
  double dy;

  /*
	* Check destination renderer
	*/
  if (renderer == nullptr) {
    return false;
  }

  /*
	* Check radius vor valid range
	*/
  if (rad0 < 0) {
    return false;
  }

  /*
	* Special case - no rounding
	*/
  if (rad0 <= 1) {
    return boxRgba(
      renderer,
      x10,
      y10,
      x20,
      y20,
      r,
      g,
      b,
      a,
      blendMode: blendMode,
    );
  }

  /*
	* Test for special cases of straight lines or single point
	*/
  if (x10 == x20) {
    if (y10 == y20) {
      return pixelRgba(renderer, x10, y10, r, g, b, a, blendMode: blendMode);
    } else {
      return vlineRgba(
        renderer,
        x10,
        y10,
        y20,
        r,
        g,
        b,
        a,
        blendMode: blendMode,
      );
    }
  } else {
    if (y10 == y20) {
      return hlineRgba(
        renderer,
        x10,
        x20,
        y10,
        r,
        g,
        b,
        a,
        blendMode: blendMode,
      );
    }
  }

  /*
	* Swap x10, x20 if required
	*/
  if (x10 > x20) {
    tmp = x10;
    x10 = x20;
    x20 = tmp;
  }

  /*
	* Swap y10, y20 if required
	*/
  if (y10 > y20) {
    tmp = y10;
    y10 = y20;
    y20 = tmp;
  }

  /*
	* Calculate width&height
	*/
  w = x20 - x10 + 1;
  h = y20 - y10 + 1;

  /*
	* Maybe adjust radius
	*/
  r2 = rad0 + rad0;
  if (r2 > w) {
    rad0 = w / 2;
    r2 = rad0 + rad0;
  }
  if (r2 > h) {
    rad0 = h / 2;
  }

  /* Setup filled circle drawing for corners */
  x = x10 + rad0;
  y = y10 + rad0;
  dx = x20 - x10 - rad0 - rad0;
  dy = y20 - y10 - rad0 - rad0;

  /*
	* Set color
	*/
  result = true;
  if (result) {
    result = sdlSetRenderDrawBlendMode(renderer, blendMode);
  }
  if (result) {
    result = sdlSetRenderDrawColor(renderer, r, g, b, a);
  }

  /*
	* Draw corners
	*/
  do {
    xpcx = x + cx;
    xmcx = x - cx;
    xpcy = x + cy;
    xmcy = x - cy;
    if (ocy != cy) {
      if (cy > 0) {
        ypcy = y + cy;
        ymcy = y - cy;
        if (result) {
          result = hline(renderer, xmcx, xpcx + dx, ypcy + dy);
        }
        if (result) {
          result = hline(renderer, xmcx, xpcx + dx, ymcy);
        }
      } else {
        if (result) {
          result = hline(renderer, xmcx, xpcx + dx, y);
        }
      }
      ocy = cy;
    }
    if (ocx != cx) {
      if (cx != cy) {
        if (cx > 0) {
          ypcx = y + cx;
          ymcx = y - cx;
          if (result) {
            result = hline(renderer, xmcy, xpcy + dx, ymcx);
          }
          if (result) {
            result = hline(renderer, xmcy, xpcy + dx, ypcx + dy);
          }
        } else {
          if (result) {
            result = hline(renderer, xmcy, xpcy + dx, y);
          }
        }
      }
      ocx = cx;
    }

    /*
		* Update
		*/
    if (df < 0) {
      df += dE;
      dE += 2;
      dSe += 2;
    } else {
      df += dSe;
      dE += 2;
      dSe += 4;
      cy--;
    }
    cx++;
  } while (cx <= cy);

  /* Inside */
  if (dx > 0 && dy > 0) {
    if (result) {
      result = boxRgba(
        renderer,
        x10,
        y10 + rad0 + 1,
        x20,
        y20 - rad0,
        r,
        g,
        b,
        a,
        blendMode: blendMode,
      );
    }
  }
  return result;
}