Hi all,
consider the following example (print it):
"Example 1"
f := Form extent: 1 asPoint depth: 1.
f colorAt: 0 @ 0 put: Color red.
g := f asFormOfDepth: 2.
g colorAt: 0 @ 0
Expected output: Color red. Actual output: Color black!
Other examples:
"Example 2"
f := Form extent: 1 asPoint depth: 1.
f colorAt: 0 @ 0 put: Color red.
g := f asFormOfDepth: 32.
g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)"
"Example 3"
f := Form extent: 1 asPoint depth: 16.
f colorAt: 0 @ 0 put: Color red.
g := f asFormOfDepth: 32.
g colorAt: 0 @ 0 "> (Color r: 0.973 g: 0.0 b: 0.0)"
I am not familiar with color depths, but afaik Color red could be stored exactly using only 1 bit? Do I misunderstand the concept or is this really a bad output?
(I came across to this when performing #collectColors: on an 8 bit ColorForm loaded from disk, which did not work as expected.)
Christoph

Hi Christoph,
> On 09.09.2019, at 13:25, Thiede, Christoph <[hidden email]> wrote: > > Hi all, > > consider the following example (print it): > > "Example 1" > f := Form extent: 1 asPoint depth: 1. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 2. > g colorAt: 0 @ 0 > > Expected output: Color red. > Actual output: Color black! No, Forms of depth 1 are black and white, and of depth2 are gray. > > Other examples: > > "Example 2" > f := Form extent: 1 asPoint depth: 1. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 32. > g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)" yes, because you go from black/white to 32bit. I would have expected r0g0b0, but there might some rounding go on. > > "Example 3" > f := Form extent: 1 asPoint depth: 16. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 32. > g colorAt: 0 @ 0 "> (Color r: 0.973 g: 0.0 b: 0.0)" Something's wonky here! If we do (((Form extent: 1 asPoint depth: 16) colorAt: 0 @ 0 put: Color red) asFormOfDepth: 32) pixelValueAt: 0@0 we get 4294443008 (aka 0xFFF80000) which is a 32bit value. But the meaning is 11111111 11111000 00000000 00000000 ^ alpha ^ r ^ g ^ b which means that the r component is not "upscaled" during the #asFormOfDepth: process o.O (see PS) > > I am not familiar with color depths, but afaik Color red could be stored exactly using only 1 bit? Do I misunderstand the concept or is this really a bad output? No, the first bit depth to support red is 4 bit. Have a look at Color class>>colorFromPixelValue: p depth: d BTW: You can use a ColorForm to work with your own palette, so that you can have for example a 1bit form with 1=yellow & 0=red… Best regards Tobias > > (I came across to this when performing #collectColors: on an 8 bit ColorForm loaded from disk, which did not work as expected.) > > Best, > Christoph PS: PS: Color red is r:1.0 g:0.0 b:0.0 but stored in a different fashion: Color comment: " Think of Color's instance variables as: r amount of red, a Float between 0.0 and 1.0. g amount of green, a Float between 0.0 and 1.0. b amount of blue, a Float between 0.0 and 1.0. (But, in fact, the three are encoded as values from 0 to 1023 and combined in a single integer, rgb. The user does not need to know this.) " that means "Color red" is stored as 0x3FF00000 or, 1111111111 0000000000 0000000000 ^ red ^ green ^ blue that makes 10 bit per component. However, in the 16 bit form we have only 5 bit per component, so, f := Form extent: 1 asPoint depth: 16. f colorAt: 0 @ 0 put: Color red. f pixelValueAt: 0@0. yields 0x7C00 aka 11111 00000 00000 ^ r ^ g ^ b 
Hi Tobias,
oops, I mistook the depth with the number of bits per channel. Sorry and many thanks for your explanations!
How would one fix the upscaling issue? Form>>#colormapIfNeededFor: returns nil in example 3, the comment in Color>>#colorMapIfNeededFrom:to: states this task is delegated to BitBlt. Is this comment wrong or is the defect in the primitive called that is in BitBlt>>#copyBits?
Best, Christoph Von: Squeakdev <[hidden email]> im Auftrag von Tobias Pape <[hidden email]>
Gesendet: Montag, 9. September 2019 14:56 Uhr An: The generalpurpose Squeak developers list Betreff: Re: [squeakdev] Bug in Form>>#asFormOfDepth:? Hi Christoph,
> On 09.09.2019, at 13:25, Thiede, Christoph <[hidden email]> wrote: > > Hi all, > > consider the following example (print it): > > "Example 1" > f := Form extent: 1 asPoint depth: 1. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 2. > g colorAt: 0 @ 0 > > Expected output: Color red. > Actual output: Color black! No, Forms of depth 1 are black and white, and of depth2 are gray. > > Other examples: > > "Example 2" > f := Form extent: 1 asPoint depth: 1. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 32. > g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)" yes, because you go from black/white to 32bit. I would have expected r0g0b0, but there might some rounding go on. > > "Example 3" > f := Form extent: 1 asPoint depth: 16. > f colorAt: 0 @ 0 put: Color red. > g := f asFormOfDepth: 32. > g colorAt: 0 @ 0 "> (Color r: 0.973 g: 0.0 b: 0.0)" Something's wonky here! If we do (((Form extent: 1 asPoint depth: 16) colorAt: 0 @ 0 put: Color red) asFormOfDepth: 32) pixelValueAt: 0@0 we get 4294443008 (aka 0xFFF80000) which is a 32bit value. But the meaning is 11111111 11111000 00000000 00000000 ^ alpha ^ r ^ g ^ b which means that the r component is not "upscaled" during the #asFormOfDepth: process o.O (see PS) > > I am not familiar with color depths, but afaik Color red could be stored exactly using only 1 bit? Do I misunderstand the concept or is this really a bad output? No, the first bit depth to support red is 4 bit. Have a look at Color class>>colorFromPixelValue: p depth: d BTW: You can use a ColorForm to work with your own palette, so that you can have for example a 1bit form with 1=yellow & 0=red… Best regards Tobias > > (I came across to this when performing #collectColors: on an 8 bit ColorForm loaded from disk, which did not work as expected.) > > Best, > Christoph PS: PS: Color red is r:1.0 g:0.0 b:0.0 but stored in a different fashion: Color comment: " Think of Color's instance variables as: r amount of red, a Float between 0.0 and 1.0. g amount of green, a Float between 0.0 and 1.0. b amount of blue, a Float between 0.0 and 1.0. (But, in fact, the three are encoded as values from 0 to 1023 and combined in a single integer, rgb. The user does not need to know this.) " that means "Color red" is stored as 0x3FF00000 or, 1111111111 0000000000 0000000000 ^ red ^ green ^ blue that makes 10 bit per component. However, in the 16 bit form we have only 5 bit per component, so, f := Form extent: 1 asPoint depth: 16. f colorAt: 0 @ 0 put: Color red. f pixelValueAt: 0@0. yields 0x7C00 aka 11111 00000 00000 ^ r ^ g ^ b 
> On 09.09.2019, at 15:53, Thiede, Christoph <[hidden email]> wrote: > > Hi Tobias, > > oops, I mistook the depth with the number of bits per channel. Sorry and many thanks for your explanations! > > How would one fix the upscaling issue? Form>>#colormapIfNeededFor: returns nil in example 3, the comment in Color>>#colorMapIfNeededFrom:to: states this task is delegated to BitBlt. Is this comment wrong or is the defect in the primitive called that is in BitBlt>>#copyBits? > No, that part is only for crossconversion of Forms and ColorForms t > Best, > Christoph > > Von: Squeakdev <[hidden email]> im Auftrag von Tobias Pape <[hidden email]> > Gesendet: Montag, 9. September 2019 14:56 Uhr > An: The generalpurpose Squeak developers list > Betreff: Re: [squeakdev] Bug in Form>>#asFormOfDepth:? > > Hi Christoph, > > > On 09.09.2019, at 13:25, Thiede, Christoph <[hidden email]> wrote: > > > > Hi all, > > > > consider the following example (print it): > > > > "Example 1" > > f := Form extent: 1 asPoint depth: 1. > > f colorAt: 0 @ 0 put: Color red. > > g := f asFormOfDepth: 2. > > g colorAt: 0 @ 0 > > > > Expected output: Color red. > > Actual output: Color black! > > No, Forms of depth 1 are black and white, and of depth2 are gray. > > > > > Other examples: > > > > "Example 2" > > f := Form extent: 1 asPoint depth: 1. > > f colorAt: 0 @ 0 put: Color red. > > g := f asFormOfDepth: 32. > > g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)" > > yes, because you go from black/white to 32bit. I would have expected r0g0b0, but there might some rounding go on. > > > > > "Example 3" > > f := Form extent: 1 asPoint depth: 16. > > f colorAt: 0 @ 0 put: Color red. > > g := f asFormOfDepth: 32. > > g colorAt: 0 @ 0 "> (Color r: 0.973 g: 0.0 b: 0.0)" > > > > Something's wonky here! > If we do > > (((Form extent: 1 asPoint depth: 16) > colorAt: 0 @ 0 put: Color red) > asFormOfDepth: 32) > pixelValueAt: 0@0 > > we get > 4294443008 (aka 0xFFF80000) which is a 32bit value. > But the meaning is > > 11111111 11111000 00000000 00000000 > ^ alpha ^ r ^ g ^ b > > which means that the r component is not "upscaled" during the #asFormOfDepth: process o.O (see PS) > > > > > > > > I am not familiar with color depths, but afaik Color red could be stored exactly using only 1 bit? Do I misunderstand the concept or is this really a bad output? > > No, the first bit depth to support red is 4 bit. > > Have a look at Color class>>colorFromPixelValue: p depth: d > > BTW: You can use a ColorForm to work with your own palette, so that you can have for example a 1bit form with 1=yellow & 0=red… > > > Best regards > Tobias > > > > > (I came across to this when performing #collectColors: on an 8 bit ColorForm loaded from disk, which did not work as expected.) > > > > Best, > > Christoph > > PS: PS: > Color red is r:1.0 g:0.0 b:0.0 but stored in a different fashion: > > Color comment: > " > Think of Color's instance variables as: > r amount of red, a Float between 0.0 and 1.0. > g amount of green, a Float between 0.0 and 1.0. > b amount of blue, a Float between 0.0 and 1.0. > (But, in fact, the three are encoded as values from 0 to 1023 and combined in a single integer, rgb. The user does not need to know this.) > " > that means "Color red" is stored as 0x3FF00000 or, > > 1111111111 0000000000 0000000000 > ^ red ^ green ^ blue > > that makes 10 bit per component. > > However, in the 16 bit form we have only 5 bit per component, so, > > f := Form extent: 1 asPoint depth: 16. > f colorAt: 0 @ 0 put: Color red. > f pixelValueAt: 0@0. > > yields 0x7C00 aka > > 11111 00000 00000 > ^ r ^ g ^ b 
In reply to this post by Tobias Pape
fwiw, Color r: 0.0 g: 0.0 b: 0.004 is squeak's way of representing black in 16 bits
so 0 can mean transparent
On 9/9/19 8:56 AM, Tobias Pape wrote:
Other examples: "Example 2" f := Form extent: 1 asPoint depth: 1. f colorAt: 0 @ 0 put: Color red. g := f asFormOfDepth: 32. g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)"yes, because you go from black/white to 32bit. I would have expected r0g0b0, but there might some rounding go on. 
> On 09.09.2019, at 17:03, Bob Arning <[hidden email]> wrote: > > fwiw, Color r: 0.0 g: 0.0 b: 0.004 is squeak's way of representing black in 16 bits so 0 can mean transparent ah; i remember. thanks bob! > > On 9/9/19 8:56 AM, Tobias Pape wrote: >>> Other examples: >>> >>> "Example 2" >>> f := Form extent: 1 asPoint depth: 1. >>> f colorAt: 0 @ 0 put: Color red. >>> g := f asFormOfDepth: 32. >>> g colorAt: 0 @ 0 "> (Color r: 0.0 g: 0.0 b: 0.004)" >>> >> yes, because you go from black/white to 32bit. I would have expected r0g0b0, but there might some rounding go on. >> >> > > 
Free forum by Nabble  Edit this page 