gbadev.org forum archive

This is a read-only mirror of the content originally found on forum.gbadev.org (now offline), salvaged from Wayback machine copies. A new forum can be found here.

DS development > Bitshift and colour simple question but difficult for me XD

#154142 - TheMagnitude - Fri Apr 11, 2008 10:21 pm

Is there any reason why I shouldn't be able to do:

Code:
long variable = 1 << 15 /* It doesn't work for anything more than 14 and the calculations are not precise at 14 /*


Also is there another colour function like RGB15(31,31,31) but RGB255(255,255,255) so I can have greater colour precision (im writing directly to the framebuffer);

#154143 - kusma - Fri Apr 11, 2008 10:32 pm

TheMagnitude wrote:
Is there any reason why I shouldn't be able to do:

Code:
long variable = 1 << 15 /* It doesn't work for anything more than 14 and the calculations are not precise at 14 /*


Because 1 << 15 is a value where only the 16th bit is set, and the DS only has 15 bit color depth.

Quote:

Also is there another colour function like RGB15(31,31,31) but RGB255(255,255,255) so I can have greater colour precision (im writing directly to the framebuffer);

No, the DS has (as said before) only 15 bits of color depth. That's 5 bits per component, and (1 << 5) - 1 = 31, which is the highest allowed value per color component.

#154144 - TheMagnitude - Fri Apr 11, 2008 10:51 pm

kusma wrote:
TheMagnitude wrote:
Is there any reason why I shouldn't be able to do:

Code:
long variable = 1 << 15 /* It doesn't work for anything more than 14 and the calculations are not precise at 14 /*


Because 1 << 15 is a value where only the 16th bit is set, and the DS only has 15 bit color depth.

Quote:

Also is there another colour function like RGB15(31,31,31) but RGB255(255,255,255) so I can have greater colour precision (im writing directly to the framebuffer);

No, the DS has (as said before) only 15 bits of color depth. That's 5 bits per component, and (1 << 5) - 1 = 31, which is the highest allowed value per color component.
Thanks for replying, is there any way I can use the memory of the DS or a cache or something to work with 30 point fixed numbers i.e: 1 << 30 or higher?

#154149 - kusma - Fri Apr 11, 2008 11:27 pm

TheMagnitude wrote:
Thanks for replying, is there any way I can use the memory of the DS or a cache or something to work with 30 point fixed numbers i.e: 1 << 30 or higher?

The LCD controller of the Nintendo DS can only output 15 bits per pixel. There's no way around that, and neither memory nor cache have anything to do with this. Of course, you can do internal calculations in higher precision than the output-precision if you're doing some complex rendering, but you must down-convert to 15 bit before displaying your image no matter what.

#154151 - strager - Fri Apr 11, 2008 11:52 pm

TheMagnitude wrote:
[...], is there any way I can use the memory of the DS or a cache or something to work with 30 point fixed numbers i.e: 1 << 30 or higher?


Yes; you can use the `long long` type (s64/u64). sgstair has a fixed multiply function designed for 4.60 fixed numbers in his Mandelbrot example program. Adding and subtracting should be simple, as with multiplying with an integer. Division and square roots may be done using the math co-processor.

As for your first question, GBATek may be able to help you with colours on the GBA. DS colours use the previously unused bit 15 for opacity in some cases; set this to one if your bitmap does not appear. Remember, when assigning a `long` expression to a `short` variable, the top 16 bits* are truncated.

* On the GBA and NDS, where sizeof(long) == 4, sizeof(short) == 2, and CHAR_BITS == 8, this applies.

#154162 - tepples - Sat Apr 12, 2008 2:01 am

kusma wrote:
TheMagnitude wrote:
Thanks for replying, is there any way I can use the memory of the DS or a cache or something to work with 30 point fixed numbers i.e: 1 << 30 or higher?

The LCD controller of the Nintendo DS can only output 15 bits per pixel. There's no way around that

I know of a workaround. Later Sega Genesis games used it, and so do cheap LCD TVs that advertise "16 million" or "16.2 million" not "16.8 million" colors. You use spatial dithering to simulate an extra bit, and then you use flickering to simulate another. Games for TI-89 graphing calculators, which have 1-bit displays, simulate 4-level grayscale the same way. So you're still displaying 15-bit images, but the human eye makes them look 18- or even 21-bit.
_________________
-- Where is he?
-- Who?
-- You know, the human.
-- I think he moved to Tilwick.

#154173 - TheMagnitude - Sat Apr 12, 2008 7:30 am

Wow thanks for the replies that was really useful!

When I use s64's it runs about 3 times as slow :(

How can someone make a function to multiply too fixed point numbers? Surely the way to do it is:

Code:
fixed1*fixed2 >> precision


Ill check it out later anyhow

I think spatial dithering and flickering techniques are a bit too hard so Ill just leave the colour depth as it is.

#154177 - TwentySeven - Sat Apr 12, 2008 10:15 am

You're right.


X = 24.8
Y = 24.8

X*Y = 24.16

so to correctly multiply X*Y you have to lop off 8 bits.

so if you know your final range is going to fit into an int32, you don't need to use int64's for all of it, just the actual calculation

int64 Z = X*Y;
int32 Result = (int32)(Z >> 8);

#154178 - PlagueSpark - Sat Apr 12, 2008 10:48 am

In libnds there are ready-to-use some useful stuff for fixed point math
Excpecialy in videoGL.h header file there macroses for multiply 16bit 4.12 integers and SIN[512] COS[512] tables that is very useful not just for 3d

If to believe the manual, DS also has the native accelerated div/mod functions

Here some define macroses examples for 16.16 s32 integers with no usage of 64bit integers
Code:

#define FPMUL(x,y)   ((((x)>>6)*((y)>>6))>>4)
#define FPDIV(x,y)   ((((x)<<6)/((y)>>6))>>4)

I got them from old tutorial for n-gage on flipcode.net