September 13, 2016
On 13 September 2016 at 17:47, John Colvin via Digitalmars-d <digitalmars-d@puremagic.com> wrote:
> On Tuesday, 13 September 2016 at 01:05:56 UTC, Manu wrote:
>>>
>>> Also can I swizzle channels directly?
>>
>>
>> I could add something like:
>>   auto brg =  c.swizzle!"brg";
>>
>> The result would be strongly typed to the new arrangement.
>
>
> Perfect use-case for opDispatch like in gl3n.

One trouble with arbitrary swizzling is that people often want to
write expressions like "c.xyzy", or whatever, but repeating
components... and that's not something my colours can do. It's useful
in realtime code, but it doesn't mean anything, and you can't
interpret that value as a colour anymore after you do that.
This sort of thing is used when you're not actually storing colours in
textures, but instead just some arbitrary data. Don't use a colour
type for that, use a vector type instead.
What that sort of swizzling really is, are vector operations, not
colour operations. Maybe I could add an API to populate a vector from
the components of colours, in-order... but then we don't actually have
linear algebra functions in phobos either! So colour->vectors and
arbitrary swizzling is probably not something we need immediately.

In my lib, colours are colours. If you have `BGR8 x` and `RGB8 y`, and add them, you don't get x.b+y.r, x.g+y.g, x.r+y.b... that's not a colour operation, that's an element-wise vector operation.
September 13, 2016
On 9/12/16 10:50 PM, Manu via Digitalmars-d wrote:
> std.conv.to  seems to 'just work' for color type conversion.
> I'd like to support string -> color conversion via std.conv.to; ie:
> auto c = "#FFFF00".to!RGB8;
> Is there a simple way to do that?

That was the purpose of toImpl, which I recall has been recently removed... -- Andrei
September 13, 2016
On Tuesday, 13 September 2016 at 02:50:02 UTC, Manu wrote:
> std.conv.to  seems to 'just work' for color type conversion.
> I'd like to support string -> color conversion via std.conv.to; ie:
> auto c = "#FFFF00".to!RGB8;
> Is there a simple way to do that?

yes. just define a ctor that accepts string, and you're there. it works both for classes and structs.
September 13, 2016
On Monday, 12 September 2016 at 22:51:14 UTC, Walter Bright wrote:
>
> My last comment is what can I do with a color library that would not require some additional library?

I think it's easy to do some image processing using netbpm [1] as format.
Reading/Writing images doesn't require any other library.

And using ndslices a lot of things can be done :)

Andrea

[1] https://en.wikipedia.org/wiki/Netpbm_format

September 13, 2016
On 13 September 2016 at 20:19, ketmar via Digitalmars-d <digitalmars-d@puremagic.com> wrote:
> On Tuesday, 13 September 2016 at 02:50:02 UTC, Manu wrote:
>>
>> std.conv.to  seems to 'just work' for color type conversion.
>> I'd like to support string -> color conversion via std.conv.to; ie:
>> auto c = "#FFFF00".to!RGB8;
>> Is there a simple way to do that?
>
>
> yes. just define a ctor that accepts string, and you're there. it works both for classes and structs.

Oh... it already works! :P
September 13, 2016
On Monday, 12 September 2016 at 22:51:14 UTC, Walter Bright wrote:
>
> My last comment is what can I do with a color library that would not require some additional library?

Having correct conversions.

