2005-04-12 Dick Porter <dick@ximian.com>
[mono.git] / mcs / class / System.Drawing / Test / System.Drawing / TestBitmap.cs
1 //
2 // Bitmap class testing unit
3 //
4 // Author:
5 //
6 //       Jordi Mas i Hernàndez (jmas@softcatala.org>
7 //
8 // (C) 2004 Ximian, Inc.  http://www.ximian.com
9 //
10
11 //
12 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
13 //
14 // Permission is hereby granted, free of charge, to any person obtaining
15 // a copy of this software and associated documentation files (the
16 // "Software"), to deal in the Software without restriction, including
17 // without limitation the rights to use, copy, modify, merge, publish,
18 // distribute, sublicense, and/or sell copies of the Software, and to
19 // permit persons to whom the Software is furnished to do so, subject to
20 // the following conditions:
21 // 
22 // The above copyright notice and this permission notice shall be
23 // included in all copies or substantial portions of the Software.
24 // 
25 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
29 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
30 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
31 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32 //
33 using System;
34 using System.Drawing;
35 using System.Drawing.Imaging;
36 using NUnit.Framework;
37 using System.IO;
38 using System.Security.Cryptography;
39 using System.Text;
40 using System.Runtime.InteropServices;
41
42 namespace MonoTests.System.Drawing{
43
44         [TestFixture]   
45         public class TestBitmap {
46                 
47                 [TearDown]
48                 public void Clean() {}
49                 
50                 [SetUp]
51                 public void GetReady()          
52                 {
53                 
54                 }
55                         
56                 [Test]
57                 public void TestPixels() 
58                 {               
59                         // Tests GetSetPixel/SetPixel                   
60                         Bitmap bmp= new Bitmap(100,100, PixelFormat.Format32bppRgb);                                                                                    
61                         bmp.SetPixel(0,0,Color.FromArgb(255,128,128,128));                                      
62                         Color color = bmp.GetPixel(0,0);                                
63                                                 
64                         Assert.AreEqual (Color.FromArgb(255,128,128,128), color);
65                         
66                         bmp.SetPixel(99,99,Color.FromArgb(255,255,0,155));                                      
67                         Color color2 = bmp.GetPixel(99,99);                                                                             
68                         Assert.AreEqual (Color.FromArgb(255,255,0,155), color2);                        
69                 }
70                 
71                 /* Get the output directory depending on the runtime and location*/
72                 public static string getOutSubDir()
73                 {                               
74                         string sSub, sRslt;                     
75                         
76                         if (Environment.GetEnvironmentVariable("MSNet")==null)
77                                 sSub = "mono/";
78                         else
79                                 sSub = "MSNet/";                        
80                         
81                         sRslt = Path.GetFullPath (sSub);
82                                 
83                         if (Directory.Exists(sRslt) ==  false) 
84                                 sRslt = "Test/System.Drawing/" + sSub;                                                  
85                         
86                         if (sRslt.Length > 0)
87                                 if (sRslt[sRslt.Length-1] != '\\' && sRslt[sRslt.Length-1] != '/')
88                                         sRslt += "/";                                   
89                         
90                         return sRslt;
91                 }
92                 
93                 /* Get the input directory depending on the runtime*/
94                 public static string getInFile(string file)
95                 {                               
96                         string sRslt;                                           
97                         
98                         sRslt = Path.GetFullPath (file);
99                                 
100                         if (File.Exists(file)==false) 
101                                 sRslt = "Test/System.Drawing/" + file;                                                  
102                         
103                         return sRslt;
104                 }
105                 
106                 //[Test]
107                 public void MakeTransparent() 
108                 {
109                         string sInFile =   getInFile("bitmaps/maketransparent.bmp");
110                         string sOutFile =  getOutSubDir() + "transparent.bmp";
111                                                 
112                         Bitmap  bmp = new Bitmap(sInFile);
113                                         
114                         bmp.MakeTransparent();
115                         bmp.Save(sOutFile);                                                     
116                         
117                         Color color = bmp.GetPixel(1,1);                                                        
118                         Assert.AreEqual (Color.Black.R, color.R);                                                                                       
119                         Assert.AreEqual (Color.Black.G, color.G);                                                                                       
120                         Assert.AreEqual (Color.Black.B, color.B);                                                                               
121                 }
122                 
123                 [Test]
124                 public void Clone()
125                 {
126                         string sInFile = getInFile ("bitmaps/almogaver24bits.bmp");
127                         string sOutFile =  getOutSubDir() + "clone24.bmp";                      
128                         
129                         Rectangle rect = new Rectangle(0,0,50,50);                                              
130                         Bitmap  bmp = new Bitmap(sInFile);                      
131                         
132                         Bitmap bmpNew = bmp.Clone (rect, PixelFormat.Format32bppArgb);                                                                  
133                         
134                         Color colororg0 = bmp.GetPixel(0,0);            
135                         Color colororg50 = bmp.GetPixel(49,49);                                 
136                         Color colornew0 = bmpNew.GetPixel(0,0);         
137                         Color colornew50 = bmpNew.GetPixel(49,49);                              
138                         
139                         Assert.AreEqual (colororg0, colornew0);                                                                                 
140                         Assert.AreEqual (colororg50, colornew50);                               
141                 }       
142                 
143                 [Test]
144                 public void CloneImage()
145                 {
146                         string sInFile = getInFile ("bitmaps/almogaver24bits.bmp");                     
147                         Bitmap  bmp = new Bitmap(sInFile);                      
148                         
149                         Bitmap bmpNew = (Bitmap) bmp.Clone ();                  
150                         
151                         Assert.AreEqual (bmp.Width, bmpNew.Width);
152                         Assert.AreEqual (bmp.Height, bmpNew.Height);            
153                         Assert.AreEqual (bmp.PixelFormat, bmpNew.PixelFormat);
154                         
155                 }       
156
157                 [Test]
158                 public void Frames()
159                 {
160                         string sInFile = getInFile ("bitmaps/almogaver24bits.bmp");                     
161                         Bitmap  bmp = new Bitmap(sInFile);                                              
162                         int cnt = bmp.GetFrameCount(FrameDimension.Page);                       
163                         int active = bmp.SelectActiveFrame (FrameDimension.Page, 0);
164                         
165                         Assert.AreEqual (1, cnt);                                                               
166                         Assert.AreEqual (0, active);                                                                                    
167                 }
168
169                 static string ByteArrayToString(byte[] arrInput)
170                 {
171                         int i;
172                         StringBuilder sOutput = new StringBuilder(arrInput.Length);
173                         for (i=0;i < arrInput.Length -1; i++) 
174                         {
175                                 sOutput.Append(arrInput[i].ToString("X2"));
176                         }
177                         return sOutput.ToString();
178                 }
179
180
181                 public string RotateBmp (Bitmap src, RotateFlipType rotate)
182                 {                       
183                         int witdh = 150, height = 150, index = 0;                       
184                         byte[] pixels = new byte [witdh * height * 3];
185                         Bitmap bmp_rotate;
186                         byte[] hash;
187                         Color clr;
188
189
190                         bmp_rotate = src.Clone (new RectangleF (0,0, witdh, height), PixelFormat.Format32bppArgb);      
191                         bmp_rotate.RotateFlip (rotate);                 
192
193                         for (int y = 0; y < height; y++) {
194                                 for (int x = 0; x < witdh; x++) {                               
195                                         clr = bmp_rotate.GetPixel (x,y);
196                                         pixels[index++] = clr.R; pixels[index++] = clr.G; pixels[index++]  = clr.B;     
197                                 }                               
198                         }
199                 
200                         hash = new MD5CryptoServiceProvider().ComputeHash (pixels);
201                         return ByteArrayToString (hash);
202                 }
203                 
204                 
205                 /*
206                         Rotate bitmap in diffent ways, and check the result
207                         pixels using MD5
208                 */
209                 [Test]
210                 public void Rotate()
211                 {
212                         string sInFile = getInFile ("bitmaps/almogaver24bits.bmp");     
213                         Bitmap  bmp = new Bitmap(sInFile);              
214                         
215                         Assert.AreEqual ("312958A3C67402E1299413794988A3", RotateBmp (bmp, RotateFlipType.Rotate90FlipNone));   
216                         Assert.AreEqual ("BF70D8DA4F1545AEDD77D0296B47AE", RotateBmp (bmp, RotateFlipType.Rotate180FlipNone));
217                         Assert.AreEqual ("15AD2ADBDC7090C0EC744D0F7ACE2F", RotateBmp (bmp, RotateFlipType.Rotate270FlipNone));
218                         Assert.AreEqual ("2E10FEC1F4FD64ECC51D7CE68AEB18", RotateBmp (bmp, RotateFlipType.RotateNoneFlipX));
219                         Assert.AreEqual ("E63204779B566ED01162B90B49BD9E", RotateBmp (bmp, RotateFlipType.Rotate90FlipX));
220                         Assert.AreEqual ("B1ECB17B5093E13D04FF55CFCF7763", RotateBmp (bmp, RotateFlipType.Rotate180FlipX));
221                         Assert.AreEqual ("71A173882C16755D86F4BC26532374", RotateBmp (bmp, RotateFlipType.Rotate270FlipX));
222
223                 }
224                 
225                 public void LockBmp (PixelFormat fmt, PixelFormat fmtlock, string output, 
226                         int lwidth , int lheight, ref string hash1, ref string hash2)
227                 {                       
228                         int width = 100, height = 100, bbps, cur, pos;
229                         Bitmap  bmp = new Bitmap (width, height, fmt);                                                                          
230                         Graphics gr = Graphics.FromImage (bmp);                 
231                         byte[] hash;
232                         Color clr;
233                         byte[] btv = new byte[1];                                               
234                         int y, x, len = width * height * 4, index = 0;                  
235                         byte[] pixels = new byte [len];
236                         hash1 = hash2 ="";
237                         
238                         bbps = Image.GetPixelFormatSize (fmt);                  
239                                  
240                         Pen p = new Pen (Color.FromArgb (255, 100, 200, 250), 2);                               
241                         gr.DrawRectangle(p, 1.0F, 1.0F, 80.0F, 80.0F);                          
242                         
243                         BitmapData bd = bmp.LockBits (new Rectangle (0, 0, lwidth, lheight), ImageLockMode.ReadOnly,  fmtlock);
244                         
245                         pos = bd.Scan0.ToInt32();                       
246                         for (y = 0; y < bd.Height; y++) {                       
247                                 for (x = 0; x < bd.Width; x++) {
248                                         
249                                         /* Read the pixels*/
250                                         for (int bt =0; bt < bbps/8; bt++, index++) {
251                                                 cur = pos;
252                                                 cur+= y * bd.Stride;
253                                                 cur+= x * bbps/8;                                       
254                                                 cur+= bt;                                       
255                                                 Marshal.Copy ((IntPtr)cur, btv, 0, 1);
256                                                 pixels[index] = btv[0];
257                                                 
258                                                 /* Make change of all the colours = 250 to 10*/                                         
259                                                 if (btv[0] == 250) {
260                                                         btv[0] = 10;
261                                                         Marshal.Copy (btv, 0, (IntPtr)cur, 1);
262                                                 }
263                                         }
264                                 }
265                         }                                       
266                         
267                         for (int i = index; i < len; i++)
268                                 pixels[index] = 0;
269                 
270                         hash = new MD5CryptoServiceProvider().ComputeHash (pixels);                     
271                         bmp.UnlockBits (bd);                                                    
272                                                 
273                         hash1 = ByteArrayToString (hash);
274                         
275                         /* MD5 of the changed bitmap*/
276                         for (y = 0, index = 0; y < height; y++) {
277                                 for (x = 0; x < width; x++) {                           
278                                         clr = bmp.GetPixel (x,y);
279                                         pixels[index++] = clr.R; pixels[index++] = clr.G; pixels[index++]  = clr.B;     
280                                 }                               
281                         }
282                         
283                         hash = new MD5CryptoServiceProvider().ComputeHash (pixels);                                             
284                         hash2 = ByteArrayToString (hash);
285                         
286                         /*bmp.Save (output, ImageFormat.Bmp);*/
287                 }
288                 /*
289                         Tests the LockBitmap functions. Makes a hash of the block of pixels that it returns
290                         firsts, changes them, and then using GetPixel does another check of the changes.
291                         The results match the .Net framework
292                 */
293                 //[Test]
294                 public void LockBitmap ()
295                 {       
296                         string hash = "";               
297                         string hashchg = "";                            
298                                                         
299                         /* Locks the whole bitmap*/                     
300                         LockBmp (PixelFormat.Format32bppArgb, PixelFormat.Format32bppArgb, "output32bppArgb.bmp", 100, 100, ref hash, ref hashchg);                             
301                         Assert.AreEqual ("AF5BFD4E98D6708FF4C9982CC9C68F", hash);                       
302                         Assert.AreEqual ("BBEE27DC85563CB58EE11E8951230F", hashchg);                    
303                         
304                         LockBmp (PixelFormat.Format32bppPArgb, PixelFormat.Format32bppPArgb, "output32bppPArgb.bmp", 100, 100, ref hash, ref hashchg);                  
305                         Assert.AreEqual ("AF5BFD4E98D6708FF4C9982CC9C68F", hash);                       
306                         Assert.AreEqual ("BBEE27DC85563CB58EE11E8951230F", hashchg);                    
307                         
308                         LockBmp (PixelFormat.Format32bppRgb, PixelFormat.Format32bppRgb, "output32bppRgb.bmp", 100, 100, ref hash, ref hashchg);
309                         Assert.AreEqual ("AF5BFD4E98D6708FF4C9982CC9C68F", hash);                       
310                         Assert.AreEqual ("BBEE27DC85563CB58EE11E8951230F", hashchg);            
311                         
312                         LockBmp (PixelFormat.Format24bppRgb, PixelFormat.Format24bppRgb, "output24bppRgb.bmp", 100, 100, ref hash, ref hashchg);
313                         Assert.AreEqual ("A8A071D0B3A3743905B4E193A62769", hash);                       
314                         Assert.AreEqual ("EEE846FA8F892339C64082DFF775CF", hashchg);                                    
315                         
316                         /* Locks a portion of the bitmap*/              
317                         LockBmp (PixelFormat.Format32bppArgb, PixelFormat.Format32bppArgb, "output32bppArgb.bmp", 50, 50, ref hash, ref hashchg);                               
318                         Assert.AreEqual ("C361FBFD82A4F3C278605AE9EC5385", hash);                       
319                         Assert.AreEqual ("8C2C04B361E1D5875EE8ACF5073F4E", hashchg);                    
320                         
321                         LockBmp (PixelFormat.Format32bppPArgb, PixelFormat.Format32bppPArgb, "output32bppPArgb.bmp", 50, 50, ref hash, ref hashchg);                    
322                         Assert.AreEqual ("C361FBFD82A4F3C278605AE9EC5385", hash);                       
323                         Assert.AreEqual ("8C2C04B361E1D5875EE8ACF5073F4E", hashchg);                    
324                 
325                         LockBmp (PixelFormat.Format32bppRgb, PixelFormat.Format32bppRgb, "output32bppRgb.bmp", 50, 50, ref hash, ref hashchg);
326                         Assert.AreEqual ("C361FBFD82A4F3C278605AE9EC5385", hash);                       
327                         Assert.AreEqual ("8C2C04B361E1D5875EE8ACF5073F4E", hashchg);                    
328                         
329                         LockBmp (PixelFormat.Format24bppRgb, PixelFormat.Format24bppRgb, "output24bppRgb.bmp", 50, 50, ref hash, ref hashchg);
330                         Assert.AreEqual ("FFE86628478591D1A1EB30E894C34F", hash);                       
331                         Assert.AreEqual ("8C2C04B361E1D5875EE8ACF5073F4E", hashchg);                            
332                                                 
333                 }
334                 
335         }
336 }