ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/common/abitmap.h
Revision: 2.2
Committed: Sat Aug 24 23:25:24 2024 UTC (8 months, 1 week ago) by greg
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 2.1: +1 -0 lines
Log Message:
chore: Added RCS tags to files

File Contents

# User Rev Content
1 greg 2.2 /* RCSid $Id$ */
2 greg 2.1 /*
3     * abitmap.h
4     * panlib
5     *
6     * General bitmap class (mostly inline)
7     *
8     * Created by gward on Tue May 15 2001.
9     * Copyright (c) 2001 Anyhere Software. All rights reserved.
10     *
11     */
12     #ifndef _ABITMAP_H_
13     #define _ABITMAP_H_
14    
15     #ifndef _TIFF_
16     #include "tiff.h" /* needed for uint32 type */
17     #endif
18    
19     #define ABMend 0xffffffff // terminal return
20    
21     // Inline bitmap class
22     class ABitMap {
23     private:
24     uint32 * bmap; // bitmap storage
25     uint32 len; // bitmap size
26     public:
27     ABitMap() { len=0; bmap=0; }
28     ABitMap(uint32 n, bool clrset=false) {
29     bmap=0; len=0; NewBitMap(n,clrset);
30     }
31     ABitMap(const ABitMap &orig) {
32     bmap=0; len=0; *this=orig;
33     }
34     ~ABitMap() {
35     delete [] bmap;
36     }
37     // Access to raw word data
38     uint32 * base() {
39     return bmap;
40     }
41     // Read-only word access
42     const uint32 * base() const {
43     return bmap;
44     }
45     // Number of words from #bits
46     static int32 bmlen(uint32 nbits) {
47     return (nbits+0x1f)>>5;
48     }
49     // Total number of words
50     int32 bmlen() const {
51     return bmlen(len);
52     }
53     // Reallocate and clear bitmap
54     bool NewBitMap(uint32 n, bool clrset=false);
55     // Clear bitmap to all 0's or 1's
56     void ClearBitMap(bool clrset=false);
57     // Steal another bitmap's contents
58     bool Take(ABitMap *srcp) {
59     if (srcp == this) return false;
60     delete [] bmap; bmap=0; len=0;
61     if (!srcp) return false;
62     bmap=srcp->bmap; len=srcp->len;
63     srcp->bmap=0; srcp->len=0;
64     return len;
65     }
66     // Return number of bits in bitmap
67     uint32 Length() const {
68     return len;
69     }
70     // Get original length if RLE (or 0)
71     uint32 RLength() const;
72     // Compress into a run-length encoded bitmap
73     bool GetRLE(ABitMap *rlep) const;
74     // Reconstitute bits from RLE encoding
75     bool SetFromRLE(const ABitMap &rle);
76     // Extract bitmap section (true if some overlap)
77     bool GetBits(ABitMap *dp, uint32 i) const;
78     // Extract bitmap section (fill if past end)
79     ABitMap GetBits(uint32 i, uint32 n, bool fill=false) const {
80     ABitMap bm(n, fill);
81     GetBits(&bm, i);
82     return bm;
83     }
84     // Overlay bitmap section (ignores bits past end)
85     bool AssignBits(uint32 i, const ABitMap &src);
86     // Apply operation to bitmap section
87     bool OpBits(uint32 i, char op, const ABitMap &src);
88     // Clear bitmap section
89     void ClearBits(uint32 i, uint32 n, bool clrset=false);
90     // Clear bits set in second bitmap
91     bool ClearBitsFrom(const ABitMap &src);
92     // Count number of bits set in bitmap
93     uint32 SumTotal(bool bit2cnt = true) const;
94     // Return the next bit position matching val (or ABMend)
95     uint32 Find(uint32 i = 0, bool val = true) const;
96     uint32 Find(int i, bool val = true) const {
97     return Find((uint32)i, val);
98     }
99     uint32 Find(long i, bool val = true) const {
100     return Find((uint32)i, val);
101     }
102     // Different interface to find the next bit matching val
103     bool Find(uint32 *ip, bool val = true) const {
104     if (!ip) return false;
105     if (*ip >= len) return false;
106     *ip = Find(*ip, val);
107     return (*ip < len);
108     }
109     // Access word for i'th bit
110     uint32 & Word(uint32 i) {
111     static uint32 dummy;
112     if (i >= len) return dummy;
113     return bmap[i>>5];
114     }
115     // Get word value for i'th bit (0 if out of range)
116     uint32 WordV(uint32 i) const {
117     if (i >= len) return 0;
118     return bmap[i>>5];
119     }
120     // Index corresponding bit in word
121     static uint32 Bit(uint32 i) {
122     return 1 << (i & 0x1f);
123     }
124     // Return value of i'th bit in bitmap
125     bool Check(uint32 i) const {
126     return (WordV(i) & Bit(i));
127     }
128     // Set i'th bit
129     void Set(uint32 i) {
130     Word(i) |= Bit(i);
131     }
132     // Reset i'th bit
133     void Reset(uint32 i) {
134     Word(i) &= ~Bit(i);
135     }
136     // Set i'th bit explicitly on or off
137     void Set(uint32 i, bool switchon) {
138     uint32 b = Bit(i);
139     uint32 & w = Word(i);
140     if (switchon) w |= b;
141     else w &= ~b;
142     }
143     // Toggle i'th bit
144     void Toggle(uint32 i) {
145     Word(i) ^= Bit(i);
146     }
147     // Set i'th bit if it's clear (or fail)
148     bool TestAndSet(uint32 i) {
149     if (i >= len) return false;
150     uint32 b = Bit(i);
151     uint32 & w = Word(i);
152     uint32 wasset = w & b;
153     w |= b;
154     return !wasset;
155     }
156     // Clear i'th bit if it's set (or fail)
157     bool TestAndReset(uint32 i) {
158     if (i >= len) return false;
159     uint32 b = Bit(i);
160     uint32 & w = Word(i);
161     uint32 wasset = w & b;
162     w &= ~b;
163     return wasset;
164     }
165     // Set i'th bit on/off (fail if no change)
166     bool TestAndSet(uint32 i, bool switchon) {
167     return switchon ? TestAndSet(i) : TestAndReset(i);
168     }
169     // Invert the entire bitmap
170     void Invert();
171     // Downward shift operator, zero fill
172     ABitMap & operator>>=(uint32 nbits);
173     // Upward shift operator, zero fill
174     ABitMap & operator<<=(uint32 nbits);
175     // Copy operator
176     ABitMap & operator=(const ABitMap &src);
177     // Bitwise OR-copy operator
178     ABitMap & operator|=(const ABitMap &src);
179     // Bitwise AND-assign operator
180     ABitMap & operator&=(const ABitMap &src);
181     // Bitwise XOR-assign operator
182     ABitMap & operator^=(const ABitMap &src);
183     // Subtraction operator, synonym for ClearBitsFrom()
184     ABitMap & operator-=(const ABitMap &src) {
185     ClearBitsFrom(src);
186     return *this;
187     }
188     // Compare two bitmaps for equality
189     bool operator==(const ABitMap &that) const;
190     };
191    
192     inline bool
193     operator!=(const ABitMap &bm1, const ABitMap &bm2)
194     {
195     return !(bm1 == bm2);
196     }
197    
198     inline ABitMap
199     operator>>(ABitMap bmLeft, uint32 nbr)
200     {
201     return bmLeft >>= nbr;
202     }
203    
204     inline ABitMap
205     operator<<(ABitMap bmLeft, uint32 nbl)
206     {
207     return bmLeft <<= nbl;
208     }
209    
210     inline ABitMap
211     operator|(ABitMap bmLeft, const ABitMap &bmRight)
212     {
213     return bmLeft |= bmRight;
214     }
215    
216     inline ABitMap
217     operator&(ABitMap bmLeft, const ABitMap &bmRight)
218     {
219     return bmLeft &= bmRight;
220     }
221    
222     inline ABitMap
223     operator^(ABitMap bmLeft, const ABitMap &bmRight)
224     {
225     return bmLeft ^= bmRight;
226     }
227    
228     inline ABitMap
229     operator-(ABitMap bmLeft, const ABitMap &bmRight)
230     {
231     return bmLeft -= bmRight;
232     }
233    
234     inline ABitMap
235     operator~(ABitMap bmUnary)
236     {
237     bmUnary.Invert();
238     return bmUnary;
239     }
240    
241     // 2-dimensional bitmap class
242     class ABitMap2 : protected ABitMap {
243     private:
244     int width, height; // bitmap dimensions
245     protected:
246     uint32 bmi(int x, int y) const {
247     if (OffBitMap(x, y)) return ABMend;
248     return (uint32)y*width + x;
249     }
250     public:
251     ABitMap2() { width=height=0; }
252     ABitMap2(int w, int h, bool clrset=false) :
253     ABitMap((w>0)&(h>0)&&(w <= ABMend/h)
254     ? (uint32)w*h : (uint32)0, clrset) {
255     if (Length()) {
256     width=w; height=h;
257     } else { width=height=0; }
258     }
259     ABitMap2(const ABitMap2 &orig) {
260     *this=orig;
261     }
262     // Access to raw word data
263     uint32 * base() {
264     return ABitMap::base();
265     }
266     // Read-only word access
267     const uint32 * base() const {
268     return ABitMap::base();
269     }
270     // Total number of words
271     int32 bmlen() const {
272     return ABitMap::bmlen();
273     }
274     // Return bitmap width
275     int Width() const {
276     return width;
277     }
278     // Return bitmap height
279     int Height() const {
280     return height;
281     }
282     // Is the indicated bit off our bitmap?
283     bool OffBitMap(int x, int y) const {
284     return ((x < 0) | (x >= width) |
285     (y < 0) | (y >= height));
286     }
287     // Count number of bits set in bitmap
288     uint32 SumTotal(bool bit2cnt = true) const {
289     return ABitMap::SumTotal(bit2cnt);
290     }
291     // Reallocate and clear bitmap
292     bool NewBitMap(int w, int h, bool clrset=false) {
293     if ((w <= 0) | (h <= 0) || w > ABMend/h)
294     w = h = 0;
295     width=w; height=h;
296     return ABitMap::NewBitMap((uint32)w*h, clrset);
297     }
298     // Clear bitmap to all 0's or 1's
299     void ClearBitMap(bool clrset=false) {
300     ABitMap::ClearBitMap(clrset);
301     }
302     // Compress with run-length encoding into a 1-D bitmap
303     bool GetRLE(ABitMap *rlep) const {
304     return ABitMap::GetRLE(rlep);
305     }
306     // Reconstitute bits from RLE encoding (size must match)
307     bool SetFromRLE(int w, int h, const ABitMap &rle);
308     // Steal another bitmap's contents
309     bool Take(ABitMap2 *srcp) {
310     if (srcp == this) return false;
311     width=height=0;
312     if (!ABitMap::Take(srcp)) return false;
313     width=srcp->width; height=srcp->height;
314     srcp->width=srcp->height=0;
315     return true;
316     }
317     // Extract bitmap section (true if some overlap)
318     bool GetRect(ABitMap2 *dp, int sx, int sy) const;
319     // Extract bitmap section (fill outside overlap)
320     ABitMap2 GetRect(int sx, int sy, int w, int h, bool fill=false) const {
321     ABitMap2 bm2(w, h, fill);
322     GetRect(&bm2, sx, sy);
323     return bm2;
324     }
325     // Assign bitmap section (ignores anything past edges)
326     bool AssignRect(int dx, int dy, const ABitMap2 &src);
327     // Apply operation to bitmap section
328     bool OpRect(int dx, int dy, char op, const ABitMap2 &src);
329     // Clear a rectangle
330     void ClearRect(int x, int y, int w, int h, bool clrset=false);
331     // Find the next bit matching val (scanline order)
332     bool Find(int *xp, int *yp, bool val=true) const {
333     if (!xp | !yp) return false;
334     if (width <= 0) return false;
335     if ((*xp < 0) | (*yp < 0)) *xp = *yp = 0;
336     else if (*xp >= width) { *xp=0; ++(*yp); }
337     uint32 i = ABitMap::Find(bmi(*xp,*yp), val);
338     if (i == ABMend) { *yp = height; return false; }
339     *yp = int(i / width);
340     *xp = int(i - *yp*width);
341     return true;
342     }
343     // Get bounds of assigned region
344     bool GetBoundRect(int xymin[2], int wh[2], bool val=true) const;
345     // Return value of bit in bitmap
346     bool Check(int x, int y) const {
347     return ABitMap::Check(bmi(x,y));
348     }
349     // Set bit
350     void Set(int x, int y) {
351     ABitMap::Set(bmi(x,y));
352     }
353     // Reset bit
354     void Reset(int x, int y) {
355     ABitMap::Reset(bmi(x,y));
356     }
357     // Set bit explicitly on or off
358     void Set(int x, int y, bool switchon) {
359     ABitMap::Set(bmi(x,y), switchon);
360     }
361     // Toggle bit
362     void Toggle(int x, int y) {
363     ABitMap::Toggle(bmi(x,y));
364     }
365     // Set bit if it's clear (or fail)
366     bool TestAndSet(int x, int y) {
367     return ABitMap::TestAndSet(bmi(x,y));
368     }
369     // Clear bit if it's set (or fail)
370     bool TestAndReset(int x, int y) {
371     return ABitMap::TestAndReset(bmi(x,y));
372     }
373     // Set bit on/off (fail if no change)
374     bool TestAndSet(int x, int y, bool switchon) {
375     return ABitMap::TestAndSet(bmi(x,y), switchon);
376     }
377     // Invert the entire bitmap
378     void Invert() {
379     ABitMap::Invert();
380     }
381     // Shift bitmap, filling uncovered area as indicated
382     void Shift(int dx, int dy, int fill=0);
383     // Dilate (or erode) selection by given radius
384     void Expand(double rad, bool val=true);
385     // Clear bits set in second map
386     bool ClearBitsFrom(const ABitMap2 &src) {
387     if (width != src.width)
388     return false;
389     return ABitMap::ClearBitsFrom(src);
390     }
391     // Copy operator
392     ABitMap2 & operator=(const ABitMap2 &src) {
393     ABitMap::operator=(src);
394     width=src.width; height=src.height;
395     return *this;
396     }
397     // Bitwise OR-copy operator
398     ABitMap2 & operator|=(const ABitMap2 &src) {
399     ABitMap::operator|=(src);
400     width=src.width; height=src.height;
401     return *this;
402     }
403     // Bitwise AND-assign operator
404     ABitMap2 & operator&=(const ABitMap2 &src) {
405     if ((width!=src.width)|(height!=src.height))
406     return *this;
407     ABitMap::operator&=(src);
408     return *this;
409     }
410     // Bitwise XOR-assign operator
411     ABitMap2 & operator^=(const ABitMap2 &src) {
412     if ((width!=src.width)|(height!=src.height))
413     return *this;
414     ABitMap::operator^=(src);
415     return *this;
416     }
417     // Subtraction operator, synonym for ClearBitsFrom()
418     ABitMap2 & operator-=(const ABitMap2 &src) {
419     ClearBitsFrom(src);
420     return *this;
421     }
422     // Compare two bitmaps for equality
423     bool operator==(const ABitMap2 &that) const {
424     if (width != that.width)
425     return false;
426     return ABitMap::operator==(that);
427     }
428     };
429    
430     inline bool
431     operator!=(const ABitMap2 &bm1, const ABitMap2 &bm2)
432     {
433     return !(bm1 == bm2);
434     }
435    
436     inline ABitMap2
437     operator|(ABitMap2 bmLeft, const ABitMap2 &bmRight)
438     {
439     return bmLeft |= bmRight;
440     }
441    
442     inline ABitMap2
443     operator&(ABitMap2 bmLeft, const ABitMap2 &bmRight)
444     {
445     return bmLeft &= bmRight;
446     }
447    
448     inline ABitMap2
449     operator^(ABitMap2 bmLeft, const ABitMap2 &bmRight)
450     {
451     return bmLeft ^= bmRight;
452     }
453    
454     inline ABitMap2
455     operator-(ABitMap2 bmLeft, const ABitMap2 &bmRight)
456     {
457     return bmLeft -= bmRight;
458     }
459    
460     inline ABitMap2
461     operator~(ABitMap2 bmUnary)
462     {
463     bmUnary.Invert();
464     return bmUnary;
465     }
466    
467     // Function to write a bitmap to a BMP file
468     extern bool WriteBitMap(const ABitMap &bm, const char *fname);
469    
470     // Function to write a 2-D bitmap to a BMP file
471     extern bool WriteBitMap2(const ABitMap2 &bm2, const char *fname);
472    
473     // Function to read a bitmap from a BMP file
474     extern bool ReadBitMap(ABitMap *bmp, const char *fname);
475    
476     // Function to read a 2-D bitmap from a BMP file
477     extern bool ReadBitMap2(ABitMap2 *bm2p, const char *fname);
478    
479     #endif // ! _ABITMAP_H_