#ifndef objeto_H #define objeto_H /* Representação geométrica e óptica da cena. */ #define objeto_H_COPYRIGHT "Copyright © 2008 Danillo Pereira e J. Stolfi, UNICAMP" /* Last edited on 2008-07-22 20:19:36 by stolfi */ #define _GNU_SOURCE #include #include #include #include #include "geometria_basica.h" typedef enum { TipoDeObjeto_Bola, //uma esfera. TipoDeObjeto_Cubo, //uma caixa alinhada com os eixos. TipoDeObjeto_Nenhum //quando não há objeto. } TipoDeObjeto; /* Código que indica o tipo de um objeto primitivo da cena. */ typedef struct Objeto { char *nome; //nome do objeto (para fins de acabamento). int iac; //índice do acabamento, ou -1 se inválido/indefinido. TipoDeObjeto tipo; //tipo do objeto. Ponto3d canto[2]; //coordenadas de dois cantos opostos da caixa envolvente. } Objeto; /* Descrição de um objeto geométrico primitivo. Todos os objetos com o mesmo {nome} terão o mesmo acabamento; e, se forem emissores, serão parte da mesma fonte de luz. */ void EscreveObjeto(FILE *wr, Objeto *ob); /* Escreve o objeto {*st} no arquivo {wr}. */ Objeto LeObjeto(FILE *rd); /* Lê um objeto do arquivo {rd}, no formato criado por {EscreveObjeto}. */ /* LISTAS DE OBJETOS */ vec_typedef(ListaDeObjetos, ListaDeObjetos, Objeto); /* Um vetor auto-delimitado de objetos, {A.e[0..A.ne-1]}. Também define {ListaDeObjetos_new()}, {ListaDeObjetos_expand()}, {ListaDeObjetos_trim()}, {ListaDeObjetos_free()}. */ void EscreveListaDeObjetos(FILE *wr, ListaDeObjetos *obs); /* Escreve em {wr} a descrição da lista de objetos {obs}. */ ListaDeObjetos LeListaDeObjetos(FILE *rd); /* Le do arquivo {rd} a descrição de uma lista de objetos, no formato . */ /* TRAÇADO DE RAIOS As rotinas de traçado de raios aplicam uma pequena perturbação (controlada pelo parâmetro ???) a fim de garantir que um raio lançado a partir de um ponto que deveria estar na superfície de um objeto, com direção apontando para fora do mesmo, não encontre imediatamente esse mesmo objeto. Note que essa perturbação pode fazer com que o raio atravesse objetos muito pequenos sem perceber sua existência. */ #define EPSILON_DE_ORIGEM_DO_RAIO 1.0e-8 /* Deslocamento aplicado à origem de um raio que supostamente está na superfície da cena, numa direção apropriada, para evitar que o raio encontre imediatamente esse mesmo ponto da superfície. */ void PrimeiraInterseccaoRaioObjetos(ListaDeObjetos *obs, Ponto3d *olho, Vetor3d *dir, double *distP, int *iobP); /* Coloca em {*distP} o parâmetro {t} do raio {olho + t*dir} correspondente ao primeiro ponto em que o raio entra em algum objeto da lista {obs}; e coloca em {*iobP} o índice desse objeto. Se o raio não encontra nenhum objeto, coloca {+INF} em {*distP} e {-1} em {*iobP}. Se o ponto {olho} está dentro de algum objeto, devolve {-1.0} em {*distP} e o índice desse objeto em {*iobP}. */ double DistInterseccaoRaioObjeto(Objeto *ob, Ponto3d *olho, Vetor3d *dir); /* Determina o parâmetro {t} do raio {olho + t*dir} correspondente ao ponto em que o raio entra no objeto {ob} dado. Devolve {+INF} se o raio não intercepta o objeto. Devolve {-1.0} se o ponto {olho} está dentro do objeto. */ double DistInterseccaoRaioBola(Ponto3d canto[], Ponto3d *olho, Vetor3d *dir); double DistInterseccaoRaioCubo(Ponto3d canto[], Ponto3d *olho, Vetor3d *dir); /* Similar a {InterseccaoRaioObjeto}, mas especializado para um determinado tipo de objeto. */ void DeterminaNormalDeObjeto(Objeto *ob, Ponto3d *posicao, Vetor3d *normal); /* Supõe que o ponto {posicao} está na superfície do objeto {ob}. Coloca em {*normal} o vetor unitário normal à superfície desse objeto nesse ponto, apontando de dentro para fora do objeto. */ void DeterminaNormalDeBola(Ponto3d canto[], Ponto3d *posicao, Vetor3d *normal); void DeterminaNormalDeCubo(Ponto3d canto[], Ponto3d *posicao, Vetor3d *normal); /* Similar a {DeterminaNormalDeObjeto}, mas especializado para um determinado tipo de objeto. */ #define TOLERANCIA_VISIB 0.0000005 double VisibilidadePontoParaPonto(Ponto3d *pA, Ponto3d *pB, ListaDeObjetos *obs); /* Devolve o fator de visibilidade entre os pontos {pA} e {pB} levando em conta os objetos {obs}. Especificamente, devolve 0.0 (oclusão) se o segmento de reta com extremos {pA} e {pB}, encurtado por {TOLERANCIA_VISIB} nas duas pontas, intercepta algum objeto da lista {obs}; senão devolve 1.0 (vista livre). */ #endif