// File: iannisdezwart[P]forcefield-visualiser/./colour.hpp
// Function: angle_to_rgb(double)
png::rgb_pixel angle_to_rgb(double angle)
{
	// We convert the angle such that it becomes a number between 0 and 1.
	// Here, 0 means an angle of 0 radians, and 1 means an angle of 2 PI radians.

	double angle_ratio = (angle / M_PI) / 2; // [-0.5, 0.5]
	if (angle_ratio < 0) angle_ratio += 1; // [0, 1]

	// Now we multiply this `angle_ratio` by 6 and cast it to an int.
	// This will initialise `int angle_sector` to an integer between [0, 6].
	// The edge case `angle_sector == 6` will be handled by the switch below.

	int angle_sector = angle_ratio * 6; // [0, 6] (int)

	// We calculate how far the angle is from the `angle_sector` base.
	// We store this value into `int remaining_value` and multiply it by 255
	// to make it a pixel value.

	int remaining_value = ((angle_ratio * 6) - (double) angle_sector) * 255.0;

	// The switch will return the correct png::rgb_pixel

	switch (angle_sector) {
		case 0:
		default: // If the `angle_sector` is 6 (equivalent to 6 mod 6 == 0)
			return png::rgb_pixel(255, remaining_value, 0);
		case 1:
			return png::rgb_pixel(255 - remaining_value, 255, 0);
		case 2:
			return png::rgb_pixel(0, 255, remaining_value);
		case 3:
			return png::rgb_pixel(0, 255 - remaining_value, 255);
		case 4:
			return png::rgb_pixel(remaining_value, 0, 255);
		case 5:
			return png::rgb_pixel(255, 0, 255 - remaining_value);
	}
}

// Assembly:
subq $0x38, %rsp
movsd %xmm0, 0x28(%rsp)
movsd 0x28(%rsp), %xmm0
movsd 0xb7c8(%rip), %xmm1     # 0xf010
divsd %xmm1, %xmm0
movsd 0xb7b4(%rip), %xmm1     # 0xf008
divsd %xmm1, %xmm0
movsd %xmm0, 0x20(%rsp)
xorps %xmm0, %xmm0
ucomisd 0x20(%rsp), %xmm0
jbe 0x387d
movsd 0xb7a7(%rip), %xmm0     # 0xf018
addsd 0x20(%rsp), %xmm0
movsd %xmm0, 0x20(%rsp)
movsd 0x20(%rsp), %xmm0
movsd 0xb795(%rip), %xmm2     # 0xf020
mulsd %xmm2, %xmm0
cvttsd2si %xmm0, %eax
movl %eax, 0x1c(%rsp)
movsd 0x20(%rsp), %xmm0
cvtsi2sdl 0x1c(%rsp), %xmm1
mulsd %xmm2, %xmm0
subsd %xmm1, %xmm0
movsd 0xb775(%rip), %xmm1     # 0xf028
mulsd %xmm1, %xmm0
cvttsd2si %xmm0, %eax
movl %eax, 0x18(%rsp)
movl 0x1c(%rsp), %eax
movq %rax, 0x8(%rsp)
subq $0x5, %rax
ja 0x38e5
movq 0x8(%rsp), %rax
leaq 0xb7b6(%rip), %rcx      # 0xf090
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
jmp 0x38e5
movl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
movl $0xff, %esi
xorl %ecx, %ecx
movzbl %al, %edx
callq 0x5bd0
jmp 0x3991
movl $0xff, %eax
subl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
movl $0xff, %edx
xorl %ecx, %ecx
movzbl %al, %esi
callq 0x5bd0
jmp 0x3991
movl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
xorl %esi, %esi
movl $0xff, %edx
movzbl %al, %ecx
callq 0x5bd0
jmp 0x3991
movl $0xff, %eax
subl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
xorl %esi, %esi
movl $0xff, %ecx
movzbl %al, %edx
callq 0x5bd0
jmp 0x3991
movl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
xorl %edx, %edx
movl $0xff, %ecx
movzbl %al, %esi
callq 0x5bd0
jmp 0x3991
movl $0xff, %eax
subl 0x18(%rsp), %eax
leaq 0x35(%rsp), %rdi
movl $0xff, %esi
xorl %edx, %edx
movzbl %al, %ecx
callq 0x5bd0
movb 0x37(%rsp), %al
movb %al, 0x16(%rsp)
movw 0x35(%rsp), %ax
movw %ax, 0x14(%rsp)
movzbl 0x16(%rsp), %ecx
shll $0x10, %ecx
movzwl 0x14(%rsp), %eax
orl %ecx, %eax
addq $0x38, %rsp
retq
nopw (%rax,%rax)