È dato un metodo per generare una lista di rette in forma implicita (ax+by+c=0) codificate in float4 nel seguente modo: U.x = a, U.y = b, U.z = c (la quarta componente è nulla e non viene utilizzata).
Si scriva un programma che:
maxval
) le rette in input.Un pixel (x,y) sta sulla retta di coefficienti (a,b,c) se a x + b y + c = 0. Per motivi di precisione numerica, si usi il controllo abs(a x + b y + c) < T dove T è una tolleranza costante (si ponga ad esempio T = 0.5f).
BONUS: disegnare le rette con antialiasing. Per ottenere l'effetto di
antialiasing, si può colorare il singolo pixel (x, y) con un valore compreso
tra 0 e maxval
secondo la formula
fmin(maxval, fmax(0, maxval*(abs(a*x + b*y + c) - T)))
rispetto alla retta (a,b,c).
Come si può gestire la vicinanza a più rette? (suggerimento: il primo valore
nella formula, invece di essere maxval
(bianco) dovrebbe essere …)
File ausiliari forniti:
makelines.h
: alloca e genera un elenco di rette con la funzione
int make_lines(float4 **lines, size_t numlines, size_t R, size_t H)
dove
lines
è un puntatore all'array di righe da allocare e inizializzare
(suggerimento: si dichiari float4 *lines;
e si usi make_lines(&lines, …)
),numlines
il numero di righe,R
un valore arbitrario (si suggerisce R
uguale a circa un terzo
dell'altezza dell'immagine)H
un offset (si suggerisce H
uguale a circa metà dell'immagine)pamalign.h
: fornisce strutture dati e funzioni per il caricamento ed
il salvataggio di immagini in formato PAM. I dati dell'immagine sono
sempre allineati ad un numero pari di canali (2, 4) anche quando i
canali dell'immagine sono dispari (1, 3).
Strutture definite:
struct imgInfo {
uint width; /* larghezza dell'immagine */
uint height; /* altezza dell'immagine */
uint channels; /* numero di canali reali dell'immagine */
uint maxval; /* massimo valore del singolo canale */
uint depth; /* bits per value */
size_t data_size; /* dimensioni in byte dell'array data */
ushort *data; /* dati */
};
Funzioni definite:
int load_pam(const char *fname, imgInfo *img);
int save_pam(const char *fname, const imgInfo *img);
int alloc_img(imgInfo *img);
Le prime due hanno come scopo rispettivamente il caricamento ed
il salvataggio dell'immagine dal/sul file fname
con dati in img
.
La terza alloca memoria per l'immagine ed inizializza i campi
data_size
e data
della struttura img
in cui siano stati impostati
correttamente width
, height
, channels
e depth
. La memoria
allocata da alloc_img
non è inizializzata.
Le funzioni restituiscono 0 in caso di successo, 1 in caso di fallimento.