// File: /workspace/github_cpp_makefile_star2_O3/tomfunkhouser[P]gaps/apps/gapsview/gapsview.cpp
// Function: DrawImageDepths(ImageData*, gaps::R3Point const&, gaps::R3Vector const&, gaps::R3Vector const&, gaps::R3Vector const&, double, double, double)
static void
DrawImageDepths(ImageData *data, const R3Point& viewpoint,
  const R3Vector& towards, const R3Vector& right, const R3Vector& up,
  RNAngle xfov, RNAngle yfov, RNLength image_billboard_depth)
{
  // Check if drawing image depths
  if (!show_image_depths) return;

  // Check image data
  int w = data->image_width;
  int h = data->image_height;
  if (w == 0) return;
  if (h == 0) return;
  if (data->depth_image.XResolution() != w) return;
  if (data->depth_image.YResolution() != h) return;
  
  // Load texture
  LoadTexture(data);
  if (data->texture_id == 0) return;

  // Enable texture
  glBindTexture(GL_TEXTURE_2D, data->texture_id);
  glEnable(GL_TEXTURE_2D);
  glDisable(GL_LIGHTING);
  RNLoadRgb(1, 1, 1);

  // Check if have ray images
  if ((data->ray_origin_images[0].XResolution() == w) &&
      (data->ray_origin_images[1].XResolution() == w) &&
      (data->ray_origin_images[2].XResolution() == w) && 
      (data->ray_origin_images[0].YResolution() == h) &&
      (data->ray_origin_images[1].YResolution() == h) &&
      (data->ray_origin_images[2].YResolution() == h) && 
      (data->ray_direction_images[0].XResolution() == w) &&
      (data->ray_direction_images[1].XResolution() == w) &&
      (data->ray_direction_images[2].XResolution() == w) && 
      (data->ray_direction_images[0].YResolution() == h) &&
      (data->ray_direction_images[1].YResolution() == h) &&
      (data->ray_direction_images[2].YResolution() == h)) {
    RNGrfxBegin(RN_GRFX_POINTS);
    for (int ix = 0; ix < w; ix++) {
      for (int iy = 0; iy < h; iy++) {
        // Get/check depth
        double depth = data->depth_image.GridValue(ix, iy);
        if ((depth <= 0) || (depth == R2_GRID_UNKNOWN_VALUE)) continue;

        // Get/check ray direction
        double dx = data->ray_direction_images[0].GridValue(ix, iy);    
        double dy = data->ray_direction_images[1].GridValue(ix, iy);    
        double dz = data->ray_direction_images[2].GridValue(ix, iy);
        R3Vector direction(dx, dy, dz);
        if (direction.IsZero()) continue;

        // Get ray origin
        double ox = data->ray_origin_images[0].GridValue(ix, iy);    
        double oy = data->ray_origin_images[1].GridValue(ix, iy);    
        double oz = data->ray_origin_images[2].GridValue(ix, iy);    
        R3Point origin(ox, oy, oz);

        // Get point position
        RNScalar t = depth * direction.Dot(towards);
        R3Point p = origin + t * direction;

        // Get texture coordinates
        double u = (double) ix / (double) w;
        double v = (double) iy / (double) h;

        // Draw point
        R3LoadTextureCoords(u, v);
        R3LoadPoint(p);
      }
    }
    RNGrfxEnd();
  }
  else {
    // Compute view plane rectangle in world coordinates
    R3Vector dx = 2.0 * right * image_billboard_depth * tan(xfov);
    R3Vector dy = 2.0 * up * image_billboard_depth * tan(yfov);
    R3Point origin = viewpoint + towards * image_billboard_depth;
    R3Point lower_left = origin - 0.5*dx - 0.5*dy;

    // Backproject pixels from the view plane rectangle
    RNGrfxBegin(RN_GRFX_POINTS);
    for (int ix = 0; ix < w; ix++) {
      for (int iy = 0; iy < h; iy++) {
        double depth = data->depth_image.GridValue(ix, iy);
        if ((depth <= 0) || (depth == R2_GRID_UNKNOWN_VALUE)) continue;
        double u = (double) ix / (double) w;
        double v = (double) iy / (double) h;
        R3Point pA = lower_left + u*dx + v*dy;
        R3Vector vA = pA - viewpoint;
        double dA = vA.Dot(towards);
        if (dA <= 0) continue;
        R3Point p = viewpoint + vA * depth / dA;
        R3LoadTextureCoords(u, v);
        R3LoadPoint(p);
      }
    }
    RNGrfxEnd();
  }
  
  // Disable texture
  glDisable(GL_TEXTURE_2D);
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x138, %rsp            # imm = 0x138
movq %rdx, 0x48(%rsp)
movq %rsi, 0x20(%rsp)
cmpl $0x0, 0x1a9a9e(%rip)    # 0x1db3b4
je 0x31fdf
movq %rcx, %rbx
movq %rdi, %r14
movl 0x768(%rdi), %ebp
movl 0x76c(%rdi), %edx
testl %ebp, %ebp
sete %al
testl %edx, %edx
sete %cl
orb %al, %cl
jne 0x31fdf
cmpl %ebp, 0xd8(%r14)
jne 0x31fdf
cmpl %edx, 0xdc(%r14)
jne 0x31fdf
movq %r8, %r12
movq %r14, %rdi
movl %edx, 0x8(%rsp)
movsd %xmm1, 0x10(%rsp)
movsd %xmm0, 0x28(%rsp)
callq 0x321fa
movl 0x770(%r14), %esi
testl %esi, %esi
je 0x31fdf
movl $0xde1, %edi            # imm = 0xDE1
callq 0x27be0
movl $0xde1, %edi            # imm = 0xDE1
callq 0x27880
movl $0xb50, %edi            # imm = 0xB50
callq 0x27200
movss 0x11a782(%rip), %xmm0   # 0x14c12c
movapd %xmm0, %xmm1
movapd %xmm0, %xmm2
callq 0x28380
cmpl %ebp, 0x348(%r14)
movl %ebp, 0xc(%rsp)
jne 0x31cb3
cmpl %ebp, 0x418(%r14)
jne 0x31cb3
cmpl %ebp, 0x4e8(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x34c(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x41c(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x4ec(%r14)
jne 0x31cb3
cmpl %ebp, 0x5b8(%r14)
jne 0x31cb3
cmpl %ebp, 0x688(%r14)
jne 0x31cb3
cmpl %ebp, 0x758(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x5bc(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x68c(%r14)
jne 0x31cb3
movl 0x8(%rsp), %eax
cmpl %eax, 0x75c(%r14)
jne 0x31cb3
xorl %ebx, %ebx
xorl %edi, %edi
callq 0x271a0
testl %ebp, %ebp
movl 0x8(%rsp), %edx
jle 0x31fd0
xorps %xmm0, %xmm0
cvtsi2sdl 0xc(%rsp), %xmm0
movsd %xmm0, 0x40(%rsp)
xorps %xmm0, %xmm0
cvtsi2sd %edx, %xmm0
movsd %xmm0, 0x30(%rsp)
xorpd %xmm1, %xmm1
movsd 0x11a5cc(%rip), %xmm0   # 0x14c078
leaq 0x60(%rsp), %r15
xorpd %xmm2, %xmm2
movsd %xmm2, 0x18(%rsp)
testl %edx, %edx
jle 0x31c92
movsd 0x18(%rsp), %xmm2
divsd 0x40(%rsp), %xmm2
movsd %xmm2, 0x20(%rsp)
xorl %r12d, %r12d
xorpd %xmm2, %xmm2
movq 0xd0(%r14), %rax
movl 0xe0(%r14), %ecx
imull %r12d, %ecx
addl %ebx, %ecx
movslq %ecx, %rcx
movsd (%rax,%rcx,8), %xmm3
ucomisd %xmm3, %xmm1
jae 0x31c82
ucomisd 0x11a60e(%rip), %xmm3   # 0x14c118
jne 0x31b12
jnp 0x31c82
movsd %xmm3, 0x28(%rsp)
movsd %xmm2, 0x10(%rsp)
movl 0x5c0(%r14), %eax
imull %r12d, %eax
addl %ebx, %eax
cltq
movq 0x5b0(%r14), %rcx
movq 0x680(%r14), %rdx
movsd (%rcx,%rax,8), %xmm0
movl 0x690(%r14), %eax
imull %r12d, %eax
addl %ebx, %eax
cltq
movsd (%rdx,%rax,8), %xmm1
movq 0x750(%r14), %rax
movl 0x760(%r14), %ecx
imull %r12d, %ecx
addl %ebx, %ecx
movslq %ecx, %rcx
movsd (%rax,%rcx,8), %xmm2
movq %r15, %rdi
callq 0xd4e72
xorpd %xmm1, %xmm1
movsd 0x60(%rsp), %xmm0
ucomisd %xmm1, %xmm0
jne 0x31baa
jp 0x31baa
movsd 0x68(%rsp), %xmm0
ucomisd %xmm1, %xmm0
jne 0x31baa
jp 0x31baa
movsd 0x70(%rsp), %xmm0
ucomisd %xmm1, %xmm0
jne 0x31baa
jnp 0x31c70
movl 0x350(%r14), %eax
imull %r12d, %eax
addl %ebx, %eax
cltq
movq 0x340(%r14), %rcx
movq 0x410(%r14), %rdx
movsd (%rcx,%rax,8), %xmm0
movl 0x420(%r14), %eax
imull %r12d, %eax
addl %ebx, %eax
cltq
movsd (%rdx,%rax,8), %xmm1
movq 0x4e0(%r14), %rax
movl 0x4f0(%r14), %ecx
imull %r12d, %ecx
addl %ebx, %ecx
movslq %ecx, %rcx
movsd (%rax,%rcx,8), %xmm2
leaq 0x90(%rsp), %rdi
callq 0xd43de
movq %r15, %rdi
movq 0x48(%rsp), %rsi
callq 0xd50fe
mulsd 0x28(%rsp), %xmm0
leaq 0x78(%rsp), %rbp
movq %rbp, %rdi
movq %r15, %rsi
callq 0xd580e
movq %r15, %r13
leaq 0xa8(%rsp), %r15
movq %r15, %rdi
leaq 0x90(%rsp), %rsi
movq %rbp, %rdx
callq 0xd4723
movsd 0x10(%rsp), %xmm1
divsd 0x30(%rsp), %xmm1
movsd 0x20(%rsp), %xmm0
callq 0x28360
movq %r15, %rdi
movq %r13, %r15
callq 0x271c0
xorpd %xmm1, %xmm1
movl 0x8(%rsp), %edx
movsd 0x11a3fc(%rip), %xmm0   # 0x14c078
movsd 0x10(%rsp), %xmm2
addsd %xmm0, %xmm2
incl %r12d
cmpl %r12d, %edx
jne 0x31adc
movsd 0x18(%rsp), %xmm2
addsd %xmm0, %xmm2
movsd %xmm2, 0x18(%rsp)
incl %ebx
cmpl 0xc(%rsp), %ebx
jne 0x31abb
jmp 0x31fd0
leaq 0xa8(%rsp), %r13
movsd 0x11a44d(%rip), %xmm0   # 0x14c110
movq %r13, %rdi
movq %rbx, %rsi
callq 0xd580e
leaq 0x90(%rsp), %rbp
movsd 0x11a39a(%rip), %xmm0   # 0x14c078
movq %rbp, %rdi
movq %r13, %rsi
callq 0xd580e
movsd 0x28(%rsp), %xmm0
callq 0x274e0
leaq 0x60(%rsp), %rbx
movq %rbx, %rdi
movq %rbp, %rsi
callq 0xd580e
leaq 0x78(%rsp), %r13
movq %r13, %rdi
movq %r12, %rsi
movsd 0x11a3f9(%rip), %xmm0   # 0x14c110
callq 0xd580e
leaq 0xa8(%rsp), %rbp
movq %rbp, %rdi
movq %r13, %rsi
movsd 0x11a346(%rip), %xmm0   # 0x14c078
callq 0xd580e
movsd 0x10(%rsp), %xmm0
callq 0x274e0
leaq 0x90(%rsp), %r12
movq %r12, %rdi
movq %rbp, %rsi
callq 0xd580e
leaq 0x78(%rsp), %r13
movq %r13, %rdi
movq 0x48(%rsp), %rsi
movsd 0x11a30e(%rip), %xmm0   # 0x14c078
callq 0xd580e
leaq 0xa8(%rsp), %rbp
movq %rbp, %rdi
movq 0x20(%rsp), %rsi
movq %r13, %rdx
callq 0xd4723
leaq 0xd8(%rsp), %r13
movsd 0x11a279(%rip), %xmm0   # 0x14c010
movq %r13, %rdi
movq %rbx, %rsi
callq 0xd580e
leaq 0xf0(%rsp), %rbx
movq %rbx, %rdi
movq %rbp, %rsi
movq %r13, %rdx
callq 0xd4dff
leaq 0xc0(%rsp), %r13
movq %r13, %rdi
movq %r12, %rsi
movsd 0x11a242(%rip), %xmm0   # 0x14c010
callq 0xd580e
leaq 0x78(%rsp), %rdi
movq %rbx, %rsi
movq %r13, %rdx
callq 0xd4dff
xorl %r15d, %r15d
xorl %edi, %edi
callq 0x271a0
movsd 0x11a283(%rip), %xmm0   # 0x14c078
cmpl $0x0, 0xc(%rsp)
movl 0x8(%rsp), %edx
jle 0x31fd0
cvtsi2sdl 0xc(%rsp), %xmm1
movsd %xmm1, 0x50(%rsp)
xorps %xmm1, %xmm1
cvtsi2sd %edx, %xmm1
movsd %xmm1, 0x40(%rsp)
xorpd %xmm1, %xmm1
leaq 0xd8(%rsp), %rbp
leaq 0x120(%rsp), %r13
xorpd %xmm2, %xmm2
movsd %xmm2, 0x38(%rsp)
testl %edx, %edx
jle 0x31fb2
movsd 0x38(%rsp), %xmm2
divsd 0x50(%rsp), %xmm2
movsd %xmm2, 0x30(%rsp)
xorl %ebx, %ebx
xorpd %xmm2, %xmm2
movq 0xd0(%r14), %rax
movl 0xe0(%r14), %ecx
imull %ebx, %ecx
addl %r15d, %ecx
movslq %ecx, %rcx
movsd (%rax,%rcx,8), %xmm3
ucomisd %xmm3, %xmm1
jae 0x31fa4
ucomisd 0x11a28f(%rip), %xmm3   # 0x14c118
jne 0x31e91
jnp 0x31fa4
movsd %xmm3, 0x18(%rsp)
movq %r14, %r12
movsd %xmm2, 0x28(%rsp)
divsd 0x40(%rsp), %xmm2
movsd %xmm2, 0x10(%rsp)
leaq 0xc0(%rsp), %r14
movq %r14, %rdi
leaq 0x60(%rsp), %rsi
movsd 0x30(%rsp), %xmm0
callq 0xd580e
movq %rbp, %rdi
leaq 0x78(%rsp), %rsi
movq %r14, %rdx
callq 0xd4723
movq %r13, %rdi
leaq 0x90(%rsp), %rsi
movsd 0x10(%rsp), %xmm0
callq 0xd580e
leaq 0xf0(%rsp), %r14
movq %r14, %rdi
movq %rbp, %rsi
movq %r13, %rdx
callq 0xd4723
movq %rbp, %rdi
movq %r14, %rsi
movq 0x20(%rsp), %rdx
callq 0xd463a
movq %rbp, %rdi
movq 0x48(%rsp), %rsi
callq 0xd50fe
xorpd %xmm1, %xmm1
ucomisd %xmm0, %xmm1
jae 0x31f8f
leaq 0x108(%rsp), %r14
movq %r14, %rdi
movq %rbp, %rsi
movsd %xmm0, 0x58(%rsp)
movsd 0x18(%rsp), %xmm0
callq 0xd580e
movq %r13, %rdi
movq %r14, %rsi
movsd 0x58(%rsp), %xmm0
callq 0xd5b58
leaq 0xc0(%rsp), %r14
movq %r14, %rdi
movq 0x20(%rsp), %rsi
movq %r13, %rdx
callq 0xd4723
movsd 0x30(%rsp), %xmm0
movsd 0x10(%rsp), %xmm1
callq 0x28360
movq %r14, %rdi
callq 0x271c0
xorpd %xmm1, %xmm1
movl 0x8(%rsp), %edx
movsd 0x11a0dd(%rip), %xmm0   # 0x14c078
movq %r12, %r14
movsd 0x28(%rsp), %xmm2
addsd %xmm0, %xmm2
incl %ebx
cmpl %ebx, %edx
jne 0x31e5b
movsd 0x38(%rsp), %xmm2
addsd %xmm0, %xmm2
movsd %xmm2, 0x38(%rsp)
incl %r15d
cmpl 0xc(%rsp), %r15d
jne 0x31e3b
callq 0x27cd0
movl $0xde1, %edi            # imm = 0xDE1
callq 0x27200
addq $0x138, %rsp            # imm = 0x138
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq