J2ME插值算法实现图片的放大缩小[3]

[入库:2006年2月23日] [更新:2007年3月24日]

本文简介:

很明显原始表格宽度srcW = 4;放大后的表格宽度desW = 6;所以distance = desW = 6
接下来进入for循环,我们一步步的演算其循环的过程
-----------------------------------------------
| i| tabX赋值操作| tems | temd| sb | db |
-----------------------------------------------
|0|  tabX[0] = 0 |   4   |   6    |  0  |  0 |
-----------------------------------------------
|1|  tabX[0] = 0 |   2   |   6    |  1  |  1 |
-----------------------------------------------
|2|  tabX[0] = 1 |   6   |   6    |  1  |  2 |
-----------------------------------------------
|3|  tabX[0] = 1 |   4   |   6    |  2  |  3 |
-----------------------------------------------
|4|  tabX[0] = 2 |   2   |   6    |  3  |  4 |
-----------------------------------------------
|5|  tabX[0] = 3 |   6   |   6    |  3  |  5 |
-----------------------------------------------
|6|  tabX[0] = 3 |   4   |   6    |  4  |  6 |
-----------------------------------------------
有此得到放大后1*6的表格为下图所示。其中每一个单元格中的数字n表示这个单元格的内容,和原始表格中第n个单元格的内容一样。
--------------------------
| 0 | 1 | 1 | 2 | 3 | 3 |
--------------------------
例如,左图为原始表格,右图为放大的表格
---------------------      --------------------------------
| 红 | 绿 | 兰 | 紫 |      | 红 | 绿 |  绿 | 兰 | 紫 | 紫 |
---------------------      --------------------------------
同样,垂直方向的插值表我们也可以用相同的方法获得。

有了2个插值表,下面就可以生成放大和缩小后的图像了。
    short[] desBuf = new short[desW * desH];
    int dx = 0;
    int dy = 0;
    int sx = 0;
    int sy = 0;
    int oldy = -1;
    for (int i = 0; i < desH; i++) {
      if (oldy == tabY[i]) {  /**********情况一**********/
        System.arraycopy(desBuf, dy - desW, desBuf, dy, desW);

      } else { /**********情况二**********/
        dx = 0;
        for (int j = 0; j < desW; j++) {
          desBuf[dy + dx] = srcBuf[sy + tabX[j]];
          dx++;
        }
        sy += (tabY[i] - oldy) * srcW;

      }
      oldy = tabY[i];
      dy += desW;
    }

desBuf是用来保存放大缩小后的图像数据。例如我们把一个4*4像素的图像A放大成6*6的图像B,据前面的介绍我们可以生成2个插值表。tabX = {0,1,1,2,3,3},tabY = {0,1,1,2,3,3}。
在循环中会判断是否oldy 等于 tabY[i],这个操作等同于tabY[i-1]是否等于tabY[i]。如果等于,表示图像B前一行已经生成的数据和即将要生成的第i行数据相同,则只要执行System.arraycopy(desBuf, dy - desW, desBuf, dy, desW)把上一行的数据复制过来即可;如果不等,则需要对照水平插值表tabX生成这一行的数据。
算法演示过程如下:
----------------------------
| i|oldy|tabY[i]|运算情况|
----------------------------
|0|-1   |   0    | 情况2  |
----------------------------
|1| 0   |   1    | 情况2  |
----------------------------
|2| 1   |   1    | 情况1  |
----------------------------
|3| 1   |   2    | 情况2  |
----------------------------
|4| 2   |   3    | 情况2  |
----------------------------
|5| 3   |   3    | 情况1  |
----------------------------
然后我们用desBuf生成最终放大或缩小后的图片
    desImg = Image.createImage(desW, desH);
    DirectUtils.getDirectGraphics(desImg.getGraphics()).
        drawPixels(desBuf, true, 0, desW, 0, 0, desW, desH, 0, 444);
    return desImg;

下面是采用此算法实现放大缩小的效果图

 

 

 

 

本文关键:J2ME插值算法实现图片的放大缩小
 

本站最佳浏览方式为 分辨率 1024x768 IE 6.0(或更高版本的 IE浏览器)

go top