Advertisement
Guest User

Untitled

a guest
Feb 20th, 2019
82
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 2.63 KB | None | 0 0
  1. //
  2. // imgdiff.c
  3. // imgdiff
  4. //
  5. // Created by Rory B. Bellows on 26/03/2018.
  6. // Copyright © 2018 Rory B. Bellows. All rights reserved.
  7. //
  8.  
  9. #define STB_IMAGE_IMPLEMENTATION
  10. #include "3rdparty/stb_image.h"
  11. #define STB_IMAGE_RESIZE_IMPLEMENTATION
  12. #include "3rdparty/stb_image_resize.h"
  13. #include <stdio.h>
  14. #include <unistd.h>
  15.  
  16. typedef struct {
  17. int* data, w, h;
  18. } image_t;
  19.  
  20. #define RGB(r, g, b) (((unsigned int)r) << 16) | (((unsigned int)g) << 8) | b
  21. #define XYSET(img, x, y, v) (img->data[(y) * img->w + (x)] = (v))
  22. #define XYGET(img, x, y) (img->data[(y) * img->w + (x)])
  23.  
  24. image_t* load_image(const char* path, int re_w, int re_h) {
  25. if (access(path, F_OK) == -1) {
  26. fprintf(stderr, "ERROR! Invlaid filepath \"%s\"!\n", path);
  27. return NULL;
  28. }
  29.  
  30. int w, h, c;
  31. unsigned char* data = stbi_load(path, &w, &h, &c, STBI_rgb);
  32. if (!data) {
  33. fprintf(stderr, "ERROR! Failed to load \"%s\"!\n", path);
  34. return NULL;
  35. }
  36.  
  37. if ((re_w > 0 && re_h > 0) && (re_w != w || re_h != h)) {
  38. unsigned char* re_data = malloc(re_w * re_h * 3);
  39. stbir_resize_uint8(data, w, h, 0, re_data, re_w, re_h, 0, 3);
  40. stbi_image_free(data);
  41. data = re_data;
  42. w = re_w;
  43. h = re_h;
  44. }
  45.  
  46. image_t* ret = malloc(sizeof(image_t));
  47. if (!ret) {
  48. fprintf(stderr, "ERROR! Out of memory!\n");
  49. return NULL;
  50. }
  51. size_t s = w * h * sizeof(unsigned int) + 1;
  52. ret->data = malloc(s);
  53. if (!ret->data) {
  54. fprintf(stderr, "ERROR! Out of memory!\n");
  55. return NULL;
  56. }
  57. memset(ret->data, 0, s);
  58.  
  59. ret->w = w;
  60. ret->h = h;
  61. for (int x = 0; x < w; ++x) {
  62. for (int y = 0; y < h; ++y) {
  63. unsigned char* p = data + (x + h * y) * c;
  64. XYSET(ret, x, y, RGB(p[0], p[1], p[2]));
  65. }
  66. }
  67.  
  68. stbi_image_free(data);
  69. return ret;
  70. }
  71.  
  72. int main(int argc, const char * argv[]) {
  73. if (argc != 3) {
  74. fprintf(stderr, "ERROR! Invlaid number of arguments! Expected 2, got %d\n", argc - 1);
  75. return 1;
  76. }
  77.  
  78. image_t *a = NULL, *b = NULL;
  79. if (!(a = load_image(argv[1], -1, -1)))
  80. return 2;
  81. if (!(b = load_image(argv[2], a->w, a->h))) {
  82. free(a->data);
  83. free(a);
  84. return 3;
  85. }
  86.  
  87. double diff = 0.;
  88. for (int x = 0; x < a->w; ++x) {
  89. for (int y = 0; y < a->h; ++y) {
  90. int a_col = XYGET(a, x, y), b_col = XYGET(b, x, y);
  91. diff += fabs(((a_col >> 16) & 0xFF) - ((b_col >> 16) & 0xFF)) / 255.0;
  92. diff += fabs(((a_col >> 8) & 0xFF) - ((b_col >> 8) & 0xFF)) / 255.0;
  93. diff += fabs( (a_col & 0xFF) - (b_col & 0xFF)) / 255.0;
  94. }
  95. }
  96. printf("%lf%%\n", 100. * diff / (double)(a->w * a->h * 3));
  97.  
  98. if (a) {
  99. free(a->data);
  100. free(a);
  101. }
  102. if (b) {
  103. free(b->data);
  104. free(b);
  105. }
  106. return 0;
  107. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement