📄 gvx.c
字号:
else {
x = (int)(event->x);
y = (int)(event->y);
state = (GdkModifierType)event->state;
}
gs_addmessf("motion_notify_event: motion %d %d\n", x, y);
#endif
in_img_window = TRUE;
if (draghand) {
GtkAdjustment *hadjust = gtk_scrolled_window_get_hadjustment(
GTK_SCROLLED_WINDOW(scroll_window));
GtkAdjustment *vadjust = gtk_scrolled_window_get_vadjustment(
GTK_SCROLLED_WINDOW(scroll_window));
int dx = (int)event->x - draghand_x;
int dy = (int)event->y - draghand_y;
set_scroll(hadjust->value - dx, vadjust->value - dy);
}
}
if (get_cursorpos(&x, &y)) {
PDFLINK link;
int iword;
info_link();
if (is_link(x, y, &link)) {
/* should change cursor to a hand */
/* not implemented */
}
if (text_marking) {
if ( (iword = word_find((int)x, (int)y)) >= 0 ) {
if (iword != text_mark_last) {
int first, last;
if ((text_mark_last-text_mark_first >= 0) != (iword-text_mark_first >= 0)) {
/* changing direction */
/* clear everything */
highlight_words(text_mark_first, text_mark_last, FALSE);
/* reinstate first word */
text_mark_last = text_mark_first;
highlight_words(text_mark_first, text_mark_last, TRUE);
}
if (iword != text_mark_last) {
if (iword >= text_mark_first) {
if (iword > text_mark_last)
first=text_mark_last+1, last=iword;
else
first=iword+1, last=text_mark_last;
}
else {
if (iword > text_mark_last)
first=text_mark_last, last=iword-1;
else
first=iword, last=text_mark_last-1;
}
highlight_words(first, last, TRUE);
text_mark_last = iword;
}
}
}
}
measure_paint(x, y);
}
statuscoord_update();
return TRUE;
}
gint
configure_event(GtkWidget *widget, GdkEventConfigure *event, gpointer user_data)
{
return TRUE;
}
gint
size_event(GtkWidget *widget, GtkAllocation *allocation, gpointer user_data)
{
gint x, y;
/* remember image size and location */
if (window->window) {
gdk_window_get_position(window->window, &x, &y);
option.img_origin.x = x;
option.img_origin.y = y;
}
option.img_size.x = window->allocation.width;
option.img_size.y = window->allocation.height;
return TRUE;
}
static void
window_draw(GtkWidget *widget, int x, int y, int width, int height)
{
if (image.open && image.image) {
int color = image.format & DISPLAY_COLORS_MASK;
int depth = image.format & DISPLAY_DEPTH_MASK;
switch (color) {
case DISPLAY_COLORS_NATIVE:
if (depth == DISPLAY_DEPTH_8) {
gdk_draw_indexed_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.image + x + y*image.raster,
image.raster, image.cmap);
}
else if ((depth == DISPLAY_DEPTH_16) && image.rgbbuf) {
gdk_draw_rgb_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.rgbbuf + x*3 + image.width*3*y,
image.width * 3);
}
break;
case DISPLAY_COLORS_GRAY:
if (depth == DISPLAY_DEPTH_8)
gdk_draw_gray_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.image + x + y*image.raster,
image.raster);
else if (depth == DISPLAY_DEPTH_1) {
/* FIX */
gs_addmess("1 bit/pixel drawing not implemented\n");
}
break;
case DISPLAY_COLORS_RGB:
if (depth == DISPLAY_DEPTH_8) {
if (image.rgbbuf) {
gdk_draw_rgb_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.rgbbuf + x*3 + image.width*3*y,
image.width * 3);
}
else {
gdk_draw_rgb_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.image + x*3 + y*image.raster,
image.raster);
}
}
break;
case DISPLAY_COLORS_CMYK:
if ((depth == DISPLAY_DEPTH_8) && image.rgbbuf)
gdk_draw_rgb_image(widget->window,
widget->style->fg_gc[GTK_STATE_NORMAL],
x, y, width, height, GDK_RGB_DITHER_MAX,
image.rgbbuf + x*3 + image.width*3*y,
image.width * 3);
break;
}
}
}
gint
expose_event(GtkWidget *widget, GdkEventExpose *event, gpointer user_data)
{
GdkGC *gcdash;
GdkGC *gcinvert;
GdkColor black = {0, 0, 0, 0};
image_lock(view.img);
if (image.open && image.image) {
int x = event->area.x;
int y = event->area.y;
int width = event->area.width;
int height = event->area.height;
if ((x>=0) && (y>=0) && (x <= image.width) && (y <= image.height)) {
/* drawing area intersects the bitmap, so draw it */
if (x + width > image.width)
width = image.width - x;
if (y + height > image.height)
height = image.height - y;
window_draw(img, x, y, width, height);
}
}
if (option.show_bbox && (psfile.dsc != (CDSC *)NULL) &&
(psfile.dsc->bbox != (CDSCBBOX *)NULL)) {
int left, right, top, bottom;
float x, y;
/* map bounding box to device coordinates */
x = psfile.dsc->bbox->llx;
y = psfile.dsc->bbox->lly;
map_pt_to_pixel(&x, &y);
left = (int)x;
bottom = (int)y;
x = psfile.dsc->bbox->urx;
y = psfile.dsc->bbox->ury;
map_pt_to_pixel(&x, &y);
right = (int)x;
top = (int)y;
if (left > right) {
int temp = left;
left = right;
right = temp;
}
if (bottom < top) {
int temp = top;
top = bottom;
bottom = temp;
}
gcdash = gdk_gc_new(img->window);
#ifdef NOTUSED
/* DOUBLE_DASH didn't seem to work. Always ended up with solid black */
GdkColor white = {1, 65535, 65535, 65535};
gdk_gc_set_fill(gcdash, GDK_SOLID);
gdk_gc_set_background(gcdash, &white);
gdk_gc_set_line_attributes(gcdash, 1, GDK_LINE_DOUBLE_DASH,
GDK_CAP_BUTT, GDK_JOIN_MITER);
#endif
gdk_gc_set_foreground(gcdash, &black);
gdk_gc_set_line_attributes(gcdash, 1, GDK_LINE_ON_OFF_DASH,
GDK_CAP_BUTT, GDK_JOIN_MITER);
gdk_draw_rectangle(img->window, gcdash, FALSE,
left, top, right-left, bottom-top);
gdk_gc_unref(gcdash);
}
/* highlight found search word */
if (image.open && display.show_find) {
float x, y;
int left, top, bottom, right;
/* map bounding box to device coordinates */
x = psfile.text_bbox.llx;
y = psfile.text_bbox.lly;
map_pt_to_pixel(&x, &y);
left = (int)x;
bottom = (int)y;
x = psfile.text_bbox.urx;
y = psfile.text_bbox.ury;
map_pt_to_pixel(&x, &y);
right = (int)x;
top = (int)y;
if (top > bottom) {
int temp = top;
top = bottom;
bottom = temp;
}
if (left > right) {
int temp = right;
right = left;
left = temp;
}
if (image.open) {
/* redraw rectangle we about to invert */
window_draw(img, left, top, right-left, bottom-top);
}
/* invert text */
gcinvert = gdk_gc_new(img->window);
gdk_gc_set_function(gcinvert, GDK_INVERT);
gdk_draw_rectangle(img->window, gcinvert,
TRUE, left, top, right-left, bottom-top);
gdk_gc_unref(gcinvert);
}
/* highlight marked words */
highlight_words(text_mark_first, text_mark_last, TRUE);
/* GS 6.50 highlights links itself for PDF files */
if ((option.gsversion < 650) || !psfile.ispdf)
highlight_links();
image_unlock(view.img);
return FALSE;
}
/* map from a coordinate in points, to a coordinate in pixels */
/* This is the opposite of the transform part of get_cursorpos */
/* Used when showing bbox */
void
map_pt_to_pixel(float *x, float *y)
{
if (zoom) {
/* WARNING - this doesn't cope with EPS Clip */
*x = (*x - display.zoom_xoffset) * option.zoom_xdpi / 72.0;
*y = (*y - display.zoom_yoffset) * option.zoom_ydpi / 72.0;
*x = (*x * 72.0 / option.xdpi);
*y = (*y * 72.0 / option.ydpi);
itransform_point(x, y);
*x = (*x * option.xdpi / 72.0) + display.offset.x;
*y = -(*y * option.ydpi / 72.0) + (image.height - 1)
+ display.offset.y;
}
else {
int xoffset = display.xoffset / display.xdpi * 72.0 + 0.5;
int yoffset = display.yoffset / display.ydpi * 72.0 + 0.5;
*x = *x - xoffset;
*y = *y - yoffset;
itransform_point(x, y);
*x = *x * option.xdpi/72.0 + display.offset.x;
*y = -(*y * option.ydpi/72.0)
+ (image.height - 1) + display.offset.y;
}
}
BOOL
get_cursorpos(float *x, float *y)
{
int ix=0, iy=0;
GdkModifierType state;
if (!in_img_window)
return FALSE;
gdk_window_get_pointer(img->window, &ix, &iy, &state);
*x = ix;
*y = image.height - 1 - iy;
transform_cursorpos(x, y);
return TRUE;
}
void
statuscoord_update(void)
{
float x, y;
char buf[64];
char fmt[32];
int digits = option.unitfine ? 2 : 0;
if ((psfile.name[0] != '\0') && gsdll.hmodule) {
/* show coordinate */
if (get_cursorpos(&x, &y)) {
switch(option.unit) {
case IDM_UNITPT:
sprintf(fmt, "%%.%df, %%.%dfpt", digits, digits);
sprintf(buf, fmt, x, y);
break;
case IDM_UNITMM:
sprintf(fmt, "%%.%df, %%.%dfmm", digits, digits);
sprintf(buf, fmt, x/72*25.4, y/72*25.4);
break;
case IDM_UNITINCH:
digits += 1;
sprintf(fmt, "%%.%df, %%.%dfin", digits, digits);
sprintf(buf, fmt, x/72, y/72);
break;
}
/* measure_paint(x, y); not implemented */
}
else {
buf[0] = '\0';
}
}
else {
buf[0] = '\0';
}
if (strcmp(coord_text, buf) != 0) {
gtk_label_set_text(GTK_LABEL(statuscoord), buf);
strncpy(coord_text, buf, sizeof(coord_text)-1);
while (g_main_iteration(FALSE)); /* flush display */
}
}
/* update the status bar */
void
statusbar_update(void)
{
CDSC *dsc = psfile.dsc;
int i;
char buf[256];
char fmt[256];
char coord[64];
coord[0] = '\0';
if (psfile.name[0] != '\0') {
char *p;
p = strrchr(psfile.name, '/');
if (p == NULL)
p = psfile.name;
else
p++;
i = load_string(IDS_FILE, buf, sizeof(buf));
strncpy(buf+i, p, sizeof(buf)-i-1);
gtk_label_set_text(GTK_LABEL(statusfile), buf);
if (szWait[0] != '\0') {
sprintf(buf, szWait, percent_done);
gtk_label_set_text(GTK_LABEL(statuspage), buf);
}
else {
if (psfile.dsc!=(CDSC *)NULL) {
int n = map_page(psfile.pagenum - 1);
load_string(IDS_PAGEINFO, fmt, sizeof(fmt));
if (on_link) {
if ((on_link_page == 0) && on_link_action[0]) {
strncpy(buf, on_link_action, sizeof(buf)-1);
}
else
{
load_string(IDS_LINKPAGE, fmt, sizeof(fmt));
sprintf(buf, fmt, on_link_page);
}
}
else {
if (psfile.dsc->page_count)
sprintf(buf, fmt, dsc->page[n].label ?
dsc->page[n].label : " ", psfile.pagenum,
dsc->page_count);
else
sprintf(buf, fmt, " " ,psfile.pagenum, dsc->page_count);
}
if (zoom)
load_string(IDS_ZOOMED, buf+strlen(buf), sizeof(buf)-strlen(buf));
gtk_label_set_text(GTK_LABEL(statuspage), buf);
}
else {
if ((gsdll.state == GS_IDLE) || (gsdll.state == GS_UNINIT))
load_string(IDS_NOMORE, buf, sizeof(buf));
else {
load_string(IDS_PAGE, buf, sizeof(buf));
sprintf(buf+i, "%d", psfile.pagenum);
}
gtk_label_set_text(GTK_LABEL(statuspage), buf);
}
}
}
else {
load_string(IDS_NOFILE, buf, sizeof(buf));
gtk_label_set_text(GTK_LABEL(statusfile), buf);
if (szWait[0] != '\0') {
sprintf(buf, szWait, percent_done);
gtk_label_set_text(GTK_LABEL(statuspage), buf);
}
else {
gtk_label_set_text(GTK_LABEL(statuspage), "");
}
}
/* show coordinate */
statuscoord_update();
while (g_main_iteration(FALSE)); /* flush display */
}
void gsview_fullscreen_end(void)
{
/*
gs_addmess("gsview_fullscreen_end: not implemented\n");
*/
}
void gsview_fullscreen(void)
{
gs_addmess("gsview_fullscreen: not implemented\n");
}
/* Set the current resolution to fill the window.
* If neither width nor height match, fit whole page
* into window. If either width or height match
* the window size, fit the height or width respectively.
*/
void
gsview_fitwin(void)
{
int window_width, window_height;
int width, height;
float dpi, xdpi, ydpi, xdpi2, ydpi2;
if (psfile.ispdf) {
/* TESTING TESTING TESTING */
/* This also need to be copied to gvwin.cpp and gvpm.cpp */
CDSCBBOX *mediabox = NULL;
CDSCBBOX *cropbox = NULL;
int page = psfile.pagenum;
if ((page > 0) && (page <= (int)psfile.dsc->page_count)) {
if (psfile.dsc->page[page-1].media)
mediabox = psfile.dsc->page[page-1].media->mediabox;
cropbox = psfile.dsc->page[page-1].bbox;
}
if (option.epsf_clip && (cropbox != (CDSCBBOX *)NULL)) {
width = cropbox->urx - cropbox->llx;
height = cropbox->ury - cropbox->lly;
}
else {
if (mediabox) {
width = mediabox->urx - mediabox->llx;
height = mediabox->ury - mediabox->lly;
}
else {
width = get_paper_width();
height = get_paper_height();
}
}
}
else {
width = get_paper_width();
height = get_paper_height();
}
if (display.orientation & 1) {
/* page is rotated 90 degrees */
int temp = width;
width = height;
height = temp;
}
if (fullscreen) {
gs_addmess("gsview_fitwin: fullscreen not implemented\n");
window_width = scroll_window->allocation.width;
window_height = scroll_window->allocation.height;
}
else {
/* get size including scroll bars area */
window_width = scroll_window->allocation.width;
window_height = scroll_window->allocation.height;
}
/* -4 is to allow for border around window */
xdpi = (window_width - 4) * 72.0 / width;
ydpi = (window_height - 4) * 72.0 / height;
if (fullscreen) {
xdpi2 = xdpi;
ydpi2 = ydpi;
}
else {
/* These are the resolutions allowing for a scroll bar */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -