summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/GipfelWidget.H9
-rw-r--r--src/GipfelWidget.cxx126
-rw-r--r--src/Hill.cxx8
-rw-r--r--src/ImageMetaData.cxx6
-rw-r--r--src/Makefile.am2
-rw-r--r--src/ScanImage.H31
-rw-r--r--src/ScanImage.cxx118
-rw-r--r--src/Stitch.H3
-rw-r--r--src/Stitch.cxx2
-rw-r--r--src/gipfel.cxx18
10 files changed, 191 insertions, 132 deletions
diff --git a/src/GipfelWidget.H b/src/GipfelWidget.H
index 24d0bb6..2e440c5 100644
--- a/src/GipfelWidget.H
+++ b/src/GipfelWidget.H
@@ -14,6 +14,7 @@
#include "Panorama.H"
#include "ImageMetaData.H"
+#include "ScanImage.H"
class GipfelWidget : public Fl_Group {
private:
@@ -37,12 +38,6 @@ class GipfelWidget : public Fl_Group {
void set_labels(Hills *v);
int get_rel_track_width(Hill *m);
- static int get_pixel_nearest(Fl_Image *img, double x, double y,
- int *r, int *g, int *b);
- static int get_pixel_bicubic(Fl_Image *img, double x, double y,
- int *r, int *g, int *b);
- static int get_pixel(Fl_Image *img, int x, int y,
- int *r, int *g, int *b);
static void find_peak_cb(Fl_Widget *o, void *f);
public:
@@ -91,7 +86,7 @@ class GipfelWidget : public Fl_Group {
void set_distortion_params(double k0, double k1, double x0);
Hills *get_mountains() { return pan->get_mountains(); };
int comp_params();
- int get_pixel(GipfelWidget::sample_mode_t,
+ int get_pixel(ScanImage::mode_t m,
double a_alph, double a_nick, int *r, int *g, int *b);
int get_distortion_profile_name(char *buf, int buflen);
int save_distortion_params(const char *prof_name, int force);
diff --git a/src/GipfelWidget.cxx b/src/GipfelWidget.cxx
index 91a9dc5..7e9f6fc 100644
--- a/src/GipfelWidget.cxx
+++ b/src/GipfelWidget.cxx
@@ -22,6 +22,7 @@
#include "Fl_Search_Chooser.H"
#include "choose_hill.H"
+#include "ScanImage.H"
#include "GipfelWidget.H"
#define CROSS_SIZE 2
@@ -245,6 +246,9 @@ GipfelWidget::draw() {
known_hills->contains(m) || m == focused_mountain)
continue;
+ if (fabs(m->x) > img->w() / 2 || fabs(m->y) > img->h() / 2)
+ continue;
+
fl_xyline(m_x - CROSS_SIZE, m_y, m_x + CROSS_SIZE);
fl_yxline(m_x, m_y + m->label_y - height, m_y + CROSS_SIZE);
fl_xyline(m_x, m_y + m->label_y - height, m_x + m->label_x);
@@ -259,6 +263,9 @@ GipfelWidget::draw() {
(!show_hidden && (m->flags & Hill::HIDDEN)) || m == focused_mountain)
continue;
+ if (fabs(m->x) > img->w() / 2 || fabs(m->y) > img->h() / 2)
+ continue;
+
if (known_hills->contains(m)) {
if (known_hills->get_num() > 3)
fl_color(FL_GREEN);
@@ -298,16 +305,16 @@ GipfelWidget::draw() {
m = track_points->get(i);
int m_x = w() / 2 + x() + (int) rint(m->x);
int m_y = h() / 2 + y() + (int) rint(m->y);
- if (!(track_points->get(i)->flags & Hill::VISIBLE)) {
+
+ if (!(track_points->get(i)->flags & Hill::VISIBLE))
continue;
- }
if (track_points->get(i)->flags & Hill::HIDDEN)
fl_color(FL_BLUE);
else
fl_color(FL_RED);
- fl_line_style(FL_SOLID|FL_CAP_ROUND|FL_JOIN_ROUND,
+ fl_line_style(FL_SOLID | FL_CAP_ROUND | FL_JOIN_ROUND,
get_rel_track_width(track_points->get(i)));
if (last_initialized) {
fl_begin_line();
@@ -348,6 +355,9 @@ GipfelWidget::set_labels(Hills *v) {
if (!show_hidden && (m->flags & Hill::HIDDEN))
continue;
+ if (fabs(m->x) > img->w() / 2 || fabs(m->y) > img->h() / 2)
+ continue;
+
m->label_x = (int) fl_width(m->name) + 1;
m->label_y = 0;
@@ -360,6 +370,9 @@ GipfelWidget::set_labels(Hills *v) {
if (!show_hidden && (n->flags & Hill::HIDDEN))
continue;
+ if (fabs(m->x) > img->w() / 2 || fabs(m->y) > img->h() / 2)
+ continue;
+
if (overlap(m->x, m->label_x, n->x - CROSS_SIZE, n->label_x))
colliding.add(n);
else
@@ -707,7 +720,7 @@ GipfelWidget::export_hills(const char *file, FILE *fp) {
}
int
-GipfelWidget::get_pixel(GipfelWidget::sample_mode_t m,
+GipfelWidget::get_pixel(ScanImage::mode_t m,
double a_alph, double a_nick, int *r, int *g, int *b) {
double px, py;
int ret;
@@ -718,114 +731,13 @@ GipfelWidget::get_pixel(GipfelWidget::sample_mode_t m,
if (pan->get_coordinates(a_alph, a_nick, &px, &py) != 0)
return 1;
- if (m == GipfelWidget::BICUBIC)
- ret = get_pixel_bicubic(img, px + ((double) img->w()) / 2.0,
- py + ((double) img->h()) / 2.0, r, g, b);
- else
- ret = get_pixel_nearest(img, px + ((double) img->w()) / 2.0,
- py + ((double) img->h()) / 2.0, r, g, b);
+ ret = ScanImage::get_pixel(img, m, px + ((double) img->w()) / 2.0,
+ py + ((double) img->h()) / 2.0, r, g, b);
return ret;
}
int
-GipfelWidget::get_pixel_nearest(Fl_Image *img, double x, double y,
- int *r, int *g, int *b) {
-
- if (isnan(x) || isnan(y))
- return 1;
- else
- return get_pixel(img, (int) rint(x), (int) rint(y), r, g, b);
-}
-
-static inline double
-interp_cubic(double x, double x2, double x3, double *v) {
- double a0, a1, a2, a3;
-
- a0 = v[3] - v[2] - v[0] + v[1];
- a1 = v[0] - v[1] - a0;
- a2 = v[2] - v[0];
- a3 = v[1];
-
- return a0 * x3 + a1 * x2 + a2 * x + a3;
-}
-
-int
-GipfelWidget::get_pixel_bicubic(Fl_Image *img, double x, double y,
- int *r, int *g, int *b) {
-
- double fl_x = floor(x);
- double fl_y = floor(y);
- double dx = x - fl_x, dx2 = dx * dx, dx3 = dx2 * dx;
- double dy = y - fl_y, dy2 = dy * dy, dy3 = dy2 * dy;
- int ic[3];
- double c[3][4];
- double c1[3][4];
-
- for (int iy = 0; iy < 4; iy++) {
- for (int ix = 0; ix < 4; ix++) {
-
- if (get_pixel(img, (int) fl_x + ix - 1, (int) fl_y + iy - 1,
- &ic[0], &ic[1], &ic[2]) != 0)
- return 1;
-
- for (int l = 0; l < 3; l++)
- c[l][ix] = (double) ic[l];
- }
-
- for (int l = 0; l < 3; l++)
- c1[l][iy] = interp_cubic(dx, dx2, dx3, c[l]);
- }
-
- *r = (int) rint(interp_cubic(dy, dy2, dy3, c1[0]));
- *g = (int) rint(interp_cubic(dy, dy2, dy3, c1[1]));
- *b = (int) rint(interp_cubic(dy, dy2, dy3, c1[2]));
- return 0;
-}
-
-int
-GipfelWidget::get_pixel(Fl_Image *img, int x, int y,
- int *r, int *g, int *b) {
- if ( img->d() == 0 )
- return 1;
-
- if (x < 0 || x >=img->w() || y < 0 || y >= img->h())
- return 1;
-
- long index = (y * img->w() * img->d()) + (x * img->d()); // X/Y -> buf index
- switch (img->count()) {
- case 1:
- { // bitmap
- const unsigned char *buf = (const unsigned char*) img->data()[0];
- switch (img->d())
- {
- case 1:
- *r = *g = *b = *(buf+index);
- break;
- case 3: // 24bit
- *r = (int) *(buf+index+0);
- *g = (int) *(buf+index+1);
- *b = (int) *(buf+index+2);
- break;
- default: // ??
- printf("Not supported: chans=%d\n", img->d());
- return 1;
- }
- break;
- }
- default: // ?? pixmap, bit vals
- printf("Not supported: count=%d\n", img->count());
- return 1;
- }
-
- *r = *r * 255;
- *g = *g * 255;
- *b = *b * 255;
-
- return 0;
-}
-
-int
GipfelWidget::get_distortion_profile_name(char *buf, int buflen) {
int n;
diff --git a/src/Hill.cxx b/src/Hill.cxx
index 3b1c6bd..b059897 100644
--- a/src/Hill.cxx
+++ b/src/Hill.cxx
@@ -132,13 +132,13 @@ void Hills::mark_duplicates(double dist) {
sort(SORT_PHI);
- for(i=0; i<get_num();i++) {
+ for(i = 0; i < get_num(); i++) {
m = get(i);
- if (m->flags & Hill::TRACK_POINT)
- continue;
-
if (m) {
+ if (m->flags & Hill::TRACK_POINT)
+ continue;
+
j = i + 1;
n = get(j);
while (n && fabs(n->phi - m->phi) <= dist) {
diff --git a/src/ImageMetaData.cxx b/src/ImageMetaData.cxx
index b738b4d..03886b3 100644
--- a/src/ImageMetaData.cxx
+++ b/src/ImageMetaData.cxx
@@ -108,7 +108,7 @@ ImageMetaData::load_image_exif(char *name) {
image = Exiv2::ImageFactory::open(name);
image->readMetadata();
} catch (Exiv2::Error error) {
- fprintf(stderr, "Error reading metadata (%s)\n", error.what());
+ fprintf(stderr, "Error reading metadata\n");
return 1;
}
@@ -166,7 +166,7 @@ ImageMetaData::load_image_jpgcom(char *name) {
image = Exiv2::ImageFactory::open(name);
image->readMetadata();
} catch (Exiv2::Error error) {
- fprintf(stderr, "Error reading metadata (%s)\n", error.what());
+ fprintf(stderr, "Error reading metadata\n");
return 1;
}
@@ -258,7 +258,7 @@ ImageMetaData::save_image_jpgcom(char *in_img, char *out_img) {
try {
image->writeMetadata();
} catch (Exiv2::Error error) {
- fprintf(stderr, "Error writing metadata (%s)\n", error.what());
+ fprintf(stderr, "Error writing metadata\n");
err++;
}
diff --git a/src/Makefile.am b/src/Makefile.am
index a9fe688..3d4a174 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -18,6 +18,7 @@ gipfel_SOURCES = \
PreviewOutputImage.cxx \
ImageMetaData.cxx \
ScreenDump.cxx \
+ ScanImage.cxx \
strsep.c
noinst_HEADERS = \
@@ -40,4 +41,5 @@ noinst_HEADERS = \
PreviewOutputImage.H \
ImageMetaData.H \
ScreenDump.H \
+ ScanImage.H \
strsep.h
diff --git a/src/ScanImage.H b/src/ScanImage.H
new file mode 100644
index 0000000..e318273
--- /dev/null
+++ b/src/ScanImage.H
@@ -0,0 +1,31 @@
+//
+// Copyright 2006 Johannes Hofmann <Johannes.Hofmann@gmx.de>
+//
+// This software may be used and distributed according to the terms
+// of the GNU General Public License, incorporated herein by reference.
+
+#ifndef ScanImage_H
+#define ScanImage_H
+
+#include <FL/Fl_Image.H>
+
+class ScanImage {
+ private:
+ static int get_pixel_nearest(Fl_Image *img, double x, double y,
+ int *r, int *g, int *b);
+ static int get_pixel_bicubic(Fl_Image *img, double x, double y,
+ int *r, int *g, int *b);
+ static int get_pixel(Fl_Image *img, int x, int y,
+ int *r, int *g, int *b);
+
+ public:
+ typedef enum {
+ NEAREST = 0,
+ BICUBIC = 1
+ } mode_t;
+
+ static int get_pixel(Fl_Image *img, mode_t mode,
+ double x, double y, int *r, int *g, int *b);
+};
+
+#endif
diff --git a/src/ScanImage.cxx b/src/ScanImage.cxx
new file mode 100644
index 0000000..747da36
--- /dev/null
+++ b/src/ScanImage.cxx
@@ -0,0 +1,118 @@
+//
+// Copyright 2007-2009 Johannes Hofmann <Johannes.Hofmann@gmx.de>
+//
+// This software may be used and distributed according to the terms
+// of the GNU General Public License, incorporated herein by reference.
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <math.h>
+
+#include <Fl/Fl_Image.H>
+#include "ScanImage.H"
+
+int
+ScanImage::get_pixel(Fl_Image *img, mode_t mode,
+ double x, double y, int *r, int *g, int *b) {
+ if (mode == BICUBIC)
+ return get_pixel_bicubic(img, x, y, r, g, b);
+ else
+ return get_pixel_nearest(img, x, y, r, g, b);
+}
+
+int
+ScanImage::get_pixel_nearest(Fl_Image *img, double x, double y,
+ int *r, int *g, int *b) {
+
+ if (isnan(x) || isnan(y))
+ return 1;
+ else
+ return get_pixel(img, (int) rint(x), (int) rint(y), r, g, b);
+}
+
+static inline double
+interp_cubic(double x, double x2, double x3, double *v) {
+ double a0, a1, a2, a3;
+
+ a0 = v[3] - v[2] - v[0] + v[1];
+ a1 = v[0] - v[1] - a0;
+ a2 = v[2] - v[0];
+ a3 = v[1];
+
+ return a0 * x3 + a1 * x2 + a2 * x + a3;
+}
+
+int
+ScanImage::get_pixel_bicubic(Fl_Image *img, double x, double y,
+ int *r, int *g, int *b) {
+
+ double fl_x = floor(x);
+ double fl_y = floor(y);
+ double dx = x - fl_x, dx2 = dx * dx, dx3 = dx2 * dx;
+ double dy = y - fl_y, dy2 = dy * dy, dy3 = dy2 * dy;
+ int ic[3];
+ double c[3][4];
+ double c1[3][4];
+
+ for (int iy = 0; iy < 4; iy++) {
+ for (int ix = 0; ix < 4; ix++) {
+
+ if (get_pixel(img, (int) fl_x + ix - 1, (int) fl_y + iy - 1,
+ &ic[0], &ic[1], &ic[2]) != 0)
+ return 1;
+
+ for (int l = 0; l < 3; l++)
+ c[l][ix] = (double) ic[l];
+ }
+
+ for (int l = 0; l < 3; l++)
+ c1[l][iy] = interp_cubic(dx, dx2, dx3, c[l]);
+ }
+
+ *r = (int) rint(interp_cubic(dy, dy2, dy3, c1[0]));
+ *g = (int) rint(interp_cubic(dy, dy2, dy3, c1[1]));
+ *b = (int) rint(interp_cubic(dy, dy2, dy3, c1[2]));
+ return 0;
+}
+
+int
+ScanImage::get_pixel(Fl_Image *img, int x, int y,
+ int *r, int *g, int *b) {
+ if ( img->d() == 0 )
+ return 1;
+
+ if (x < 0 || x >=img->w() || y < 0 || y >= img->h())
+ return 1;
+
+ long index = (y * img->w() * img->d()) + (x * img->d()); // X/Y -> buf index
+ switch (img->count()) {
+ case 1:
+ { // bitmap
+ const unsigned char *buf = (const unsigned char*) img->data()[0];
+ switch (img->d())
+ {
+ case 1:
+ *r = *g = *b = *(buf+index);
+ break;
+ case 3: // 24bit
+ *r = (int) *(buf+index+0);
+ *g = (int) *(buf+index+1);
+ *b = (int) *(buf+index+2);
+ break;
+ default: // ??
+ printf("Not supported: chans=%d\n", img->d());
+ return 1;
+ }
+ break;
+ }
+ default: // ?? pixmap, bit vals
+ printf("Not supported: count=%d\n", img->count());
+ return 1;
+ }
+
+ *r = *r * 255;
+ *g = *g * 255;
+ *b = *b * 255;
+
+ return 0;
+}
diff --git a/src/Stitch.H b/src/Stitch.H
index 20087ab..7c9a60e 100644
--- a/src/Stitch.H
+++ b/src/Stitch.H
@@ -9,6 +9,7 @@
#include "GipfelWidget.H"
#include "OutputImage.H"
+#include "ScanImage.H"
#define MAX_PICS 256
@@ -24,7 +25,7 @@ class Stitch {
int load_image(char *file);
OutputImage * set_output(OutputImage *img);
- int resample(GipfelWidget::sample_mode_t m,
+ int resample(ScanImage::mode_t m,
int w, int h, double view_start, double view_end);
};
diff --git a/src/Stitch.cxx b/src/Stitch.cxx
index 8a1b429..eeb4562 100644
--- a/src/Stitch.cxx
+++ b/src/Stitch.cxx
@@ -64,7 +64,7 @@ Stitch::set_output(OutputImage *img) {
}
int
-Stitch::resample(GipfelWidget::sample_mode_t m,
+Stitch::resample(ScanImage::mode_t m,
int w, int h, double view_start, double view_end) {
view_start = view_start * deg2rad;
diff --git a/src/gipfel.cxx b/src/gipfel.cxx
index 1e038d2..8add46a 100644
--- a/src/gipfel.cxx
+++ b/src/gipfel.cxx
@@ -65,7 +65,7 @@ static Fl_Menu_Bar *mb;
#define STITCH_JPEG 2
#define STITCH_TIFF 4
-static int stitch(GipfelWidget::sample_mode_t m , int b_16,
+static int stitch(ScanImage::mode_t m , int b_16,
int stitch_w, int stitch_h,
double from, double to, int type, const char *path, int argc, char **argv);
@@ -129,12 +129,11 @@ void set_values() {
}
void quit_cb() {
+ if (Fl::event() == FL_SHORTCUT && Fl::event_key() == FL_Escape)
+ return; // ignore Escape
exit(0);
}
-void dummy_cb() {
-}
-
void open_cb() {
char *file = fl_file_chooser("Open File?", "*.jpg", img_file);
if (file) {
@@ -286,6 +285,7 @@ void about_cb() {
fl_message("gipfel -- Photogrammetry for Mountain Images.\n"
"Version %s\n\n"
"(c) Johannes Hofmann 2006-2009\n\n"
+ "Homepage: http://www.ecademix.com/JohannesHofmann\n\n"
"Default datafile from http://www.viewfinderpanoramas.org/ and\n"
"http://www.alpin-koordinaten.de\n",
VERSION);
@@ -602,7 +602,7 @@ int main(int argc, char** argv) {
type = STITCH_PREVIEW;
}
- return stitch(bicubic_flag?GipfelWidget::BICUBIC:GipfelWidget::NEAREST,
+ return stitch(bicubic_flag ? ScanImage::BICUBIC : ScanImage::NEAREST,
b_16_flag,
stitch_w, stitch_h, stitch_from, stitch_to,
type, outpath, my_argc, my_argv);
@@ -620,10 +620,10 @@ int main(int argc, char** argv) {
Fl::scheme("plastic");
control_win = create_control_window();
- control_win->callback((Fl_Callback*) dummy_cb);
+ control_win->callback((Fl_Callback*) quit_cb);
view_win = new Fl_Window(800, 600);
- view_win->callback((Fl_Callback*) dummy_cb);
+ view_win->callback((Fl_Callback*) quit_cb);
// The Fl_Group is used to avoid FL_DAMAGE_ALL in Fl_Scroll::position
Fl_Group *g = new Fl_Group(0, 0, view_win->w(), view_win->h());
@@ -667,7 +667,7 @@ int main(int argc, char** argv) {
}
static int
-stitch(GipfelWidget::sample_mode_t m, int b_16,
+stitch(ScanImage::mode_t m, int b_16,
int stitch_w, int stitch_h, double from, double to,
int type, const char *path, int argc, char **argv) {
@@ -685,7 +685,7 @@ stitch(GipfelWidget::sample_mode_t m, int b_16,
} else if (type & STITCH_TIFF) {
- st->set_output(new TIFFOutputImage(path, 90));
+ st->set_output(new TIFFOutputImage(path, b_16 ? 16 : 8));
st->resample(m, stitch_w, stitch_h, from, to);
} else {