// File: tomfunkhouser[P]gaps/pkgs/R3Utils/R3SurfelViewer.cpp
// Function: gaps::R3SurfelViewer::CreateColor(unsigned char*, int, gaps::R3Surfel const*, gaps::R3SurfelBlock*, gaps::R3SurfelNode*, gaps::R3SurfelObject*, gaps::R3SurfelLabel*) const
void R3SurfelViewer::
CreateColor(unsigned char *color, int color_scheme,
  const R3Surfel *surfel, R3SurfelBlock *block, R3SurfelNode *node,
  R3SurfelObject *object, R3SurfelLabel *label) const
{
  // Check color scheme
  switch (color_scheme) {    
  case R3_SURFEL_VIEWER_COLOR_BY_PICK_INDEX: {
    int node_index = (node) ? node->TreeIndex() + 1 : 0;
    *color++ = (node_index >> 16) & 0xFF;
    *color++ = (node_index >> 8) & 0xFF;
    *color++ = node_index & 0xFF;
    break; }

  case R3_SURFEL_VIEWER_COLOR_BY_CURRENT_LABEL: {
    if (!label && object) label = object->CurrentLabel();
    const RNRgb& rgb = (label) ? label->Color() : RNwhite_rgb;
    *color++ = 255 * rgb.R();
    *color++ = 255 * rgb.G();
    *color++ = 255 * rgb.B();
    break; }
    
  case R3_SURFEL_VIEWER_COLOR_BY_GROUND_TRUTH_LABEL: {
    R3SurfelLabel *gtlabel = (object) ? object->GroundTruthLabel() : NULL;
    const RNRgb& rgb = (gtlabel) ? gtlabel->Color() : RNwhite_rgb;
    *color++ = 255 * rgb.R();
    *color++ = 255 * rgb.G();
    *color++ = 255 * rgb.B();
    break; }
    
  case R3_SURFEL_VIEWER_COLOR_BY_SCAN: {
    R3SurfelScan *scan = (node) ? node->Scan() : NULL;
    int scan_index = (scan) ? scan->SceneIndex() : 0;
    CreateColor(color, scan_index);
    break; }
    
  case R3_SURFEL_VIEWER_COLOR_BY_OBJECT: {
    int object_index = (object) ? object->SceneIndex() : 0;
    CreateColor(color, object_index);
    break; }

  case R3_SURFEL_VIEWER_COLOR_BY_NODE: {
    int node_index = (node) ? node->TreeIndex() : 0;
    CreateColor(color, node_index);
    break; }
    
  case R3_SURFEL_VIEWER_COLOR_BY_BLOCK: {
    int block_index = (block) ? block->DatabaseIndex() : 0;
    CreateColor(color, block_index);
    break; }
      
  case R3_SURFEL_VIEWER_COLOR_BY_NORMAL:
    if (surfel) {
      *color++ = 128 + 127 * surfel->NX();
      *color++ = 128 + 127 * surfel->NY();
      *color++ = 128 + 127 * surfel->NZ();
    }
    else {
      *color++ = 128;
      *color++ = 128;
      *color++ = 128;
    }
    break;

  case R3_SURFEL_VIEWER_COLOR_BY_Z: {
    double z = 0;
    if (block && surfel) z = block->PositionOrigin().Z() + surfel->Z();
    else if (node) z = node->Centroid().Z();
    else if (object) z = object->Centroid().Z();
    double dz = (z > center_point.Z()) ? z - center_point.Z() : 0;
    double value = 0.5 * sqrt(dz);
    CreateColor(color, value);
    break; }
      
  case R3_SURFEL_VIEWER_COLOR_BY_ELEVATION: {
    double elevation = 1;
    if (surfel) elevation = surfel->Elevation();
    double value = (elevation > 0) ? 0.5 * sqrt(elevation) : 0;
    CreateColor(color, value);
    break; }

  case R3_SURFEL_VIEWER_COLOR_BY_SURFEL_LABEL: {
    int label_identifier = 0;
    if (surfel) label_identifier = surfel->Attribute() & 0xFF;
    else if (label) label_identifier = label->Identifier();
    CreateColor(color, label_identifier);
    break; }

  case R3_SURFEL_VIEWER_COLOR_BY_CONFIDENCE: {
    double confidence = 0.5;
    if (surfel) confidence = ((surfel->Attribute() >> 8) & 0xFF) / 255.0;
    CreateColor(color, confidence);
    break; }

  case R3_SURFEL_VIEWER_COLOR_BY_OBJECT_ATTRIBUTES: {
    RNFlags flags = (object) ? object->Flags() : RNFlags(0);
    CreateColor(color, (int) flags);
    break; }
      
  default:
    if (surfel) {
      *color++ = surfel->R();
      *color++ = surfel->G();
      *color++ = surfel->B();
    }
    else {
      *color++ = 127;
      *color++ = 127;
      *color++ = 127;
    }
    break;
  }
}

