JPG and PNG decoder

2012-06-16 Thread cal
I've been working on decoders for simple (baseline) JPEG and 
PNG's, mostly for my own amusement, and they seem to work ok now, 
so if anyone has need of some simple D modules to load these 
formats you can grab them here:

https://github.com/callumenator/imaged

Notes:
- Will load 8-bit baseline sequential JPEG's only. All PNG image 
types are supported (only critical chunks are decoded however).
- Can load from a stream or a file. In the case of the PNG's, 
this allows progressive display with an interlaced image.
- I haven't put much effort into speeding up these routines, and 
have not tested the JPEG decoder extensively, so there are bound 
to be bugs and there is plenty room for improvement.
- The example shows stream usage, and uses Adam Ruppe's 
simpledisplay to make a little viewer, that can flick through all 
images in a directory.


Cheers,
cal


Re: JPG and PNG decoder

2012-06-17 Thread cal

On Sunday, 17 June 2012 at 07:07:35 UTC, Philippe Sigaud wrote:

Still, I'm interested in writing a JPEG/PNG to disk from a
ubyte[3][][], or whatever.


Do you mean that you want to encode a ubyte array to disk as 
JPEG/PNG? Encoding a JPEG would be a bit of work I think, the 
format's kind of a monster. PNG should be easier, depending on 
how good you want the compression to be. If you don't care too 
much about compression level, you simply zlib compress the data, 
write it out by image row/scanline, include appropriate header 
and chunk info, and you're done. I'll give a simple encoder a go 
if you think you could use it.


Cheers,
cal



Re: JPG and PNG decoder

2012-06-17 Thread cal

On Sunday, 17 June 2012 at 12:15:36 UTC, bearophile wrote:

Suggestions on the code:
- Try to use final switches.
- switch cases don't need (), so instead of case(foo):  write 
case foo:

- Try to add const/immutable/pure/nothrow where possible.

Bye,
bearophile


Problem with final switches in this context is that images may be 
corrupt or badly encoded or something, which the decoder should 
just handle gracefully through a default I think, without 
crashing. The case statements though I will change, and though I 
have worlds of trouble with const-ness, I will endeavour to add 
those guarantees :)


Thanks for looking through






Re: JPG and PNG decoder

2012-06-17 Thread cal

On Sunday, 17 June 2012 at 12:35:41 UTC, David wrote:
Cool so I don't need to use my stb_image binding ( 
https://bitbucket.org/dav1d/gl-utils/src/0b97f77c14d7/stb_image 
) anylonger!


I used stb_image with C++ opengl projects, and it was great. 
stb_truetype is another gem, I would love to write a truetype 
loader, but I think the payoff is not worth the effort given the 
freetype bindings.





Re: JPG and PNG decoder

2012-06-17 Thread cal

On Sunday, 17 June 2012 at 23:17:54 UTC, Stewart Gordon wrote:
You two should fuse it into one module, to give us 
loading/writing.

That would be quite cool.


I don't know how much of the code will need rewriting in order 
to support interlacing or all PNG colour types/depths.


But I also began writing a PNG library a while back - with the 
intention that it will be a full PNG editing library, not just 
encoding/decoding of the image data.  But I haven't had much 
time to work on it recently.  And it would help a lot if we 
could have the replacement for std.stream some time soon.


Stewart.


I just pushed an update which implements a PNG encoder. It is 
implemented in the Image class as a write method. If you have a 
raw buffer, and want to encode it, you can do something like this:


ubyte[] data = some data;
Image img = new Img!(Px.R8G8B8)(width, height, data);
img.write("mypng.png");

