文章目录

  • I. Floyd-Steinberg-Dithering
    • I.i. 动态数组实现
    • I.ii. 指针实现
  • II. Stucki
  • III. 示例

I. Floyd-Steinberg-Dithering

Github: Native-Floyd-Steinberg-Dithering
该作者对Floyd-Steinberg-Dithering 的处理中,使用的是静态数组,容易栈溢出。
这里,给出两种实现来避免。当然,若一次处理的位图信息过大,也是会堆溢出,OOM的。

I.i. 动态数组实现

cpp 代码如下。

void floydSteinberg1(AndroidBitmapInfo *info, void *pixels) {uint32_t *pixelLine;void *p = pixels;int w = info->width;int h = info->height;
//    uint32_t ary[h][w];uint32_t **ary = new uint32_t *[h];for (int y = 0; y < h; ++y) {ary[y] = new uint32_t[w];pixelLine = (uint32_t *) p;for (int x = 0; x < w; ++x) {//extract the RGB values from the pixelary[y][x] = 0xFF000000 | (pixelLine[x] & 0x00FFFFFF);}p = (char *) p + info->stride;}for (int y = 0; y < h; ++y) {pixelLine = (uint32_t *) pixels;for (int x = 0; x < w; ++x) {uint32_t oldPixel = ary[y][x];
//            uint32_t newPixel = find_closest_palette_color(oldPixel);uint32_t newPixel = (int) oldPixel >= 128 ? 0xFFFFFFFF : 0xFF000000;pixelLine[x] = newPixel;uint32_t err = oldPixel - newPixel;if (x + 1 < w)ary[y][x + 1] += (int) (err * (7. / 16));if (x > 0 && y + 1 < h)ary[y + 1][x - 1] += (int) (err * (3. / 16));if (y + 1 < h)ary[y + 1][x] += (int) (err * (5. / 16));if (x + 1 < w && y + 1 < h)ary[y + 1][x + 1] += (int) (err * (1. / 16));}pixels = (char *) pixels + info->stride;}for (int y = 0; y < h; ++y) {delete ary[y];}delete[] ary;
}

I.ii. 指针实现

void floydSteinberg2(AndroidBitmapInfo *info, void *pixels) {int w = info->width;int h = info->height;int mid = 128;uint32_t min = 0xFF000000;uint32_t max = 0xFFFFFFFF;
//    uint32_t minWhite = 0xFFFF0000;for (int y = 0; y < h; ++y) {for (int x = 0; x < w; ++x) {uint32_t pixel = *((uint32_t *) pixels + y * w + x);
//            if (pixel >= minWhite && pixel <= max) {//接近白色不处理
//                continue;
//            }uint32_t err = (int) pixel >= mid ? pixel - max : pixel - min;if (x + 1 < w) {*((uint32_t *) pixels + y * w + (x + 1)) += (int) (err * (7. / 16));}if (x >= 1 && y + 1 < h) {*((uint32_t *) pixels + (y + 1) * w + (x - 1)) += (int) (err * (3. / 16));}if (y + 1 < h) {*((uint32_t *) pixels + (y + 1) * w + x) += (int) (err * (5. / 16));}if (x + 1 < w && y + 1 < h) {*((uint32_t *) pixels + (y + 1) * w + (x + 1)) += (int) (err * (1. / 16));}pixel = (int) pixel >= mid ? max : min;*((uint32_t *) pixels + y * w + x) = pixel;}}
}

II. Stucki

本算法,是从一段c#代码中移植出来的。

void stucki(AndroidBitmapInfo *info, void *pixels) {int w = info->width;int h = info->height;int mid = 128;uint32_t max = 0xFF000000;uint32_t min = 0xFFFFFFFF;for (int y = 0; y < h; ++y) {for (int x = 0; x < w; ++x) {uint32_t pixel = *((uint32_t *) pixels + y * w + x);uint32_t err = (int) pixel >= mid ? pixel - min : pixel - max;if (x + 1 < w)*((uint32_t *) pixels + y * w + (x + 1)) += (int) (err * (8. / 42));if (x + 2 < w)*((uint32_t *) pixels + y * w + (x + 2)) += (int) (err * (4. / 42));if (x >= 2 && y + 1 < h)*((uint32_t *) pixels + (y + 1) * w + (x - 2)) += (int) (err * (2. / 42));if (x >= 1 && y + 1 < h)*((uint32_t *) pixels + (y + 1) * w + (x - 1)) += (int) (err * (4. / 42));if (y + 1 < h)*((uint32_t *) pixels + (y + 1) * w + (x)) += (int) (err * (8. / 42));if (x + 1 < w && y + 1 < h)*((uint32_t *) pixels + (y + 1) * w + (x + 1)) += (int) (err * (4. / 42));if (x + 2 < w && y + 1 < h)*((uint32_t *) pixels + (y + 1) * w + (x + 2)) += (int) (err * (2. / 42));if (x >= 2 && y + 2 < h)*((uint32_t *) pixels + (y + 2) * w + (x - 2)) += (int) (err * (1. / 42));if (x >= 1 && y + 2 < h)*((uint32_t *) pixels + (y + 2) * w + (x - 1)) += (int) (err * (2. / 42));if (y + 2 < h)*((uint32_t *) pixels + (y + 2) * w + (x)) += (int) (err * (4. / 42));if (x + 1 < w && y + 2 < h)*((uint32_t *) pixels + (y + 2) * w + (x + 1)) += (int) (err * (2. / 42));if (x + 2 < w && y + 2 < h)*((uint32_t *) pixels + (y + 2) * w + (x + 2)) += (int) (err * (1. / 42));pixel = (int) pixel >= mid ? min : max;*((uint32_t *) pixels + y * w + x) = pixel;}}
}

