Logo
  • Main Page
  • Related Pages
  • Modules
  • Classes
  • Files

mmsfbconv.cpp

Go to the documentation of this file.
00001 /***************************************************************************
00002  *   Copyright (C) 2005-2007 Stefan Schwarzer, Jens Schneider,             *
00003  *                           Matthias Hardt, Guido Madaus                  *
00004  *                                                                         *
00005  *   Copyright (C) 2007-2008 BerLinux Solutions GbR                        *
00006  *                           Stefan Schwarzer & Guido Madaus               *
00007  *                                                                         *
00008  *   Copyright (C) 2009-2013 BerLinux Solutions GmbH                       *
00009  *                                                                         *
00010  *   Authors:                                                              *
00011  *      Stefan Schwarzer   <stefan.schwarzer@diskohq.org>,                 *
00012  *      Matthias Hardt     <matthias.hardt@diskohq.org>,                   *
00013  *      Jens Schneider     <jens.schneider@diskohq.org>,                   *
00014  *      Guido Madaus       <guido.madaus@diskohq.org>,                     *
00015  *      Patrick Helterhoff <patrick.helterhoff@diskohq.org>,               *
00016  *      René Bählkow       <rene.baehlkow@diskohq.org>                     *
00017  *                                                                         *
00018  *   This library is free software; you can redistribute it and/or         *
00019  *   modify it under the terms of the GNU Lesser General Public            *
00020  *   License version 2.1 as published by the Free Software Foundation.     *
00021  *                                                                         *
00022  *   This library is distributed in the hope that it will be useful,       *
00023  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
00024  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU     *
00025  *   Lesser General Public License for more details.                       *
00026  *                                                                         *
00027  *   You should have received a copy of the GNU Lesser General Public      *
00028  *   License along with this library; if not, write to the                 *
00029  *   Free Software Foundation, Inc.,                                       *
00030  *   51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA            *
00031  **************************************************************************/
00032 
00033 #include "mmsgui/fb/mmsfbconv.h"
00034 #include <string.h>
00035 
00036 void stretch_byte_buffer_no_antialiasing(unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00037                                          unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00038     // please note that the src and dst have to point to the first pixel which is to process
00039     int horifact = (dw<<16)/sw;
00040     int vertfact = (dh<<16)/sh;
00041     int vertcnt;
00042     unsigned char *src_end = src + src_pitch_pix * sh;
00043     if (src_end > src + src_pitch_pix * src_height)
00044         src_end = src + src_pitch_pix * src_height;
00045     unsigned char *dst_end = dst + dst_pitch_pix * dst_height;
00046 
00047     // no antialiasing
00048     if (horifact == 0x10000) {
00049         // no horizontal stretch needed, so use optimized loop
00050         vertcnt = 0x8000;
00051         while ((src < src_end)&&(dst < dst_end)) {
00052             // for all pixels in the line
00053             vertcnt+=vertfact;
00054             if (vertcnt & 0xffff0000) {
00055                 do {
00056                     memcpy(dst, src, sw);
00057                     vertcnt-=0x10000;
00058                     dst = dst + dst_pitch;
00059                 } while (vertcnt & 0xffff0000);
00060             }
00061             // next line
00062             src+=src_pitch;
00063         }
00064     }
00065     if (horifact == 0x20000) {
00066         // duplicate each horizontal pixel
00067         vertcnt = 0x8000;
00068         while ((src < src_end)&&(dst < dst_end)) {
00069             // for all pixels in the line
00070             vertcnt+=vertfact;
00071             if (vertcnt & 0xffff0000) {
00072                 unsigned char *line_end = src + sw;
00073                 unsigned char *old_dst = dst;
00074 
00075                 do {
00076                     //int horicnt = 0x8000;
00077                     while (src < line_end) {
00078                         register unsigned short int SRC  = *src;
00079                         *((unsigned short int *)dst) = SRC | (SRC << 8);
00080                         dst+=2;
00081                         src++;
00082                     }
00083                     src-=sw;
00084                     vertcnt-=0x10000;
00085                     dst = old_dst +  dst_pitch;
00086                     old_dst = dst;
00087                 } while (vertcnt & 0xffff0000);
00088             }
00089 
00090             // next line
00091             src+=src_pitch;
00092         }
00093     }
00094     else {
00095         // normal stretch in both directions
00096         vertcnt = 0x8000;
00097         while ((src < src_end)&&(dst < dst_end)) {
00098             // for all pixels in the line
00099             vertcnt+=vertfact;
00100             if (vertcnt & 0xffff0000) {
00101                 unsigned char *line_end = src + sw;
00102                 unsigned char *old_dst = dst;
00103 
00104                 do {
00105                     int horicnt = 0x8000;
00106                     while (src < line_end) {
00107                         horicnt+=horifact;
00108                         if (horicnt & 0xffff0000) {
00109                             register unsigned char SRC  = *src;
00110 
00111                             do {
00112                                 *dst = SRC;
00113                                 dst++;
00114                                 horicnt-=0x10000;
00115                             } while (horicnt & 0xffff0000);
00116                         }
00117 
00118                         src++;
00119                     }
00120                     src-=sw;
00121                     vertcnt-=0x10000;
00122                     dst = old_dst +  dst_pitch;
00123                     old_dst = dst;
00124                 } while (vertcnt & 0xffff0000);
00125             }
00126 
00127             // next line
00128             src+=src_pitch;
00129         }
00130     }
00131 }
00132 
00133 void stretch_byte_buffer_v_antialiasing(unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00134                                         unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00135     // please note that the src and dst have to point to the first pixel which is to process
00136     int horifact = (dw<<16)/sw;
00137     int vertfact = (dh<<16)/sh;
00138     int vertcnt;
00139     unsigned char *src_end = src + src_pitch_pix * sh;
00140     if (src_end > src + src_pitch_pix * src_height)
00141         src_end = src + src_pitch_pix * src_height;
00142     unsigned char *dst_end = dst + dst_pitch_pix * dst_height;
00143 
00144     // vertical antialiasing
00145     if (vertfact >= 0x10000) {
00146         // positive vertical stretch (scale up)
00147         if (horifact == 0x10000) {
00148             // no horizontal stretch needed, so use optimized loop
00149             vertcnt = 0x8000;
00150             register unsigned char vcnt = 0;
00151             while ((src < src_end)&&(dst < dst_end)) {
00152                 // for all pixels in the line
00153                 vertcnt+=vertfact;
00154                 if (vertcnt & 0xffff0000) {
00155                     unsigned char *line_end = src + sw;
00156 
00157                     bool vaa = (vcnt > 1);
00158                     vcnt = 0;
00159                     if (!vaa) {
00160                         // line without vertical antialiasing
00161                         do {
00162                             memcpy(dst, src, sw);
00163                             vertcnt-=0x10000;
00164                             dst = dst + dst_pitch;
00165                             vcnt++;
00166                         } while (vertcnt & 0xffff0000);
00167                     }
00168                     else {
00169                         unsigned char *old_dst = dst;
00170                         do {
00171                             if (vaa) {
00172                                 // first line with vertical antialiasing
00173                                 register unsigned int SRC;
00174                                 while (src < line_end) {
00175                                     // load pixel
00176                                     SRC = *src;
00177 
00178                                     // put first pixel
00179                                     *dst = SRC;
00180                                     *(dst-dst_pitch) = (*(dst-dst_pitch) + SRC) >> 1;
00181                                     dst++;
00182 
00183                                     src++;
00184                                 }
00185                                 src-=sw;
00186                             }
00187                             else {
00188                                 // next line without vertical antialiasing
00189                                 memcpy(dst, src, sw);
00190                             }
00191                             vertcnt-=0x10000;
00192                             dst = old_dst + dst_pitch;
00193                             old_dst = dst;
00194                             vcnt++;
00195                             vaa = false;
00196                         } while (vertcnt & 0xffff0000);
00197                     }
00198                 }
00199 
00200                 // next line
00201                 src+=src_pitch;
00202             }
00203         }
00204         else {
00205             // normal stretch in both directions
00206             vertcnt = 0x8000;
00207             register unsigned char vcnt = 0;
00208             while ((src < src_end)&&(dst < dst_end)) {
00209                 // for all pixels in the line
00210                 vertcnt+=vertfact;
00211                 if (vertcnt & 0xffff0000) {
00212                     unsigned char *line_end = src + sw;
00213                     unsigned char *old_dst = dst;
00214 
00215                     bool vaa = (vcnt > 1);
00216                     vcnt = 0;
00217                     if (!vaa) {
00218                         do {
00219                             int horicnt = 0x8000;
00220                             register unsigned int SRC;
00221                             while (src < line_end) {
00222                                 horicnt+=horifact;
00223                                 if (horicnt & 0xffff0000) {
00224                                     // load pixel
00225                                     SRC = *src;
00226 
00227                                     // put first pixel
00228                                     *dst = SRC;
00229                                     dst++;
00230                                     horicnt-=0x10000;
00231 
00232                                     // have to put further?
00233                                     if (horicnt & 0xffff0000) {
00234                                         do {
00235                                             *dst = SRC;
00236                                             dst++;
00237                                             horicnt-=0x10000;
00238                                         } while (horicnt & 0xffff0000);
00239                                     }
00240                                 }
00241 
00242                                 src++;
00243                             }
00244                             src-=sw;
00245                             vertcnt-=0x10000;
00246                             dst = old_dst + dst_pitch;
00247                             old_dst = dst;
00248                             vcnt++;
00249                         } while (vertcnt & 0xffff0000);
00250                     }
00251                     else {
00252                         do {
00253                             int horicnt = 0x8000;
00254                             register unsigned int SRC;
00255                             if (vaa) {
00256                                 // first line with vertical antialiasing
00257                                 while (src < line_end) {
00258                                     horicnt+=horifact;
00259                                     if (horicnt & 0xffff0000) {
00260                                         // load pixel
00261                                         SRC = *src;
00262 
00263                                         // put first pixel
00264                                         *dst = SRC;
00265                                         *(dst-dst_pitch) = (*(dst-dst_pitch) + SRC) >> 1;
00266                                         dst++;
00267                                         horicnt-=0x10000;
00268 
00269                                         // have to put further?
00270                                         if (horicnt & 0xffff0000) {
00271                                             do {
00272                                                 *dst = SRC;
00273                                                 *(dst-dst_pitch) = (*(dst-dst_pitch) + SRC) >> 1;
00274                                                 dst++;
00275                                                 horicnt-=0x10000;
00276                                             } while (horicnt & 0xffff0000);
00277                                         }
00278                                     }
00279 
00280                                     src++;
00281                                 }
00282                             }
00283                             else {
00284                                 // next line without vertical antialiasing
00285                                 while (src < line_end) {
00286                                     horicnt+=horifact;
00287                                     if (horicnt & 0xffff0000) {
00288                                         // load pixel
00289                                         SRC = *src;
00290 
00291                                         // put first pixel
00292                                         *dst = SRC;
00293                                         dst++;
00294                                         horicnt-=0x10000;
00295 
00296                                         // have to put further?
00297                                         if (horicnt & 0xffff0000) {
00298                                             do {
00299                                                 *dst = SRC;
00300                                                 dst++;
00301                                                 horicnt-=0x10000;
00302                                             } while (horicnt & 0xffff0000);
00303                                         }
00304                                     }
00305 
00306                                     src++;
00307                                 }
00308                             }
00309                             src-=sw;
00310                             vertcnt-=0x10000;
00311                             dst = old_dst + dst_pitch;
00312                             old_dst = dst;
00313                             vcnt++;
00314                             vaa = false;
00315                         } while (vertcnt & 0xffff0000);
00316                     }
00317                 }
00318 
00319                 // next line
00320                 src+=src_pitch;
00321             }
00322         }
00323     }
00324     else {
00325         // negative vertical stretch (scale down)
00326         if (horifact == 0x10000) {
00327             // no horizontal stretch needed, so use optimized loop
00328             vertcnt = 0x8000;
00329             bool vaa = false;
00330             while ((src < src_end)&&(dst < dst_end)) {
00331                 // for all pixels in the line
00332                 vertcnt+=vertfact;
00333                 if (vertcnt & 0xffff0000) {
00334                     unsigned char *line_end = src + sw;
00335 
00336                     if (!vaa) {
00337                         // line without vertical antialiasing
00338                         memcpy(dst, src, sw);
00339                         vertcnt-=0x10000;
00340                         dst = dst + dst_pitch;
00341                     }
00342                     else {
00343                         // line with vertical antialiasing
00344                         unsigned char *old_dst = dst;
00345                         while (src < line_end) {
00346                             // put pixel with arithmetic mean
00347                             *dst = (*(src-src_pitch) + *src) >> 1;
00348                             dst++;
00349                             src++;
00350                         }
00351                         src-=sw;
00352                         vertcnt-=0x10000;
00353                         dst = old_dst + dst_pitch;
00354                         vaa = false;
00355                     }
00356                 }
00357                 else
00358                     vaa = true;
00359 
00360                 // next line
00361                 src+=src_pitch;
00362             }
00363         }
00364         else {
00365             // normal stretch in both directions
00366             vertcnt = 0x8000;
00367             bool vaa = false;
00368             while ((src < src_end)&&(dst < dst_end)) {
00369                 // for all pixels in the line
00370                 vertcnt+=vertfact;
00371                 if (vertcnt & 0xffff0000) {
00372                     unsigned char *line_end = src + sw;
00373                     unsigned char *old_dst = dst;
00374 
00375                     if (!vaa) {
00376                         // line without vertical antialiasing
00377                         int horicnt = 0x8000;
00378                         register unsigned int SRC;
00379                         while (src < line_end) {
00380                             horicnt+=horifact;
00381                             if (horicnt & 0xffff0000) {
00382                                 // load pixel
00383                                 SRC = *src;
00384 
00385                                 // put first pixel
00386                                 *dst = SRC;
00387                                 dst++;
00388                                 horicnt-=0x10000;
00389 
00390                                 // have to put further?
00391                                 if (horicnt & 0xffff0000) {
00392                                     do {
00393                                         *dst = SRC;
00394                                         dst++;
00395                                         horicnt-=0x10000;
00396                                     } while (horicnt & 0xffff0000);
00397                                 }
00398                             }
00399 
00400                             src++;
00401                         }
00402                         src-=sw;
00403                         vertcnt-=0x10000;
00404                         dst = old_dst + dst_pitch;
00405                         old_dst = dst;
00406                     }
00407                     else {
00408                         // line with vertical antialiasing
00409                         int horicnt = 0x8000;
00410                         register unsigned int SRC;
00411                         while (src < line_end) {
00412                             horicnt+=horifact;
00413                             if (horicnt & 0xffff0000) {
00414                                 // load pixel (arithmetic mean)
00415                                 SRC = (*(src-src_pitch) + *src) >> 1;
00416 
00417                                 // put first pixel
00418                                 *dst = SRC;
00419                                 dst++;
00420                                 horicnt-=0x10000;
00421 
00422                                 // have to put further?
00423                                 if (horicnt & 0xffff0000) {
00424                                     do {
00425                                         *dst = SRC;
00426                                         dst++;
00427                                         horicnt-=0x10000;
00428                                     } while (horicnt & 0xffff0000);
00429                                 }
00430                             }
00431 
00432                             src++;
00433                         }
00434                         src-=sw;
00435                         vertcnt-=0x10000;
00436                         dst = old_dst + dst_pitch;
00437                         old_dst = dst;
00438                         vaa = false;
00439                     }
00440                 }
00441                 else
00442                     vaa = true;
00443 
00444                 // next line
00445                 src+=src_pitch;
00446             }
00447         }
00448     }
00449 }
00450 
00451 void stretch_byte_buffer_h_antialiasing(unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00452                                         unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00453     // please note that the src and dst have to point to the first pixel which is to process
00454     int horifact = (dw<<16)/sw;
00455     int vertfact = (dh<<16)/sh;
00456     int vertcnt;
00457     unsigned char *src_end = src + src_pitch_pix * sh;
00458     if (src_end > src + src_pitch_pix * src_height)
00459         src_end = src + src_pitch_pix * src_height;
00460     unsigned char *dst_end = dst + dst_pitch_pix * dst_height;
00461 
00462     // horizontal antialiasing
00463     // normal stretch in both directions
00464     vertcnt = 0x8000;
00465     while ((src < src_end)&&(dst < dst_end)) {
00466         // for all pixels in the line
00467         vertcnt+=vertfact;
00468         if (vertcnt & 0xffff0000) {
00469             unsigned char *line_end = src + sw;
00470             unsigned char *old_dst = dst;
00471 
00472             do {
00473                 int horicnt = 0x8000;
00474                 register unsigned int SRC;
00475                 register bool haa = false;
00476                 while (src < line_end) {
00477                     horicnt+=horifact;
00478                     if (horicnt & 0xffff0000) {
00479                         // check for antialiasing
00480                         if (haa) {
00481                             *(dst-1) = (SRC + *src) >> 1;
00482                             haa = false;
00483                         }
00484 
00485                         // load pixel
00486                         SRC = *src;
00487 
00488                         // put first pixel
00489                         *dst = SRC;
00490                         dst++;
00491                         horicnt-=0x10000;
00492 
00493                         // have to put further?
00494                         if ((haa=(horicnt & 0xffff0000))) {
00495                             do {
00496                                 *dst = SRC;
00497                                 dst++;
00498                                 horicnt-=0x10000;
00499                             } while (horicnt & 0xffff0000);
00500                         }
00501                     }
00502 
00503                     src++;
00504                 }
00505                 src-=sw;
00506                 vertcnt-=0x10000;
00507                 dst = old_dst + dst_pitch;
00508                 old_dst = dst;
00509             } while (vertcnt & 0xffff0000);
00510         }
00511 
00512         // next line
00513         src+=src_pitch;
00514     }
00515 }
00516 
00517 void stretch_byte_buffer_hv_antialiasing(unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00518                                          unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00519     // please note that the src and dst have to point to the first pixel which is to process
00520     int horifact = (dw<<16)/sw;
00521     int vertfact = (dh<<16)/sh;
00522     int vertcnt;
00523     unsigned char *src_end = src + src_pitch_pix * sh;
00524     if (src_end > src + src_pitch_pix * src_height)
00525         src_end = src + src_pitch_pix * src_height;
00526     unsigned char *dst_end = dst + dst_pitch_pix * dst_height;
00527 
00528     // horizontal and vertical antialiasing
00529     // normal stretch in both directions
00530     vertcnt = 0x8000;
00531     register unsigned char vcnt = 0;
00532     while ((src < src_end)&&(dst < dst_end)) {
00533         // for all pixels in the line
00534         vertcnt+=vertfact;
00535         if (vertcnt & 0xffff0000) {
00536             unsigned char *line_end = src + sw;
00537             unsigned char *old_dst = dst;
00538 
00539             bool vaa = (vcnt > 1);
00540             vcnt = 0;
00541             if (!vaa) {
00542                 do {
00543                     int horicnt = 0x8000;
00544                     register unsigned int SRC;
00545                     register bool haa = false;
00546                     while (src < line_end) {
00547                         horicnt+=horifact;
00548                         if (horicnt & 0xffff0000) {
00549                             // check for antialiasing
00550                             if (haa) {
00551                                 *(dst-1) = (SRC + *src) >> 1;
00552                                 haa = false;
00553                             }
00554 
00555                             // load pixel
00556                             SRC = *src;
00557 
00558                             // put first pixel
00559                             *dst = SRC;
00560                             dst++;
00561                             horicnt-=0x10000;
00562 
00563                             // have to put further?
00564                             if ((haa=(horicnt & 0xffff0000))) {
00565                                 do {
00566                                     *dst = SRC;
00567                                     dst++;
00568                                     horicnt-=0x10000;
00569                                 } while (horicnt & 0xffff0000);
00570                             }
00571                         }
00572 
00573                         src++;
00574                     }
00575                     src-=sw;
00576                     vertcnt-=0x10000;
00577                     dst = old_dst + dst_pitch;
00578                     old_dst = dst;
00579                     vcnt++;
00580                 } while (vertcnt & 0xffff0000);
00581             }
00582             else {
00583                 do {
00584                     int horicnt = 0x8000;
00585                     register unsigned int SRC;
00586                     if (vaa) {
00587                         // first line with vertical antialiasing
00588                         register bool haa = false;
00589                         while (src < line_end) {
00590                             horicnt+=horifact;
00591                             if (horicnt & 0xffff0000) {
00592                                 // check for antialiasing
00593                                 if (haa) {
00594                                     *(dst-1) = (SRC + *src) >> 1;
00595                                     haa = false;
00596                                 }
00597 
00598                                 // load pixel
00599                                 SRC = *src;
00600 
00601                                 // put first pixel
00602                                 *dst = SRC;
00603                                 *(dst-dst_pitch) = (*(dst-dst_pitch) + SRC) >> 1;
00604                                 dst++;
00605                                 horicnt-=0x10000;
00606 
00607                                 // have to put further?
00608                                 if ((haa=(horicnt & 0xffff0000))) {
00609                                     do {
00610                                         *dst = SRC;
00611                                         *(dst-dst_pitch) = (*(dst-dst_pitch) + SRC) >> 1;
00612                                         dst++;
00613                                         horicnt-=0x10000;
00614                                     } while (horicnt & 0xffff0000);
00615                                 }
00616                             }
00617 
00618                             src++;
00619                         }
00620 
00621                         vaa = false;
00622                     }
00623                     else {
00624                         // line without vertical antialiasing
00625                         register bool haa = false;
00626                         while (src < line_end) {
00627                             horicnt+=horifact;
00628                             if (horicnt & 0xffff0000) {
00629                                 // check for antialiasing
00630                                 if (haa) {
00631                                     *(dst-1) = (SRC + *src) >> 1;
00632                                     haa = false;
00633                                 }
00634 
00635                                 // load pixel
00636                                 SRC = *src;
00637 
00638                                 // put first pixel
00639                                 *dst = SRC;
00640                                 dst++;
00641                                 horicnt-=0x10000;
00642 
00643                                 // have to put further?
00644                                 if ((haa=(horicnt & 0xffff0000))) {
00645                                     do {
00646                                         *dst = SRC;
00647                                         dst++;
00648                                         horicnt-=0x10000;
00649                                     } while (horicnt & 0xffff0000);
00650                                 }
00651                             }
00652 
00653                             src++;
00654                         }
00655                     }
00656                     src-=sw;
00657                     vertcnt-=0x10000;
00658                     dst = old_dst + dst_pitch;
00659                     old_dst = dst;
00660                     vcnt++;
00661                 } while (vertcnt & 0xffff0000);
00662             }
00663         }
00664 
00665         // next line
00666         src+=src_pitch;
00667     }
00668 }
00669 
00670 void stretch_byte_buffer(bool h_antialiasing, bool v_antialiasing,
00671                          unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00672                          unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00673     // please note that the src and dst have to point to the first pixel which is to process
00674 
00675     if (!h_antialiasing) {
00676         if (!v_antialiasing) {
00677             // no antialiasing
00678             stretch_byte_buffer_no_antialiasing(src, src_pitch, src_pitch_pix, src_height, sw, sh,
00679                                                 dst, dst_pitch, dst_pitch_pix, dst_height, dw, dh);
00680         }
00681         else {
00682             // vertical antialiasing
00683             stretch_byte_buffer_v_antialiasing(src, src_pitch, src_pitch_pix, src_height, sw, sh,
00684                                                dst, dst_pitch, dst_pitch_pix, dst_height, dw, dh);
00685         }
00686     }
00687     else {
00688         if (!v_antialiasing) {
00689             // horizontal antialiasing
00690             stretch_byte_buffer_h_antialiasing(src, src_pitch, src_pitch_pix, src_height, sw, sh,
00691                                                dst, dst_pitch, dst_pitch_pix, dst_height, dw, dh);
00692         }
00693         else {
00694             // horizontal and vertical antialiasing
00695             stretch_byte_buffer_hv_antialiasing(src, src_pitch, src_pitch_pix, src_height, sw, sh,
00696                                                 dst, dst_pitch, dst_pitch_pix, dst_height, dw, dh);
00697         }
00698     }
00699 }
00700 
00701 
00702 void compress_2x2_matrix(unsigned char *src, int src_pitch, int src_pitch_pix, int src_height, int sw, int sh,
00703                          unsigned char *dst, int dst_pitch, int dst_pitch_pix, int dst_height, int dw, int dh) {
00704     // please note that the src and dst have to point to the first pixel which is to process
00705     unsigned char *src_end = src + src_pitch_pix * sh;
00706     if (src_end > src + src_pitch_pix * src_height)
00707         src_end = src + src_pitch_pix * src_height;
00708     unsigned char *dst_end = dst + dst_pitch_pix * dst_height;
00709 
00710     // prepare (have to work with even width/height)
00711     sw &= 0xfffffffe;
00712     sh &= 0xfffffffe;
00713     int src_pitch_diff = (src_pitch_pix << 1) - sw;
00714     int dst_pitch_diff = dst_pitch_pix - (sw >> 1);
00715 
00716     // calculate the arithmetic mean
00717     while ((src < src_end)&&(dst < dst_end)) {
00718         // go through two lines in parallel (square 2x2 pixel)
00719         unsigned char *line_end = src + sw;
00720         while (src < line_end) {
00721             int d = (int)*src + (int)src[1] + (int)src[src_pitch_pix] + (int)src[src_pitch_pix+1];
00722             *dst = d >> 2;
00723             src+=2;
00724             dst++;
00725         }
00726 
00727         // go to the next two lines
00728         src += src_pitch_diff;
00729         dst += dst_pitch_diff;
00730     }
00731 }
00732 
00733 void stretch_uint_buffer(bool h_antialiasing, bool v_antialiasing,
00734                          unsigned int *src, int src_pitch, int src_pitch_pix,
00735                          int src_height, int sx, int sy, int sw, int sh,
00736                          unsigned int *dst, int dst_pitch, int dst_pitch_pix,
00737                          int dst_height, int dx, int dy, int dw, int dh) {
00738 
00739     // point to the first pixel which is to process
00740     src = src + sx + sy * src_pitch_pix;
00741     dst = dst + dx + dy * dst_pitch_pix;
00742 
00743     // calc the end pointers
00744     unsigned int *src_end = src + src_pitch_pix * sh;
00745     if (src_end > src + src_pitch_pix * src_height)
00746         src_end = src + src_pitch_pix * src_height;
00747     unsigned int *dst_end = dst + dst_pitch_pix * dst_height;
00748 
00749     // setup defaults
00750     int start_vertcnt = 0x8000;
00751     int start_horicnt = 0x8000;
00752     bool vbreak = false;
00753     bool hbreak = false;
00754     int vertfact = (dh<<16)/sh;
00755     int horifact = (dw<<16)/sw;
00756 
00757     if (vertfact <= 0) {
00758         // have to calculate accurate factor based on surface dimensions
00759         vertfact = (dst_height<<16)/src_height;
00760 
00761         // have to calculate accurate start vertcnt
00762         for (int i=0, j=0; i<sy; i++) {
00763             start_vertcnt+=vertfact;
00764             if (start_vertcnt & 0xffff0000) {
00765                 do {
00766                     j++;
00767                     if (j > dy) {
00768                         vbreak = true;
00769                         break;
00770                     }
00771                     start_vertcnt-=0x10000;
00772                 } while (start_vertcnt & 0xffff0000);
00773             }
00774             if (vbreak) break;
00775         }
00776     }
00777 
00778     if (horifact <= 0) {
00779         // have to calculate accurate factor based on surface dimensions
00780         horifact = (dst_pitch_pix<<16)/src_pitch_pix;
00781 
00782         // have to calculate accurate start horicnt
00783         for (int i=0, j=0; i<sx; i++) {
00784             start_horicnt+=horifact;
00785             if (start_horicnt & 0xffff0000) {
00786                 do {
00787                     j++;
00788                     if (j > dx) {
00789                         hbreak = true;
00790                         break;
00791                     }
00792                     start_horicnt-=0x10000;
00793                 } while (start_horicnt & 0xffff0000);
00794             }
00795             if (hbreak) break;
00796         }
00797     }
00798 
00799     if ((!vbreak)&&(!hbreak)) {
00800         // optimized loop
00801         int vertcnt = start_vertcnt;
00802         while ((src < src_end)&&(dst < dst_end)) {
00803             // for all pixels in the line
00804             vertcnt+=vertfact;
00805             if (vertcnt & 0xffff0000) {
00806                 unsigned int *line_end = src + sw;
00807                 unsigned int *old_dst = dst;
00808 
00809                 do {
00810                     int horicnt = start_horicnt;
00811                     while (src < line_end) {
00812                         horicnt+=horifact;
00813                         if (horicnt & 0xffff0000) {
00814                             register unsigned int SRC  = *src;
00815 
00816                             do {
00817                                 *dst = SRC;
00818                                 dst++;
00819                                 horicnt-=0x10000;
00820                             } while (horicnt & 0xffff0000);
00821                         }
00822 
00823                         src++;
00824                     }
00825                     src-=sw;
00826                     vertcnt-=0x10000;
00827                     dst = old_dst + dst_pitch_pix;
00828                     old_dst = dst;
00829                 } while (vertcnt & 0xffff0000);
00830             }
00831 
00832             // next line
00833             src+=src_pitch_pix;
00834         }
00835     }
00836     else {
00837         // consider vbreak and hbreak values
00838         int vertcnt = start_vertcnt;
00839         while ((src < src_end)&&(dst < dst_end)) {
00840             // for all pixels in the line
00841             if (vbreak) {
00842                 vbreak = false;
00843                 src-= src_pitch_pix;
00844             }
00845             else
00846                 vertcnt+=vertfact;
00847 
00848             if (vertcnt & 0xffff0000) {
00849                 unsigned int *line_end = src + sw;
00850                 unsigned int *old_dst = dst;
00851 
00852                 do {
00853                     int horicnt = start_horicnt;
00854                     bool hb = hbreak;
00855                     while (src < line_end) {
00856                         if (hb) {
00857                             hb = false;
00858                             src--;
00859                         }
00860                         else
00861                             horicnt+=horifact;
00862 
00863                         if (horicnt & 0xffff0000) {
00864                             register unsigned int SRC  = *src;
00865 
00866                             do {
00867                                 *dst = SRC;
00868                                 dst++;
00869                                 horicnt-=0x10000;
00870                             } while (horicnt & 0xffff0000);
00871                         }
00872 
00873                         src++;
00874                     }
00875                     src-=sw;
00876                     vertcnt-=0x10000;
00877                     dst = old_dst + dst_pitch_pix;
00878                     old_dst = dst;
00879                 } while (vertcnt & 0xffff0000);
00880             }
00881 
00882             // next line
00883             src+=src_pitch_pix;
00884         }
00885     }
00886 }
00887 
00888 void stretch_usint_buffer(bool h_antialiasing, bool v_antialiasing,
00889                           unsigned short int *src, int src_pitch, int src_pitch_pix,
00890                           int src_height, int sx, int sy, int sw, int sh,
00891                           unsigned short int *dst, int dst_pitch, int dst_pitch_pix,
00892                           int dst_height, int dx, int dy, int dw, int dh) {
00893 
00894     // point to the first pixel which is to process
00895     src = src + sx + sy * src_pitch_pix;
00896     dst = dst + dx + dy * dst_pitch_pix;
00897 
00898     // calc the end pointers
00899     unsigned short int *src_end = src + src_pitch_pix * sh;
00900     if (src_end > src + src_pitch_pix * src_height)
00901         src_end = src + src_pitch_pix * src_height;
00902     unsigned short int *dst_end = dst + dst_pitch_pix * dst_height;
00903 
00904     // setup defaults
00905     int start_vertcnt = 0x8000;
00906     int start_horicnt = 0x8000;
00907     bool vbreak = false;
00908     bool hbreak = false;
00909     int vertfact = (dh<<16)/sh;
00910     int horifact = (dw<<16)/sw;
00911 
00912     if (vertfact <= 0) {
00913         // have to calculate accurate factor based on surface dimensions
00914         vertfact = (dst_height<<16)/src_height;
00915 
00916         // have to calculate accurate start vertcnt
00917         for (int i=0, j=0; i<sy; i++) {
00918             start_vertcnt+=vertfact;
00919             if (start_vertcnt & 0xffff0000) {
00920                 do {
00921                     j++;
00922                     if (j > dy) {
00923                         vbreak = true;
00924                         break;
00925                     }
00926                     start_vertcnt-=0x10000;
00927                 } while (start_vertcnt & 0xffff0000);
00928             }
00929             if (vbreak) break;
00930         }
00931     }
00932 
00933     if (horifact <= 0) {
00934         // have to calculate accurate factor based on surface dimensions
00935         horifact = (dst_pitch_pix<<16)/src_pitch_pix;
00936 
00937         // have to calculate accurate start horicnt
00938         for (int i=0, j=0; i<sx; i++) {
00939             start_horicnt+=horifact;
00940             if (start_horicnt & 0xffff0000) {
00941                 do {
00942                     j++;
00943                     if (j > dx) {
00944                         hbreak = true;
00945                         break;
00946                     }
00947                     start_horicnt-=0x10000;
00948                 } while (start_horicnt & 0xffff0000);
00949             }
00950             if (hbreak) break;
00951         }
00952     }
00953 
00954     if ((!vbreak)&&(!hbreak)) {
00955         // optimized loop
00956         int vertcnt = start_vertcnt;
00957         while ((src < src_end)&&(dst < dst_end)) {
00958             // for all pixels in the line
00959             vertcnt+=vertfact;
00960             if (vertcnt & 0xffff0000) {
00961                 unsigned short int *line_end = src + sw;
00962                 unsigned short int *old_dst = dst;
00963 
00964                 do {
00965                     int horicnt = start_horicnt;
00966                     while (src < line_end) {
00967                         horicnt+=horifact;
00968                         if (horicnt & 0xffff0000) {
00969                             register unsigned short int SRC  = *src;
00970 
00971                             do {
00972                                 *dst = SRC;
00973                                 dst++;
00974                                 horicnt-=0x10000;
00975                             } while (horicnt & 0xffff0000);
00976                         }
00977 
00978                         src++;
00979                     }
00980                     src-=sw;
00981                     vertcnt-=0x10000;
00982                     dst = old_dst + dst_pitch_pix;
00983                     old_dst = dst;
00984                 } while (vertcnt & 0xffff0000);
00985             }
00986 
00987             // next line
00988             src+=src_pitch_pix;
00989         }
00990     }
00991     else {
00992         // consider vbreak and hbreak values
00993         int vertcnt = start_vertcnt;
00994         while ((src < src_end)&&(dst < dst_end)) {
00995             // for all pixels in the line
00996             if (vbreak) {
00997                 vbreak = false;
00998                 src-= src_pitch_pix;
00999             }
01000             else
01001                 vertcnt+=vertfact;
01002 
01003             if (vertcnt & 0xffff0000) {
01004                 unsigned short int *line_end = src + sw;
01005                 unsigned short int *old_dst = dst;
01006 
01007                 do {
01008                     int horicnt = start_horicnt;
01009                     bool hb = hbreak;
01010                     while (src < line_end) {
01011                         if (hb) {
01012                             hb = false;
01013                             src--;
01014                         }
01015                         else
01016                             horicnt+=horifact;
01017 
01018                         if (horicnt & 0xffff0000) {
01019                             register unsigned short int SRC  = *src;
01020 
01021                             do {
01022                                 *dst = SRC;
01023                                 dst++;
01024                                 horicnt-=0x10000;
01025                             } while (horicnt & 0xffff0000);
01026                         }
01027 
01028                         src++;
01029                     }
01030                     src-=sw;
01031                     vertcnt-=0x10000;
01032                     dst = old_dst + dst_pitch_pix;
01033                     old_dst = dst;
01034                 } while (vertcnt & 0xffff0000);
01035             }
01036 
01037             // next line
01038             src+=src_pitch_pix;
01039         }
01040     }
01041 }
01042 
01043 
01044 
01045 void stretch_324byte_buffer(bool h_antialiasing, bool v_antialiasing,
01046                             unsigned char *src, int src_pitch, int src_pitch_pix,
01047                             int src_height, int sx, int sy, int sw, int sh,
01048                             unsigned int *dst, int dst_pitch, int dst_pitch_pix,
01049                             int dst_height, int dx, int dy, int dw, int dh) {
01050 
01051     // point to the first pixel which is to process
01052     src = src + (sx + sy * src_pitch_pix) * 3;
01053     dst = dst + dx + dy * dst_pitch_pix;
01054 
01055     // calc the end pointers
01056     unsigned char *src_end = src + (src_pitch_pix * sh) * 3;
01057     if (src_end > src + (src_pitch_pix * src_height) * 3)
01058         src_end = src + (src_pitch_pix * src_height) * 3;
01059     unsigned int *dst_end = dst + dst_pitch_pix * dst_height;
01060 
01061     // setup defaults
01062     int start_vertcnt = 0x8000;
01063     int start_horicnt = 0x8000;
01064     bool vbreak = false;
01065     bool hbreak = false;
01066     int vertfact = (dh<<16)/sh;
01067     int horifact = (dw<<16)/sw;
01068     int sww = sw * 3;
01069     int spp = src_pitch_pix * 3;
01070 
01071     if (vertfact <= 0) {
01072         // have to calculate accurate factor based on surface dimensions
01073         vertfact = (dst_height<<16)/src_height;
01074 
01075         // have to calculate accurate start vertcnt
01076         for (int i=0, j=0; i<sy; i++) {
01077             start_vertcnt+=vertfact;
01078             if (start_vertcnt & 0xffff0000) {
01079                 do {
01080                     j++;
01081                     if (j > dy) {
01082                         vbreak = true;
01083                         break;
01084                     }
01085                     start_vertcnt-=0x10000;
01086                 } while (start_vertcnt & 0xffff0000);
01087             }
01088             if (vbreak) break;
01089         }
01090     }
01091 
01092     if (horifact <= 0) {
01093         // have to calculate accurate factor based on surface dimensions
01094         horifact = (dst_pitch_pix<<16)/src_pitch_pix;
01095 
01096         // have to calculate accurate start horicnt
01097         for (int i=0, j=0; i<sx; i++) {
01098             start_horicnt+=horifact;
01099             if (start_horicnt & 0xffff0000) {
01100                 do {
01101                     j++;
01102                     if (j > dx) {
01103                         hbreak = true;
01104                         break;
01105                     }
01106                     start_horicnt-=0x10000;
01107                 } while (start_horicnt & 0xffff0000);
01108             }
01109             if (hbreak) break;
01110         }
01111     }
01112 
01113     if ((!vbreak)&&(!hbreak)) {
01114         // optimized loop
01115         int vertcnt = start_vertcnt;
01116         while ((src < src_end)&&(dst < dst_end)) {
01117             // for all pixels in the line
01118             vertcnt+=vertfact;
01119             if (vertcnt & 0xffff0000) {
01120                 unsigned char *line_end = src + sww;
01121                 unsigned int *old_dst = dst;
01122 
01123                 do {
01124                     int horicnt = start_horicnt;
01125                     while (src < line_end) {
01126                         horicnt+=horifact;
01127                         if (horicnt & 0xffff0000) {
01128                             register unsigned int SRC  = 0xff000000 | ((*src)<<16) | ((*(src+1))<<8) | *(src+2);
01129 
01130                             do {
01131                                 *dst = SRC;
01132                                 dst++;
01133                                 horicnt-=0x10000;
01134                             } while (horicnt & 0xffff0000);
01135                         }
01136 
01137                         src+=3;
01138                     }
01139                     src-=sww;
01140                     vertcnt-=0x10000;
01141                     dst = old_dst + dst_pitch_pix;
01142                     old_dst = dst;
01143                 } while (vertcnt & 0xffff0000);
01144             }
01145 
01146             // next line
01147             src+=spp;
01148         }
01149     }
01150     else {
01151         // consider vbreak and hbreak values
01152         int vertcnt = start_vertcnt;
01153         while ((src < src_end)&&(dst < dst_end)) {
01154             // for all pixels in the line
01155             if (vbreak) {
01156                 vbreak = false;
01157                 src-= spp;
01158             }
01159             else
01160                 vertcnt+=vertfact;
01161 
01162             if (vertcnt & 0xffff0000) {
01163                 unsigned char *line_end = src + sww;
01164                 unsigned int *old_dst = dst;
01165 
01166                 do {
01167                     int horicnt = start_horicnt;
01168                     bool hb = hbreak;
01169                     while (src < line_end) {
01170                         if (hb) {
01171                             hb = false;
01172                             src-=3;
01173                         }
01174                         else
01175                             horicnt+=horifact;
01176 
01177                         if (horicnt & 0xffff0000) {
01178                             register unsigned int SRC  = 0xff000000 | ((*src)<<16) | ((*(src+1))<<8) | *(src+2);
01179 
01180                             do {
01181                                 *dst = SRC;
01182                                 dst++;
01183                                 horicnt-=0x10000;
01184                             } while (horicnt & 0xffff0000);
01185                         }
01186 
01187                         src+=3;
01188                     }
01189                     src-=sww;
01190                     vertcnt-=0x10000;
01191                     dst = old_dst + dst_pitch_pix;
01192                     old_dst = dst;
01193                 } while (vertcnt & 0xffff0000);
01194             }
01195 
01196             // next line
01197             src+=spp;
01198         }
01199     }
01200 }
01201 
01202 
01203 void mmsfb_blit_uint(MMSFBSurfacePlanes *src_planes, int src_height, int sx, int sy, int sw, int sh,
01204                      MMSFBSurfacePlanes *dst_planes, int dst_height, int dx, int dy) {
01205 
01206     // get the first source ptr/pitch
01207     unsigned int *src = (unsigned int *)src_planes->ptr;
01208     int src_pitch = src_planes->pitch;
01209 
01210     // get the first destination ptr/pitch
01211     unsigned int *dst = (unsigned int *)dst_planes->ptr;
01212     int dst_pitch = dst_planes->pitch;
01213 
01214     // prepare...
01215     int src_pitch_pix = src_pitch >> 2;
01216     int dst_pitch_pix = dst_pitch >> 2;
01217     src+= sx + sy * src_pitch_pix;
01218     dst+= dx + dy * dst_pitch_pix;
01219 
01220     // check the surface range
01221     if (dst_pitch_pix - dx < sw - sx)
01222         sw = dst_pitch_pix - dx - sx;
01223     if (dst_height - dy < sh - sy)
01224         sh = dst_height - dy - sy;
01225     if ((sw <= 0)||(sh <= 0))
01226         return;
01227 
01228     unsigned int *src_end = src + src_pitch_pix * sh;
01229 
01230     // for all lines
01231     while (src < src_end) {
01232         // copy the line
01233         memcpy(dst, src, sw << 2);
01234 
01235         // go to the next line
01236         src+= src_pitch_pix;
01237         dst+= dst_pitch_pix;
01238     }
01239 }
01240 
01241 void mmsfb_blit_usint(MMSFBSurfacePlanes *src_planes, int src_height, int sx, int sy, int sw, int sh,
01242                       MMSFBSurfacePlanes *dst_planes, int dst_height, int dx, int dy) {
01243 
01244     // get the first source ptr/pitch
01245     unsigned short int *src = (unsigned short int *)src_planes->ptr;
01246     int src_pitch = src_planes->pitch;
01247 
01248     // get the first destination ptr/pitch
01249     unsigned short int *dst = (unsigned short int *)dst_planes->ptr;
01250     int dst_pitch = dst_planes->pitch;
01251 
01252     // prepare...
01253     int src_pitch_pix = src_pitch >> 1;
01254     int dst_pitch_pix = dst_pitch >> 1;
01255     src+= sx + sy * src_pitch_pix;
01256     dst+= dx + dy * dst_pitch_pix;
01257 
01258     // check the surface range
01259     if (dst_pitch_pix - dx < sw - sx)
01260         sw = dst_pitch_pix - dx - sx;
01261     if (dst_height - dy < sh - sy)
01262         sh = dst_height - dy - sy;
01263     if ((sw <= 0)||(sh <= 0))
01264         return;
01265 
01266     unsigned short int *src_end = src + src_pitch_pix * sh;
01267 
01268     // for all lines
01269     while (src < src_end) {
01270         // copy the line
01271         memcpy(dst, src, sw << 1);
01272 
01273         // go to the next line
01274         src+= src_pitch_pix;
01275         dst+= dst_pitch_pix;
01276     }
01277 }
01278 

Generated by doxygen