It uses adaptive filtering, and should work with the pixel 
formats supported by the image class (except for the 16 bit ones 
I've just realised). I've only tested it on images that I have 
previously loaded in however.


Stewart, I used your makepng.d as a template for this, can I add 
you to the author list?


Also, if preferred, I can keep the master branch as a single 
merged module, just let me know.


Cheers,
cal






Re: JPG and PNG decoder

2012-06-21 Thread cal

On Thursday, 21 June 2012 at 17:58:47 UTC, Stewart Gordon wrote:

On 18/06/2012 00:49, cal wrote:


ubyte[] data = some data;
Image img = new Img!(Px.R8G8B8)(width, height, data);


Image?  Img?


img.write("mypng.png");


Image is the interface, Img the templated class that does all the 
work. It is parameterized by the pixel format. It may not be the 
best strategy (or naming scheme!) but enumerating the formats and 
templating based on that limited the number of cases I had to 
think about.


Does it always take in a ubyte[], or does that depend on the 
bit depth?


It currently just takes a ubyte, and doesn't do any rearranging 
of the array, so it will only work for 8-bit depths. If you had 
4-bit greyscale tightly packed into your ubyte (two pixels per 
byte) then it would not be correctly interpreted, nor would 16 
bit. The reason was I didn't want to have the Image class 'own' 
the passed-in array. If it did own it, then it would be free to 
unpack the smaller bit depths the way it does when decoding. I 
will fix this when I have time to think about it a bit more.


Re: NaNs Just Don't Get No Respect

2012-08-20 Thread cal

On Monday, 20 August 2012 at 19:28:33 UTC, Peter Alexander wrote:

On Sunday, 19 August 2012 at 22:22:28 UTC, Walter Bright wrote:

> I find it more likely that the NaN will go unnoticed and
> cause rare bugs.

NaNs in your output are pretty obvious. For example, if your 
accounting program prints "NAN" for the amount on the payroll 
cheques, someone is guaranteed to notice. But if it's a few 
cents off in your disfavor, it might take you years to 
discover there's a problem.


Critical systems also would find a NaN command a lot easier to 
detect than an off-by-two command, and would be able to shut 
down and engage the backup.


The problem is that it's easy for even NaN's to be filtered out.

float x = 0.0f;
float y; // oops
float z = min(x, y); // NaN has disappeared, unnoticed!

My argument is that conservative compile time errors on 
uninitialised variables are more likely to catch these errors.


I just tried this:

float a, b = 10;
writeln(min(a, b), ", ", fmin(a, b));

Result:
nan, 10

I think that is incorrect - both should give NaN. The scientific 
viz software I use at work returns NaN for any numerical 
operation on NaN values, means, smoothing, etc.


Re: NaNs Just Don't Get No Respect

2012-08-21 Thread cal

On Tuesday, 21 August 2012 at 08:15:10 UTC, Don Clugston wrote:

No, it's the other way around.
The IEEE 754 standard defines min(x, NaN) == min(NaN, x) == x.

According to the C standard, fmin() should be returning 10, as 
well.

There is a bug in fmin().

However min() and max() are extremely unusual in this respect. 
Almost everything else involving a NaN returns NaN.


I did not know that. It seems like a not-so-useful rule but I 
guess they have their reasons. Note that in my example, fmin() 
_did_ return 10 - it was min() that returned NaN...




Re: gl3n - OpenGL Maths for D

2012-08-31 Thread cal

On Friday, 31 August 2012 at 16:54:49 UTC, David wrote:

Anything you miss?


Matrix constructor for building projection matrices (I have a bit 
of code for doing this from near/far + FOV if you want it, but 
there are plenty examples on google).


I've also found it useful to be able to set a given matrix column 
using a vector, I didn't see a function specifically for this 
(row-major makes it handy to have a dedicated function for this).


Nice work!


Re: early alpha of D REPL

2014-02-11 Thread cal

On Tuesday, 11 February 2014 at 11:33:53 UTC, thedeemon wrote:



Have you seen Dabble?
https://github.com/callumenator/dabble


Just found out its author added Linux support. I was able to 
build an x86 version but it didn't work properly in a 64 bit 
system: it assumes dmd makes x86 binaries by default while it 
really makes 64-bit ones. And for 64 bits Dabble doesn't 
compile: as it often happens, it's too easy to forget that 
array.length is not always uint.


I don't have a 64-bit tool-chain to play with, could submit those 
64 bit build errors on github?


Re: early alpha of D REPL

2014-02-12 Thread cal
On Wednesday, 12 February 2014 at 18:08:11 UTC, Martin Nowak 
wrote:
For example it should be possible to call a function or inherit 
from a class that were defined earlier.


Dabble allows both of these things, if I understand your comment 
correctly.


Re: early alpha of D REPL

2014-02-14 Thread cal

On Tuesday, 11 February 2014 at 04:46:41 UTC, Martin Nowak wrote:

Barely running but already fun and a little useful.

Example:

D> import std.algorithm, std.array, std.file;
=> std
D> auto name(T)(T t) {
 | return t.name;
 | }
=> name
D> dirEntries(".", SpanMode.depth).map!name.join(", ")
=> ./drepl_sandbox
D>

https://github.com/MartinNowak/drepl
http://drepl.dawg.eu/


This approach with separate modules is far superior to what I did 
with dabble, and much simpler. My target was windows initially, 
where I guess this won't work currently. Hopefully the situation 
there will improve soon.