III. 示例

完整示例


Android Floyd-Steinberg-Dithering、Stucki-dither 抖动处理相关推荐

  1. matlab抖g是什么,MATLAB中dither抖动函数的用法

    不知道dither存在的意义,既然MATLAB中有它,就一定有它的价值吧,书上说在出版和印刷业中应用的较多,我也不清楚. MATLAB帮助文档说dither可抖动灰度图像和RGB彩色图像,将灰度图像转 ...

  2. Android 性能优化 - 彻底解决内存抖动

    起源 内存抖动是由于短时间内有大量对象进出新生区导致的,它伴随着频繁的GC. gc会大量占用ui线程和cpu资源,会导致app整体卡顿 android profile 效果图如下图 Memory 中 ...

  3. 图像处理的Dither和Banding

    最近在看动态改变Android,xml中<shape>标签的文件.其中 dither不明白,就搜了下. 转载于:http://teok.iteye.com/blog/1190942   ( ...

  4. Unity Shader - 搬砖日志 - Dithering

    文章目录 什么时 Dithering 色阶纹理图案 - Texture Dither Pattern 程序化 动态 Dithering - 让 RGBA8888 压缩到 RGBA4444 而没有明显色 ...

  5. 基于错误扩散的Floyd-Steinbery抖动算法简单理解

    1. 图像处理中的dithering技术     它是一种欺骗你眼睛,使用有限的色彩让你看到比实际图象更多色彩的显示方式.通过在相邻像素间随机的加入不同的颜色来修饰图象,通常这种方式被用于颜色较少的情 ...

  6. python Png图片压缩工具

    引言 最近在做 H5 小游戏的开发,与 App 不同,由于 H5 所有的资源都是通过 CDN 获取的,考虑到网络资源加载速度的问题,优化资源显得格外重要.因此,图片资源的压缩也是必不可少的. 起源 起 ...

  7. BppAttack:通过图像量化和对比对抗学习来攻击深度神经网络

    BppAttack:通过图像量化和对比对抗学习来攻击深度神经网络 论文地址:BppAttack 一. 当前主流trigger: image patches:BadNet watermark: imag ...

  8. 【pngquant】使用Python压缩图片,降低网页加载时间

    更多内容请点击 我的博客 查看,欢迎来访. 用来做什么? 个人在写博客时,发现上传的图片如果很大,web访问第一次加载该图片就特别的慢. 可以考虑使用缩略图,浏览时显示缩略图,如果要看高清图,需点击图 ...

  9. Image Dithering: Eleven Algorithms and Source Code Dithering: An Overview

    Image Dithering: Eleven Algorithms and Source Code Dithering: An Overview Today's graphics programmi ...

  10. 编程小知识之 Dithering

    本文简单介绍了 Dithering(抖动) 的一些知识 图形后处理有一种操作称为 Dithering(抖动),所谓 Dithering,就是一种能够在较小色彩空间上"模拟出"较大色 ...

最新文章

  1. Laravel-自定全局函数
  2. 【错误记录】Ubuntu 修改 hosts 文件 ( 使用 gedit /etc/hosts 命令打开并修改 hosts 文件 )
  3. 链表反转相关的题(C++模板)
  4. 计算机接口技术试题及答案,2014.3计算机接口技术总复习题及答案
  5. centos7源代码安装mysql5.7_CentOS7源码编译安装MySQL5.7.11
  6. 02-继承的本质-Objective-C基础
  7. 外点惩处函数法·约束优化问题
  8. python 会增加内存吗,Python+不断增加的内存分配
  9. ElasticSearch聚合查询
  10. Django1.7如何配置静态资源访问
  11. autocad型源代码_C# 实现预览dwg文件完整源代码(无需autocad环境)
  12. unity ui框架_[教程汇总+持续更新]Unity从入门到入坟——收藏这一篇就够了
  13. soltrace教程(3)基本使用
  14. 使用Mapnik生成地形图——thematicmapping.org译文(四)
  15. 使用Docker保护软件供应链安全
  16. SNN系列|神经元模型篇(1) Hodgkin Huxley
  17. git分支拉取develop分支最新代码
  18. 【颜纠日记】笔记本电脑很卡怎么办,教你解决电脑卡机卡顿
  19. Linux命令分隔符
  20. 万能RecyclerView分割线扩展

热门文章

  1. docker出现 Error starting userland proxy: listen tcp4 0.0.0.0:3306: bind: address already in use的解决方法
  2. Xilinx FPGA MIPI 接口简单说明
  3. 「Linux」网络配置大揭秘
  4. 小记 xian80 坐标转换 wgs84
  5. arcgis server 无法识别字体原因
  6. 人可以N次踏进同一条河流
  7. mac bookpro m1 笔记本关闭键盘屏幕 禁用键盘屏幕使用 键盘屏幕误触 Touch Bar禁用 禁用MacBook-Pro的触摸栏
  8. molar mass
  9. 鸡兔同笼——算法详解
  10. 爬取分析拉勾网招聘信息