Exemple #1
0
        public static ushort Float32ToUInt16(float value)
        {
            var f32infty = new Float32IntegerUnion {
                I = 255 << 23
            };
            var f16infty = new Float32IntegerUnion {
                I = 31 << 23
            };
            var magic = new Float32IntegerUnion {
                I = 15 << 23
            };
            var inval = new Float32IntegerUnion {
                F = value
            };
            var sign_mask  = 0x80000000;
            var round_mask = ~0xFFFU;

            var sign = inval.I & sign_mask;

            inval.I ^= sign;

            ushort @out;

            if (inval.I >= f32infty.I)                           // Inf or NaN (all exponent bits set)
            {
                @out = (ushort)(inval.I > f32infty.I ? 0x7FFFu : 0x7C00u);
            }
            else
            {
                inval.I &= round_mask;
                inval.F *= magic.F;
                inval.I -= round_mask;
                if (inval.I > f16infty.I)
                {
                    inval.I = f16infty.I;                        // Clamp to signed infinity if overflowed
                }
                @out = (ushort)((inval.I >> 13) & 0xFFFF);       // Take the bits!
            }
            return((ushort)(@out | (sign >> 16) & 0xFFFF));
        }
Exemple #2
0
        public static float UInt16ToFloat32(ushort value)
        {
            var magic = new Float32IntegerUnion {
                I = (254 - 15) << 23
            };
            var was_inf_nan = new Float32IntegerUnion {
                I = (127 + 16) << 23
            };

            var union = new Float32IntegerUnion {
                I = ((uint)value & 0x7FFF) << 13
            };                                                                        // exponent/mantissa bits

            union.F *= magic.F;                                                       // exponent adjust
            if (union.F >= was_inf_nan.F)                                             // make sure Inf/NaN survive
            {
                union.I |= 255 << 23;
            }
            union.I |= ((uint)value & 0x8000) << 16;                                  // sign bit

            return(union.F);
        }