Drawing Smooth Curves in Java Graphics
graphics, java
Solution
You need to enable antaliasing for Graphics2D object.
Do it like this
Graphics graphics = ...
Graphics2D g2d = (Graphics2D) graphics;
g2d.setRenderingHint(
RenderingHints.KEY_ANTIALIASING,
RenderingHints.VALUE_ANTIALIAS_ON);
// You can also enable antialiasing for text:
g2d.setRenderingHint(
RenderingHints.KEY_TEXT_ANTIALIASING,
RenderingHints.VALUE_TEXT_ANTIALIAS_ON);
Do this before drawing anything using the `graphics` object.
Also see the RenderingHints javadoc.
Problem
I am trying to draw smooth, bezier-type curves to fit a set of data I have in order to plot it in a java graphics drawing. Below is the code I am currently using to plot. It is plotting the points just fine, except that the curves have sharp edges and sometimes have small fractures in them. Is there a better way that I can make a smooth, fitted curve using java graphics? ``` int numProfiles = speedList.size(); int lenOfList; System.out.println(); System.out.println("Creating a new general path"); //BasicStroke boldStroke = new BasicStroke(.3f); //((Graphics2D)g).setStroke(boldStroke); for (int i=0; i<numProfiles; i++){ GeneralPath gp = new GeneralPath(); g.setColor(colors[i]); lenOfList = speedList.get(i).length; if (lenOfList < 3) { double xPlotVal1 = xMarginLeft + (((speedList.get(i)[0].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal1 = yMarginTopAxisTop + (((depthList.get(i)[0].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal2 = xMarginLeft + (((speedList.get(i)[1].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal2 = yMarginTopAxisTop + (((depthList.get(i)[1].getVal() - yMin) / (yMax - yMin)) * height); g.drawLine((int) xPlotVal1, (int) yPlotVal1, (int) xPlotVal2, (int) yPlotVal2); } else { System.out.println("More than 2 pts"); for (int j = 0; j < (lenOfList - 2); j++) { double xPlotVal1 = xMarginLeft + (((speedList.get(i)[j].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal1 = yMarginTopAxisTop + (((depthList.get(i)[j].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal2 = xMarginLeft + (((speedList.get(i)[j + 1].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal2 = yMarginTopAxisTop + (((depthList.get(i)[j + 1].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal3 = xMarginLeft + (((speedList.get(i)[j + 2].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal3 = yMarginTopAxisTop + (((depthList.get(i)[j + 2].getVal() - yMin) / (yMax - yMin)) * height); gp.moveTo(xPlotVal1, yPlotVal1); if (j==0) gp.moveTo(xPlotVal1, yPlotVal1); // gp.moveTo(xPlotVal1, yPlotVal1); gp.curveTo(xPlotVal1, yPlotVal1, xPlotVal2, yPlotVal2, xPlotVal3, yPlotVal3); } ((Graphics2D) g).draw(gp); } } ``` Here is a picture of what it's drawing: //June 26, 2012 at 7:34AM //Here is the updated code after I added the rendering hint ``` // the profiles Graphics2D g2d = (Graphics2D)g; int numProfiles = speedList.size(); int lenOfList; for (int i=0; i<numProfiles; i++){ GeneralPath gp = new GeneralPath(); g2d.setColor(colors[i]); lenOfList = speedList.get(i).length; if (lenOfList < 3) { double xPlotVal1 = xMarginLeft + (((speedList.get(i)[0].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal1 = yMarginTopAxisTop + (((depthList.get(i)[0].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal2 = xMarginLeft + (((speedList.get(i)[1].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal2 = yMarginTopAxisTop + (((depthList.get(i)[1].getVal() - yMin) / (yMax - yMin)) * height); g2d.drawLine((int) xPlotVal1, (int) yPlotVal1, (int) xPlotVal2, (int) yPlotVal2); } else { for (int j = 0; j < (lenOfList - 2); j++) { double xPlotVal1 = xMarginLeft + (((speedList.get(i)[j].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal1 = yMarginTopAxisTop + (((depthList.get(i)[j].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal2 = xMarginLeft + (((speedList.get(i)[j + 1].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal2 = yMarginTopAxisTop + (((depthList.get(i)[j + 1].getVal() - yMin) / (yMax - yMin)) * height); double xPlotVal3 = xMarginLeft + (((speedList.get(i)[j + 2].getVal() - xMin) / (xMax - xMin)) * width); double yPlotVal3 = yMarginTopAxisTop + (((depthList.get(i)[j + 2].getVal() - yMin) / (yMax - yMin)) * height); gp.moveTo(xPlotVal1, yPlotVal1); if (j==0) gp.moveTo(xPlotVal1, yPlotVal1); //only move at the begining of the curve drawing // gp.moveTo(xPlotVal1, yPlotVal1); gp.curveTo(xPlotVal1, yPlotVal1, xPlotVal2, yPlotVal2, xPlotVal3, yPlotVal3); } g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); g2d.draw(gp); } } ``` Here is the newest picture. I am not sure why it's making my background grid lines disappear. I plot the grid lines after I plot the colored profiles.