Well, I did a test.  The double shift does clamp the top end.  But negative
numbers are twisted to be 255.  In bi-cubic interpolation (the reason for all
this nonsense) negative byte (channel) values can occur. The goal is to
clamp to the range [0-255] so -100 goes to 0 and 300 goes to 255.

Here's the snippet:

//        sum = (s1[s1PixelOffset]&0xFF) + (s2[s2PixelOffset]&0xFF);
//        d[dPixelOffset] = (byte)((((sum<<23) >> 31) | sum) & 0xFF);

       int foo = 0;
       int bar = 0;
       for(int i = -10; i < 265; i++)
       {
           foo = i;
           bar = ((((foo << 23) >> 31) | foo) & 0xFF);

           System.err.println(i + ": foo = " + foo + ", bar = " + bar );

       }

And here is the abbreviated output:
-4: foo = -4, bar = 255
-3: foo = -3, bar = 255
-2: foo = -2, bar = 255
-1: foo = -1, bar = 255
0: foo = 0, bar = 0
1: foo = 1, bar = 1
2: foo = 2, bar = 2
3: foo = 3, bar = 3
4: foo = 4, bar = 4
.
.
.
252: foo = 252, bar = 252
253: foo = 253, bar = 253
254: foo = 254, bar = 254
255: foo = 255, bar = 255
256: foo = 256, bar = 255
257: foo = 257, bar = 255
258: foo = 258, bar = 255
259: foo = 259, bar = 255



Finally, com.sun.media.jai.util.ImageUtil.java does this to clamp a byte value
which is equivalent to what I was doing.  I need to clamp both ends reliably.
I wonder if it can be done with shifts and masks?  Maybe I've done the best
that can be done.

public static final byte clampByte(int in) {
       return (in > 0xFF ? (byte)0xFF : (in >= 0 ? (byte)in : (byte)0));
   }

Ken Warner wrote:
Never mind -- found it...

http://java.sun.com/docs/books/jls/third_edition/html/expressions.html#15.19


At run time, shift operations are performed on the two's complement
integer representation of the value of the left operand.

The value of n<<s is n left-shifted s bit positions; this is equivalent
(even if overflow occurs) to multiplication by two to the power s.

The value of n>>s is n right-shifted s bit positions with
sign-extension. The resulting value is � n/2s⌋. For nonnegative values
of n, this is equivalent to truncating integer division, as computed by
the integer division operator /, by two to the power s.

Now if I could only understand this...

[EMAIL PROTECTED] wrote:

if(r < 0) r = 0;
if(r > 255) r = 255;
if(g < 0) g = 0;
if(g > 255) g = 255;
if(b < 0) b = 0;
if(b > 255) b = 255;

Clumsy and awkward.  Is there a better way to clamp
the values?
Maybe with a mask or something?



If your "better" meant "faster", you might like to take a look at this:
https://jai-core.dev.java.net/source/browse/jai-core/src/share/classes/com/sun/media/jai/opimage/AddOpImage.java?rev=1.1&view=markup

under computeRectByte()

                    //
                    // The next two lines are a fast way to do
                    // an add with saturation on U8 elements.
                    // It eliminates the need to do clamping.
                    //
                    sum = (s1[s1PixelOffset]&0xFF) +
(s2[s2PixelOffset]&0xFF);
                    d[dPixelOffset] = (byte)((((sum<<23) >> 31) | sum)
& 0xFF);

HTH,
-James
[Message sent by forum member 'jxc' (jxc)]

http://forums.java.net/jive/thread.jspa?messageID=230881

===========================================================================

To unsubscribe, send email to [EMAIL PROTECTED] and include in the
body
of the message "signoff JAVA2D-INTEREST".  For general help, send
email to
[EMAIL PROTECTED] and include in the body of the message "help".



===========================================================================
To unsubscribe, send email to [EMAIL PROTECTED] and include in the body
of the message "signoff JAVA2D-INTEREST".  For general help, send email to
[EMAIL PROTECTED] and include in the body of the message "help".



===========================================================================
To unsubscribe, send email to [EMAIL PROTECTED] and include in the body
of the message "signoff JAVA2D-INTEREST".  For general help, send email to
[EMAIL PROTECTED] and include in the body of the message "help".

Reply via email to