gst_plugins_base/gst/videoscale/vs_scanline.c
changeset 0 0e761a78d257
child 8 4a7fac7dd34a
equal deleted inserted replaced
-1:000000000000 0:0e761a78d257
       
     1 /*
       
     2  * Image Scaling Functions
       
     3  * Copyright (c) 2005 David A. Schleef <ds@schleef.org>
       
     4  * All rights reserved.
       
     5  *
       
     6  * Redistribution and use in source and binary forms, with or without
       
     7  * modification, are permitted provided that the following conditions
       
     8  * are met:
       
     9  * 1. Redistributions of source code must retain the above copyright
       
    10  *    notice, this list of conditions and the following disclaimer.
       
    11  * 2. Redistributions in binary form must reproduce the above copyright
       
    12  *    notice, this list of conditions and the following disclaimer in the
       
    13  *    documentation and/or other materials provided with the distribution.
       
    14  * 
       
    15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
       
    16  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
       
    17  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
       
    18  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
       
    19  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
       
    20  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
       
    21  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
       
    22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
       
    23  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
       
    24  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
       
    25  * POSSIBILITY OF SUCH DAMAGE.
       
    26  */
       
    27 
       
    28 #include "vs_scanline.h"
       
    29 #include <gst/liboil.h>
       
    30 
       
    31 /* greyscale, i.e., single componenet */
       
    32 #ifdef __SYMBIAN32__
       
    33 EXPORT_C
       
    34 #endif
       
    35 
       
    36 
       
    37 void
       
    38 vs_scanline_downsample_Y (uint8_t * dest, uint8_t * src, int n)
       
    39 {
       
    40   int i;
       
    41 
       
    42   for (i = 0; i < n; i++) {
       
    43     dest[i] = (src[i * 2] + src[i * 2 + 1]) / 2;
       
    44   }
       
    45 }
       
    46 #ifdef __SYMBIAN32__
       
    47 EXPORT_C
       
    48 #endif
       
    49 
       
    50 
       
    51 void
       
    52 vs_scanline_resample_nearest_Y (uint8_t * dest, uint8_t * src, int n,
       
    53     int *accumulator, int increment)
       
    54 {
       
    55   int acc = *accumulator;
       
    56   int i;
       
    57   int j;
       
    58   int x;
       
    59 
       
    60   for (i = 0; i < n; i++) {
       
    61     j = acc >> 16;
       
    62     x = acc & 0xffff;
       
    63     dest[i] = (x < 32768) ? src[j] : src[j + 1];
       
    64 
       
    65     acc += increment;
       
    66   }
       
    67 
       
    68   *accumulator = acc;
       
    69 }
       
    70 #ifdef __SYMBIAN32__
       
    71 EXPORT_C
       
    72 #endif
       
    73 
       
    74 
       
    75 void
       
    76 vs_scanline_resample_linear_Y (uint8_t * dest, uint8_t * src, int n,
       
    77     int *accumulator, int increment)
       
    78 {
       
    79   uint32_t vals[2];
       
    80 
       
    81   vals[0] = *accumulator;
       
    82   vals[1] = increment;
       
    83 
       
    84   oil_resample_linear_u8 (dest, src, n, vals);
       
    85 
       
    86   *accumulator = vals[0];
       
    87 }
       
    88 #ifdef __SYMBIAN32__
       
    89 EXPORT_C
       
    90 #endif
       
    91 
       
    92 
       
    93 void
       
    94 vs_scanline_merge_linear_Y (uint8_t * dest, uint8_t * src1, uint8_t * src2,
       
    95     int n, int x)
       
    96 {
       
    97   uint32_t value = x >> 8;
       
    98 
       
    99   oil_merge_linear_u8 (dest, src1, src2, &value, n);
       
   100 }
       
   101 
       
   102 
       
   103 /* RGBA */
       
   104 #ifdef __SYMBIAN32__
       
   105 EXPORT_C
       
   106 #endif
       
   107 
       
   108 
       
   109 void
       
   110 vs_scanline_downsample_RGBA (uint8_t * dest, uint8_t * src, int n)
       
   111 {
       
   112   int i;
       
   113 
       
   114   for (i = 0; i < n; i++) {
       
   115     dest[i * 4 + 0] = (src[i * 8 + 0] + src[i * 8 + 4]) / 2;
       
   116     dest[i * 4 + 1] = (src[i * 8 + 1] + src[i * 8 + 5]) / 2;
       
   117     dest[i * 4 + 2] = (src[i * 8 + 2] + src[i * 8 + 6]) / 2;
       
   118     dest[i * 4 + 3] = (src[i * 8 + 3] + src[i * 8 + 7]) / 2;
       
   119   }
       
   120 }
       
   121 #ifdef __SYMBIAN32__
       
   122 EXPORT_C
       
   123 #endif
       
   124 
       
   125 
       
   126 void
       
   127 vs_scanline_resample_nearest_RGBA (uint8_t * dest, uint8_t * src, int n,
       
   128     int *accumulator, int increment)
       
   129 {
       
   130   int acc = *accumulator;
       
   131   int i;
       
   132   int j;
       
   133   int x;
       
   134 
       
   135   for (i = 0; i < n; i++) {
       
   136     j = acc >> 16;
       
   137     x = acc & 0xffff;
       
   138     dest[i * 4 + 0] = (x < 32768) ? src[j * 4 + 0] : src[j * 4 + 4];
       
   139     dest[i * 4 + 1] = (x < 32768) ? src[j * 4 + 1] : src[j * 4 + 5];
       
   140     dest[i * 4 + 2] = (x < 32768) ? src[j * 4 + 2] : src[j * 4 + 6];
       
   141     dest[i * 4 + 3] = (x < 32768) ? src[j * 4 + 3] : src[j * 4 + 7];
       
   142 
       
   143     acc += increment;
       
   144   }
       
   145 
       
   146   *accumulator = acc;
       
   147 }
       
   148 #ifdef __SYMBIAN32__
       
   149 EXPORT_C
       
   150 #endif
       
   151 
       
   152 
       
   153 void
       
   154 vs_scanline_resample_linear_RGBA (uint8_t * dest, uint8_t * src, int n,
       
   155     int *accumulator, int increment)
       
   156 {
       
   157   uint32_t vals[2];
       
   158 
       
   159   vals[0] = *accumulator;
       
   160   vals[1] = increment;
       
   161 
       
   162   oil_resample_linear_argb ((uint32_t *) dest, (uint32_t *) src, n, vals);
       
   163 
       
   164   *accumulator = vals[0];
       
   165 }
       
   166 #ifdef __SYMBIAN32__
       
   167 EXPORT_C
       
   168 #endif
       
   169 
       
   170 
       
   171 void
       
   172 vs_scanline_merge_linear_RGBA (uint8_t * dest, uint8_t * src1, uint8_t * src2,
       
   173     int n, int x)
       
   174 {
       
   175   uint32_t value = x >> 8;
       
   176 
       
   177   oil_merge_linear_argb ((uint32_t *) dest, (uint32_t *) src1,
       
   178       (uint32_t *) src2, &value, n);
       
   179 }
       
   180 
       
   181 
       
   182 /* RGB */
       
   183 #ifdef __SYMBIAN32__
       
   184 EXPORT_C
       
   185 #endif
       
   186 
       
   187 
       
   188 void
       
   189 vs_scanline_downsample_RGB (uint8_t * dest, uint8_t * src, int n)
       
   190 {
       
   191   int i;
       
   192 
       
   193   for (i = 0; i < n; i++) {
       
   194     dest[i * 3 + 0] = (src[i * 6 + 0] + src[i * 6 + 3]) / 2;
       
   195     dest[i * 3 + 1] = (src[i * 6 + 1] + src[i * 6 + 4]) / 2;
       
   196     dest[i * 3 + 2] = (src[i * 6 + 2] + src[i * 6 + 5]) / 2;
       
   197   }
       
   198 }
       
   199 #ifdef __SYMBIAN32__
       
   200 EXPORT_C
       
   201 #endif
       
   202 
       
   203 
       
   204 void
       
   205 vs_scanline_resample_nearest_RGB (uint8_t * dest, uint8_t * src, int n,
       
   206     int *accumulator, int increment)
       
   207 {
       
   208   int acc = *accumulator;
       
   209   int i;
       
   210   int j;
       
   211   int x;
       
   212 
       
   213   for (i = 0; i < n; i++) {
       
   214     j = acc >> 16;
       
   215     x = acc & 0xffff;
       
   216     dest[i * 3 + 0] = (x < 32768) ? src[j * 3 + 0] : src[j * 3 + 3];
       
   217     dest[i * 3 + 1] = (x < 32768) ? src[j * 3 + 1] : src[j * 3 + 4];
       
   218     dest[i * 3 + 2] = (x < 32768) ? src[j * 3 + 2] : src[j * 3 + 5];
       
   219 
       
   220     acc += increment;
       
   221   }
       
   222 
       
   223   *accumulator = acc;
       
   224 }
       
   225 #ifdef __SYMBIAN32__
       
   226 EXPORT_C
       
   227 #endif
       
   228 
       
   229 
       
   230 void
       
   231 vs_scanline_resample_linear_RGB (uint8_t * dest, uint8_t * src, int n,
       
   232     int *accumulator, int increment)
       
   233 {
       
   234   int acc = *accumulator;
       
   235   int i;
       
   236   int j;
       
   237   int x;
       
   238 
       
   239   for (i = 0; i < n; i++) {
       
   240     j = acc >> 16;
       
   241     x = acc & 0xffff;
       
   242     dest[i * 3 + 0] = (src[j * 3 + 0] * (65536 - x) + src[j * 3 + 3] * x) >> 16;
       
   243     dest[i * 3 + 1] = (src[j * 3 + 1] * (65536 - x) + src[j * 3 + 4] * x) >> 16;
       
   244     dest[i * 3 + 2] = (src[j * 3 + 2] * (65536 - x) + src[j * 3 + 5] * x) >> 16;
       
   245 
       
   246     acc += increment;
       
   247   }
       
   248 
       
   249   *accumulator = acc;
       
   250 }
       
   251 #ifdef __SYMBIAN32__
       
   252 EXPORT_C
       
   253 #endif
       
   254 
       
   255 
       
   256 void
       
   257 vs_scanline_merge_linear_RGB (uint8_t * dest, uint8_t * src1, uint8_t * src2,
       
   258     int n, int x)
       
   259 {
       
   260   uint32_t value = x >> 8;
       
   261 
       
   262   oil_merge_linear_u8 (dest, src1, src2, &value, n * 3);
       
   263 }
       
   264 
       
   265 
       
   266 /* YUYV */
       
   267 
       
   268 /* n is the number of bi-pixels */
       
   269 /* increment is per Y pixel */
       
   270 #ifdef __SYMBIAN32__
       
   271 EXPORT_C
       
   272 #endif
       
   273 
       
   274 
       
   275 void
       
   276 vs_scanline_downsample_YUYV (uint8_t * dest, uint8_t * src, int n)
       
   277 {
       
   278   int i;
       
   279 
       
   280   for (i = 0; i < n; i++) {
       
   281     dest[i * 4 + 0] = (src[i * 8 + 0] + src[i * 8 + 2]) / 2;
       
   282     dest[i * 4 + 1] = (src[i * 8 + 1] + src[i * 8 + 5]) / 2;
       
   283     dest[i * 4 + 2] = (src[i * 8 + 4] + src[i * 8 + 6]) / 2;
       
   284     dest[i * 4 + 3] = (src[i * 8 + 3] + src[i * 8 + 7]) / 2;
       
   285   }
       
   286 }
       
   287 #ifdef __SYMBIAN32__
       
   288 EXPORT_C
       
   289 #endif
       
   290 
       
   291 
       
   292 void
       
   293 vs_scanline_resample_nearest_YUYV (uint8_t * dest, uint8_t * src, int n,
       
   294     int *accumulator, int increment)
       
   295 {
       
   296   int acc = *accumulator;
       
   297   int i;
       
   298   int j;
       
   299   int x;
       
   300 
       
   301   for (i = 0; i < n; i++) {
       
   302     j = acc >> 16;
       
   303     x = acc & 0xffff;
       
   304     dest[i * 4 + 0] = (x < 32768) ? src[j * 2 + 0] : src[j * 2 + 2];
       
   305 
       
   306     j = acc >> 17;
       
   307     x = acc & 0x1ffff;
       
   308     dest[i * 4 + 1] = (x < 65536) ? src[j * 4 + 1] : src[j * 4 + 5];
       
   309     dest[i * 4 + 3] = (x < 65536) ? src[j * 4 + 3] : src[j * 4 + 7];
       
   310 
       
   311     acc += increment;
       
   312 
       
   313     j = acc >> 16;
       
   314     x = acc & 0xffff;
       
   315     dest[i * 4 + 2] = (x < 32768) ? src[j * 2 + 0] : src[j * 2 + 2];
       
   316     acc += increment;
       
   317   }
       
   318 
       
   319   *accumulator = acc;
       
   320 }
       
   321 #ifdef __SYMBIAN32__
       
   322 EXPORT_C
       
   323 #endif
       
   324 
       
   325 
       
   326 void
       
   327 vs_scanline_resample_linear_YUYV (uint8_t * dest, uint8_t * src, int n,
       
   328     int *accumulator, int increment)
       
   329 {
       
   330   int acc = *accumulator;
       
   331   int i;
       
   332   int j;
       
   333   int x;
       
   334 
       
   335   for (i = 0; i < n; i++) {
       
   336     j = acc >> 16;
       
   337     x = acc & 0xffff;
       
   338     dest[i * 4 + 0] = (src[j * 2 + 0] * (65536 - x) + src[j * 2 + 2] * x) >> 16;
       
   339 
       
   340     j = acc >> 17;
       
   341     x = acc & 0x1ffff;
       
   342     dest[i * 4 + 1] =
       
   343         (src[j * 4 + 1] * (131072 - x) + src[j * 4 + 5] * x) >> 17;
       
   344     dest[i * 4 + 3] =
       
   345         (src[j * 4 + 3] * (131072 - x) + src[j * 4 + 7] * x) >> 17;
       
   346 
       
   347     acc += increment;
       
   348 
       
   349     j = acc >> 16;
       
   350     x = acc & 0xffff;
       
   351     dest[i * 4 + 2] = (src[j * 2 + 0] * (65536 - x) + src[j * 2 + 2] * x) >> 16;
       
   352     acc += increment;
       
   353   }
       
   354 
       
   355   *accumulator = acc;
       
   356 }
       
   357 #ifdef __SYMBIAN32__
       
   358 EXPORT_C
       
   359 #endif
       
   360 
       
   361 
       
   362 void
       
   363 vs_scanline_merge_linear_YUYV (uint8_t * dest, uint8_t * src1, uint8_t * src2,
       
   364     int n, int x)
       
   365 {
       
   366   int i;
       
   367 
       
   368   for (i = 0; i < n; i++) {
       
   369     dest[i * 4 + 0] =
       
   370         (src1[i * 4 + 0] * (65536 - x) + src2[i * 4 + 0] * x) >> 16;
       
   371     dest[i * 4 + 1] =
       
   372         (src1[i * 4 + 1] * (65536 - x) + src2[i * 4 + 1] * x) >> 16;
       
   373     dest[i * 4 + 2] =
       
   374         (src1[i * 4 + 2] * (65536 - x) + src2[i * 4 + 2] * x) >> 16;
       
   375     dest[i * 4 + 3] =
       
   376         (src1[i * 4 + 3] * (65536 - x) + src2[i * 4 + 3] * x) >> 16;
       
   377   }
       
   378 }
       
   379 
       
   380 
       
   381 /* UYVY */
       
   382 
       
   383 /* n is the number of bi-pixels */
       
   384 /* increment is per Y pixel */
       
   385 #ifdef __SYMBIAN32__
       
   386 EXPORT_C
       
   387 #endif
       
   388 
       
   389 
       
   390 void
       
   391 vs_scanline_downsample_UYVY (uint8_t * dest, uint8_t * src, int n)
       
   392 {
       
   393   int i;
       
   394 
       
   395   for (i = 0; i < n; i++) {
       
   396     dest[i * 4 + 0] = (src[i * 8 + 0] + src[i * 8 + 4]) / 2;
       
   397     dest[i * 4 + 1] = (src[i * 8 + 1] + src[i * 8 + 3]) / 2;
       
   398     dest[i * 4 + 2] = (src[i * 8 + 2] + src[i * 8 + 6]) / 2;
       
   399     dest[i * 4 + 3] = (src[i * 8 + 5] + src[i * 8 + 7]) / 2;
       
   400   }
       
   401 }
       
   402 #ifdef __SYMBIAN32__
       
   403 EXPORT_C
       
   404 #endif
       
   405 
       
   406 
       
   407 void
       
   408 vs_scanline_resample_nearest_UYVY (uint8_t * dest, uint8_t * src, int n,
       
   409     int *accumulator, int increment)
       
   410 {
       
   411   int acc = *accumulator;
       
   412   int i;
       
   413   int j;
       
   414   int x;
       
   415 
       
   416   for (i = 0; i < n; i++) {
       
   417     j = acc >> 16;
       
   418     x = acc & 0xffff;
       
   419     dest[i * 4 + 1] = (x < 32768) ? src[j * 2 + 1] : src[j * 2 + 3];
       
   420 
       
   421     j = acc >> 17;
       
   422     x = acc & 0x1ffff;
       
   423     dest[i * 4 + 0] = (x < 65536) ? src[j * 4 + 0] : src[j * 4 + 4];
       
   424     dest[i * 4 + 2] = (x < 65536) ? src[j * 4 + 2] : src[j * 4 + 6];
       
   425 
       
   426     acc += increment;
       
   427 
       
   428     j = acc >> 16;
       
   429     x = acc & 0xffff;
       
   430     dest[i * 4 + 3] = (x < 32768) ? src[j * 2 + 1] : src[j * 2 + 3];
       
   431     acc += increment;
       
   432   }
       
   433 
       
   434   *accumulator = acc;
       
   435 }
       
   436 #ifdef __SYMBIAN32__
       
   437 EXPORT_C
       
   438 #endif
       
   439 
       
   440 
       
   441 void
       
   442 vs_scanline_resample_linear_UYVY (uint8_t * dest, uint8_t * src, int n,
       
   443     int *accumulator, int increment)
       
   444 {
       
   445   int acc = *accumulator;
       
   446   int i;
       
   447   int j;
       
   448   int x;
       
   449 
       
   450   for (i = 0; i < n; i++) {
       
   451     j = acc >> 16;
       
   452     x = acc & 0xffff;
       
   453     dest[i * 4 + 1] = (src[j * 2 + 1] * (65536 - x) + src[j * 2 + 3] * x) >> 16;
       
   454 
       
   455     j = acc >> 17;
       
   456     x = acc & 0x1ffff;
       
   457     dest[i * 4 + 0] =
       
   458         (src[j * 4 + 0] * (131072 - x) + src[j * 4 + 4] * x) >> 17;
       
   459     dest[i * 4 + 2] =
       
   460         (src[j * 4 + 2] * (131072 - x) + src[j * 4 + 6] * x) >> 17;
       
   461 
       
   462     acc += increment;
       
   463 
       
   464     j = acc >> 16;
       
   465     x = acc & 0xffff;
       
   466     dest[i * 4 + 3] = (src[j * 2 + 1] * (65536 - x) + src[j * 2 + 3] * x) >> 16;
       
   467     acc += increment;
       
   468   }
       
   469 
       
   470   *accumulator = acc;
       
   471 }
       
   472 #ifdef __SYMBIAN32__
       
   473 EXPORT_C
       
   474 #endif
       
   475 
       
   476 
       
   477 void
       
   478 vs_scanline_merge_linear_UYVY (uint8_t * dest, uint8_t * src1, uint8_t * src2,
       
   479     int n, int x)
       
   480 {
       
   481   uint32_t value = x >> 8;
       
   482 
       
   483   oil_merge_linear_argb ((uint32_t *) dest, (uint32_t *) src1,
       
   484       (uint32_t *) src2, &value, n);
       
   485 }
       
   486 
       
   487 
       
   488 /* RGB565 */
       
   489 
       
   490 /* note that src and dest are uint16_t, and thus endian dependent */
       
   491 
       
   492 #define RGB565_R(x) (((x)&0xf800)>>8 | ((x)&0xf800)>>13)
       
   493 #define RGB565_G(x) (((x)&0x07e0)>>3 | ((x)&0x07e0)>>9)
       
   494 #define RGB565_B(x) (((x)&0x001f)<<3 | ((x)&0x001f)>>2)
       
   495 
       
   496 #define RGB565(r,g,b) \
       
   497   ((((r)<<8)&0xf800) | (((g)<<3)&0x07e0) | (((b)>>3)&0x001f))
       
   498 
       
   499 #ifdef __SYMBIAN32__
       
   500 EXPORT_C
       
   501 #endif
       
   502 void
       
   503 vs_scanline_downsample_RGB565 (uint8_t * dest_u8, uint8_t * src_u8, int n)
       
   504 {
       
   505   uint16_t *dest = (uint16_t *) dest_u8;
       
   506   uint16_t *src = (uint16_t *) src_u8;
       
   507   int i;
       
   508 
       
   509   for (i = 0; i < n; i++) {
       
   510     dest[i] = RGB565 (
       
   511         (RGB565_R (src[i * 2]) + RGB565_R (src[i * 2 + 1])) / 2,
       
   512         (RGB565_G (src[i * 2]) + RGB565_G (src[i * 2 + 1])) / 2,
       
   513         (RGB565_B (src[i * 2]) + RGB565_B (src[i * 2 + 1])) / 2);
       
   514   }
       
   515 }
       
   516 #ifdef __SYMBIAN32__
       
   517 EXPORT_C
       
   518 #endif
       
   519 
       
   520 
       
   521 void
       
   522 vs_scanline_resample_nearest_RGB565 (uint8_t * dest_u8, uint8_t * src_u8, int n,
       
   523     int *accumulator, int increment)
       
   524 {
       
   525   uint16_t *dest = (uint16_t *) dest_u8;
       
   526   uint16_t *src = (uint16_t *) src_u8;
       
   527   int acc = *accumulator;
       
   528   int i;
       
   529   int j;
       
   530   int x;
       
   531 
       
   532   for (i = 0; i < n; i++) {
       
   533     j = acc >> 16;
       
   534     x = acc & 0xffff;
       
   535     dest[i] = (x < 32768) ? src[j] : src[j + 1];
       
   536 
       
   537     acc += increment;
       
   538   }
       
   539 
       
   540   *accumulator = acc;
       
   541 }
       
   542 #ifdef __SYMBIAN32__
       
   543 EXPORT_C
       
   544 #endif
       
   545 
       
   546 
       
   547 void
       
   548 vs_scanline_resample_linear_RGB565 (uint8_t * dest_u8, uint8_t * src_u8, int n,
       
   549     int *accumulator, int increment)
       
   550 {
       
   551   uint16_t *dest = (uint16_t *) dest_u8;
       
   552   uint16_t *src = (uint16_t *) src_u8;
       
   553   int acc = *accumulator;
       
   554   int i;
       
   555   int j;
       
   556   int x;
       
   557 
       
   558   for (i = 0; i < n; i++) {
       
   559     j = acc >> 16;
       
   560     x = acc & 0xffff;
       
   561     dest[i] = RGB565 (
       
   562         (RGB565_R (src[j]) * (65536 - x) + RGB565_R (src[j + 1]) * x) >> 16,
       
   563         (RGB565_G (src[j]) * (65536 - x) + RGB565_G (src[j + 1]) * x) >> 16,
       
   564         (RGB565_B (src[j]) * (65536 - x) + RGB565_B (src[j + 1]) * x) >> 16);
       
   565 
       
   566     acc += increment;
       
   567   }
       
   568 
       
   569   *accumulator = acc;
       
   570 }
       
   571 #ifdef __SYMBIAN32__
       
   572 EXPORT_C
       
   573 #endif
       
   574 
       
   575 
       
   576 void
       
   577 vs_scanline_merge_linear_RGB565 (uint8_t * dest_u8, uint8_t * src1_u8,
       
   578     uint8_t * src2_u8, int n, int x)
       
   579 {
       
   580   uint16_t *dest = (uint16_t *) dest_u8;
       
   581   uint16_t *src1 = (uint16_t *) src1_u8;
       
   582   uint16_t *src2 = (uint16_t *) src2_u8;
       
   583   int i;
       
   584 
       
   585   for (i = 0; i < n; i++) {
       
   586     dest[i] = RGB565 (
       
   587         (RGB565_R (src1[i]) * (65536 - x) + RGB565_R (src2[i]) * x) >> 16,
       
   588         (RGB565_G (src1[i]) * (65536 - x) + RGB565_G (src2[i]) * x) >> 16,
       
   589         (RGB565_B (src1[i]) * (65536 - x) + RGB565_B (src2[i]) * x) >> 16);
       
   590   }
       
   591 }
       
   592 
       
   593 
       
   594 /* RGB555 */
       
   595 
       
   596 /* note that src and dest are uint16_t, and thus endian dependent */
       
   597 
       
   598 #define RGB555_R(x) (((x)&0x7c00)>>8 | ((x)&0x7c00)>>13)
       
   599 #define RGB555_G(x) (((x)&0x03e0)>>3 | ((x)&0x03e0)>>9)
       
   600 #define RGB555_B(x) (((x)&0x001f)<<3 | ((x)&0x001f)>>2)
       
   601 
       
   602 #define RGB555(r,g,b) \
       
   603   ((((r)<<7)&0x7c00) | (((g)<<3)&0x03e0) | (((b)>>3)&0x001f))
       
   604 
       
   605 #ifdef __SYMBIAN32__
       
   606 EXPORT_C
       
   607 #endif
       
   608 void
       
   609 vs_scanline_downsample_RGB555 (uint8_t * dest_u8, uint8_t * src_u8, int n)
       
   610 {
       
   611   uint16_t *dest = (uint16_t *) dest_u8;
       
   612   uint16_t *src = (uint16_t *) src_u8;
       
   613   int i;
       
   614 
       
   615   for (i = 0; i < n; i++) {
       
   616     dest[i] = RGB555 (
       
   617         (RGB555_R (src[i * 2]) + RGB555_R (src[i * 2 + 1])) / 2,
       
   618         (RGB555_G (src[i * 2]) + RGB555_G (src[i * 2 + 1])) / 2,
       
   619         (RGB555_B (src[i * 2]) + RGB555_B (src[i * 2 + 1])) / 2);
       
   620   }
       
   621 }
       
   622 #ifdef __SYMBIAN32__
       
   623 EXPORT_C
       
   624 #endif
       
   625 
       
   626 
       
   627 void
       
   628 vs_scanline_resample_nearest_RGB555 (uint8_t * dest_u8, uint8_t * src_u8, int n,
       
   629     int *accumulator, int increment)
       
   630 {
       
   631   uint16_t *dest = (uint16_t *) dest_u8;
       
   632   uint16_t *src = (uint16_t *) src_u8;
       
   633   int acc = *accumulator;
       
   634   int i;
       
   635   int j;
       
   636   int x;
       
   637 
       
   638   for (i = 0; i < n; i++) {
       
   639     j = acc >> 16;
       
   640     x = acc & 0xffff;
       
   641     dest[i] = (x < 32768) ? src[j] : src[j + 1];
       
   642 
       
   643     acc += increment;
       
   644   }
       
   645 
       
   646   *accumulator = acc;
       
   647 }
       
   648 #ifdef __SYMBIAN32__
       
   649 EXPORT_C
       
   650 #endif
       
   651 
       
   652 
       
   653 void
       
   654 vs_scanline_resample_linear_RGB555 (uint8_t * dest_u8, uint8_t * src_u8, int n,
       
   655     int *accumulator, int increment)
       
   656 {
       
   657   uint16_t *dest = (uint16_t *) dest_u8;
       
   658   uint16_t *src = (uint16_t *) src_u8;
       
   659   int acc = *accumulator;
       
   660   int i;
       
   661   int j;
       
   662   int x;
       
   663 
       
   664   for (i = 0; i < n; i++) {
       
   665     j = acc >> 16;
       
   666     x = acc & 0xffff;
       
   667     dest[i] = RGB555 (
       
   668         (RGB555_R (src[j]) * (65536 - x) + RGB555_R (src[j + 1]) * x) >> 16,
       
   669         (RGB555_G (src[j]) * (65536 - x) + RGB555_G (src[j + 1]) * x) >> 16,
       
   670         (RGB555_B (src[j]) * (65536 - x) + RGB555_B (src[j + 1]) * x) >> 16);
       
   671 
       
   672     acc += increment;
       
   673   }
       
   674 
       
   675   *accumulator = acc;
       
   676 }
       
   677 #ifdef __SYMBIAN32__
       
   678 EXPORT_C
       
   679 #endif
       
   680 
       
   681 
       
   682 void
       
   683 vs_scanline_merge_linear_RGB555 (uint8_t * dest_u8, uint8_t * src1_u8,
       
   684     uint8_t * src2_u8, int n, int x)
       
   685 {
       
   686   uint16_t *dest = (uint16_t *) dest_u8;
       
   687   uint16_t *src1 = (uint16_t *) src1_u8;
       
   688   uint16_t *src2 = (uint16_t *) src2_u8;
       
   689   int i;
       
   690 
       
   691   for (i = 0; i < n; i++) {
       
   692     dest[i] = RGB555 (
       
   693         (RGB555_R (src1[i]) * (65536 - x) + RGB555_R (src2[i]) * x) >> 16,
       
   694         (RGB555_G (src1[i]) * (65536 - x) + RGB555_G (src2[i]) * x) >> 16,
       
   695         (RGB555_B (src1[i]) * (65536 - x) + RGB555_B (src2[i]) * x) >> 16);
       
   696   }
       
   697 }