-void
-gtk_gs_start_scroll(GtkGS * gs)
-{
- gint x, y, w, h;
-
- if(!GTK_WIDGET_REALIZED(gs) || !gs->show_scroll_rect)
- return;
-
- gdk_window_get_geometry(gs->pstarget, &x, &y, &w, &h, NULL);
- gs->scroll_start_x = MAX(-x, 0);
- gs->scroll_start_y = MAX(-y, 0);
- //gs->scroll_width = MIN(gs->widget.allocation.width - 1, w - 1);
- //gs->scroll_height = MIN(gs->widget.allocation.height - 1, h - 1);
-
- if(gs->bpixmap) {
- GdkRectangle rect;
- rect.x = gs->scroll_start_x;
- rect.y = gs->scroll_start_y;
- rect.width = gs->scroll_width + 1;
- rect.height = gs->scroll_height + 1;
- gdk_draw_rectangle(gs->bpixmap, gs->psgc, FALSE,
- gs->scroll_start_x, gs->scroll_start_y,
- gs->scroll_width, gs->scroll_height);
- rect.width = 1;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.x = gs->scroll_start_x + gs->scroll_width;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.x = gs->scroll_start_x + 1;
- rect.width = gs->scroll_start_x + gs->scroll_width - 1;
- rect.height = 1;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.y = gs->scroll_start_y + gs->scroll_height;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- }
-}
-
-void
-gtk_gs_end_scroll(GtkGS * gs)
-{
- if(!GTK_WIDGET_REALIZED(gs) || !gs->show_scroll_rect)
- return;
-
- if(gs->scroll_start_x == -1 || gs->scroll_start_y == -1)
- return;
-
- if(gs->bpixmap) {
- GdkRectangle rect;
- rect.x = gs->scroll_start_x;
- rect.y = gs->scroll_start_y;
- rect.width = gs->scroll_width + 1;
- rect.height = gs->scroll_height + 1;
- gdk_draw_rectangle(gs->bpixmap, gs->psgc, FALSE,
- gs->scroll_start_x, gs->scroll_start_y,
- gs->scroll_width, gs->scroll_height);
- rect.width = 1;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.x = gs->scroll_start_x + gs->scroll_width;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.x = gs->scroll_start_x + 1;
- rect.width = gs->scroll_start_x + gs->scroll_width - 1;
- rect.height = 1;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- rect.y = gs->scroll_start_y + gs->scroll_height;
- gdk_window_invalidate_rect(gs->pstarget, &rect, TRUE);
- }
- gs->scroll_start_x = -1;
- gs->scroll_start_y = -1;
-}
-
-void
-gtk_gs_set_show_scroll_rect(GtkGS * gs, gboolean f)
-{
- gs->show_scroll_rect = f;
-}
-
-gboolean
-gtk_gs_get_show_scroll_rect(GtkGS * gs)
-{
- return gs->show_scroll_rect;
-}
-
-gboolean
-gtk_gs_scroll_to_edge(GtkGS * gs, GtkPositionType vertical,
- GtkPositionType horizontal)
-{
- g_return_val_if_fail(gs != NULL, FALSE);
- g_return_val_if_fail(GTK_IS_GS(gs), FALSE);
-
- switch (vertical) {
- case GTK_POS_TOP:
- gs->vadj->value = gs->vadj->lower;
- gtk_adjustment_value_changed(gs->vadj);
- break;
- case GTK_POS_BOTTOM:
- gs->vadj->value = gs->vadj->upper - gs->vadj->page_size;
- gtk_adjustment_value_changed(gs->vadj);
- break;
- default:
- g_assert(0); /* Illegal parameter error */
- }
-
-
- switch (horizontal) {
- case GTK_POS_TOP:
- gs->hadj->value = gs->hadj->lower;
- gtk_adjustment_value_changed(gs->hadj);
- break;
- case GTK_POS_BOTTOM:
- gs->hadj->value = gs->hadj->upper - gs->hadj->page_size;
- gtk_adjustment_value_changed(gs->hadj);
- break;
- default:
- g_assert(0); /* Illegal parameter error */
- }
-
- return TRUE;
-}
-
-gboolean
-gtk_gs_scroll_step(GtkGS * gs, GtkScrollType direction, gboolean dowrap)
-{
- GtkAdjustment *MainAdj; /* We will move this adjustment */
- GtkAdjustment *SecoAdj; /* And this _only_ if we can't move MainAdj (ie. we're edge)
- and there is wrapping */
-
- gboolean MoveHorizontal = TRUE; /* Positive if we move horizontal */
- gboolean DirectionFlag = TRUE; /* Positive if we move towards upper */
- g_return_val_if_fail(gs != NULL, FALSE);
- g_return_val_if_fail(GTK_IS_GS(gs), FALSE);
-
-#define EPSILON 0.00005
-
-#define CHECK_THERE_IS_NO_LOWER_SPACE(adj) \
- ((adj)->value - (EPSILON) <= (adj)->lower)
-#define CHECK_THERE_IS_NO_UPPER_SPACE(adj) \
- ((adj)->value + (EPSILON) >= (adj)->upper - (adj)->page_size)
-
-#define CHECK_THERE_IS_NO_SPACE_FOR_STEP(adj,dir) \
- (dir?CHECK_THERE_IS_NO_UPPER_SPACE(adj):CHECK_THERE_IS_NO_LOWER_SPACE(adj))
-
- /* To make code more readable, we make a macro */
-#define ADVANCE_TOWARDS_LOWER(adj) \
- (adj->value -= gs->scroll_step * (adj->page_size))
-#define ADVANCE_TOWARDS_UPPER(adj) \
- (adj->value += gs->scroll_step * (adj->page_size))
-
-#define ADVANCE_STEP(adj,dir) \
- (dir?ADVANCE_TOWARDS_UPPER(adj):ADVANCE_TOWARDS_LOWER(adj))
-
-#define MOVE_TO_LOWER_EDGE(adj) \
- (adj->value = adj->lower)
-#define MOVE_TO_UPPER_EDGE(adj) \
- (adj->value = adj->upper - adj->page_size)
-
- /* if upper is 1 goto upper, otherwise to lower */
-#define MOVE_TO_EDGE(adj,upper) (upper?MOVE_TO_UPPER_EDGE(adj):MOVE_TO_LOWER_EDGE(adj))
-
- /* These variables make our life easier */
- switch (direction) {
- case GTK_SCROLL_STEP_RIGHT:
- MoveHorizontal = TRUE;
- DirectionFlag = TRUE;
- break;
- case GTK_SCROLL_STEP_LEFT:
- MoveHorizontal = TRUE;
- DirectionFlag = FALSE;
- break;
- case GTK_SCROLL_STEP_DOWN:
- MoveHorizontal = FALSE;
- DirectionFlag = TRUE;
- break;
- case GTK_SCROLL_STEP_UP:
- MoveHorizontal = FALSE;
- DirectionFlag = FALSE;
- break;
- default:
- g_warning("Illegal scroll step direction.");
- }
-
- if(MoveHorizontal) {
- MainAdj = gs->hadj;
- SecoAdj = gs->vadj;
- }
- else {
- MainAdj = gs->vadj;
- SecoAdj = gs->hadj;
- }
-
- if(CHECK_THERE_IS_NO_SPACE_FOR_STEP(MainAdj, DirectionFlag)) {
- if(!dowrap)
- return FALSE;
- /* Move in the oposite axis */
- if(CHECK_THERE_IS_NO_SPACE_FOR_STEP(SecoAdj, DirectionFlag)) {
- /* there is no place to move, we need a new page */
- return FALSE;
- }
- ADVANCE_STEP(SecoAdj, DirectionFlag);
-
- if(CHECK_THERE_IS_NO_SPACE_FOR_STEP(SecoAdj, DirectionFlag)) {
- /* We move it too far, lets move it to the edge */
- MOVE_TO_EDGE(SecoAdj, DirectionFlag);
- }
- /* now move to edge (other axis) in oposite direction */
- MOVE_TO_EDGE(MainAdj, !DirectionFlag);
- gtk_adjustment_value_changed(SecoAdj);
- return TRUE;
- }
-
- /* Now we know we can move in the direction sought */
- ADVANCE_STEP(MainAdj, DirectionFlag);
-
- if(CHECK_THERE_IS_NO_SPACE_FOR_STEP(MainAdj, DirectionFlag)) {
- /* We move it too far, lets move it to the edge */
- MOVE_TO_EDGE(MainAdj, DirectionFlag);
- }
- gtk_adjustment_value_changed(MainAdj);
-
- return TRUE;
-}
-