Converting sRGB to linear RGB is typically not done correctly, pow isn't enough.
It also dissipates most misunderstanding about color space (yes Lab also are dependent on the color point, it was something I wasn't sure about and this library says it clearly).

Right now I rely on the OS for Apple RGB to sRGB conversion, this library would allow me to do it without using a system call.

Other uses I can imagine:
- Downsampling an image preserving colors (compressed RGB isn't necessarily the right sep to do those)
- Perceptually correct color gradients. In font rendering,
- HSV is very useful for colouring stuff in video games, it's what the color selection does in painter-programs like GIMP. So lots of library out there have a HSV <-> RGB conversions
- converting to packed RGB is useful for programs using GPUs. Same reason than half-float support is useful.


September 13, 2016
On Tuesday, 13 September 2016 at 09:31:53 UTC, Manu wrote:
>
> In my lib, colours are colours. If you have `BGR8 x` and `RGB8 y`, and add them, you don't get x.b+y.r, x.g+y.g, x.r+y.b... that's not a colour operation, that's an element-wise vector operation.

I think swizzling is way overrated, especially swizzling assignment.


Which is the most readable?

    color.rb = color.br;     // swizzling
    swap(color.r, color.b);  // no swizzling

    auto color = RGBA8(c.rgb, 255);         // swizzling
    auto color = RGBA8(c.r, c.g, c.b, 255); // no swizzling

And finally:

    auto rb = color.rgrb; // When do you ever need that?
September 13, 2016
On Tuesday, 13 September 2016 at 09:31:53 UTC, Manu wrote:
> On 13 September 2016 at 17:47, John Colvin via Digitalmars-d <digitalmars-d@puremagic.com> wrote:
>> On Tuesday, 13 September 2016 at 01:05:56 UTC, Manu wrote:
>>>>
>>>> Also can I swizzle channels directly?
>>>
>>>
>>> I could add something like:
>>>   auto brg =  c.swizzle!"brg";
>>>
>>> The result would be strongly typed to the new arrangement.
>>
>>
>> Perfect use-case for opDispatch like in gl3n.
>
> One trouble with arbitrary swizzling is that people often want to
> write expressions like "c.xyzy", or whatever, but repeating
> components... and that's not something my colours can do. It's useful
> in realtime code, but it doesn't mean anything, and you can't
> interpret that value as a colour anymore after you do that.
> This sort of thing is used when you're not actually storing colours in
> textures, but instead just some arbitrary data. Don't use a colour
> type for that, use a vector type instead.
> What that sort of swizzling really is, are vector operations, not
> colour operations. Maybe I could add an API to populate a vector from
> the components of colours, in-order... but then we don't actually have
> linear algebra functions in phobos either! So colour->vectors and
> arbitrary swizzling is probably not something we need immediately.
>
> In my lib, colours are colours. If you have `BGR8 x` and `RGB8 y`, and add them, you don't get x.b+y.r, x.g+y.g, x.r+y.b... that's not a colour operation, that's an element-wise vector operation.

Fair enough, you know much better than me how useful it would be. I was just suggesting that if you do support some sorts of swizzling then opDispatch would allow you to avoid users having to use strings. It would be as simple to implement as `alias opDispatch = swizzle;` given the swizzle function you were using before.
September 13, 2016
On Tuesday, 13 September 2016 at 01:05:56 UTC, Manu wrote:
>
> Can you describe what  you  perceive to be hard?

Well, I just skimmed through the docs and I didn't look at the code, so that sense it was an "honest" view for phobos proposal. Also I was trying to convey that based on the docs it "looks hard", although I was suspecting that it isn't really.

So the list of things was a list of examples that I would've wanted to see in the docs. Maybe in an overview or "here's how you use it" page. I can read the details if I really need them, but I think it's important to have a cook book examples for quick start.

In general, I think basics should be dead simple (even over simplified for the very basic case), but the API and the docs should provide me layers of increasing detail and sophistication, which I can study if (or when) I really need control and care about the details.

>> Few basic things I'd be interested in (examples):
>> 1. How to pack/unpack color into uint/rgba channels.
>
> auto c  = RGBA8(r, g, b, a);
> uint r = c.r.value; // 'r' is a 'NormalizedInt", so you need '.value'
> to get the raw integer value
> float g = cast(float)c.g; // cast to float knows about the normalized 0-1 range

Let's put these in the docs.

>
>> Also can I swizzle channels directly?
>
> I could add something like:
>   auto brg =  c.swizzle!"brg";

It's just a nicety. I guess I could just define exact color formats and convert (let the lib do the rest), or just unpack and repack.

Also the docs might want to mention which way is the preferred/designed way.

>> 2. Can I just cast an array of bytes into a RGBA array and operate on that?
>
> Yes. Of course, if the image library returned an array of colors, you wouldn't have an array of raw bytes in the first place.

Cool. I just wanted to make sure something like this possible.

Also should be in the docs as an example, so that people don't have to try this out themselves.
Or search through github for details.

>
>> 3. How to scale color channels e.g. 5 bits to 8 bits and vice versa. How to convert color formats? Can I combine scale/conversion with single channel or channel swizzling?
>
> alias CustomPackedColor = PackedRGB!("BGR_5_6_5", ubyte); // <- ordered bgr
> CustomPackedColor[] image = loadPackedImage();
>
> auto unpacked = cast(RGB8)image[0]; // unpack and swizzle
>
> I'm not sure what you mean by "with single channel"?

For example if you first unpack RGBA_uint32 into R,G,B,A then you want to take G (or just swizzle color.g) and scale that to 5 bits or 16 bits for what ever use case you might have.

Looks to me like this can be handled with something like PackedRGB!("G_5") and then do color conversion into that.

>
>> 4. Which way are RGBA format names defined ("byte array order" r is first byte or "uint order" r is in high bits)?
>
> I describe formats in byte (bit) order. It's the only reasonable way
> that works outside of a uint.

Agreed. This should be in the docs, so that it's clear to users. (especially, since RGBA8888 is the common case and it does fit into uint)

>
> I'm showing that parsing colors from string's follow the web
> convention. I can't redefine how colours are expressed on the web for
> decades.
> I think you've just highlighted that I need to remove the '0x'
> notation though, that is definitely misleading! Use '#', that should
> be clear.

Right. I was interpreting 0x........ as c hex literal. You should document that it's following the web convention.

>> 6. Perhaps you should define all the usual color formats, since everybody
>> and their cat has their own preference for rgba channel orders.
>> In my experience all these 4 variants for RGBA8888 are pretty common:
>> RGBA8888
>> BGRA8888
>> ARGB8888
>> ABGR8888
>> and their X and 24bit variants.
>
> I don't think they're common at all. Only 2 are common (one of which
> is deprecated), the other 2 are very niche.

Deprecated by who? Shouldn't phobos grade lib include all reasonable platforms?

I agree that you probably don't see too much variation within windows APIs, images (BMP etc.) or with D3D GPU textures (they're compressed anyway and asset pipelines to do the conversions beforehand), but I was more of thinking image libraries and the numerous, sometimes old and quirky, image formats. Or perhaps someone wants to implement a software blitter for their favorite toy device/embedded project.

> I was trying to balance a tasteful amount of instantiations. I don't
> really want to provide an instantiation of every single realtime
> format I've ever encountered out of the box.
Seems reasonable.

>
>> For 16 bits fairly common are:
>> RGB565 and RGBA5551, also sometimes you see one of RGBA4444 permutations
>> (like RGBA8 above).
>
> Nobody uses 16bit textures anymore. Compressed textures are both MUCH smaller, and generally higher quality.

Sure, agreed. These are not too useful as GPU textures these days (even on mobile), but if you do software 2d, load older image formats (image viewer etc.) or something even more specialized, these are pretty useful.

I guess I was going for comprehensive (within reason), where as you were going for "90% of 2016 colors/image data", which is fine.

Anyways, it would be nice to see color (and hopefully image + simple blitter) in phobos.
There's no need to write the same convert/copy/stretch/blend loop over and over again. And cpu-side code is nice to have for quick prototyping and small-scale work.

>
>> Just as a completely random idea - How about aliases for HDR formats like HDR10 and Dolby Vision? Kind of looks like they're just combinations what you already have.
>
> This is very specialist. Instantiations are expensive. If they're not used, it's a waste of compiler effort.

HDR TVs and displays are coming fast and with that I'm sure HDR editing and photography will be common, which of course means HDR color formats and apps. But these can be added later.


September 13, 2016
On Tuesday, 13 September 2016 at 02:00:44 UTC, Manu wrote:
> On 13 September 2016 at 07:00, Marco Leise via Digitalmars-d <digitalmars-d@puremagic.com> wrote:
>> Am Tue, 13 Sep 2016 00:37:22 +1000
>> schrieb Manu via Digitalmars-d <digitalmars-d@puremagic.com>:
>> Alright, but hybrid gamma is really not something that can be googled. Or rather I end up at Toyota's Gamma Hybrid product page. :D
>
> True. I'm not even sure what the technical term for this sort of gamma
> function is... I just made that up! :/
> As Walter and others have asked, I'll have to start adding links to
> reference material I guess, although that still feels really weird to
> me for some reason.

FWIW I stumbled into this while double-checking HDR standards for my previous post. (I'm not a HDR expert, only somewhat interested because it's the future of displays/graphics)

https://en.wikipedia.org/wiki/Hybrid_Log-Gamma