C++ - Matemática - falando em 3D: como posso calcular os pontos de 1 recta?

Cambalinho

Power Member
seja 1 recta 3D:
1 - origem{100, 200, 0};
2 - Destino{300, 200, 0};

como posso calcular os pontos da recta?
neste caso parece que tem 200 pontos, porque o Y e Z têm a mesma posição. mas não sei calcular a quantidade de pontos.
outra coisa: neste caso, também devido a rotações, devemos usar perspectiva para calcular os pontos?(pois usa Z também)
 
A minha interpretação da primeira pergunta é "como é que podes rasterizar uma recta", e se for isso, vê se estes links ajudam:

https://en.wikipedia.org/wiki/Rasterisation
https://en.wikipedia.org/wiki/Line_drawing_algorithm
https://en.wikipedia.org/wiki/Bresenham's_line_algorithm
https://en.wikipedia.org/wiki/Digital_differential_analyzer_(graphics_algorithm)

mas não sei calcular a quantidade de pontos.
Isto não entendo. O número de pontos depende da tua resolução. Se for discreto, é |X1-X2| (ou |100-300|=200). Se for contínuo, tens infinitos pontos. Se for discreto com anti-aliasing, podes mexer em mais de 200 pontos, porque também podes mexer nos seus vizinhos.
 
desculpe a falta de palavras para descrever, mas tem razão.
preciso de entender mais 1 coisa: falando em 3D, é preciso usar perspectiva?
muito obrigado. vou tentar ver isso
 
eu achei, graças ás suas palavras, este link: http://members.chello.at/easyfilter/bresenham.html
estou com problemas nesta linha:

Código:
void DrawLine3D(HDC HDCDestination, point OriginPoint, point DestinationPoint)
{
    int x0 = OriginPoint.x;
    int y0 = OriginPoint.y;
    int z0 = OriginPoint.z;
    int x1 = DestinationPoint.x;
    int y1 = DestinationPoint.y;
    int z1 = DestinationPoint.z;
   int dx = abs(x1-x0), sx = x0<x1 ? 1 : -1;
   int dy = abs(y1-y0), sy = y0<y1 ? 1 : -1;
   int dz = abs(z1-z0), sz = z0<z1 ? 1 : -1;
   int dm = max(dx,dy,dz), i = dm; /* maximum difference */
   x1 = y1 = z1 = dm/2; /* error offset */

   for(;;) {  /* loop */
      SetPixel(HDCDestination, x0/z0*100,y0/z0*100,RGB(255,0,0));
      if (i-- == 0) break;
      x1 -= dx; if (x1 < 0) { x1 += dm; x0 += sx; }
      y1 -= dy; if (y1 < 0) { y1 += dm; y0 += sy; }
      z1 -= dz; if (z1 < 0) { z1 += dm; z0 += sz; }
   }
}
Código:
int dm = max(dx,dy,dz), i = dm; /* maximum difference */
ao menos penso que o erro seja daqui:
"error: '__comp' cannot be used as a function"
qual é o problema?
 
Nota que a única experiência que tenho em computação gráfica foi uma cadeira na faculdade, portanto há pessoas muito melhores que eu para responder!

desculpe a falta de palavras para descrever, mas tem razão.
preciso de entender mais 1 coisa: falando em 3D, é preciso usar perspectiva?
muito obrigado. vou tentar ver isso

Acho que aquilo que queres é escolher uma projecção. Existe a projecção ortogonal e a projecção em perspectiva, e a decisão depende do que for adequado para o teu projecto, não "precisas" de usar nada.

(se tiveres o fórum com fundo escuro e não a conseguires ver bem, muda para um fundo claro, ou clica na imagem para ires ter ao tópico onde ela aparece)


eu achei, graças ás suas palavras, este link: http://members.chello.at/easyfilter/bresenham.html
estou com problemas nesta linha:

Código:
void DrawLine3D(HDC HDCDestination, point OriginPoint, point DestinationPoint)
{
    int x0 = OriginPoint.x;
    int y0 = OriginPoint.y;
    int z0 = OriginPoint.z;
    int x1 = DestinationPoint.x;
    int y1 = DestinationPoint.y;
    int z1 = DestinationPoint.z;
   int dx = abs(x1-x0), sx = x0<x1 ? 1 : -1;
   int dy = abs(y1-y0), sy = y0<y1 ? 1 : -1;
   int dz = abs(z1-z0), sz = z0<z1 ? 1 : -1;
   int dm = max(dx,dy,dz), i = dm; /* maximum difference */
   x1 = y1 = z1 = dm/2; /* error offset */

   for(;;) {  /* loop */
      SetPixel(HDCDestination, x0/z0*100,y0/z0*100,RGB(255,0,0));
      if (i-- == 0) break;
      x1 -= dx; if (x1 < 0) { x1 += dm; x0 += sx; }
      y1 -= dy; if (y1 < 0) { y1 += dm; y0 += sy; }
      z1 -= dz; if (z1 < 0) { z1 += dm; z0 += sz; }
   }
}
Código:
int dm = max(dx,dy,dz), i = dm; /* maximum difference */
ao menos penso que o erro seja daqui:
"error: '__comp' cannot be used as a function"
qual é o problema?
Nota que esse código é C, não é C++.
Não sei qual é o problema, mas a minha suspeita é que a função max é diferente em C e C++.