// Assembly:
subq $0x168, %rsp            # imm = 0x168
movq 0x178(%rsp), %rax
movq 0x170(%rsp), %rax
movq %rdi, 0x160(%rsp)
movq %rsi, 0x158(%rsp)
movl %edx, 0x154(%rsp)
movq %rcx, 0x148(%rsp)
movq %r8, 0x140(%rsp)
movq %r9, 0x138(%rsp)
movq 0x160(%rsp), %rax
movq %rax, 0x80(%rsp)
movl 0x154(%rsp), %eax
addl $-0x2, %eax
movl %eax, %ecx
movq %rcx, 0x88(%rsp)
subl $0xc, %eax
ja 0x315d5
movq 0x88(%rsp), %rax
leaq 0x21097a(%rip), %rcx    # 0x2415fc
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
cmpq $0x0, 0x138(%rsp)
je 0x30cac
movq 0x138(%rsp), %rdi
callq 0x3d5c0
addl $0x1, %eax
movl %eax, 0x7c(%rsp)
jmp 0x30cb4
xorl %eax, %eax
movl %eax, 0x7c(%rsp)
jmp 0x30cb4
movl 0x7c(%rsp), %eax
movl %eax, 0x134(%rsp)
movl 0x134(%rsp), %eax
sarl $0x10, %eax
andl $0xff, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movl 0x134(%rsp), %eax
sarl $0x8, %eax
andl $0xff, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movl 0x134(%rsp), %eax
andl $0xff, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
jmp 0x316aa
cmpq $0x0, 0x178(%rsp)
jne 0x30d6a
cmpq $0x0, 0x170(%rsp)
je 0x30d6a
movq 0x170(%rsp), %rdi
callq 0x662c0
movq %rax, 0x178(%rsp)
cmpq $0x0, 0x178(%rsp)
je 0x30d89
movq 0x178(%rsp), %rdi
callq 0x3d5d0
movq %rax, 0x70(%rsp)
jmp 0x30d97
leaq 0x6a5d50(%rip), %rax    # 0x6d6ae0
movq %rax, 0x70(%rsp)
jmp 0x30d97
movq 0x70(%rsp), %rax
movq %rax, 0x128(%rsp)
movq 0x128(%rsp), %rdi
callq 0x3d5e0
movsd 0x21074f(%rip), %xmm1   # 0x241508
movsd %xmm1, 0x68(%rsp)
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x128(%rsp), %rdi
callq 0x3d5f0
movsd 0x68(%rsp), %xmm1
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x128(%rsp), %rdi
callq 0x3d600
movsd 0x68(%rsp), %xmm1
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
jmp 0x316aa
cmpq $0x0, 0x170(%rsp)
je 0x30e70
movq 0x170(%rsp), %rdi
callq 0x661d0
movq %rax, 0x60(%rsp)
jmp 0x30e79
xorl %eax, %eax
movq %rax, 0x60(%rsp)
jmp 0x30e79
movq 0x60(%rsp), %rax
movq %rax, 0x120(%rsp)
cmpq $0x0, 0x120(%rsp)
je 0x30ea5
movq 0x120(%rsp), %rdi
callq 0x3d5d0
movq %rax, 0x58(%rsp)
jmp 0x30eb3
leaq 0x6a5c34(%rip), %rax    # 0x6d6ae0
movq %rax, 0x58(%rsp)
jmp 0x30eb3
movq 0x58(%rsp), %rax
movq %rax, 0x118(%rsp)
movq 0x118(%rsp), %rdi
callq 0x3d5e0
movsd 0x210633(%rip), %xmm1   # 0x241508
movsd %xmm1, 0x50(%rsp)
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x118(%rsp), %rdi
callq 0x3d5f0
movsd 0x50(%rsp), %xmm1
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x118(%rsp), %rdi
callq 0x3d600
movsd 0x50(%rsp), %xmm1
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
jmp 0x316aa
cmpq $0x0, 0x138(%rsp)
je 0x30f91
movq 0x138(%rsp), %rdi
movl $0x1, %esi
callq 0x590e0
movq %rax, 0x48(%rsp)
jmp 0x30f9a
xorl %eax, %eax
movq %rax, 0x48(%rsp)
jmp 0x30f9a
movq 0x48(%rsp), %rax
movq %rax, 0x110(%rsp)
cmpq $0x0, 0x110(%rsp)
je 0x30fc5
movq 0x110(%rsp), %rdi
callq 0x3d610
movl %eax, 0x44(%rsp)
jmp 0x30fcd
xorl %eax, %eax
movl %eax, 0x44(%rsp)
jmp 0x30fcd
movq 0x80(%rsp), %rdi
movl 0x44(%rsp), %eax
movl %eax, 0x10c(%rsp)
movq 0x158(%rsp), %rsi
movl 0x10c(%rsp), %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
cmpq $0x0, 0x170(%rsp)
je 0x3101b
movq 0x170(%rsp), %rdi
callq 0x3d620
movl %eax, 0x40(%rsp)
jmp 0x31023
xorl %eax, %eax
movl %eax, 0x40(%rsp)
jmp 0x31023
movq 0x80(%rsp), %rdi
movl 0x40(%rsp), %eax
movl %eax, 0x108(%rsp)
movq 0x158(%rsp), %rsi
movl 0x108(%rsp), %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
cmpq $0x0, 0x138(%rsp)
je 0x31071
movq 0x138(%rsp), %rdi
callq 0x3d5c0
movl %eax, 0x3c(%rsp)
jmp 0x31079
xorl %eax, %eax
movl %eax, 0x3c(%rsp)
jmp 0x31079
movq 0x80(%rsp), %rdi
movl 0x3c(%rsp), %eax
movl %eax, 0x104(%rsp)
movq 0x158(%rsp), %rsi
movl 0x104(%rsp), %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
cmpq $0x0, 0x140(%rsp)
je 0x310c7
movq 0x140(%rsp), %rdi
callq 0x3d630
movl %eax, 0x38(%rsp)
jmp 0x310cf
xorl %eax, %eax
movl %eax, 0x38(%rsp)
jmp 0x310cf
movq 0x80(%rsp), %rdi
movl 0x38(%rsp), %eax
movl %eax, 0x100(%rsp)
movq 0x158(%rsp), %rsi
movl 0x100(%rsp), %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
cmpq $0x0, 0x148(%rsp)
je 0x311de
movq 0x148(%rsp), %rdi
callq 0x3d650
movss 0x2108fd(%rip), %xmm1   # 0x241a20
movss %xmm1, 0x30(%rsp)
mulss %xmm1, %xmm0
movss 0x2108ef(%rip), %xmm1   # 0x241a24
movss %xmm1, 0x34(%rsp)
addss %xmm1, %xmm0
cvttss2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x148(%rsp), %rdi
callq 0x3d670
movss 0x30(%rsp), %xmm2
movss 0x34(%rsp), %xmm1
mulss %xmm2, %xmm0
addss %xmm1, %xmm0
cvttss2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
incq %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x148(%rsp), %rdi
callq 0x3d690
movss 0x30(%rsp), %xmm2
movss 0x34(%rsp), %xmm1
mulss %xmm2, %xmm0
addss %xmm1, %xmm0
cvttss2si %xmm0, %eax
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
jmp 0x3122c
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $-0x80, (%rax)
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $-0x80, (%rax)
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $-0x80, (%rax)
jmp 0x316aa
xorps %xmm0, %xmm0
movsd %xmm0, 0xf8(%rsp)
cmpq $0x0, 0x140(%rsp)
je 0x31297
cmpq $0x0, 0x148(%rsp)
je 0x31297
movq 0x140(%rsp), %rdi
callq 0x3d6b0
movq %rax, %rdi
callq 0x2ee90
movsd %xmm0, 0x28(%rsp)
movq 0x148(%rsp), %rdi
callq 0x3d6c0
movaps %xmm0, %xmm1
movsd 0x28(%rsp), %xmm0
cvtss2sd %xmm1, %xmm1
addsd %xmm1, %xmm0
movsd %xmm0, 0xf8(%rsp)
jmp 0x31309
cmpq $0x0, 0x138(%rsp)
je 0x312cf
movq 0x138(%rsp), %rsi
leaq 0xe0(%rsp), %rdi
callq 0x3d6d0
leaq 0xe0(%rsp), %rdi
callq 0x2ee90
movsd %xmm0, 0xf8(%rsp)
jmp 0x31307
cmpq $0x0, 0x170(%rsp)
je 0x31305
movq 0x170(%rsp), %rsi
leaq 0xc8(%rsp), %rdi
callq 0x3d710
leaq 0xc8(%rsp), %rdi
callq 0x2ee90
movsd %xmm0, 0xf8(%rsp)
jmp 0x31307
jmp 0x31309
movq 0x80(%rsp), %rdi
movsd 0xf8(%rsp), %xmm0
movsd %xmm0, 0x20(%rsp)
addq $0x2b0, %rdi            # imm = 0x2B0
callq 0x2ee90
movaps %xmm0, %xmm1
movsd 0x20(%rsp), %xmm0
ucomisd %xmm1, %xmm0
jbe 0x31373
movq 0x80(%rsp), %rdi
movsd 0xf8(%rsp), %xmm0
movsd %xmm0, 0x10(%rsp)
addq $0x2b0, %rdi            # imm = 0x2B0
callq 0x2ee90
movaps %xmm0, %xmm1
movsd 0x10(%rsp), %xmm0
subsd %xmm1, %xmm0
movsd %xmm0, 0x18(%rsp)
jmp 0x3137e
xorps %xmm0, %xmm0
movsd %xmm0, 0x18(%rsp)
jmp 0x3137e
movsd 0x18(%rsp), %xmm0
movsd %xmm0, 0xc0(%rsp)
movsd 0xc0(%rsp), %xmm0
callq 0x287c0
movq 0x80(%rsp), %rdi
movaps %xmm0, %xmm1
movsd 0x20fc8a(%rip), %xmm0   # 0x241038
mulsd %xmm1, %xmm0
movsd %xmm0, 0xb8(%rsp)
movq 0x158(%rsp), %rsi
movsd 0xb8(%rsp), %xmm0
movq (%rdi), %rax
callq *0x208(%rax)
jmp 0x316aa
movsd 0x20fc2e(%rip), %xmm0   # 0x241010
movsd %xmm0, 0xb0(%rsp)
cmpq $0x0, 0x148(%rsp)
je 0x31410
movq 0x148(%rsp), %rdi
callq 0x3d750
cvtss2sd %xmm0, %xmm0
movsd %xmm0, 0xb0(%rsp)
movsd 0xb0(%rsp), %xmm0
xorps %xmm1, %xmm1
ucomisd %xmm1, %xmm0
jbe 0x31447
movsd 0xb0(%rsp), %xmm0
callq 0x287c0
movaps %xmm0, %xmm1
movsd 0x20fbfd(%rip), %xmm0   # 0x241038
mulsd %xmm1, %xmm0
movsd %xmm0, 0x8(%rsp)
jmp 0x31452
xorps %xmm0, %xmm0
movsd %xmm0, 0x8(%rsp)
jmp 0x31452
movq 0x80(%rsp), %rdi
movsd 0x8(%rsp), %xmm0
movsd %xmm0, 0xa8(%rsp)
movq 0x158(%rsp), %rsi
movsd 0xa8(%rsp), %xmm0
movq (%rdi), %rax
callq *0x208(%rax)
jmp 0x316aa
movl $0x0, 0xa4(%rsp)
cmpq $0x0, 0x148(%rsp)
je 0x314b9
movq 0x148(%rsp), %rdi
callq 0x3d780
andl $0xff, %eax
movl %eax, 0xa4(%rsp)
jmp 0x314da
cmpq $0x0, 0x178(%rsp)
je 0x314d8
movq 0x178(%rsp), %rdi
callq 0x68700
movl %eax, 0xa4(%rsp)
jmp 0x314da
movq 0x80(%rsp), %rdi
movq 0x158(%rsp), %rsi
movl 0xa4(%rsp), %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
movsd 0x20fb31(%rip), %xmm0   # 0x241038
movsd %xmm0, 0x98(%rsp)
cmpq $0x0, 0x148(%rsp)
je 0x31546
movq 0x148(%rsp), %rdi
callq 0x3d780
movb %ah, %al
movzbl %al, %eax
cvtsi2sd %eax, %xmm0
movsd 0x20ffcf(%rip), %xmm1   # 0x241508
divsd %xmm1, %xmm0
movsd %xmm0, 0x98(%rsp)
movq 0x80(%rsp), %rdi
movq 0x158(%rsp), %rsi
movsd 0x98(%rsp), %xmm0
movq (%rdi), %rax
callq *0x208(%rax)
jmp 0x316aa
cmpq $0x0, 0x170(%rsp)
je 0x3158f
movq 0x170(%rsp), %rdi
callq 0x3d310
movq %rax, 0x90(%rsp)
jmp 0x315a0
leaq 0x90(%rsp), %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x2f310
movq 0x158(%rsp), %rax
movq %rax, (%rsp)
leaq 0x90(%rsp), %rdi
callq 0x3d4b0
movq 0x80(%rsp), %rdi
movq (%rsp), %rsi
movl %eax, %edx
movq (%rdi), %rax
callq *0x200(%rax)
jmp 0x316aa
cmpq $0x0, 0x148(%rsp)
je 0x3165a
movq 0x148(%rsp), %rdi
callq 0x3d790
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x148(%rsp), %rdi
callq 0x3d7a0
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
movq 0x148(%rsp), %rdi
callq 0x3d7b0
movb %al, %cl
movq 0x158(%rsp), %rax
movq %rax, %rdx
addq $0x1, %rdx
movq %rdx, 0x158(%rsp)
movb %cl, (%rax)
jmp 0x316a8
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $0x7f, (%rax)
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $0x7f, (%rax)
movq 0x158(%rsp), %rax
movq %rax, %rcx
addq $0x1, %rcx
movq %rcx, 0x158(%rsp)
movb $0x7f, (%rax)
jmp 0x316aa
addq $0x168, %rsp            # imm = 0x168
retq
nopw %cs:(%rax,%rax)