Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

KineticJS strokeWidth of 1 causes a blurred, semi-opaque line instead of a sharp 1 pixel line

I've looked around the internet and found nothing, I've looked on other KineticJS examples that use a strokeWidth of 1 on their rectangles and they all appear to have a semi-opaque 2 pixel line rather than a nice sharp 1px opaque black line.

Now, I am guessing that as Google has nothing that the solution is either really simple or impossible, but.. do you know how I can get a one px border using KineticJS?

$(window).load(function(){
    var stage = new Kinetic.Stage({container: "kineticdiv", width: 700, height: 400});
    var layer = new Kinetic.Layer();

    var rect = new Kinetic.Rect({
        x: stage.attrs.width/2, y: stage.attrs.height/2,
        width: 100, height: 100,
        fill: "#eee", stroke: "black", strokeWidth: 1
    });

    layer.add(rect);
    stage.add(layer);
});

Fig 1

Anyone got any ideas?

like image 466
Adam K Dean Avatar asked Apr 27 '12 19:04

Adam K Dean


3 Answers

when you draw a line from (x,y1) to (x,y2) (say; the same is true for horizontal lines) you need to worry about whether x is "in the middle of a pixel". if the line is "between pixels" then it will be half in one and half in another. the result will look blurred (it's basically anti-aliasing).

graphics systems vary on whether coordinates are for corners or centres, but you can fix the issue by experimenting a little - you just need to add half a pixel width to the coord and try again.

in the case of an html5 canvas (0,0) is the top left corner, so if you have no transform i guess the top left pixel centre is at (0.5, 0.5).

like image 126
andrew cooke Avatar answered Oct 18 '22 10:10

andrew cooke


Another approach: if you use Integer numbers as coordinates and ortogonal 1px weight lines, then you can move the whole stage by [0.5, 0.5] and you dont have to add the half of a pixel to each coordinate, you can then use Integer numbers as coordinate as your whole stage will be moved half of pixel to right and the same to down.

like image 29
Ervin Avatar answered Oct 18 '22 11:10

Ervin


There is a cool approach to get exactly what you want: group two similar shapes. The one at the lower level is one pixel larger then the one at the top. Fill the bottom one with the color you want your border (in your case: Black). works fine for me and has the precision and quality of CSS

like image 21
user2167592 Avatar answered Oct 18 '22 12:10

user2167592