Hi Blair,
I'd like to follow up on creating Bitmaps (and Icons) from ByteArrays. How would I do that? Günther |
Günther Schmidt wrote:
> I'd like to follow up on creating Bitmaps (and Icons) from ByteArrays. I'm not sure about Bitmaps and Icons ... but something similar can be done with OLEPictures. Take a look here: http://groups.google.com/group/comp.lang.smalltalk.dolphin/browse_frm/thread/7f33c877af3094a4/246bf8ddf7131cde?q=OLEPicture+fromByteArray:&rnum=1#246bf8ddf7131cde CU, Udo |
In reply to this post by Günther Schmidt
Günther,
> I'd like to follow up on creating Bitmaps (and Icons) from ByteArrays. Icons are complicated since they consist of several images. Bitmaps are less complicated, but since there are many possible formats, there is a fair amount to consider, and to get wrong. If you want to keep it simple, then a good way is just to write the ByteArray to a temporary .BMP or .ICO file, and then load that in the normal way. Otherwise, the following may help get you started on manipulating image data directly. But please note the following warnings: a) there are several possible image formats, with correspondingly different pixel layouts in memory. See Petzold for guidance. b) doing this kind of thing can totally trash your image, and not necessarily in ways that will show up immediately, since you are writing to arbitrary memory locations. (in fact I discaded the image I used to write this demo code -- I didn't trust myself to have got it right). Anyway. To create sample bitmap. We'll start with a "DIB section" (silly Windows terminology) that is 11x7 and 24 bits deep. Note that we're working with odd numbers to help show up where rounding-up happens: dibs := DIBSection width: 11 height: 7 depth: 24. Get a view of it. This will be automatically stretched, which is handy since we are using a very small image: v := (ImagePresenter showOn: dibs) view. Now get some important information about the bitmap's size and shape in memory: info := dibs getInfo. bytesPerPixel := info bmBitsPixel / 8. bytesPerRow := info bmWidthBytes. "note that this is rounded up" totalSize := bytesPerRow * info bmHeight. Now get the address where the actual binary data is stored: addr := dibs imageBits. Copy that data into a ByteArray (actually the data is pretty dull since it starts off all zero): copyBytes := ByteArray fromAddress: addr length: totalSize. Change the copy to all ones (for white): copyBytes atAllPut: 16rFF. Copy the changed data back to the image, and #invalidate the view, so we will see the effect immediately: addr replaceFrom: 1 to: copyBytes size with: copyBytes startingAt: 1. v invalidate. Or instead we can scribble directly onto the binary data. This stuff is pretty tricky to get right; it helps if you take as few short-cuts as possible. This code will draw a black X on the bitmap: "draw one bar" 0 to: info bmHeight-1 do: [:i || x y offset | x := i. y := i. offset := (y * bytesPerRow) + (x * bytesPerPixel). 0 to: bytesPerPixel-1 do: [:b | "safety!" self assert: [offset+b < totalSize]. addr byteAtOffset: offset+b put: 0]]. "draw the other bar, the only difference is the value of y in the loop" 0 to: info bmHeight-1 do: [:i || x y offset | x := i. y := info bmHeight - 1 - i. offset := (y * bytesPerRow) + (x * bytesPerPixel). 0 to: bytesPerPixel-1 do: [:b | "safety!" self assert: [offset+b < totalSize]. addr byteAtOffset: offset+b put: 0]]. v invalidate. On the whole, I think it's probably better (safer) do all the difficult work in ByteArrays that are copies of the image data, and have only one or two very well-tested methods for transfering data between the real image and the copy. I'm afraid I have no idea how to play similar tricks with icons -- as I said, they are more complicated beasts. Some time ago Diego posted a link to a small package by Hernan Galante that could create single-image Icons from bitmaps. It used to be at: http://www.smalltalking.net/Goodies/Dolphin/ but doesn't seem to be on that page any longer (the stuff there is still worth looking at, though!). I can send you a copy if you like. -- chris |
Chris,
thanks. See the basic idea behind this is to be able to store the icons in a byte array in a method. And the idea behind that is so that we all can do without having to create separate icon or resource files when we deploy the application. I'll give it some more tries. Günther |
Free forum by Nabble | Edit this page |