image.cpp
Go to the documentation of this file.
1 /******************************************************************************
2  *
3  *
4  *
5  *
6  * Copyright (C) 1997-2015 by Dimitri van Heesch.
7  *
8  * Permission to use, copy, modify, and distribute this software and its
9  * documentation under the terms of the GNU General Public License is hereby
10  * granted. No representations are made about the suitability of this software
11  * for any purpose. It is provided "as is" without express or implied warranty.
12  * See the GNU General Public License for more details.
13  *
14  * Documents produced by Doxygen are derivative works derived from the
15  * input used in their production; they are not affected by this license.
16  *
17  */
18 
19 #include "image.h"
20 #include <qfile.h>
21 #include <math.h>
22 #include "lodepng.h"
23 #include "config.h"
24 
25 typedef unsigned char Byte;
26 
27 /** Helper struct representing a RGBA color */
28 struct Color
29 {
34 };
35 
36 const int charSetWidth=80;
37 const int charHeight=12;
38 const int numChars=96;
39 
40 unsigned short charPos[numChars] =
41  {
42  0, 5, 8, 13, 20, 27, 38, 47,
43  50, 54, 58, 65, 72, 76, 83, 87,
44  91, 98,105,112,119,126,133,140,
45  147,154,161,164,167,174,181,188,
46  195,207,216,224,233,242,250,258,
47  267,276,279,286,294,301,312,321,
48  331,339,349,357,365,372,380,389,
49  400,409,418,427,430,434,437,443,
50  450,453,460,467,474,481,488,492,
51  499,506,509,512,518,521,530,537,
52  544,551,557,562,568,571,578,585,
53  594,600,607,613,617,620,624,631
54  };
55 
56 unsigned char charWidth[numChars] =
57  {
58  5, 3, 5, 7, 7,11, 9, 3,
59  4, 4, 7, 7, 4, 7, 4, 4,
60 
61  7, 7, 7, 7, 7, 7, 7, 7,
62  7, 7, 3, 3, 7, 7, 7, 7,
63  12, 9, 8, 9, 9, 8, 8, 9,
64  9, 3, 7, 8, 7,11, 9,10,
65  8,10, 8, 8, 7, 8, 9,11,
66  9, 9, 9, 3, 4, 3, 6, 7,
67  3, 7, 7, 7, 7, 7, 4, 7,
68  7, 3, 3, 6, 3, 9, 7, 7,
69  7, 6, 5, 6, 3, 7, 7, 9,
70  6, 7, 6, 4, 3, 4, 7, 5
71  };
72 
73 unsigned char fontRaw[charSetWidth*charHeight] = {
74  0x02, 0x50, 0x01, 0x06, 0x20, 0x60, 0xc6, 0x04, 0x00, 0x00, 0x00, 0x27,
75  0x04, 0x1c, 0x38, 0x11, 0xf1, 0xc7, 0xc7, 0x0e, 0x00, 0x00, 0x00, 0x03,
76  0x81, 0xf0, 0x10, 0x7c, 0x1e, 0x3e, 0x1f, 0x9f, 0x87, 0x88, 0x24, 0x09,
77  0x09, 0x02, 0x02, 0x41, 0x0f, 0x0f, 0x83, 0xc3, 0xe1, 0xe7, 0xf4, 0x24,
78  0x12, 0x22, 0x41, 0x20, 0x9f, 0xce, 0x30, 0x00, 0x10, 0x04, 0x00, 0x01,
79  0x00, 0x30, 0x08, 0x12, 0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
80  0x00, 0x00, 0x00, 0x00, 0x01, 0xac, 0x00, 0x00, 0x02, 0x51, 0x43, 0x89,
81  0x40, 0x90, 0x49, 0x15, 0x00, 0x00, 0x00, 0x28, 0x9c, 0x22, 0x44, 0x31,
82  0x02, 0x20, 0x48, 0x91, 0x00, 0x00, 0x00, 0x04, 0x46, 0x08, 0x28, 0x42,
83  0x21, 0x21, 0x10, 0x10, 0x08, 0x48, 0x24, 0x09, 0x11, 0x03, 0x06, 0x61,
84  0x10, 0x88, 0x44, 0x22, 0x12, 0x10, 0x84, 0x24, 0x12, 0x22, 0x22, 0x20,
85  0x80, 0x4a, 0x11, 0x00, 0x20, 0x04, 0x00, 0x01, 0x00, 0x40, 0x08, 0x00,
86  0x41, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00,
87  0x02, 0x22, 0x00, 0x00, 0x02, 0x51, 0x45, 0x49, 0x40, 0x90, 0x89, 0x0a,
88  0x00, 0x00, 0x00, 0x48, 0x84, 0x02, 0x04, 0x51, 0x02, 0x00, 0x88, 0x91,
89  0x00, 0x00, 0x00, 0x04, 0x44, 0xd4, 0x28, 0x42, 0x40, 0x20, 0x90, 0x10,
90  0x10, 0x08, 0x24, 0x09, 0x21, 0x03, 0x06, 0x51, 0x20, 0x48, 0x48, 0x12,
91  0x12, 0x00, 0x84, 0x22, 0x22, 0x22, 0x22, 0x11, 0x00, 0x89, 0x12, 0x80,
92  0x31, 0xc5, 0x87, 0x0d, 0x1c, 0xe3, 0x4b, 0x12, 0x49, 0x29, 0x16, 0x1c,
93  0x58, 0x69, 0x4c, 0xe8, 0x91, 0x44, 0x61, 0x44, 0xf2, 0x22, 0x00, 0x00,
94  0x02, 0x07, 0xe5, 0x06, 0x80, 0x60, 0x10, 0x95, 0x08, 0x00, 0x00, 0x48,
95  0x84, 0x04, 0x18, 0x51, 0xe2, 0xc0, 0x87, 0x11, 0x24, 0x18, 0x03, 0x00,
96  0x89, 0x24, 0x44, 0x42, 0x40, 0x20, 0x90, 0x10, 0x10, 0x08, 0x24, 0x09,
97  0x41, 0x02, 0x8a, 0x51, 0x20, 0x48, 0x48, 0x12, 0x11, 0x80, 0x84, 0x22,
98  0x21, 0x24, 0x14, 0x11, 0x01, 0x09, 0x14, 0x40, 0x02, 0x26, 0x48, 0x93,
99  0x22, 0x44, 0xcc, 0x92, 0x51, 0x36, 0x99, 0x22, 0x64, 0x99, 0x92, 0x48,
100  0x91, 0x44, 0x52, 0x44, 0x12, 0x22, 0x00, 0x00, 0x02, 0x01, 0x43, 0x80,
101  0x80, 0xa0, 0x10, 0x84, 0x08, 0x00, 0x00, 0x88, 0x84, 0x08, 0x04, 0x90,
102  0x13, 0x21, 0x08, 0x8f, 0x00, 0x61, 0xf0, 0xc0, 0x8a, 0x24, 0x44, 0x7c,
103  0x40, 0x20, 0x9f, 0x9f, 0x11, 0xcf, 0xe4, 0x09, 0xc1, 0x02, 0x8a, 0x49,
104  0x20, 0x4f, 0x88, 0x13, 0xe0, 0x60, 0x84, 0x22, 0x21, 0x54, 0x08, 0x0a,
105  0x02, 0x08, 0x90, 0x00, 0x00, 0x24, 0x48, 0x11, 0x22, 0x44, 0x48, 0x92,
106  0x61, 0x24, 0x91, 0x22, 0x44, 0x89, 0x10, 0x48, 0x91, 0x24, 0x8c, 0x44,
107  0x22, 0x22, 0x64, 0x00, 0x02, 0x07, 0xe1, 0x41, 0x31, 0x14, 0x10, 0x80,
108  0x3e, 0x07, 0xc0, 0x88, 0x84, 0x10, 0x05, 0x10, 0x12, 0x21, 0x08, 0x81,
109  0x01, 0x80, 0x00, 0x31, 0x0a, 0x24, 0x7c, 0x42, 0x40, 0x20, 0x90, 0x10,
110  0x10, 0x48, 0x24, 0x09, 0x21, 0x02, 0x52, 0x45, 0x20, 0x48, 0x08, 0x92,
111  0x20, 0x10, 0x84, 0x21, 0x41, 0x54, 0x14, 0x04, 0x04, 0x08, 0x90, 0x00,
112  0x01, 0xe4, 0x48, 0x11, 0x3e, 0x44, 0x48, 0x92, 0x61, 0x24, 0x91, 0x22,
113  0x44, 0x89, 0x0c, 0x48, 0x8a, 0x24, 0x8c, 0x48, 0x44, 0x21, 0x98, 0x00,
114  0x02, 0x02, 0x85, 0x41, 0x49, 0x08, 0x10, 0x80, 0x08, 0x00, 0x00, 0x88,
115  0x84, 0x20, 0x45, 0xf9, 0x12, 0x21, 0x08, 0x81, 0x00, 0x61, 0xf0, 0xc1,
116  0x0a, 0x68, 0x82, 0x42, 0x40, 0x20, 0x90, 0x10, 0x10, 0x48, 0x24, 0x89,
117  0x11, 0x02, 0x52, 0x45, 0x20, 0x48, 0x08, 0x52, 0x12, 0x10, 0x84, 0x21,
118  0x40, 0x88, 0x22, 0x04, 0x08, 0x08, 0x90, 0x00, 0x02, 0x24, 0x48, 0x11,
119  0x20, 0x44, 0x48, 0x92, 0x51, 0x24, 0x91, 0x22, 0x44, 0x89, 0x02, 0x48,
120  0x8a, 0x2a, 0x92, 0x28, 0x42, 0x22, 0x00, 0x00, 0x00, 0x02, 0x85, 0x41,
121  0x49, 0x18, 0x10, 0x80, 0x08, 0x00, 0x01, 0x08, 0x84, 0x20, 0x44, 0x11,
122  0x12, 0x22, 0x08, 0x91, 0x00, 0x18, 0x03, 0x00, 0x09, 0xb0, 0x82, 0x42,
123  0x21, 0x21, 0x10, 0x10, 0x08, 0xc8, 0x24, 0x89, 0x09, 0x02, 0x22, 0x43,
124  0x10, 0x88, 0x04, 0x22, 0x12, 0x10, 0x84, 0x20, 0x80, 0x88, 0x22, 0x04,
125  0x10, 0x08, 0x50, 0x00, 0x02, 0x26, 0x48, 0x93, 0x22, 0x44, 0xc8, 0x92,
126  0x49, 0x24, 0x91, 0x22, 0x64, 0x99, 0x12, 0x49, 0x84, 0x11, 0x21, 0x28,
127  0x82, 0x22, 0x00, 0x00, 0x02, 0x02, 0x83, 0x82, 0x30, 0xe4, 0x10, 0x80,
128  0x00, 0x20, 0x05, 0x07, 0x04, 0x3e, 0x38, 0x10, 0xe1, 0xc2, 0x07, 0x0e,
129  0x24, 0x00, 0x00, 0x01, 0x04, 0x00, 0x82, 0x7c, 0x1e, 0x3e, 0x1f, 0x90,
130  0x07, 0x48, 0x24, 0x71, 0x05, 0xf2, 0x22, 0x41, 0x0f, 0x08, 0x03, 0xd2,
131  0x11, 0xe0, 0x83, 0xc0, 0x80, 0x88, 0x41, 0x04, 0x1f, 0xc8, 0x50, 0x00,
132  0x01, 0xd5, 0x87, 0x0d, 0x1c, 0x43, 0x48, 0x92, 0x45, 0x24, 0x91, 0x1c,
133  0x58, 0x69, 0x0c, 0x66, 0x84, 0x11, 0x21, 0x10, 0xf2, 0x22, 0x00, 0x00,
134  0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x20, 0x00, 0x00,
135  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
136  0x03, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
137  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
138  0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
139  0x00, 0x00, 0x40, 0x02, 0x00, 0x00, 0x00, 0x00, 0x40, 0x08, 0x00, 0x00,
140  0x00, 0x00, 0x00, 0x10, 0x02, 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
141  0x00, 0x00, 0x09, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
142  0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
143  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
144  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
145  0x00, 0x08, 0x10, 0x1f, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x04, 0x40, 0x02,
146  0x00, 0x00, 0x00, 0x00, 0x40, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20,
147  0x02, 0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00,
148  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
149  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
150  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
151  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x30, 0x00,
152  0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x04, 0x00, 0x00, 0x00, 0x00,
153  0x40, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x01, 0xac, 0x00, 0x00
154 };
155 
156 static Color palette[] =
157 {
158  { 0xff, 0xff, 0xff, 0x00 },
159  { 0x00, 0x00, 0x00, 0xff },
160  { 0xff, 0xff, 0xc0, 0xff },
161  { 0x9f, 0x9f, 0x60, 0xff },
162  { 0x90, 0x00, 0x00, 0xff },
163  { 0x00, 0x90, 0x00, 0xff },
164  { 0x00, 0x00, 0x90, 0xff },
165  { 0xc0, 0xc0, 0xc0, 0xff }
166 };
167 
168 // for alpha we use x^(1/1.3)
169 static Color palette2[] =
170 {
171  { 0x00, 0x00, 0x00, 0x00 },
172  { 0x00, 0x00, 0x00, 0x2e },
173  { 0x00, 0x00, 0x00, 0x48 },
174  { 0x00, 0x00, 0x00, 0x5d },
175  { 0x00, 0x00, 0x00, 0x6f },
176  { 0x00, 0x00, 0x00, 0x80 },
177  { 0x00, 0x00, 0x00, 0x8f },
178  { 0x00, 0x00, 0x00, 0x9e },
179  { 0x00, 0x00, 0x00, 0xac },
180  { 0x00, 0x00, 0x00, 0xb9 },
181  { 0x00, 0x00, 0x00, 0xc5 },
182  { 0x00, 0x00, 0x00, 0xd2 },
183  { 0x00, 0x00, 0x00, 0xdd },
184  { 0x00, 0x00, 0x00, 0xe9 },
185  { 0x00, 0x00, 0x00, 0xf4 },
186  { 0x00, 0x00, 0x00, 0xff }
187 };
188 
189 static Color palette3[] =
190 {
191  { 0xff, 0xff, 0xff, 0xff },
192  { 0xe0, 0xe0, 0xe0, 0xff },
193  { 0xd0, 0xd0, 0xd0, 0xff },
194  { 0xc0, 0xc0, 0xc0, 0xff },
195  { 0xb0, 0xb0, 0xb0, 0xff },
196  { 0xa0, 0xa0, 0xa0, 0xff },
197  { 0x90, 0x90, 0x90, 0xff },
198  { 0x80, 0x80, 0x80, 0xff },
199  { 0x70, 0x70, 0x70, 0xff },
200  { 0x60, 0x60, 0x60, 0xff },
201  { 0x50, 0x50, 0x50, 0xff },
202  { 0x40, 0x40, 0x40, 0xff },
203  { 0x30, 0x30, 0x30, 0xff },
204  { 0x20, 0x20, 0x20, 0xff },
205  { 0x10, 0x10, 0x10, 0xff },
206  { 0x00, 0x00, 0x00, 0xff }
207 };
208 
209 
210 Image::Image(int w,int h)
211 {
212  static int hue = Config_getInt("HTML_COLORSTYLE_HUE");
213  static int sat = Config_getInt("HTML_COLORSTYLE_SAT");
214  static int gamma = Config_getInt("HTML_COLORSTYLE_GAMMA");
215 
216  double red1,green1,blue1;
217  double red2,green2,blue2;
218 
219  ColoredImage::hsl2rgb(hue/360.0, // hue
220  sat/255.0, // saturation
221  pow(235/255.0,gamma/100.0), // luma (gamma corrected)
222  &red1,&green1,&blue1
223  );
224 
225  ColoredImage::hsl2rgb(hue/360.0, // hue
226  sat/255.0, // saturation
227  pow(138/255.0,gamma/100.0), // luma (gamma corrected)
228  &red2,&green2,&blue2
229  );
230 
231  palette[2].red = (int)(red1 * 255.0);
232  palette[2].green = (int)(green1 * 255.0);
233  palette[2].blue = (int)(blue1 * 255.0);
234 
235  palette[3].red = (int)(red2 * 255.0);
236  palette[3].green = (int)(green2 * 255.0);
237  palette[3].blue = (int)(blue2 * 255.0);
238 
239  data = new uchar[w*h];
240  memset(data,0,w*h);
241  width = w;
242  height = h;
243 }
244 
246 {
247  delete[] data;
248 }
249 
250 void Image::setPixel(int x,int y,uchar val)
251 {
252  if (x>=0 && x<width && y>=0 && y<height)
253  data[y*width+x] = val;
254 }
255 
256 uchar Image::getPixel(int x,int y) const
257 {
258  if (x>=0 && x<width && y>=0 && y<height)
259  return data[y*width+x];
260  else
261  return 0;
262 }
263 
264 void Image::writeChar(int x,int y,char c,uchar fg)
265 {
266  if (c>=' ')
267  {
268  int xf,yf,ci=c-' ';
269  int rowOffset=0;
270  int cw = charWidth[ci];
271  int cp = charPos[ci];
272  for (yf=0;yf<charHeight;yf++)
273  {
274  unsigned short bitPattern=0;
275  int bitsLeft=cw;
276  int byteOffset = rowOffset+(cp>>3);
277  int bitOffset = cp&7;
278  // get the bit pattern for row yf of the character from the font data
279  while (bitsLeft>0)
280  {
281  int bits=8-bitOffset;
282  if (bits>bitsLeft) bits=bitsLeft;
283  bitPattern<<=bits;
284  bitPattern|=((fontRaw[byteOffset]<<bitOffset)&0xff)>>(8-bits);
285  bitsLeft-=bits;
286  bitOffset=0;
287  byteOffset++;
288  }
289  int mask=1<<(cw-1);
290  // draw character row yf
291  for (xf=0;xf<cw;xf++)
292  {
293  setPixel(x+xf,y+yf,(bitPattern&mask) ? fg : getPixel(x+xf,y+yf));
294  mask>>=1;
295  }
296  rowOffset+=charSetWidth;
297  }
298  }
299 }
300 
301 void Image::writeString(int x,int y,const char *s,uchar fg)
302 {
303  if (s)
304  {
305  char c;
306  while ((c=*s++))
307  {
308  writeChar(x,y,c,fg);
309  x+=charWidth[c-' '];
310  }
311  }
312 }
313 
315 {
316  int w=0;
317  if (s)
318  {
319  char c;
320  while ((c=*s++)) w+=charWidth[c-' '];
321  }
322  return w;
323 }
324 
325 void Image::drawHorzLine(int y,int xs,int xe,uchar colIndex,uint mask)
326 {
327  int x,i=0,j=0;
328  for (x=xs;x<=xe;x++,j++)
329  {
330  if (j&1) i++;
331  if (mask&(1<<(i&0x1f))) setPixel(x,y,colIndex);
332  }
333 }
334 
335 void Image::drawHorzArrow(int y,int xs,int xe,uchar colIndex,uint mask)
336 {
337  drawHorzLine(y,xs,xe,colIndex,mask);
338  int i;
339  for (i=0;i<6;i++)
340  {
341  int h=i>>1;
342  drawVertLine(xe-i,y-h,y+h,colIndex,0xffffffff);
343  }
344 }
345 
346 void Image::drawVertLine(int x,int ys,int ye,uchar colIndex,uint mask)
347 {
348  int y,i=0;
349  for (y=ys;y<=ye;y++,i++)
350  {
351  if (mask&(1<<(i&0x1f))) setPixel(x,y,colIndex);
352  }
353 }
354 
355 void Image::drawVertArrow(int x,int ys,int ye,uchar colIndex,uint mask)
356 {
357  drawVertLine(x,ys,ye,colIndex,mask);
358  int i;
359  for (i=0;i<6;i++)
360  {
361  int h=i>>1;
362  drawHorzLine(ys+i,x-h,x+h,colIndex,0xffffffff);
363  }
364 }
365 
366 void Image::drawRect(int x,int y,int w,int h,uchar colIndex,uint mask)
367 {
368  drawHorzLine(y,x,x+w-1,colIndex,mask);
369  drawHorzLine(y+h-1,x,x+w-1,colIndex,mask);
370  drawVertLine(x,y,y+h-1,colIndex,mask);
371  drawVertLine(x+w-1,y,y+h-1,colIndex,mask);
372 }
373 
374 void Image::fillRect(int x,int y,int lwidth,int lheight,uchar colIndex,uint mask)
375 {
376  int xp,yp,xi,yi;
377  for (yp=y,yi=0;yp<y+lheight;yp++,yi++)
378  for (xp=x,xi=0;xp<x+lwidth;xp++,xi++)
379  if (mask&(1<<((xi+yi)&0x1f)))
380  setPixel(xp,yp,colIndex);
381 }
382 
383 bool Image::save(const char *fileName,int mode)
384 {
385 #if 0
386  GifEncoder gifenc(data,
387  mode==0 ? palette : palette2,
388  width,height,
389  mode==0 ? 3 : 4,
390  0);
391  QFile file(fileName);
392  if (file.open(IO_WriteOnly))
393  {
394  gifenc.writeGIF(file);
395  return TRUE;
396  }
397  else
398  {
399  return FALSE;
400  }
401 #endif
402  static bool useTransparency = Config_getBool("FORMULA_TRANSPARENT");
403  uchar* buffer;
404  size_t bufferSize;
406  LodePNG_Encoder_init(&encoder);
407  int numCols = mode==0 ? 8 : 16;
408  Color *pPal = mode==0 ? palette :
409  useTransparency ? palette2 :
410  palette3 ;
411  int i;
412  for (i=0;i<numCols;i++,pPal++)
413  {
415  pPal->red,pPal->green,pPal->blue,pPal->alpha);
416  }
417  encoder.infoPng.color.colorType = 3;
418  encoder.infoRaw.color.colorType = 3;
419  LodePNG_encode(&encoder, &buffer, &bufferSize, data, width, height);
420  LodePNG_saveFile(buffer, bufferSize, fileName);
421  free(buffer);
422  LodePNG_Encoder_cleanup(&encoder);
423  return TRUE;
424 }
425 
426 //----------------------------------------------------------------
427 
428 void ColoredImage::hsl2rgb(double h,double s,double l,
429  double *pRed,double *pGreen,double *pBlue)
430 {
431  double v;
432  double r,g,b;
433 
434  r = l; // default to gray
435  g = l;
436  b = l;
437  v = (l <= 0.5) ? (l * (1.0 + s)) : (l + s - l * s);
438  if (v > 0)
439  {
440  double m;
441  double sv;
442  int sextant;
443  double fract, vsf, mid1, mid2;
444 
445  m = l + l - v;
446  sv = (v - m ) / v;
447  h *= 6.0;
448  sextant = (int)h;
449  fract = h - sextant;
450  vsf = v * sv * fract;
451  mid1 = m + vsf;
452  mid2 = v - vsf;
453  switch (sextant)
454  {
455  case 0:
456  r = v;
457  g = mid1;
458  b = m;
459  break;
460  case 1:
461  r = mid2;
462  g = v;
463  b = m;
464  break;
465  case 2:
466  r = m;
467  g = v;
468  b = mid1;
469  break;
470  case 3:
471  r = m;
472  g = mid2;
473  b = v;
474  break;
475  case 4:
476  r = mid1;
477  g = m;
478  b = v;
479  break;
480  case 5:
481  r = v;
482  g = m;
483  b = mid2;
484  break;
485  }
486  }
487  *pRed = r;
488  *pGreen = g;
489  *pBlue = b;
490 }
491 
492 ColoredImage::ColoredImage(int width,int height,
493  const uchar *greyLevels,const uchar *alphaLevels,
494  int saturation,int hue,int gamma)
495 {
496  m_hasAlpha = alphaLevels!=0;
497  m_width = width;
498  m_height = height;
499  m_data = (uchar*)malloc(width*height*4);
500  int i;
501  for (i=0;i<width*height;i++)
502  {
503  uchar r,g,b,a;
504  double red,green,blue;
505  hsl2rgb(hue/360.0, // hue
506  saturation/255.0, // saturation
507  pow(greyLevels[i]/255.0,gamma/100.0), // luma (gamma corrected)
508  &red,&green,&blue);
509  r = (int)(red *255.0);
510  g = (int)(green*255.0);
511  b = (int)(blue *255.0);
512  a = alphaLevels ? alphaLevels[i] : 255;
513  m_data[i*4+0]=r;
514  m_data[i*4+1]=g;
515  m_data[i*4+2]=b;
516  m_data[i*4+3]=a;
517  }
518 }
519 
521 {
522  free(m_data);
523 }
524 
525 bool ColoredImage::save(const char *fileName)
526 {
527  uchar *buffer;
528  size_t bufferSize;
530  LodePNG_Encoder_init(&encoder);
531  encoder.infoPng.color.colorType = m_hasAlpha ? 6 : 2; // 2=RGB 24 bit, 6=RGBA 32 bit
532  encoder.infoRaw.color.colorType = 6; // 6=RGBA 32 bit
533  LodePNG_encode(&encoder, &buffer, &bufferSize, m_data, m_width, m_height);
534  LodePNG_saveFile(buffer, bufferSize, fileName);
535  LodePNG_Encoder_cleanup(&encoder);
536  free(buffer);
537  return TRUE;
538 }
539 
540 
unsigned char fontRaw[charSetWidth *charHeight]
Definition: image.cpp:73
unsigned short charPos[numChars]
Definition: image.cpp:40
void writeChar(int x, int y, char c, uchar fg)
Definition: image.cpp:264
void fillRect(int x, int y, int width, int height, uchar colIndex, uint mask)
Definition: image.cpp:374
~ColoredImage()
Definition: image.cpp:520
void setPixel(int x, int y, uchar val)
Definition: image.cpp:250
~Image()
Definition: image.cpp:245
unsigned colorType
Definition: lodepng.h:127
LodePNG_InfoRaw infoRaw
Definition: lodepng.h:342
static constexpr double g
Definition: Units.h:144
#define IO_WriteOnly
Definition: qiodevice.h:62
LodePNG_InfoColor color
Definition: lodepng.h:225
Byte blue
Definition: image.cpp:32
void drawHorzArrow(int y, int xs, int xe, uchar colIndex, uint mask)
Definition: image.cpp:335
bool save(const char *fileName)
Definition: image.cpp:525
void drawHorzLine(int y, int xs, int xe, uchar colIndex, uint mask)
Definition: image.cpp:325
constexpr T pow(T x)
Definition: pow.h:72
Byte red
Definition: image.cpp:30
friend uint stringLength(const char *s)
Definition: image.cpp:314
const bool FALSE
Definition: qglobal.h:370
void LodePNG_Encoder_init(LodePNG_Encoder *encoder)
Definition: lodepng.cpp:4076
static void hsl2rgb(double h, double s, double l, double *pRed, double *pGreen, double *pBlue)
Definition: image.cpp:428
Byte green
Definition: image.cpp:31
unsigned char charWidth[numChars]
Definition: image.cpp:56
Definition: image.cpp:28
void LodePNG_encode(LodePNG_Encoder *encoder, unsigned char **out, size_t *outsize, const unsigned char *image, unsigned w, unsigned h)
Definition: lodepng.cpp:3910
bool save(const char *fileName, int mode=0)
Definition: image.cpp:383
static QStrList * l
Definition: config.cpp:1044
const int numChars
Definition: image.cpp:38
unsigned char uchar
Definition: nybbler.cc:11
void writeString(int x, int y, const char *s, uchar fg)
Definition: image.cpp:301
#define Config_getInt(val)
Definition: config.cpp:661
ColoredImage(int width, int height, const uchar *greyLevels, const uchar *alphaLevels, int saturation, int hue, int gamma)
Definition: image.cpp:492
unsigned LodePNG_InfoColor_addPalette(LodePNG_InfoColor *info, unsigned char r, unsigned char g, unsigned char b, unsigned char a)
Definition: lodepng.cpp:2046
unsigned char Byte
Definition: image.cpp:25
fileName
Definition: dumpTree.py:9
const int charHeight
Definition: image.cpp:37
void LodePNG_Encoder_cleanup(LodePNG_Encoder *encoder)
Definition: lodepng.cpp:4084
const double a
bool open(int)
Definition: qfile_unix.cpp:134
LodePNG_InfoColor color
Definition: lodepng.h:266
void drawRect(int x, int y, int width, int height, uchar colIndex, uint mask)
Definition: image.cpp:366
static Color palette3[]
Definition: image.cpp:189
static Color palette2[]
Definition: image.cpp:169
#define Config_getBool(val)
Definition: config.cpp:664
double gamma(double KE, const simb::MCParticle *part)
unsigned LodePNG_saveFile(const unsigned char *buffer, size_t buffersize, const char *filename)
Definition: lodepng.cpp:4141
The QFile class is an I/O device that operates on files.
Definition: qfile.h:50
LodePNG_InfoPng infoPng
Definition: lodepng.h:341
const int charSetWidth
Definition: image.cpp:36
Byte alpha
Definition: image.cpp:33
Image(int w, int h)
Definition: image.cpp:210
void drawVertArrow(int x, int ys, int ye, uchar colIndex, uint mask)
Definition: image.cpp:355
static Color palette[]
Definition: image.cpp:156
static bool * b
Definition: config.cpp:1043
void drawVertLine(int x, int ys, int ye, uchar colIndex, uint mask)
Definition: image.cpp:346
list x
Definition: train.py:276
static constexpr double ys
Definition: Units.h:103
unsigned uint
Definition: qglobal.h:351
static QCString * s
Definition: config.cpp:1042
static QFile::EncoderFn encoder
Definition: qfile.cpp:470
const bool TRUE
Definition: qglobal.h:371
uchar getPixel(int x, int y) const
Definition: image.cpp:256
void hsl2rgb(double h, double s, double l, double *pRed, double *pGreen, double *pBlue)
Definition: wizard.cpp:211