where : ibrtses delphi
Delphi - snap and grid
the source code of this page may not appear correctly in certain browsers
due to special characters. Have a look at the source of this HTML page
with notepad instead
Scaled and/or scalable graphic, mainly vector graphic, can lead to uneven
coordinate numbers. The preferable even numbers can be achieved with the
implementation of a snap.
uneven numbers even numbers instead
related : Mapping world and screen
The inter pixel distance may not become just any number, but has to be
restricted to even numbers :
0.1 x 10^N (1/10 based)
0.125 x 10^N (1/8 based)
0.1667 x 10^N (1/6 based)
0.2 x 10^N (1/5 based)
0.25 x 10^N (1/4 based)
0.333 x 10^N (1/3 based)
0.4 x 10^N (1/2.5 based)
0.5 x 10^N (1/2 based)
0.6667 x 10^N (2/3 based)
or similar, whereas N is integer
For a given drawing the interpixel snap is given :
then each number to be displayed or stored is rounded to the nearest
multiple of the pixelsnap.
Faster operation of the drawing application can be achieved when the
objects cannot be moved or placed at each pixel but only at a multiple
of a pixel. Values may be every 6th, 8th, 10th, 12th, 20th or so pixel.
The user has to concentrate less, the bigger the object snap. The pixel
snap and the object snap have to be adjusted for sensible numbers.
drawing a grid poses the same problems as the snap does. Grid lines
should have a certain gap between them. The grid could be placed at
the object snap or a multiple.
finding sensible numbers
after introducing the snap, the numbers are considered even at the small scale.
Still some care has to be taken when drawing a grid or ruler.
examples with 0.2 and 0.002 distance :
-0.05 -0.1 -0.2 | 0.995 0.994
0.15 0.1 0.0 | 0.997 0.996
0.35 0.3 0.2 | 0.999 0.998
0.55 0.5 0.4 | 1.001 1.000
0.75 0.7 0.6 | 1.003 1.002
0.95 0.9 0.8 | 1.005 1.004
1.15 1.1 1.0 | 1.007 1.006
As can be seen, if zero is part of the range, it has to part of the grid.
It is therefore advisable to draw a grid top-down with decreasing distance
to get a grid with about 10 lines on a range -0.1 .. 1.1, use :
findsnap(1.2,10); //which gives 0.1
// split mantissa and exponent but in decimal notation
mantissa:=u/intpower(10,exponent); // 0.1< mantissa <= 1.0
// now adjust the snap as case
if (mantissa<0.14) then m:=0.1;
if (mantissa>=0.14)and(mantissa<0.18) then m:=1/6;
if (mantissa>=0.18)and(mantissa<0.23)then m:=1/5;
if (mantissa>=0.23)and(mantissa<0.27)then m:=1/4;
if (mantissa>=0.27)and(mantissa<0.4)then m:=1/3;
if (mantissa>=0.4)and(mantissa<0.6)then m:=1/2;
if (mantissa>=0.6)then m:=1;
assume a field of x:=0 .. pi and y:= -1.1 .. 1.1 has to be mapped
onto an image of 400x400 pixels.
the pixels have to be square, meaning the snap for x and y is the same.
var range, gridsnap,x,y:extended;
xlow,xhigh,ylow,yhigh:extended; // the boundary
// make the field at least as big as requested
// lower x
// upper x
// lower y
// upper y
// draw the lines, map them to integer first
xs:=map(x); //map them to integer
ys:=map(y); //map them to integer
- using a snap changes the inter pixel distance and therefore the
scale of the drawing. Either the size of the drawing or the mapped
range on the drawing have to be adjusted.
- using EXTENDED as float gives the best result.
- when the pixels have to be square, the same snap has to be
applied for x and y.
Feedback is welcome
last updated: 24.july.99
Copyright (99,2000) Ing.Büro R.Tschaggelar