mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-02-10 17:18:10 +02:00
196 lines
6.1 KiB
C++
196 lines
6.1 KiB
C++
![]() |
/////////////////////////////////////////////////////////////////////////////
|
||
|
// Name: src/gtk/scrolwin.cpp
|
||
|
// Purpose: wxScrolledWindow implementation
|
||
|
// Author: Robert Roebling
|
||
|
// Modified by: Ron Lee
|
||
|
// Vadim Zeitlin: removed 90% of duplicated common code
|
||
|
// Created: 01/02/97
|
||
|
// RCS-ID: $Id: scrolwin.cpp 67254 2011-03-20 00:14:35Z DS $
|
||
|
// Copyright: (c) Robert Roebling
|
||
|
// Licence: wxWindows licence
|
||
|
/////////////////////////////////////////////////////////////////////////////
|
||
|
|
||
|
// For compilers that support precompilation, includes "wx.h".
|
||
|
#include "wx/wxprec.h"
|
||
|
|
||
|
#ifdef __BORLANDC__
|
||
|
#pragma hdrstop
|
||
|
#endif
|
||
|
|
||
|
#include "wx/scrolwin.h"
|
||
|
|
||
|
#include <gtk/gtk.h>
|
||
|
|
||
|
// ----------------------------------------------------------------------------
|
||
|
// wxScrollHelper implementation
|
||
|
// ----------------------------------------------------------------------------
|
||
|
|
||
|
void wxScrollHelper::SetScrollbars(int pixelsPerUnitX, int pixelsPerUnitY,
|
||
|
int noUnitsX, int noUnitsY,
|
||
|
int xPos, int yPos,
|
||
|
bool noRefresh)
|
||
|
{
|
||
|
m_win->m_scrollPos[wxWindow::ScrollDir_Horz] =
|
||
|
m_win->m_scrollBar[wxWindow::ScrollDir_Horz]->adjustment->value = xPos;
|
||
|
m_win->m_scrollPos[wxWindow::ScrollDir_Vert] =
|
||
|
m_win->m_scrollBar[wxWindow::ScrollDir_Vert]->adjustment->value = yPos;
|
||
|
base_type::SetScrollbars(
|
||
|
pixelsPerUnitX, pixelsPerUnitY, noUnitsX, noUnitsY, xPos, yPos, noRefresh);
|
||
|
}
|
||
|
|
||
|
void wxScrollHelper::DoAdjustScrollbar(GtkRange* range,
|
||
|
int pixelsPerLine,
|
||
|
int winSize,
|
||
|
int virtSize,
|
||
|
int *pos,
|
||
|
int *lines,
|
||
|
int *linesPerPage)
|
||
|
{
|
||
|
if (!range)
|
||
|
return;
|
||
|
|
||
|
int upper;
|
||
|
int page_size;
|
||
|
if (pixelsPerLine > 0 && winSize > 0 && winSize < virtSize)
|
||
|
{
|
||
|
upper = (virtSize + pixelsPerLine - 1) / pixelsPerLine;
|
||
|
page_size = winSize / pixelsPerLine;
|
||
|
*lines = upper;
|
||
|
*linesPerPage = page_size;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// GtkRange won't allow upper == lower, so for disabled state use [0,1]
|
||
|
// with a page size of 1. This will also clamp position to 0.
|
||
|
upper = 1;
|
||
|
page_size = 1;
|
||
|
*lines = 0;
|
||
|
*linesPerPage = 0;
|
||
|
}
|
||
|
|
||
|
GtkAdjustment* adj = range->adjustment;
|
||
|
adj->step_increment = 1;
|
||
|
adj->page_increment =
|
||
|
adj->page_size = page_size;
|
||
|
gtk_range_set_range(range, 0, upper);
|
||
|
|
||
|
// ensure that the scroll position is always in valid range
|
||
|
if (*pos > *lines)
|
||
|
*pos = *lines;
|
||
|
}
|
||
|
|
||
|
void wxScrollHelper::AdjustScrollbars()
|
||
|
{
|
||
|
int vw, vh;
|
||
|
m_targetWindow->GetVirtualSize(&vw, &vh);
|
||
|
|
||
|
int w, h;
|
||
|
const wxSize availSize = GetSizeAvailableForScrollTarget(
|
||
|
m_win->GetSize() - m_win->GetWindowBorderSize());
|
||
|
if ( availSize.x >= vw && availSize.y >= vh )
|
||
|
{
|
||
|
w = availSize.x;
|
||
|
h = availSize.y;
|
||
|
|
||
|
// we know that the scrollbars will be removed
|
||
|
DoAdjustHScrollbar(w, vw);
|
||
|
DoAdjustVScrollbar(h, vh);
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
m_targetWindow->GetClientSize(&w, NULL);
|
||
|
DoAdjustHScrollbar(w, vw);
|
||
|
|
||
|
m_targetWindow->GetClientSize(NULL, &h);
|
||
|
DoAdjustVScrollbar(h, vh);
|
||
|
|
||
|
const int w_old = w;
|
||
|
m_targetWindow->GetClientSize(&w, NULL);
|
||
|
if ( w != w_old )
|
||
|
{
|
||
|
// It is necessary to repeat the calculations in this case to avoid an
|
||
|
// observed infinite series of size events, involving alternating
|
||
|
// changes in visibility of the scrollbars.
|
||
|
// At this point, GTK+ has already queued a resize, which will cause
|
||
|
// AdjustScrollbars() to be called again. If the scrollbar visibility
|
||
|
// is not correct before then, yet another resize will occur, possibly
|
||
|
// leading to an unending series if the sizes are just right.
|
||
|
DoAdjustHScrollbar(w, vw);
|
||
|
|
||
|
m_targetWindow->GetClientSize(NULL, &h);
|
||
|
DoAdjustVScrollbar(h, vh);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void wxScrollHelper::DoScrollOneDir(int orient,
|
||
|
int pos,
|
||
|
int pixelsPerLine,
|
||
|
int *posOld)
|
||
|
{
|
||
|
if ( pos != -1 && pos != *posOld && pixelsPerLine )
|
||
|
{
|
||
|
m_win->SetScrollPos(orient, pos);
|
||
|
pos = m_win->GetScrollPos(orient);
|
||
|
|
||
|
int diff = (*posOld - pos)*pixelsPerLine;
|
||
|
m_targetWindow->ScrollWindow(orient == wxHORIZONTAL ? diff : 0,
|
||
|
orient == wxHORIZONTAL ? 0 : diff);
|
||
|
|
||
|
*posOld = pos;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void wxScrollHelper::DoScroll( int x_pos, int y_pos )
|
||
|
{
|
||
|
wxCHECK_RET( m_targetWindow != 0, wxT("No target window") );
|
||
|
|
||
|
DoScrollOneDir(wxHORIZONTAL, x_pos, m_xScrollPixelsPerLine, &m_xScrollPosition);
|
||
|
DoScrollOneDir(wxVERTICAL, y_pos, m_yScrollPixelsPerLine, &m_yScrollPosition);
|
||
|
}
|
||
|
|
||
|
// ----------------------------------------------------------------------------
|
||
|
// scrollbars visibility
|
||
|
// ----------------------------------------------------------------------------
|
||
|
|
||
|
namespace
|
||
|
{
|
||
|
|
||
|
GtkPolicyType GtkPolicyFromWX(wxScrollbarVisibility visibility)
|
||
|
{
|
||
|
GtkPolicyType policy;
|
||
|
switch ( visibility )
|
||
|
{
|
||
|
case wxSHOW_SB_NEVER:
|
||
|
policy = GTK_POLICY_NEVER;
|
||
|
break;
|
||
|
|
||
|
case wxSHOW_SB_DEFAULT:
|
||
|
policy = GTK_POLICY_AUTOMATIC;
|
||
|
break;
|
||
|
|
||
|
default:
|
||
|
wxFAIL_MSG( wxS("unknown scrollbar visibility") );
|
||
|
// fall through
|
||
|
|
||
|
case wxSHOW_SB_ALWAYS:
|
||
|
policy = GTK_POLICY_ALWAYS;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
return policy;
|
||
|
}
|
||
|
|
||
|
} // anonymous namespace
|
||
|
|
||
|
void wxScrollHelper::DoShowScrollbars(wxScrollbarVisibility horz,
|
||
|
wxScrollbarVisibility vert)
|
||
|
{
|
||
|
GtkScrolledWindow * const scrolled = GTK_SCROLLED_WINDOW(m_win->m_widget);
|
||
|
wxCHECK_RET( scrolled, "window must be created" );
|
||
|
|
||
|
gtk_scrolled_window_set_policy(scrolled,
|
||
|
GtkPolicyFromWX(horz),
|
||
|
GtkPolicyFromWX(vert));
|
||
|
}
|