123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172 |
- #include "global-state.h"
- #include "hashing.h"
- #include "data-structure.h"
- #include "raylib.h"
- #include <stdio.h>
- const unsigned ResizedSide64 = 8;
- const unsigned ResizedSq64 = ResizedSide64 * ResizedSide64;
- const unsigned ResizedSide256 = 16;
- const unsigned ResizedSq256 = ResizedSide256 * ResizedSide256;
- extern ProcessingOptions ProcOptions;
- void
- PUHS_Compare_Hashes_256bit ( Imagefile * im1, Imagefile * im2 )
- {
- if ( im1 == NULL || im2 == NULL )
- {
- fprintf( stderr, "ERROR, IMAGE IN ELEMENT IS NULL!\n" );
- return;
- }
- if ( im1->hash == NULL || im2->hash == NULL )
- return;
- if ( im1->group != NULL && im2->group != NULL )
- return;
- HASH64BIT similarity_hash[4];
- for ( unsigned i = 0; i < ResizedSq256; ++i )
- similarity_hash[i / 64] = im1->hash[i / 64] ^ im2->hash[i / 64];
- unsigned similar_bits = ResizedSq256;
- for ( unsigned i = 0; i < ResizedSq256 / 64; ++i )
- while ( similarity_hash[i] != 0 )
- {
- similar_bits--;
- similarity_hash[i] &= similarity_hash[i] - 1;
- }
- if ( similar_bits / (float)ResizedSq256 >= ProcOptions.threshold )
- {
- if ( im1->group == NULL && im2->group == NULL )
- PUDS_Create_group( im1, im2, sizeof(HASH64BIT) );
- else
- {
- if ( im1->group == NULL )
- PUDS_Add_to_group( im1, im2->group );
- else
- PUDS_Add_to_group( im2, im1->group );
- }
- }
- }
- void
- PUHS_Compare_Hashes_64bit ( Imagefile * im1, Imagefile * im2 )
- {
- if ( im1 == NULL || im2 == NULL )
- {
- fprintf( stderr, "ERROR, IMAGE IN ELEMENT IS NULL!\n" );
- return;
- }
- if ( im1->hash == NULL || im2->hash == NULL )
- return;
- if ( im1->group != NULL && im2->group != NULL )
- return;
- HASH64BIT similarity_hash = im1->hash[0] ^ im2->hash[0];
- unsigned similar_bits = ResizedSq64;
- while ( similarity_hash != 0 )
- {
- similar_bits--;
- similarity_hash &= similarity_hash - 1;
- }
- if ( similar_bits / (float)ResizedSq64 >= ProcOptions.threshold )
- {
- if ( im1->group == NULL && im2->group == NULL )
- PUDS_Create_group( im1, im2, sizeof(HASH64BIT) );
- else
- {
- if ( im1->group == NULL )
- PUDS_Add_to_group( im1, im2->group );
- else
- PUDS_Add_to_group( im2, im1->group );
- }
- }
- }
- void
- PUHS_Hash_Dhash_256bit ( Imagefile * im )
- {
- if ( im->hash != NULL )
- free(im->hash);
- if ( !FileExists(im->path->s) )
- {
- fprintf( stderr, "File %s is suddenly missing!\n", im->path->s );
- im->hashed = false;
- return;
- }
- Image img = LoadImage( im->path->s );
- if ( img.data == NULL )
- {
- fprintf( stderr, "Failed to load image %s\n", im->path->s );
- im->hashed = false;
- return;
- }
- ImageResize( &img, ResizedSide256 + 1, ResizedSide256 );
- ImageColorGrayscale(&img);
- im->hash = calloc( 4, sizeof(HASH64BIT) );
- uint8_t * data = img.data;
- for ( unsigned u = 0, i = 0, bt = 0; u < ResizedSide256; ++u )
- {
- for ( unsigned v = 0; v < ResizedSide256; ++v, ++i, ++bt )
- im->hash[bt / 64] |= (HASH64BIT)( (unsigned)( data[i] - data[i + 1] ) >> ( sizeof(int) * 8 - 1 ) ) << ( bt % 64 );
- i++;
- }
- UnloadImage(img);
- im->hashed = true;
- }
- void
- PUHS_Hash_Dhash_64bit ( Imagefile * im )
- {
- if ( im->hash != NULL )
- free(im->hash);
- if ( !FileExists(im->path->s) )
- {
- fprintf( stderr, "File %s is suddenly missing!\n", im->path->s );
- im->hashed = false;
- return;
- }
- Image img = LoadImage( im->path->s );
- if ( img.data == NULL )
- {
- fprintf( stderr, "Failed to load image %s\n", im->path->s );
- im->hashed = false;
- return;
- }
- ImageResize( &img, ResizedSide64 + 1, ResizedSide64 );
- ImageColorGrayscale(&img);
- im->hash = calloc( 1, sizeof(HASH64BIT) );
- uint8_t * data = img.data;
- for ( unsigned u = 0, i = 0, bt = 0; u < ResizedSide64; ++u )
- {
- for ( unsigned v = 0; v < ResizedSide64; ++v, ++i, ++bt )
- im->hash[0] |= (HASH64BIT)( (unsigned)( data[i] - data[i + 1] ) >> ( sizeof(int) * 8 - 1 ) ) << bt;
- i++;
- }
- UnloadImage(img);
- im->hashed = true;
- }
|