Encontrei isto relativamente ao funcionamento do max: https://codereview.stackexchange.com/questions/26100/maximum-of-three-values-in-c/26101

Portanto, experimenta adicionar as chavetas {} à volta da lista de argumentos do max:
C++:
int dm = max({dx,dy,dz}), i = dm; /* maximum difference */
(Talvez seja preciso também trocar por std::max, mas não sei se tens um "using namespace std")
 
Código:
int dm = std::max({dx,dy,dz}), i = dm; /* maximum difference */
'std' eu uso o "using namespace std" no header, mas não funciona no ficheiro main.cpp.. tenho de repetir :P
voltando ao erro:

error: no matching function for call to 'max(<brace-enclosed initializer list>)'
note: candidate expects 2 arguments, 1 provided
penso ser este o erro, mas me ajude por favor
 
Fazer "using namespace std" é má prática, no limite podes fazer "using std::max" e assim não trazes o std inteiro atrás :)

Pelos vistos essa sintaxe é do C++11 e requer que faças:
C++:
#include <algorithm>

Eu não programo em C++, portanto não tenho experiência com isto, só estou a pesquisar pelos erros.
 
Código:
void DrawLine3D(HDC HDCDestination, point OriginPoint, point DestinationPoint)
{
    int x0 = OriginPoint.x;
    int y0 = OriginPoint.y;
    int z0 = OriginPoint.z;
    int x1 = DestinationPoint.x;
    int y1 = DestinationPoint.y;
    int z1 = DestinationPoint.z;
   int dx = abs(x1-x0), sx = x0<x1 ? 1 : -1;
   int dy = abs(y1-y0), sy = y0<y1 ? 1 : -1;
   int dz = abs(z1-z0), sz = z0<z1 ? 1 : -1;
   int dm = std::max({dx,dy,dz}), i = dm; /* maximum difference */
   x1 = y1 = z1 = dm/2; /* error offset */

   for(;;) {  /* loop */
      SetPixel(HDCDestination, x0/z0*100,y0/z0*100,RGB(255,0,0));
      if (i-- == 0) break;
      x1 -= dx; if (x1 < 0) { x1 += dm; x0 += sx; }
      y1 -= dy; if (y1 < 0) { y1 += dm; y0 += sy; }
      z1 -= dz; if (z1 < 0) { z1 += dm; z0 += sz; }
   }
}

int main()
{
     //getting the HDC Console Window:
    HDC WindowHDC=GetDC(GetConsoleWindow());

    do
    {


        DrawLine3D(WindowHDC,TopLeft,TopRight);

        Sleep(1000);
        RECT a;
        a.left=0;
        a.right=500;
        a.top=0;
        a.bottom=400;
        FillRect(WindowHDC,&a, CreateSolidBrush(RGB(0,0,0)));
    }while(!(GetKeyState(VK_ESCAPE) & 0x8000));//press escape for exit
    cout<<"Press return to end . . ."<<endl;
    cin.get();

}
já não tem esse erro... mas além de não mostrar a linha tenho este erro:
"Process returned -1073741676 (0xC0000094) execution time : 1.094 s
Press any key to continue."
 
agora funciona e bem:
C++:
vector<point> GetLinePoints(point Origin, point Destination)
{
    vector<point> LinePoints;
    point LinePoint;
    int dx = abs(Destination.x-Origin.x), sx = Origin.x<Destination.x ? 1 : -1;
    int dy = abs(Destination.y-Origin.y), sy = Origin.y<Destination.y ? 1 : -1;
    int dz = abs(Destination.z-Origin.z), sz = Origin.z<Destination.z ? 1 : -1;
    int dm =std::max( { dx, dy, dz } ), i = dm; /* maximum difference */
    Destination.x = Destination.y = Destination.z = dm/2; /* error offset */

    do
    {
        Destination.x -= dx; if (Destination.x < 0) { Destination.x += dm; Origin.x += sx; }
        Destination.y -= dy; if (Destination.y < 0) { Destination.y += dm; Origin.y += sy; }
        Destination.z -= dz; if (Destination.z < 0) { Destination.z += dm; Origin.z += sz; }
        LinePoint.x=Origin.x;
        LinePoint.y=Origin.y;
        LinePoint.z=Origin.z;
        LinePoints.push_back(LinePoint);
        i--;
    }while(i >=0);
    return LinePoints;
}
mas preciso de perguntar 1 coisa que ainda não sei: dependendo da origem\destino(ou mesmo usando a rotação), alguns pixels não são imprimidos ou são mas tem coordenadas incorrectas e eu não sei o motivo :(
alguém me pode explicar?
 
Back
Topo