comp.lang.ada
 help / color / mirror / Atom feed
From: "Robert I. Eachus" <rieachus@comcast.net>
Subject: Re: Color components and fixed point numbers
Date: Mon, 01 Mar 2004 11:24:48 -0500
Date: 2004-03-01T11:24:48-05:00	[thread overview]
Message-ID: <uZ6dnZ7RmvRM_t7dRVn-uA@comcast.com> (raw)
In-Reply-To: <fc19748c.0403010349.123e946a@posting.google.com>

Pat wrote:

> Hi,
> 
> I would like to declare two records representing a RGB Color with two
> different percisions. The Small one with color components from 0..255
> and the Wide one with components from 0..65535. Could I use fixed
> point numbers to hide the different precision: e.g.
> 
> type Small_Component is delta 1/255 range 0.0 .. 1.0
> type Wide_Component is delta 1/65535 range 0.0 .. 1.0
> 
> type Small_RGB is record
>   r,g,b:Small_Component
> end record
> 
> type Wide_RGB is record
>   r,g,b:Wide_Component
> end record
> 
> Then later I could use something like this to convert between the
> different precisions:
> 
> w : Wide_RGB
> s : Small_RGB
> 
> 
> w.r = Wide_Component(s.r);
> 
> I tried to implement this but suprisingly Wide_Component(
> Small_Component(1.0)) < 1.0 ? Does somebody know a workaround?

No workaround is required!  But I will get to that. First fix your type 
declarations:

  type Small_Component is delta 1.0/255 range 0.0 .. 1.0;
  type Wide_Component is delta 1.0/65535 range 0.0 .. 1.0;

This may just be a problem of transcription, because I would expect a 
compiler to at the least give a warning for such a declaration. Besides, 
you also omitted the semicolons.

Second, you got the numbers wrong, or you want something that many 
compilers would not support as a value for 'Small, even with a rep 
clause.  You should use:

  type Small_Component is delta 1.0/256 range 0.0 .. 1.0;
  type Wide_Component is delta 1.0/65536 range 0.0 .. 1.0;

Notice that for these types, a compiler is not required to represent 
255.0/256 and 256.0/256 differently.  In other words, a compiler is 
allowed to choose a representation with only 256 values, not 257.  You 
can control this, but usually it is what you want.  In fact, I would 
expect that you will force this representation:

for Small_Component'Size use 8;
for Wide_Component'Size use 16;

Having done all that, you will notice that the brightest colors you can 
specify are different.  For example, the brightest whites are: 
16#FFFFFF# for Small_RGB, and 16#FFFFFFFFFFFF# for Wide_RGB.  Since that 
is how the hardware works, that should be what you expect.  So 
Small_RGB'(1.0,1.0,1.0) and Wide_RGB'(1.0,1.0,1.0) are different colors. 
  Or better stated: Small_RGB(255.0/256, 255.0/256. 255.0/256) is not 
equal to Wide_RGB(65535.0/65536, 65535.0/65536, 65535.0/65536), and you 
should not expect them to be equal.

Can you force an implementation to make the two brightest whites equal? 
  It is not too difficult.  Most compilers will give the expected result 
for:

   type Small_Component is delta 1.0/256 range 1.0/256 .. 1.0;
   type Wide_Component is delta 1.0/65536 range 1.0/65536 .. 1.0;

Without any rep clauses, if that is really what you want.  I could have 
told you this straight off.  But you really need to do the thinking 
above to be sure you are doing the right thing, for whatever the right 
value of right is for you.

--
                                           Robert I. Eachus

"The only thing necessary for the triumph of evil is for good men to do 
nothing." --Edmund Burke




  reply	other threads:[~2004-03-01 16:24 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2004-03-01 11:49 Color components and fixed point numbers Pat
2004-03-01 16:24 ` Robert I. Eachus [this message]
2004-03-02 10:58   ` Pat
2004-03-02 16:39     ` Robert I. Eachus
2004-03-02 22:23     ` tmoran
2004-03-04 13:31       ` Pat
replies disabled

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox