FAQ
Cover
This is the archive Discourse for the Processing (ALPHA) software.
Please visit the new Processing forum for current information.

   Processing 1.0 _ALPHA_
   Programming Questions & Help
   Programs
(Moderators: fry, REAS)
   Smooth thick line
« Previous topic | Next topic »

Pages: 1 
   Author  Topic: Smooth thick line  (Read 1211 times)
Mark Hill

WWW Email
Smooth thick line
« on: Mar 15th, 2005, 12:40pm »

Here's a simple piece of code to draw lines on the screen.
My problems are:
 
 
1. Drawing over a smooth() line of strokeweight(1) with anything thicker  seems to anti-alias in a weird way, even with noSmooth() on the second line.
 
2. Finally, does anyone have a good way of drawing a line between two points that reflects the natural motion of the mouse instead of a straight line, because any angle of change is pronounced on the heavier strokes, making the segmentation visible and the lines a bit ugly.
 
Testing this code and moving the mouse slowly will show what I mean.
 
Any help is appreciated.
 
void setup() {
size(500,200);
 
background(255);
 
 
smooth();
strokeWeight(4);
stroke(255,0,0);
 
}
 
 
void loop() {
 
  if(mousePressed) {  
   point(pmouseX,pmouseY); //cludge to smooth out line segmentation
   line(pmouseX, pmouseY, mouseX, mouseY);  
   point(mouseX,mouseY);
  }
}
 
void keyPressed() {
 
  if(key == '1') {strokeWeight(1);}
  else if(key == '2') {strokeWeight(2);}
  else if(key == '3') {strokeWeight(3);}
  else if(key == '4') {strokeWeight(4);}
  
  }
« Last Edit: Mar 21st, 2005, 12:22am by Mark Hill »  
bsr

WWW Email
Re: Line trouble
« Reply #1 on: Mar 15th, 2005, 4:08pm »

just a guess here, might be a solution. when the user changes line width have the screen image saved into bimage and use that as a background.
 
 

http://hippocamp.net
Mark Hill

WWW Email
Re: Line problem
« Reply #2 on: Mar 19th, 2005, 9:58am »

Thanks bsr.
 
I think that may solve one problem, but I'm trying to minimize the no. of Bimage to background tasks I have to perform as I'm already doing a few and can't afford any more loss in processing time.
 
I'll shuffle things about a bit to see if I can get it in, although I haven't tested it yet, but it sounds good.
 
bsr

WWW Email
Re: Smooth thick line
« Reply #3 on: Mar 19th, 2005, 3:37pm »

quasimondo wrote his own anti-liasing routine to get around this problem: http://incubator.quasimondo.com/processing/beziers_ballet.php
 
might be worth asking him for pointers
 

http://hippocamp.net
Mark Hill

WWW Email
Re: Smooth thick line
« Reply #4 on: Mar 19th, 2005, 4:05pm »


It certainly looks the business. This would certainly be useful on the thinner lines.
 
I know part of my problem with the thicker lines doesn't lie with anti-aliasing but rather the way two lines meet at different angles and the inevitable gaps produced by the rectangular ends.
 
I'm thinking that curves might do it, to maintain continuity??
 
 
Quasimondo

WWW Email
Re: Smooth thick line
« Reply #5 on: Mar 19th, 2005, 5:09pm »

It looks like curves won't help a lot either.
 
Here's a quick mock-up which seems to work at first look, but actually it's just a trick because the curves get painted over several times.  
 
Code:

 
point[] lineBuffer;
int bufferPointer;
 
void setup() {  
size(500,200);  
 
lineBuffer = new point[10000];
bufferPointer=0;
 
background(255);  
 
   
smooth();  
strokeWeight(4);  
stroke(255,0,0);  
 
}  
 
 
void loop() {  
 background(0xffffff);
for (int i=0;i<bufferPointer-4;i++){
curve(lineBuffer[i].x, lineBuffer[i].y, lineBuffer[i+1].x, lineBuffer[i+1].y, lineBuffer[i+2].x, lineBuffer[i+2].y, lineBuffer[i+3].x, lineBuffer[i+3].y);
}
 
  if(mousePressed) {  
    lineBuffer[bufferPointer++]=new point(mouseX,mouseY);
  }  
}  
   
  void mousePressed(){
    bufferPointer=0;
  }
   
void keyPressed() {  
 
  if(key == '1') {strokeWeight(1);}  
  else if(key == '2') {strokeWeight(2);}  
  else if(key == '3') {strokeWeight(3);}  
  else if(key == '4') {strokeWeight(4);}  
   
  }  
   
  class point
  {
  int x,y;
  point (int x,int y){
  this.x=x;
  this.y=y;
  }
  }
 

Mario Klingemann | Quasimondo | Incubator | côdeazur
Mark Hill

