BitmapToolkit Scol plugin
ScolConvert.cpp
Go to the documentation of this file.
1/*
2-----------------------------------------------------------------------------
3This source file is part of OpenSpace3D
4For the latest info, see http://www.openspace3d.com
5
6Copyright (c) 2012 I-maginer
7
8This program is free software; you can redistribute it and/or modify it under
9the terms of the GNU Lesser General Public License as published by the Free Software
10Foundation; either version 2 of the License, or (at your option) any later
11version.
12
13This program is distributed in the hope that it will be useful, but WITHOUT
14ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
15FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
16
17You should have received a copy of the GNU Lesser General Public License along with
18this program; if not, write to the Free Software Foundation, Inc., 59 Temple
19Place - Suite 330, Boston, MA 02111-1307, USA, or go to
20http://www.gnu.org/copyleft/lesser.txt
21
22-----------------------------------------------------------------------------
23*/
24
25#include <opencv2/opencv.hpp>
26#include "ScolConvert.h"
27#include "boost/thread.hpp"
28
33class ConvertBuffer
34 {
35 public:
36 ConvertBuffer(uchar* _srcBuff, void* _dstBuff, const int _width, const int _height, const int _sbpl, const int _dbpl, const int _bpp) :
37 srcBuff(_srcBuff),
38 dstBuff(_dstBuff),
39 width(_width),
40 height(_height),
41 sbpl(_sbpl),
42 abpl(0),
43 dbpl(_dbpl),
44 bpp(_bpp)
45 {}
46
47 ConvertBuffer(uchar* _srcBuff, uchar* _srcbuff8, void* _dstBuff, const int _width, const int _height, const int _sbpl, const int _abpl, const int _dbpl, const int _bpp) :
48 srcBuff(_srcBuff),
49 srcbuff8(_srcbuff8),
50 dstBuff(_dstBuff),
51 width(_width),
52 height(_height),
53 sbpl(_sbpl),
54 abpl(_abpl),
55 dbpl(_dbpl),
56 bpp(_bpp)
57 {}
58
59 uchar* srcBuff;
60 uchar* srcbuff8;
61 void* dstBuff;
62 const int width;
63 const int height;
64 const int sbpl;
65 const int abpl;
66 const int dbpl;
67 const int bpp;
68 };
69
70ConversionTools::ConversionTools()
71{
72 // Forbiden (private). Use static functions instead.
73}
74
75class bitmapToMat : public cv::ParallelLoopBody
76{
77public:
78 bitmapToMat(const ConvertBuffer _conv)
79 : conv(_conv)
80 {}
81
82 void operator()(const cv::Range& range) const
83 {
84 const int start = range.start;
85 const int end = range.end;
86 unsigned int srcByte;
87 unsigned int destByte;
88 int x, y;
89
90 for (y = start; y < end; y++)
91 {
92 for (x = 0; x < conv.width; x++)
93 {
94 srcByte = (x * conv.bpp) + (conv.sbpl * y);
95 destByte = (x * conv.bpp) + (conv.dbpl * y);
96
97 ((uchar*)conv.dstBuff)[destByte] = conv.srcBuff[srcByte];
98 if (conv.bpp == 3)
99 {
100 ((uchar*)conv.dstBuff)[destByte + 1] = conv.srcBuff[srcByte + 1];
101 ((uchar*)conv.dstBuff)[destByte + 2] = conv.srcBuff[srcByte + 2];
102 }
103 }
104 }
105 }
106
107private:
108 bitmapToMat& operator=(const bitmapToMat&); // to quiet MSVC
109
110 const ConvertBuffer conv;
111};
112
113class bitmapToMatBGR : public cv::ParallelLoopBody
114{
115public:
116 bitmapToMatBGR(const ConvertBuffer _conv)
117 : conv(_conv)
118 {}
119
120 void operator()(const cv::Range& range) const
121 {
122 const int start = range.start;
123 const int end = range.end;
124 unsigned int srcByte;
125 unsigned int destByte;
126 int x, y;
127
128 for (y = start; y < end; y++)
129 {
130 for (x = 0; x < conv.width; x++)
131 {
132 srcByte = (x * conv.bpp) + (conv.sbpl * y);
133 destByte = (x * conv.bpp) + (conv.dbpl * y);
134
135 ((uchar*)conv.dstBuff)[destByte] = conv.srcBuff[srcByte + 2];
136 ((uchar*)conv.dstBuff)[destByte + 1] = conv.srcBuff[srcByte + 1];
137 ((uchar*)conv.dstBuff)[destByte + 2] = conv.srcBuff[srcByte];
138 }
139 }
140 }
141
142private:
143 bitmapToMat& operator=(const bitmapToMat&); // to quiet MSVC
144
145 const ConvertBuffer conv;
146};
147
148class bitmapToMat4 : public cv::ParallelLoopBody
149{
150public:
151 bitmapToMat4(const ConvertBuffer _conv)
152 : conv(_conv)
153 {}
154
155 void operator()(const cv::Range& range) const
156 {
157 const int start = range.start;
158 const int end = range.end;
159 unsigned int srcByte;
160 unsigned int srcByte8;
161 unsigned int destByte;
162 int x, y;
163
164 for (y = start; y < end; y++)
165 {
166 for (x = 0; x < conv.width; x++)
167 {
168 srcByte = (x * conv.bpp) + (conv.sbpl * y);
169 destByte = (x * 4) + (conv.dbpl * y);
170 srcByte8 = x + (conv.abpl * y);
171
172 ((uchar*)conv.dstBuff)[destByte] = conv.srcBuff[srcByte];
173 ((uchar*)conv.dstBuff)[destByte + 1] = conv.srcBuff[srcByte + 1];
174 ((uchar*)conv.dstBuff)[destByte + 2] = conv.srcBuff[srcByte + 2];
175 ((uchar*)conv.dstBuff)[destByte + 3] = conv.srcbuff8[srcByte8];
176 }
177 }
178 }
179
180private:
181 bitmapToMat4& operator=(const bitmapToMat4&); // to quiet MSVC
182
183 const ConvertBuffer conv;
184};
185
186class matToBitmap4 : public cv::ParallelLoopBody
187{
188public:
189 matToBitmap4(const ConvertBuffer _conv)
190 : conv(_conv)
191 {}
192
193 void operator()(const cv::Range& range) const
194 {
195 const int start = range.start;
196 const int end = range.end;
197 unsigned int srcByte;
198 unsigned int destByte;
199 unsigned int destByte8;
200
201 int x, y;
202
203 for (y = start; y < end; y++)
204 {
205 for (x = 0; x < conv.width; x++)
206 {
207 srcByte = (x * 4) + (conv.sbpl * y);
208 destByte = (x * conv.bpp) + (conv.dbpl * y);
209 destByte8 = x + (conv.abpl * y);
210
211 ((uchar*)conv.dstBuff)[destByte] = conv.srcBuff[srcByte];
212 ((uchar*)conv.dstBuff)[destByte + 1] = conv.srcBuff[srcByte + 1];
213 ((uchar*)conv.dstBuff)[destByte + 2] = conv.srcBuff[srcByte + 2];
214 ((uchar*)conv.srcbuff8)[destByte8] = conv.srcBuff[srcByte + 3];
215 }
216 }
217 }
218
219private:
220 matToBitmap4& operator=(const matToBitmap4&); // to quiet MSVC
221
222 const ConvertBuffer conv;
223};
224
225void ConversionTools::ScolBitmapToMatRGB(PtrObjBitmap scolBitmap, cv::Mat &mat)
226{
227 if (scolBitmap == 0)
228 return;
229
230 mat = ScolBitmapToMat(scolBitmap);
231}
232
233void ConversionTools::ScolBitmapToMatRGBA(PtrObjBitmap scolBitmap, PtrObjBitmap scolBitmap8, cv::Mat &mat)
234{
235 if (scolBitmap == 0 || scolBitmap8 == 0)
236 return;
237
238 cv::Mat mrgb = ScolBitmapToMat(scolBitmap);
239 cv::Mat ma = ScolBitmapToMat(scolBitmap8);
240
241 cv::Mat inmat[] = { mrgb, ma };
242 int from_to[] = { 0,0, 1,1, 2,2, 3,3 };
243 cv::mixChannels(inmat, 2, &mat, 1, from_to, 4);
244
245 //Scol bitmap are 32bits aligned
246 /*
247 int sbpl = scolBitmap->BPL;
248 int abpl = scolBitmap8->BPL;
249 int dbpl = scolBitmap->TailleW * (scolBitmap->BytesPP + scolBitmap8->BytesPP);
250
251 ConvertBuffer conv(scolBitmap->bits, scolBitmap8->bits, mat.data, scolBitmap->TailleW, scolBitmap->TailleH, sbpl, abpl, dbpl, scolBitmap->BytesPP);
252
253 //do it parrallel
254 cv::parallel_for_(cv::Range(0, scolBitmap->TailleH), bitmapToMat4(conv));
255 */
256}
257
258void ConversionTools::MatToScolBitmapRGB(cv::Mat mat, PtrObjBitmap scolBitmap)
259{
260 if (scolBitmap == 0)
261 return;
262
263 //Scol bitmap are 32bits aligned
264 int sbpl = scolBitmap->TailleW * scolBitmap->BytesPP;
265 int dbpl = scolBitmap->BPL;
266
267 if (sbpl == dbpl)
268 memcpy(scolBitmap->bits, mat.data, scolBitmap->TailleW * scolBitmap->TailleH * scolBitmap->BytesPP);
269 else
270 {
271 ConvertBuffer conv(mat.data, scolBitmap->bits, scolBitmap->TailleW, scolBitmap->TailleH, sbpl, dbpl, scolBitmap->BytesPP);
272
273 //do it parrallel
274 cv::parallel_for_(cv::Range(0, scolBitmap->TailleH), bitmapToMat(conv));
275 }
276}
277
278void ConversionTools::MatToScolBitmapBGR(cv::Mat mat, PtrObjBitmap scolBitmap)
279{
280 if (scolBitmap == 0)
281 return;
282
283 //Scol bitmap are 32bits aligned
284 int sbpl = scolBitmap->TailleW * scolBitmap->BytesPP;
285 int dbpl = scolBitmap->BPL;
286
287#ifndef APPLE_IOS
288 if (sbpl == dbpl)
289 memcpy(scolBitmap->bits, mat.data, scolBitmap->TailleW * scolBitmap->TailleH * scolBitmap->BytesPP);
290 else
291#endif
292 {
293 ConvertBuffer conv(mat.data, scolBitmap->bits, scolBitmap->TailleW, scolBitmap->TailleH, sbpl, dbpl, scolBitmap->BytesPP);
294
295 //do it parrallel
296 cv::parallel_for_(cv::Range(0, scolBitmap->TailleH), bitmapToMatBGR(conv));
297 }
298}
299
300void ConversionTools::MatToScolBitmapRGBA(cv::Mat mat, PtrObjBitmap scolBitmap, PtrObjBitmap scolBitmap8)
301{
302 if (scolBitmap == 0 || scolBitmap8== 0)
303 return;
304
305 cv::Mat mrgb = ScolBitmapToMat(scolBitmap);
306 cv::Mat ma = ScolBitmapToMat(scolBitmap8);
307
308 // forming an array of matrices is a quite efficient operation,
309 // because the matrix data is not copied, only the headers
310 cv::Mat out[] = { mrgb, ma };
311 // bgra[0] -> bgr[2], bgra[1] -> bgr[1],
312 // bgra[2] -> bgr[0], bgra[3] -> alpha[0]
313 int from_to[] = { 0,0, 1,1, 2,2, 3,3 };
314 cv::mixChannels(&mat, 1, out, 2, from_to, 4);
315
316 //Scol bitmap are 32bits aligned
317 /*
318 int sbpl = scolBitmap->TailleW * (scolBitmap->BytesPP + scolBitmap8->BytesPP);
319 int abpl = scolBitmap8->BPL;
320 int dbpl = scolBitmap->BPL;
321
322 ConvertBuffer conv(mat.data, scolBitmap8->bits, scolBitmap->bits, scolBitmap->TailleW, scolBitmap->TailleH, sbpl, abpl, dbpl, scolBitmap->BytesPP);
323
324 //do it parrallel
325 cv::parallel_for_(cv::Range(0, scolBitmap->TailleH), matToBitmap4(conv));
326 */
327}
328
329struct BlendBuffer
330{
331 BlendBuffer(cv::Mat& mbase, const cv::Mat& mtop, float _mix)
332 {
333 base = &mbase;
334 top = mtop;
335 width = (int)mbase.cols;
336 height = (int)mbase.rows;
337 mix = MAX(MIN(_mix, 1.0f), 0.0f);
338 bpp = mbase.channels();
339 }
340
341 cv::Mat* base;
342 cv::Mat top;
343 int width;
344 int height;
345 float mix;
346 int bpp;
347};
348
349class blenderRGBA : public cv::ParallelLoopBody
350{
351public:
352 blenderRGBA(const BlendBuffer _conv)
353 : conv(_conv)
354 {}
355
356 void operator()(const cv::Range& range) const
357 {
358 const int start = range.start;
359 const int end = range.end;
360
361 if (conv.base->channels() == 4)
362 {
363 typedef cv::Vec<uchar, 4> VT;
364 cv::MatIterator_<VT> it1 = conv.base->begin<VT>() + (start * conv.width);
365 cv::MatConstIterator_<VT> it1_end = conv.base->begin<VT>() + (end * conv.width);
366 cv::MatConstIterator_<VT> it2 = conv.top.begin<VT>() + (start * conv.width);
367
368 float alpha_base;
369 float alpha_top;
370 float alpha_final;
371 VT result;
372
373 for (; it1 != it1_end; ++it1, ++it2)
374 {
375 VT pix1 = *it1;
376 VT pix2 = *it2;
377
378 // Compute Alpha values
379 alpha_base = ((float)(pix1[3])) / 255.0f;
380 alpha_top = conv.mix * ((float)(pix2[3])) / 255.0f;
381 alpha_final = alpha_top + alpha_base * (1.0f - alpha_top);
382
383 // Mix red value
384 float r_base = (pix1[0] * alpha_base) * (1.0f - alpha_top);
385 float g_base = (pix1[1] * alpha_base) * (1.0f - alpha_top);
386 float b_base = (pix1[2] * alpha_base) * (1.0f - alpha_top);
387
388 float r_top = pix2[0] * alpha_top;
389 float g_top = pix2[1] * alpha_top;
390 float b_top = pix2[2] * alpha_top;
391
392 result[0] = (uchar)((r_top + r_base) / alpha_final);
393 result[1] = (uchar)((g_top + g_base) / alpha_final);
394 result[2] = (uchar)((b_top + b_base) / alpha_final);
395 result[3] = (uchar)(alpha_final * 255.0f);
396
397 *it1 = result;
398 }
399 }
400 else if (conv.base->channels() == 3)
401 {
402 typedef cv::Vec<uchar, 3> VT;
403 cv::MatIterator_<VT> it1 = conv.base->begin<VT>() + (start * conv.width);
404 cv::MatConstIterator_<VT> it1_end = conv.base->begin<VT>() + (end * conv.width);
405 cv::MatConstIterator_<VT> it2 = conv.top.begin<VT>() + (start * conv.width);
406
407 float alpha_base;
408 float alpha_top;
409 float alpha_final;
410 VT result;
411
412 for (; it1 != it1_end; ++it1, ++it2)
413 {
414 VT pix1 = *it1;
415 VT pix2 = *it2;
416
417 // Compute Alpha values
418 alpha_base = 1.0f;
419 alpha_top = conv.mix;
420 alpha_final = alpha_top + alpha_base * (1.0f - alpha_top);
421
422 // Mix red value
423 float r_base = (pix1[0] * alpha_base) * (1.0f - alpha_top);
424 float r_top = pix2[0] * alpha_top;
425 float g_base = (pix1[1] * alpha_base) * (1.0f - alpha_top);
426 float b_base = (pix1[2] * alpha_base) * (1.0f - alpha_top);
427 float g_top = pix2[1] * alpha_top;
428 float b_top = pix2[2] * alpha_top;
429
430 result[0] = (uchar)((r_top + r_base) / alpha_final);
431 result[1] = (uchar)((g_top + g_base) / alpha_final);
432 result[2] = (uchar)((b_top + b_base) / alpha_final);
433
434 *it1 = result;
435 }
436 }
437 else
438 {
439 typedef cv::Vec<uchar, 1> VT;
440 cv::MatIterator_<VT> it1 = conv.base->begin<VT>() + (start * conv.width);
441 cv::MatConstIterator_<VT> it1_end = conv.base->begin<VT>() + (end * conv.width);
442 cv::MatConstIterator_<VT> it2 = conv.top.begin<VT>() + (start * conv.width);
443
444 float alpha_base;
445 float alpha_top;
446 float alpha_final;
447 VT result;
448
449 for (; it1 != it1_end; ++it1, ++it2)
450 {
451 VT pix1 = *it1;
452 VT pix2 = *it2;
453
454 // Compute Alpha values
455 alpha_base = 1.0f;
456 alpha_top = conv.mix;
457 alpha_final = alpha_top + alpha_base * (1.0f - alpha_top);
458
459 // Mix red value
460 float r_base = (pix1[0] * alpha_base) * (1.0f - alpha_top);
461 float r_top = pix2[0] * alpha_top;
462 result[0] = (uchar)((r_top + r_base) / alpha_final);
463
464 *it1 = result;
465 }
466 }
467 }
468
469private:
470 blenderRGBA& operator=(const blenderRGBA&);
471 const BlendBuffer conv;
472};
473
474void ConversionTools::Blend(cv::Mat& base, const cv::Mat& top, float mix)
475{
476 if (base.rows != top.rows || base.cols != top.cols)
477 return;
478
479 BlendBuffer conv(base, top, mix);
480 cv::parallel_for_(cv::Range(0, base.rows), blenderRGBA(conv));
481}
482
483
484struct BlendBufferSep
485{
486 BlendBufferSep(cv::Mat& mbase, cv::Mat& mabase, const cv::Mat& mtop, const cv::Mat& matop, float _mix)
487 {
488 base = &mbase;
489 abase = &mabase;
490 top = mtop;
491 atop = matop;
492 width = (int)mbase.cols;
493 height = (int)mbase.rows;
494 mix = MAX(MIN(_mix, 1.0f), 0.0f);
495 bpp = mbase.channels();
496 }
497
498 cv::Mat* base;
499 cv::Mat* abase;
500 cv::Mat top;
501 cv::Mat atop;
502
503 int width;
504 int height;
505 float mix;
506 int bpp;
507};
508
509class blenderRGBASep : public cv::ParallelLoopBody
510{
511public:
512 blenderRGBASep(const BlendBufferSep _conv)
513 : conv(_conv)
514 {}
515
516 void operator()(const cv::Range& range) const
517 {
518 const int start = range.start;
519 const int end = range.end;
520
521 typedef cv::Vec<uchar, 3> VT;
522 cv::MatIterator_<VT> it1 = conv.base->begin<VT>() + (start * conv.width);
523 cv::MatIterator_<uchar> it1a = conv.abase->begin<uchar>() + (start * conv.width);
524 cv::MatConstIterator_<VT> it1_end = conv.base->begin<VT>() + (end * conv.width);
525 cv::MatConstIterator_<VT> it2 = conv.top.begin<VT>() + (start * conv.width);
526 cv::MatConstIterator_<uchar> it2a = conv.atop.begin<uchar>() + (start * conv.width);
527
528 float alpha_base;
529 float alpha_top;
530 float alpha_final;
531 VT result;
532
533 for (; it1 != it1_end; ++it1, ++it2, ++it1a, ++it2a)
534 {
535 VT pix1 = *it1;
536 VT pix2 = *it2;
537 uchar pix1a = *it1a;
538 uchar pix2a = *it2a;
539
540 alpha_base = ((float)(pix1a)) / 255.0f;
541 alpha_top = conv.mix * ((float)(pix2a)) / 255.0f;
542 alpha_final = alpha_top + alpha_base * (1.0f - alpha_top);
543
544 // Mix red value
545 float r_base = (pix1[0] * alpha_base) * (1.0f - alpha_top);
546 float r_top = pix2[0] * alpha_top;
547 result[0] = (uchar)((r_top + r_base) / alpha_final);
548
549 float g_base = (pix1[1] * alpha_base) * (1.0f - alpha_top);
550 float b_base = (pix1[2] * alpha_base) * (1.0f - alpha_top);
551 float g_top = pix2[1] * alpha_top;
552 float b_top = pix2[2] * alpha_top;
553
554 result[1] = (uchar)((g_top + g_base) / alpha_final);
555 result[2] = (uchar)((b_top + b_base) / alpha_final);
556
557 *it1 = result;
558 *it1a = (uchar)(alpha_final * 255.0f);
559 }
560 }
561
562private:
563 blenderRGBASep& operator=(const blenderRGBASep&);
564 const BlendBufferSep conv;
565};
566
567void ConversionTools::Blend(cv::Mat& base, cv::Mat& abase, const cv::Mat& top, const cv::Mat& atop, float mix)
568{
569 if (base.rows != top.rows || base.cols != top.cols || abase.cols != atop.cols || abase.cols != atop.cols)
570 return;
571
572 BlendBufferSep conv(base, abase, top, atop, mix);
573 cv::parallel_for_(cv::Range(0, base.rows), blenderRGBASep(conv));
574}
575
576int ConversionTools::GetScolBitmapAlignment(int width, int nbcomponents)
577{
578 int align = width * nbcomponents;
579 if (align % 4 != 0)
580 align += 4 - (align % 4);
581
582 return align;
583}
584
585cv::Mat ConversionTools::ScolBitmapToMat(PtrObjBitmap scolBitmap)
586{
587 if (scolBitmap->bits == 0)
588 return cv::Mat();
589
590 int align = GetScolBitmapAlignment(scolBitmap->TailleW, scolBitmap->BytesPP);
591
592 int bitsType = CV_8UC3;
593 switch (scolBitmap->BytesPP)
594 {
595 case 1:
596 bitsType = CV_8UC1;
597 break;
598 case 3:
599 bitsType = CV_8UC3;
600 break;
601 case 4:
602 bitsType = CV_8UC4;
603 break;
604 default:
605 return cv::Mat();
606 }
607
608 return cv::Mat(scolBitmap->TailleH, scolBitmap->TailleW, bitsType, (void*)scolBitmap->bits, align);
609}
610
611cv::Mat ConversionTools::ScolBitmapBufferToMat(void* buffer, int width, int height, int nbcomponents, bool align)
612{
613 int align32 = GetScolBitmapAlignment(width, nbcomponents);
614
615 int bitsType = CV_8UC3;
616 switch (nbcomponents)
617 {
618 case 1:
619 bitsType = CV_8UC1;
620 break;
621 case 3:
622 bitsType = CV_8UC3;
623 break;
624 case 4:
625 bitsType = CV_8UC4;
626 break;
627 default:
628 return cv::Mat();
629 }
630
631 if (align)
632 return cv::Mat(height, width, bitsType, (void*)buffer, align32);
633 else
634 return cv::Mat(height, width, bitsType, (void*)buffer);
635}
636
637//(int dtaillew, int dtailleh, int staillew, int stailleh, int *dposx, int *dposy, int *sposx, int *sposy, int *taillew, int *tailleh)
638bool ConversionTools::ClipBitmapRect(const cv::Mat src, cv::Rect &srect, const cv::Mat dst, cv::Rect &drect)
639{
640 int swidth = src.cols;
641 int sheight = src.rows;
642 int dwidth = dst.cols;
643 int dheight = dst.rows;
644
645 if ((swidth == 0) || (sheight == 0) || (dwidth == 0) || (dheight == 0))
646 return false;
647
648 if (drect.x < 0)
649 {
650 srect.x -= drect.x;
651 srect.width += drect.x;
652 drect.width += drect.x;
653 drect.x = 0;
654 }
655 else if (drect.x >= dwidth)
656 return false;
657
658 if (drect.y < 0)
659 {
660 srect.y -= drect.y;
661 srect.height += drect.y;
662 drect.height += drect.y;
663 drect.y = 0;
664 }
665 else if (drect.y >= dheight)
666 return false;
667
668 if (srect.x < 0)
669 {
670 srect.width += srect.x;
671 drect.width += srect.x;
672 drect.x -= srect.x;
673 srect.x = 0;
674 }
675 else if (srect.x >= swidth)
676 return false;
677
678 if (srect.y < 0)
679 {
680 srect.height += srect.y;
681 drect.height += srect.y;
682 drect.y -= srect.y;
683 srect.y = 0;
684 }
685 else if (srect.y >= sheight)
686 return false;
687
688 if ((srect.width <= 0) || (drect.width <= 0))
689 return false;
690
691 if (srect.width + srect.x > swidth)
692 {
693 drect.width -= (srect.width + srect.x) - swidth;
694 srect.width -= (srect.width + srect.x) - swidth;
695 if ((srect.width <= 0) || (drect.width <= 0))
696 return false;
697 }
698
699 if (drect.width + drect.x > dwidth)
700 {
701 srect.width -= (drect.width + drect.x) - dwidth;
702 drect.width -= (drect.width + drect.x) - dwidth;
703 if ((srect.width <= 0) || (drect.width <= 0))
704 return false;
705 }
706
707 if ((srect.height <= 0) || (drect.height <= 0))
708 return false;
709
710 if (srect.height + srect.y > sheight)
711 {
712 drect.height -= (srect.height + srect.y) - sheight;
713 srect.height -= (srect.height + srect.y) - sheight;
714 if ((srect.height <= 0) || (drect.height <= 0))
715 return false;
716 }
717
718 if (drect.height + drect.y > dheight)
719 {
720 srect.height -= (drect.height + drect.y) - dheight;
721 drect.height -= (drect.height + drect.y) - dheight;
722 if ((srect.height <= 0) || (drect.height <= 0))
723 return false;
724 }
725
726 return true;
727}
static cv::Mat ScolBitmapBufferToMat(void *buffer, int width, int height, int nbcomponents, bool align=true)
static void Blend(cv::Mat &base, const cv::Mat &top, float mix)
static void ScolBitmapToMatRGBA(PtrObjBitmap scolBitmap, PtrObjBitmap scolBitmap8, cv::Mat &mat)
static cv::Mat ScolBitmapToMat(PtrObjBitmap scolBitmap)
static void ScolBitmapToMatRGB(PtrObjBitmap scolBitmap, cv::Mat &mat)
static void MatToScolBitmapBGR(cv::Mat mat, PtrObjBitmap scolBitmap)
static void MatToScolBitmapRGB(cv::Mat mat, PtrObjBitmap scolBitmap)
static bool ClipBitmapRect(const cv::Mat src, cv::Rect &srect, const cv::Mat dst, cv::Rect &drect)
static void MatToScolBitmapRGBA(cv::Mat mat, PtrObjBitmap scolBitmap, PtrObjBitmap scolBitmap8)
static int GetScolBitmapAlignment(int width, int nbcomponents)