netzel commited on 2024-03-19 18:06:41
Showing 2 changed files, with 117 additions and 5 deletions.
... | ... |
@@ -30,6 +30,7 @@ typedef struct { |
30 | 30 |
GDALRasterBandH band_h; |
31 | 31 |
int is_no_data; |
32 | 32 |
double no_data; |
33 |
+ int shift_cols, shift_rows; |
|
33 | 34 |
double *buffer; |
34 | 35 |
double *iobuffer; |
35 | 36 |
} layer; |
... | ... |
@@ -312,6 +313,34 @@ int get_band_number(const char *data) { |
312 | 313 |
return result; |
313 | 314 |
} |
314 | 315 |
|
316 |
+int get_shift_cols(const char *data) { |
|
317 |
+ int l = (int)strlen(data)+2; |
|
318 |
+ char *s = (char *)malloc(l); |
|
319 |
+ strcpy(s,data); |
|
320 |
+ char **toks = str_tokens(s,':'); |
|
321 |
+ char *tok = toks[2]; |
|
322 |
+ int result = 0; |
|
323 |
+ if(tok!=NULL && *tok!='\0') |
|
324 |
+ result = atoi(tok); |
|
325 |
+ free(s); |
|
326 |
+ free(toks); |
|
327 |
+ return result; |
|
328 |
+} |
|
329 |
+ |
|
330 |
+int get_shift_rows(const char *data) { |
|
331 |
+ int l = (int)strlen(data)+2; |
|
332 |
+ char *s = (char *)malloc(l); |
|
333 |
+ strcpy(s,data); |
|
334 |
+ char **toks = str_tokens(s,':'); |
|
335 |
+ char *tok = toks[3]; |
|
336 |
+ int result = 0; |
|
337 |
+ if(tok!=NULL && *tok!='\0') |
|
338 |
+ result = atoi(tok); |
|
339 |
+ free(s); |
|
340 |
+ free(toks); |
|
341 |
+ return result; |
|
342 |
+} |
|
343 |
+ |
|
315 | 344 |
|
316 | 345 |
layer *open_inputs(struct arg_str *input) { |
317 | 346 |
int i; |
... | ... |
@@ -339,6 +368,8 @@ layer *open_inputs(struct arg_str *input) { |
339 | 368 |
|
340 | 369 |
fname = get_file_name(input->sval[i]); |
341 | 370 |
band = get_band_number(input->sval[i]); |
371 |
+ layers[i].shift_cols = get_shift_cols(input->sval[i]); |
|
372 |
+ layers[i].shift_rows = get_shift_rows(input->sval[i]); |
|
342 | 373 |
|
343 | 374 |
layers[i].dataset_h = GDALOpenShared(fname,GA_ReadOnly); |
344 | 375 |
if(!(layers[i].dataset_h)) { |
... | ... |
@@ -360,7 +391,7 @@ layer *open_inputs(struct arg_str *input) { |
360 | 391 |
layers[i].buffer = (double *)malloc(cols*sizeof(double)); |
361 | 392 |
layers[i].iobuffer = (double *)malloc(cols*sizeof(double)); |
362 | 393 |
|
363 |
- fprintf(stderr,"Input layer %s, band: %d", fname, band); |
|
394 |
+ fprintf(stderr,"Input layer %s, band: %d, shift: %d,%d", fname, band, layers[i].shift_cols, layers[i].shift_rows); |
|
364 | 395 |
if(layers[i].is_no_data==1) |
365 | 396 |
fprintf(stderr,", no_data: %lf",layers[i].no_data); |
366 | 397 |
fprintf(stderr,"\n"); |
... | ... |
@@ -489,19 +520,62 @@ void close_outputs(layer **layers) { |
489 | 520 |
free(*layers); |
490 | 521 |
*layers = NULL; |
491 | 522 |
} |
523 |
+/* |
|
524 |
+void read_buffers(int ninputs, layer *layers, int row) { |
|
525 |
+ int i; |
|
526 |
+ CPLErr res; |
|
527 |
+ for(i=0; i<ninputs; i++) { |
|
528 |
+ |
|
529 |
+ res=GDALRasterIO(layers[i].band_h, GF_Read, 0, row, cols, 1, |
|
530 |
+ layers[i].buffer, cols, 1, GDT_Float64, 0, 0); |
|
531 |
+ if(res>2) { |
|
532 |
+ show_message(stderr, "Error in data reading!"); |
|
533 |
+ exit(1); |
|
534 |
+ } |
|
535 |
+ } |
|
536 |
+}*/ |
|
492 | 537 |
|
493 | 538 |
void read_buffers(int ninputs, layer *layers, int row) { |
494 | 539 |
int i; |
495 | 540 |
CPLErr res; |
496 | 541 |
for(i=0; i<ninputs; i++) { |
497 | 542 |
|
543 |
+ double d = 0.0; |
|
544 |
+ double *p; |
|
545 |
+ row -= layers[i].shift_rows; |
|
546 |
+ if(row<0 || row>=rows) { |
|
547 |
+ if(layers[i].is_no_data) d = layers[i].no_data; |
|
548 |
+ p = layers[i].buffer; |
|
549 |
+ for(i=0; i<cols; i++) |
|
550 |
+ *(p++) = d; |
|
551 |
+ } else { |
|
552 |
+ if(layers[i].shift_cols==0) |
|
498 | 553 |
res=GDALRasterIO(layers[i].band_h, GF_Read, 0, row, cols, 1, |
499 | 554 |
layers[i].buffer, cols, 1, GDT_Float64, 0, 0); |
555 |
+ else if(layers[i].shift_cols<0) { |
|
556 |
+ res=GDALRasterIO(layers[i].band_h, GF_Read,0, row, cols+layers[i].shift_cols, 1, |
|
557 |
+ layers[i].buffer-layers[i].shift_cols, cols + layers[i].shift_cols, 1, |
|
558 |
+ GDT_Float64, 0, 0); |
|
559 |
+ if(layers[i].is_no_data) d = layers[i].no_data; |
|
560 |
+ p = layers[i].buffer; |
|
561 |
+ for(i=0; i<-layers[i].shift_cols; i++) |
|
562 |
+ *(p++) = d; |
|
563 |
+ } else { // >0 |
|
564 |
+ res=GDALRasterIO(layers[i].band_h, GF_Read, layers[i].shift_cols, row, cols-layers[i].shift_cols, 1, |
|
565 |
+ layers[i].buffer, cols - layers[i].shift_cols, 1, GDT_Float64, 0, 0); |
|
566 |
+ if(layers[i].is_no_data) d = layers[i].no_data; |
|
567 |
+ p = layers[i].buffer + (cols - layers[i].shift_cols); |
|
568 |
+ for(i=0; i<layers[i].shift_cols; i++) |
|
569 |
+ *(p++) = d; |
|
570 |
+ } |
|
571 |
+ } |
|
500 | 572 |
if(res>2) { |
501 | 573 |
show_message(stderr, "Error in data reading!"); |
502 | 574 |
exit(1); |
503 | 575 |
} |
576 |
+ printf("layer[%d], row%d; ",i,row); |
|
504 | 577 |
} |
578 |
+ printf("\n"); |
|
505 | 579 |
} |
506 | 580 |
|
507 | 581 |
void write_buffers(int noutputs, layer *layers, int row) { |
... | ... |
@@ -518,8 +592,7 @@ void write_buffers(int noutputs, layer *layers, int row) { |
518 | 592 |
} |
519 | 593 |
} |
520 | 594 |
} |
521 |
- |
|
522 |
- |
|
595 |
+/* |
|
523 | 596 |
void read_iobuffer(layer *l, int cols, int row) { |
524 | 597 |
CPLErr res; |
525 | 598 |
res=GDALRasterIO(l->band_h, GF_Read, 0, row, cols, 1, |
... | ... |
@@ -528,6 +601,45 @@ void read_iobuffer(layer *l, int cols, int row) { |
528 | 601 |
show_message(stderr, "Error in data reading!"); |
529 | 602 |
exit(1); |
530 | 603 |
} |
604 |
+}*/ |
|
605 |
+ |
|
606 |
+void read_iobuffer(layer *l, int cols, int row) { |
|
607 |
+ |
|
608 |
+ int i; |
|
609 |
+ CPLErr res = 0; |
|
610 |
+ double d = 0.0; |
|
611 |
+ double *p; |
|
612 |
+ row += l->shift_rows; |
|
613 |
+ if(row<0 || row>=rows) { |
|
614 |
+ if(l->is_no_data) d = l->no_data; |
|
615 |
+ p = l->iobuffer; |
|
616 |
+ for(i=0; i<cols; i++) |
|
617 |
+ *(p++) = d; |
|
618 |
+ } else { |
|
619 |
+ if(l->shift_cols==0) |
|
620 |
+ res=GDALRasterIO(l->band_h, GF_Read, 0, row, cols, 1, |
|
621 |
+ l->iobuffer, cols, 1, GDT_Float64, 0, 0); |
|
622 |
+ else if(l->shift_cols<0) { |
|
623 |
+ res=GDALRasterIO(l->band_h, GF_Read,0, row, cols+l->shift_cols, 1, |
|
624 |
+ l->iobuffer-l->shift_cols, cols + l->shift_cols, 1, |
|
625 |
+ GDT_Float64, 0, 0); |
|
626 |
+ if(l->is_no_data) d = l->no_data; |
|
627 |
+ p = l->iobuffer; |
|
628 |
+ for(i=0; i<-l->shift_cols; i++) |
|
629 |
+ *(p++) = d; |
|
630 |
+ } else { // >0 |
|
631 |
+ res=GDALRasterIO(l->band_h, GF_Read, l->shift_cols, row, cols-l->shift_cols, 1, |
|
632 |
+ l->iobuffer, cols - l->shift_cols, 1, GDT_Float64, 0, 0); |
|
633 |
+ if(l->is_no_data) d = l->no_data; |
|
634 |
+ p = l->iobuffer + (cols - l->shift_cols); |
|
635 |
+ for(i=0; i<l->shift_cols; i++) |
|
636 |
+ *(p++) = d; |
|
637 |
+ } |
|
638 |
+ } |
|
639 |
+ if(res>2) { |
|
640 |
+ show_message(stderr, "Error in data reading!"); |
|
641 |
+ exit(1); |
|
642 |
+ } |
|
531 | 643 |
} |
532 | 644 |
|
533 | 645 |
void write_iobuffer(layer *l, int cols, int row) { |
... | ... |
@@ -787,7 +899,7 @@ int main(int argc,char **argv) { |
787 | 899 |
struct arg_lit *overwrite = arg_lit0("f", "force", "force to overwrite output file"); |
788 | 900 |
struct arg_lit *nan = arg_lit0(NULL, "use-nan", "force to treat NAN as a value (default: no-data)"); |
789 | 901 |
struct arg_int *threads = arg_int0("t", "threads", "<n>","number of threads"); |
790 |
- struct arg_str *input = arg_strn("i", "input", "file.tif[:band]",1,MAX_INPUTS,"input layer(s) (GeoTIFF)"); |
|
902 |
+ struct arg_str *input = arg_strn("i", "input", "file.tif[[[:band]:shit_x]:shif_y]",1,MAX_INPUTS,"input layer(s) (GeoTIFF or any other GDAL raster format), optionally followed by the band number, horizontal shift by the specified number of cells (a negative value means a rightward shift), vertical shift by the specified number of cells (a negative value means a downward shift)"); |
|
791 | 903 |
struct arg_str *output = arg_strn("o", "output", "file.tif[:type[:no_data:[compression]]]",0,MAX_OUTPUTS,"output layer(s): file name, data type (Byte, Int16, UInt16, Int32, UInt32, Float32, default Float64), no_data value (default 0.0), compress (NONE, DEFLATE, DEFLATE2, DEFLATE3, LZW, LZW2, LZW3). (GeoTIFF)"); |
792 | 904 |
struct arg_int *mem = arg_int0("m", "memory", "<n>","number of memory cells to store temporary data"); |
793 | 905 |
struct arg_str *memstore = arg_str0("s", "memory-store", "<file name>","file to store memory cells (TXT)"); |
794 | 906 |