WWW Email
Re: Smooth thick line
« Reply #6 on: Mar 19th, 2005, 5:39pm »

Thanks Mario,
 
You're right it sort of seems to work...
 
Can't really afford that amount of redraw though.
 
I wonder if dumping a joiner between the two angles from a look-up table might do it, in the same sort of way the point() cludge attempts to.
 
Here is an improvement, but still no cigar.
 
 
 void setup() {  
 size(500,200);  
   
 background(255);  
 
 stroke(255,0,0);  
 ellipseMode(CENTER_DIAMETER);
 fill(255,0,0);
 }  
   
   
 void loop() {  
   
   if(mousePressed) {  
   
    smooth();
    stroke(255,0,0);
    strokeWeight(lineWeight);
    line(pmouseX, pmouseY, mouseX, mouseY);  
 
    strokeWeight(1);
//    noStroke();
     stroke(255,0,0);
    noSmooth();
     
    es = table[lineWeight];
     
    ellipse(mouseX,mouseY,es,es);  
    ellipse(pmouseX,pmouseY,es, es);  
   }  
 }  
   
int lineWeight = 4;
int es =0;
int[] table = {0,0,3,4,6}; // values need tweaking...
 
 void keyPressed() {  
   
   if(key == '1') {lineWeight=1;}  
   else if(key == '2') {lineWeight=2;}  
   else if(key == '3') {lineWeight=3;}  
   else if(key == '4') {lineWeight=4;}  
     
   }
« Last Edit: Mar 19th, 2005, 6:09pm by Mark Hill »  
Mark Hill

WWW Email
Java 2d line call
« Reply #7 on: Mar 20th, 2005, 12:18am »

I realise I might be asking for trouble here, but using the Java2d line drawing function seems to do the trick better, and does in fact patch the ends of lines as I suspected.
 
Not being a Java head how do I integrate this into my processing sketches. I've got this far by hacking some Java source and overriding the paint method. Is there a better way of doing this. I know that loop() still gets called, but is ineffectual. I'd like to just override the processing (no offence guys!) line draw to get at the extended functionality of J2D and continue with normal processing afterwards.
 
Any ideas?
 
 
 
void setup() {  
 size(500,200);  
 }  
    
    
BasicStroke roundStroke;
RenderingHints renderHints;
 
public void paint(Graphics g){
  
 // super.paint(g);
    
  Graphics2D g2 = (Graphics2D)g;  // Cast to access Java2D  
    
  g2.setColor(Color.red);  // pen colour;
            
  renderHints = new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
  renderHints.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
    
  g2.setRenderingHints(renderHints);
  
  roundStroke = new BasicStroke(4.0f, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND);  // CAP = SQUARE, BUTT, ROUND: JOIN = MITER, BEVEL, ROUND
  g2.setStroke(roundStroke);
 
  g2.drawLine(pmouseX, pmouseY, mouseX, mouseY);    
}
 
 
void loop() {  
    
 //  background(0);
  
}  
« Last Edit: Mar 20th, 2005, 12:24am by Mark Hill »  
Mark Hill

WWW Email
Re: Smooth thick line
« Reply #8 on: Mar 21st, 2005, 12:22am »

Here's my solution if anyone's interested in drawing continous aliased thick lines. It caps the meeting of 2 lines using an ellipse. Pretty simple in the end! And on that note I'll close this thread.
 
CODE:
 
 
color pen;
color ground;
 
BGraphics buf;
 
void setup() {  
 size(500,200);
 buf = new BGraphics(width, height);  
 
 pen = color(255,255,255);
 ground = color(26,26,0);
 
 background(ground);  
 buf.background(ground);
 
 buf.ellipseMode(CENTER_DIAMETER);
 
 buf.stroke(pen);
 buf.fill(pen);
 
 buf.strokeWeight(2);
 buf.smooth();
 }  
 
void loop() {  
 
  image(buf,0,0,width, height);
  
  if(mousePressed) {
  smoothLine(buf,(int)pmouseX, (int)pmouseY, (int)mouseX, (int)mouseY, pen);  
  }
}  
 
 
 
public void smoothLine(BGraphics g, int x1, int y1, int x2, int y2, color pen) {
  g.stroke(this.pen);                // Stroke on @ set weight
  g.line(x1,y1,x2,y2);               // draw the line  
  if(g.strokeWeight>1) {
    g.noStroke();  // strokeweight>1 causes strange behaviour so noStroke to be safe, probably quicker, too.
    g.ellipse(x1, y1, g.strokeWeight*2,g.strokeWeight*2);  // cap previous line with rounded end
  }
}  
« Last Edit: Mar 21st, 2005, 12:23am by Mark Hill »  
Pages: 1 

« Previous topic | Next topic »