half_float.h
1 /*
2 ** ClanLib SDK
3 ** Copyright (c) 1997-2015 The ClanLib Team
4 **
5 ** This software is provided 'as-is', without any express or implied
6 ** warranty. In no event will the authors be held liable for any damages
7 ** arising from the use of this software.
8 **
9 ** Permission is granted to anyone to use this software for any purpose,
10 ** including commercial applications, and to alter it and redistribute it
11 ** freely, subject to the following restrictions:
12 **
13 ** 1. The origin of this software must not be misrepresented; you must not
14 ** claim that you wrote the original software. If you use this software
15 ** in a product, an acknowledgment in the product documentation would be
16 ** appreciated but is not required.
17 ** 2. Altered source versions must be plainly marked as such, and must not be
18 ** misrepresented as being the original software.
19 ** 3. This notice may not be removed or altered from any source distribution.
20 **
21 ** Note: Some of the libraries ClanLib may link to may have additional
22 ** requirements or restrictions.
23 **
24 ** File Author(s):
25 **
26 ** Magnus Norddahl
27 ** Mark Page
28 ** Harry Storbacka
29 */
30
31
32 #pragma once
33
34 namespace clan
35 {
38
39 class HalfFloat
40 {
41 public:
42 HalfFloat() : value(0)
43 {
44 }
45
46 HalfFloat(const HalfFloat &other) : value(other.value)
47 {
48 }
49
50 HalfFloat(float v) : value(float_to_half(v))
51 {
52 }
53
54 HalfFloat &operator =(const HalfFloat &other)
55 {
56 value = other.value;
57 return *this;
58 }
59
60 HalfFloat &operator =(const float v)
61 {
62 return from_float(v);
63 }
64
65 operator float() const
66 {
67 return to_float();
68 }
69
70 float to_float() const
71 {
72 return half_to_float(value);
73 }
74
75 HalfFloat &from_float(float v)
76 {
77 value = float_to_half(v);
78 return *this;
79 }
80
82 static float half_to_float_simple(unsigned short hf)
83 {
84 unsigned int float_value = ((hf & 0x8000) << 16) | (((hf & 0x7c00) + 0x1C000) << 13) | ((hf & 0x03FF) << 13);
85 void *ptr = static_cast<void*>(&float_value);
86 return *static_cast<float*>(ptr);
87 }
88
90 static unsigned short float_to_half_simple(float float_value)
91 {
92 void *ptr = static_cast<void*>(&float_value);
93 unsigned int f = *static_cast<unsigned int*>(ptr);
94 return ((f >> 16) & 0x8000) | ((((f & 0x7f800000) - 0x38000000) >> 13) & 0x7c00) | ((f >> 13) & 0x03ff);
95 }
96
97 static float half_to_float(unsigned short hf)
98 {
99 unsigned int float_value = mantissa_table[offset_table[hf >> 10] + (hf & 0x3ff)] + exponent_table[hf >> 10];
100 void *ptr = static_cast<void*>(&float_value);
101 return *static_cast<float*>(ptr);
102 }
103
104 static unsigned short float_to_half(float float_value)
105 {
106 void *ptr = static_cast<void*>(&float_value);
107 unsigned int f = *static_cast<unsigned int*>(ptr);
108 return base_table[(f >> 23) & 0x1ff] + ((f & 0x007fffff) >> shift_table[(f >> 23) & 0x1ff]);
109 }
110
111 private:
112 unsigned short value;
113
114 static unsigned int mantissa_table[2048];
115 static unsigned int exponent_table[64];
116 static unsigned short offset_table[64];
117
118 static unsigned short base_table[512];
119 static unsigned char shift_table[512];
120 };
121
122 }
123
clan::HalfFloat::operator=
HalfFloat & operator=(const HalfFloat &other)
Definition: half_float.h:54
clan::HalfFloat::HalfFloat
HalfFloat()
Definition: half_float.h:42
clan
Definition: clanapp.h:35
clan::HalfFloat::HalfFloat
HalfFloat(const HalfFloat &other)
Definition: half_float.h:46
clan::HalfFloat::float_to_half_simple
static unsigned short float_to_half_simple(float float_value)
Only works for 'normal' half-float values.
Definition: half_float.h:90
clan::HalfFloat::HalfFloat
HalfFloat(float v)
Definition: half_float.h:50
clan::Key::v
clan::Key::f
clan::HalfFloat::half_to_float
static float half_to_float(unsigned short hf)
Definition: half_float.h:97
clan::HalfFloat::float_to_half
static unsigned short float_to_half(float float_value)
Definition: half_float.h:104
clan::HalfFloat::to_float
float to_float() const
Definition: half_float.h:70
clan::HalfFloat::from_float
HalfFloat & from_float(float v)
Definition: half_float.h:75
clan::HalfFloat
Definition: half_float.h:39
clan::HalfFloat::half_to_float_simple
static float half_to_float_simple(unsigned short hf)
Only works for 'normal' half-float values.
Definition: half_float.h:82