Add a proof of concept new container class.
With the change of the drawing engine a rewrite of the containers is needed as well. This adds a new container class which the scroll_label uses. The class can't forward events and also the scrollbars are always visible.
This commit is contained in:
parent
8bf7cbad4a
commit
fba341cd49
12 changed files with 1049 additions and 9 deletions
|
@ -151,3 +151,227 @@
|
|||
[/scroll_label_definition]
|
||||
|
||||
#undef _GUI_RESOLUTION
|
||||
|
||||
|
||||
#ifdef NEW_DRAW
|
||||
|
||||
#define _GUI_VERTICAL_SCROLLBAR_GRID
|
||||
vertical_grow = "true"
|
||||
[grid]
|
||||
id = "_vertical_scrollbar_grid"
|
||||
|
||||
[row]
|
||||
|
||||
[column]
|
||||
|
||||
# note we want a special button definition for this later.
|
||||
[button]
|
||||
id = "_half_page_up"
|
||||
definition = "up_arrow"
|
||||
[/button]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[row]
|
||||
|
||||
grow_factor = 1
|
||||
[column]
|
||||
vertical_grow = "true"
|
||||
|
||||
[vertical_scrollbar]
|
||||
id = "_vertical_scrollbar"
|
||||
definition = "default"
|
||||
[/vertical_scrollbar]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[row]
|
||||
|
||||
[column]
|
||||
|
||||
# note we want a special button definition for this later.
|
||||
[button]
|
||||
id = "_half_page_down"
|
||||
definition = "down_arrow"
|
||||
[/button]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[/grid]
|
||||
#enddef
|
||||
|
||||
#define _GUI_HORIZONTAL_SCROLLBAR_GRID
|
||||
horizontal_grow = "true"
|
||||
[grid]
|
||||
id = "_horizontal_scrollbar_grid"
|
||||
|
||||
[row]
|
||||
|
||||
[column]
|
||||
|
||||
# note we want a special button definition for this later.
|
||||
[button]
|
||||
id = "_half_page_left"
|
||||
definition = "left_arrow"
|
||||
[/button]
|
||||
|
||||
[/column]
|
||||
|
||||
[column]
|
||||
grow_factor = 1
|
||||
horizontal_grow = "true"
|
||||
|
||||
[horizontal_scrollbar]
|
||||
id = "_horizontal_scrollbar"
|
||||
definition = "default"
|
||||
[/horizontal_scrollbar]
|
||||
|
||||
[/column]
|
||||
|
||||
[column]
|
||||
|
||||
# note we want a special button definition for this later.
|
||||
[button]
|
||||
id = "_half_page_right"
|
||||
definition = "right_arrow"
|
||||
[/button]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[/grid]
|
||||
#enddef
|
||||
|
||||
#define _GUI_RESOLUTION RESOLUTION FONT_SIZE FONT_STYLE FONT_COLOUR_ENABLED FONT_COLOUR_DISABLED
|
||||
[resolution]
|
||||
|
||||
{RESOLUTION}
|
||||
|
||||
min_width = 0
|
||||
min_height = 0
|
||||
|
||||
default_width = 0
|
||||
default_height = 0
|
||||
|
||||
max_width = 0
|
||||
max_height = 0
|
||||
|
||||
text_font_size = {FONT_SIZE}
|
||||
text_font_style = {FONT_STYLE}
|
||||
|
||||
[state_enabled]
|
||||
|
||||
full_redraw = "true"
|
||||
|
||||
[draw]
|
||||
[/draw]
|
||||
|
||||
[/state_enabled]
|
||||
|
||||
[state_disabled]
|
||||
|
||||
full_redraw = "true"
|
||||
|
||||
[draw]
|
||||
[/draw]
|
||||
|
||||
[/state_disabled]
|
||||
|
||||
[grid]
|
||||
|
||||
[row]
|
||||
grow_factor = 1
|
||||
|
||||
[column]
|
||||
grow_factor = 1
|
||||
horizontal_grow = "true" # needed ?
|
||||
vertical_grow = "true" # needed ?
|
||||
|
||||
[grid]
|
||||
id = "_content_grid"
|
||||
|
||||
[row]
|
||||
|
||||
[column]
|
||||
horizontal_grow = "true"
|
||||
vertical_grow = "true"
|
||||
|
||||
[label]
|
||||
id = "_label"
|
||||
definition = "default"
|
||||
[/label]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[/grid]
|
||||
|
||||
[/column]
|
||||
|
||||
[column]
|
||||
|
||||
{_GUI_VERTICAL_SCROLLBAR_GRID}
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[row]
|
||||
|
||||
[column]
|
||||
|
||||
{_GUI_HORIZONTAL_SCROLLBAR_GRID}
|
||||
|
||||
[/column]
|
||||
|
||||
[column]
|
||||
|
||||
[spacer]
|
||||
[/spacer]
|
||||
|
||||
[/column]
|
||||
|
||||
[/row]
|
||||
|
||||
[/grid]
|
||||
|
||||
[/resolution]
|
||||
#enddef
|
||||
|
||||
[scroll_label_definition]
|
||||
id = "test"
|
||||
description = "Testing version."
|
||||
|
||||
{_GUI_RESOLUTION
|
||||
({GUI_TINY__RESOLUTION})
|
||||
({GUI_TINY__FONT_SIZE__DEFAULT})
|
||||
()
|
||||
({GUI__FONT_COLOUR_ENABLED__DEFAULT})
|
||||
({GUI__FONT_COLOUR_DISABLED__DEFAULT})
|
||||
}
|
||||
|
||||
|
||||
{_GUI_RESOLUTION
|
||||
({GUI_NORMAL__RESOLUTION})
|
||||
({GUI_NORMAL__FONT_SIZE__DEFAULT})
|
||||
()
|
||||
({GUI__FONT_COLOUR_ENABLED__DEFAULT})
|
||||
({GUI__FONT_COLOUR_DISABLED__DEFAULT})
|
||||
}
|
||||
|
||||
[/scroll_label_definition]
|
||||
|
||||
#undef _GUI_VERTICAL_SCROLLBAR_GRID
|
||||
#undef _GUI_HORIZONTAL_SCROLLBAR_GRID
|
||||
#undef _GUI_RESOLUTION
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -393,7 +393,11 @@
|
|||
|
||||
[scroll_label] # NOTE maybe change the code to use message instead of label as id
|
||||
id = "label"
|
||||
#ifdef NEW_DRAW
|
||||
definition = "test"
|
||||
#else
|
||||
definition = "default"
|
||||
#endif
|
||||
[/scroll_label]
|
||||
|
||||
[/column]
|
||||
|
@ -607,7 +611,11 @@
|
|||
|
||||
[scroll_label]
|
||||
id = "label"
|
||||
definition = "default"
|
||||
#ifdef NEW_DRAW
|
||||
definition = "test"
|
||||
#else
|
||||
definition = "default"
|
||||
#endif
|
||||
[/scroll_label]
|
||||
|
||||
[/column]
|
||||
|
|
|
@ -29,6 +29,7 @@ src/gui/widgets/menubar.cpp
|
|||
src/gui/widgets/minimap.cpp
|
||||
src/gui/widgets/panel.cpp
|
||||
src/gui/widgets/scroll_label.cpp
|
||||
src/gui/widgets/scrollbar_container.cpp
|
||||
src/gui/widgets/scrollbar.cpp
|
||||
src/gui/widgets/settings.cpp
|
||||
src/gui/widgets/slider.cpp
|
||||
|
|
|
@ -249,6 +249,7 @@ SET(wesnoth-main_SRC
|
|||
gui/widgets/slider.cpp
|
||||
gui/widgets/spacer.cpp
|
||||
gui/widgets/scroll_label.cpp
|
||||
gui/widgets/scrollbar_container.cpp
|
||||
gui/widgets/scrollbar.cpp
|
||||
gui/widgets/text.cpp
|
||||
gui/widgets/text_box.cpp
|
||||
|
|
|
@ -95,6 +95,7 @@ wesnoth_source = \
|
|||
gui/widgets/settings.cpp \
|
||||
gui/widgets/scroll_label.cpp \
|
||||
gui/widgets/scrollbar.cpp \
|
||||
gui/widgets/scrollbar_container.cpp \
|
||||
gui/widgets/slider.cpp \
|
||||
gui/widgets/spacer.cpp \
|
||||
gui/widgets/text.cpp \
|
||||
|
|
|
@ -236,6 +236,7 @@ wesnoth_sources = Split("""
|
|||
gui/widgets/panel.cpp
|
||||
gui/widgets/settings.cpp
|
||||
gui/widgets/scroll_label.cpp
|
||||
gui/widgets/scrollbar_container.cpp
|
||||
gui/widgets/scrollbar.cpp
|
||||
gui/widgets/slider.cpp
|
||||
gui/widgets/spacer.cpp
|
||||
|
|
|
@ -19,6 +19,9 @@
|
|||
#include "foreach.hpp"
|
||||
#include "formatter.hpp"
|
||||
#include "gui/widgets/vertical_scrollbar_container.hpp"
|
||||
#ifdef NEW_DRAW
|
||||
#include "gui/widgets/scrollbar_container.hpp"
|
||||
#endif
|
||||
#include "gui/widgets/window.hpp"
|
||||
#include "serialization/string_utils.hpp"
|
||||
|
||||
|
@ -209,6 +212,18 @@ void tdebug_layout_graph::widget_generate_info(std::ostream& out,
|
|||
<< id << "_G"
|
||||
<< " [label=\"(grid)\"];\n";
|
||||
}
|
||||
|
||||
#ifdef NEW_DRAW
|
||||
const tscrollbar_container* scrollbar_container =
|
||||
dynamic_cast<const tscrollbar_container*>(widget);
|
||||
|
||||
if(scrollbar_container) {
|
||||
widget_generate_info(out, scrollbar_container->content_grid_, id + "_C", true);
|
||||
out << "\t" << id << " -> "
|
||||
<< id << "_C"
|
||||
<< " [label=\"(content)\"];\n";
|
||||
}
|
||||
#endif
|
||||
}
|
||||
if(grid) {
|
||||
grid_generate_info(out, grid, id);
|
||||
|
@ -281,7 +296,21 @@ void tdebug_layout_graph::widget_generate_state_info(
|
|||
<< vertical_scrollbar_container->scrollbar_mode_ << '\n'
|
||||
<< "</td></tr>\n";
|
||||
}
|
||||
#ifdef NEW_DRAW
|
||||
const tscrollbar_container* scrollbar_container =
|
||||
dynamic_cast<const tscrollbar_container*>(widget);
|
||||
|
||||
if(scrollbar_container) {
|
||||
out << "<tr><td>\n"
|
||||
<< "vertical_scrollbar_mode_="
|
||||
<< scrollbar_container->vertical_scrollbar_mode_ << '\n'
|
||||
<< "</td></tr>\n"
|
||||
<< "<tr><td>\n"
|
||||
<< "horizontal_scrollbar_mode_="
|
||||
<< scrollbar_container->horizontal_scrollbar_mode_ << '\n'
|
||||
<< "</td></tr>\n";
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void tdebug_layout_graph::widget_generate_size_info(
|
||||
|
|
|
@ -19,30 +19,45 @@
|
|||
#include "gui/widgets/spacer.hpp"
|
||||
|
||||
namespace gui2 {
|
||||
|
||||
tscroll_label::tscroll_label()
|
||||
#ifndef NEW_DRAW
|
||||
: tvertical_scrollbar_container_(COUNT)
|
||||
#else
|
||||
: tscrollbar_container(COUNT)
|
||||
#endif
|
||||
, state_(ENABLED)
|
||||
#ifndef NEW_DRAW
|
||||
, label_(NULL)
|
||||
#endif
|
||||
{
|
||||
}
|
||||
|
||||
tscroll_label::~tscroll_label()
|
||||
{
|
||||
#ifndef NEW_DRAW
|
||||
delete label_;
|
||||
#endif
|
||||
}
|
||||
|
||||
void tscroll_label::set_label(const t_string& label)
|
||||
{
|
||||
// Inherit.
|
||||
tcontrol::set_label(label);
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
tlabel* widget = find_label(false);
|
||||
if(widget) {
|
||||
widget->set_label(label);
|
||||
}
|
||||
#else
|
||||
if(content_grid()) {
|
||||
tlabel* widget = content_grid()->
|
||||
find_widget<tlabel>("_label", false, true);
|
||||
widget->set_label(label);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
tlabel* tscroll_label::find_label(const bool must_exist)
|
||||
{
|
||||
if(label_) {
|
||||
|
@ -85,7 +100,25 @@ void tscroll_label::finalize()
|
|||
label_->set_label(label());
|
||||
label_->set_can_wrap(true);
|
||||
}
|
||||
#else
|
||||
void tscroll_label::finalize_subclass()
|
||||
{
|
||||
assert(content_grid());
|
||||
tlabel* lbl = dynamic_cast<tlabel*>(
|
||||
content_grid()->find_widget("_label", false));
|
||||
|
||||
assert(lbl);
|
||||
lbl->set_label(label());
|
||||
|
||||
/**
|
||||
* @todo wrapping should be a label setting.
|
||||
* This setting shoul be mutual exclusive with the horizontal scrollbar.
|
||||
* Also the scroll_grid needs to set the status for the scrollbars.
|
||||
*/
|
||||
lbl->set_can_wrap(false);
|
||||
}
|
||||
#endif
|
||||
#ifndef NEW_DRAW
|
||||
tpoint tscroll_label::content_calculate_best_size() const
|
||||
{
|
||||
assert(label_);
|
||||
|
@ -104,7 +137,6 @@ void tscroll_label::content_layout_wrap(const unsigned maximum_width)
|
|||
}
|
||||
|
||||
label_->layout_wrap(maximum_width);
|
||||
|
||||
set_content_layout_size(label_->get_best_size());
|
||||
|
||||
DBG_G_L << "tscroll_label " << __func__ << ":"
|
||||
|
@ -140,6 +172,7 @@ void tscroll_label::content_set_size(const SDL_Rect& rect)
|
|||
scrollbar->set_visible_items(rect.h);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#ifndef NEW_DRAW
|
||||
void tscroll_label::draw_content(surface& surf, const bool force,
|
||||
const bool invalidate_background)
|
||||
|
@ -165,7 +198,21 @@ void tscroll_label::draw_content(surface& surf, const bool force,
|
|||
|
||||
blit_surface(label_surf, &src_rect , surf, &dst_rect);
|
||||
}
|
||||
#else
|
||||
void tscroll_label::content_draw_background(surface& /*frame_buffer*/)
|
||||
{
|
||||
assert(false); //fixme implement
|
||||
}
|
||||
|
||||
void tscroll_label::
|
||||
content_populate_dirty_list(twindow& /*caller*/,
|
||||
const std::vector<twidget*>& /*call_stack*/)
|
||||
{
|
||||
assert(false); //fixme implement
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
twidget* tscroll_label::content_find_widget(
|
||||
const tpoint& /*coordinate*/, const bool /*must_be_active*/)
|
||||
{
|
||||
|
@ -177,6 +224,7 @@ const twidget* tscroll_label::content_find_widget(const tpoint& /*coordinate*/,
|
|||
{
|
||||
return label_;
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace gui2
|
||||
|
||||
|
|
|
@ -15,7 +15,11 @@
|
|||
#ifndef GUI_WIDGETS_SCROLL_LABEL_HPP_INCLUDED
|
||||
#define GUI_WIDGETS_SCROLL_LABEL_HPP_INCLUDED
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
#include "gui/widgets/vertical_scrollbar_container.hpp"
|
||||
#else
|
||||
#include "gui/widgets/scrollbar_container.hpp"
|
||||
#endif
|
||||
|
||||
namespace gui2 {
|
||||
|
||||
|
@ -29,7 +33,11 @@ class tspacer;
|
|||
* scrolling features. In general this widget is slower as the normal label so
|
||||
* the normal label should be preferred.
|
||||
*/
|
||||
#ifndef NEW_DRAW
|
||||
class tscroll_label : public tvertical_scrollbar_container_
|
||||
#else
|
||||
class tscroll_label : public tscrollbar_container
|
||||
#endif
|
||||
{
|
||||
friend class tbuilder_scroll_label;
|
||||
public:
|
||||
|
@ -70,6 +78,7 @@ private:
|
|||
*/
|
||||
tstate state_;
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
/**
|
||||
* Helper label.
|
||||
*
|
||||
|
@ -94,9 +103,12 @@ private:
|
|||
const tspacer* find_spacer(const bool must_exist = true) const;
|
||||
|
||||
void finalize();
|
||||
#else
|
||||
void finalize_subclass();
|
||||
#endif
|
||||
|
||||
/***** ***** ***** ***** layout functions ***** ***** ***** *****/
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
/** Inherited from tvertical_scrollbar_container_. */
|
||||
tpoint content_calculate_best_size() const;
|
||||
|
||||
|
@ -111,19 +123,25 @@ private:
|
|||
|
||||
/** Inherited from tvertical_scrollbar_container_. */
|
||||
void content_set_size(const SDL_Rect& rect);
|
||||
|
||||
#endif
|
||||
/***** ***** ***** inherited ****** *****/
|
||||
|
||||
/** Inherited from tcontrol. */
|
||||
const std::string& get_control_type() const
|
||||
{ static const std::string type = "scroll_label"; return type; }
|
||||
#ifndef NEW_DRAW
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
/** Inherited from tvertical_scrollbar_container_. */
|
||||
void draw_content(surface& surface, const bool force = false,
|
||||
const bool invalidate_background = false);
|
||||
#else
|
||||
//FIXME we can't draw yet.
|
||||
void content_draw_background(surface& frame_buffer);
|
||||
|
||||
void content_populate_dirty_list(twindow& caller,
|
||||
const std::vector<twidget*>& call_stack);
|
||||
#endif
|
||||
|
||||
#ifndef NEW_DRAW
|
||||
/** Inherited from tvertical_scrollbar_container_. */
|
||||
twidget* content_find_widget(
|
||||
const tpoint& coordinate, const bool must_be_active);
|
||||
|
@ -131,6 +149,7 @@ private:
|
|||
/** Inherited from tvertical_scrollbar_container_. */
|
||||
const twidget* content_find_widget(const tpoint& coordinate,
|
||||
const bool must_be_active) const;
|
||||
#endif
|
||||
};
|
||||
|
||||
} // namespace gui2
|
||||
|
|
448
src/gui/widgets/scrollbar_container.cpp
Normal file
448
src/gui/widgets/scrollbar_container.cpp
Normal file
|
@ -0,0 +1,448 @@
|
|||
/* $Id$ */
|
||||
/*
|
||||
copyright (C) 2008 by mark de wever <koraq@xs4all.nl>
|
||||
part of the battle for wesnoth project http://www.wesnoth.org/
|
||||
|
||||
this program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the gnu general public license version 2
|
||||
or at your option any later version.
|
||||
this program is distributed in the hope that it will be useful,
|
||||
but without any warranty.
|
||||
|
||||
see the copying file for more details.
|
||||
*/
|
||||
|
||||
#ifdef NEW_DRAW
|
||||
|
||||
#include "gui/widgets/scrollbar_container.hpp"
|
||||
|
||||
#include "foreach.hpp"
|
||||
#include "gui/widgets/button.hpp"
|
||||
#include "gui/widgets/scrollbar.hpp"
|
||||
#include "gui/widgets/spacer.hpp"
|
||||
#include "gui/widgets/window.hpp"
|
||||
|
||||
namespace gui2 {
|
||||
|
||||
namespace {
|
||||
|
||||
static const std::string button_up_names[] = {
|
||||
"_begin", "_line_up", "_half_page_up", "_page_up" };
|
||||
|
||||
static const std::string button_down_names[] = {
|
||||
"_end", "_line_down", "_half_page_down", "_page_down" };
|
||||
|
||||
/**
|
||||
* Returns a map with the names of all buttons and the scrollbar jump they're
|
||||
* supposed to execute.
|
||||
*/
|
||||
const std::map<std::string, tscrollbar_::tscroll>& scroll_lookup()
|
||||
{
|
||||
static std::map<std::string, tscrollbar_::tscroll> lookup;
|
||||
if(lookup.empty()) {
|
||||
lookup["_begin"] = tscrollbar_::BEGIN;
|
||||
lookup["_line_up"] = tscrollbar_::ITEM_BACKWARDS;
|
||||
lookup["_half_page_up"] = tscrollbar_::HALF_JUMP_BACKWARDS;
|
||||
lookup["_page_up"] = tscrollbar_::JUMP_BACKWARDS;
|
||||
|
||||
lookup["_end"] = tscrollbar_::END;
|
||||
lookup["_line_down"] = tscrollbar_::ITEM_FORWARD;
|
||||
lookup["_half_page_down"] = tscrollbar_::HALF_JUMP_FORWARD;
|
||||
lookup["_page_down"] = tscrollbar_::JUMP_FORWARD;
|
||||
}
|
||||
|
||||
return lookup;
|
||||
}
|
||||
|
||||
void callback_vertical_scrollbar_button(twidget* caller)
|
||||
{
|
||||
gui2::get_parent<gui2::tscrollbar_container>
|
||||
(caller)->vertical_scrollbar_click(caller);
|
||||
}
|
||||
|
||||
void callback_horizontal_scrollbar_button(twidget* caller)
|
||||
{
|
||||
gui2::get_parent<gui2::tscrollbar_container>
|
||||
(caller)->horizontal_scrollbar_click(caller);
|
||||
}
|
||||
|
||||
void callback_vertical_scrollbar(twidget* caller)
|
||||
{
|
||||
gui2::get_parent<gui2::tscrollbar_container>
|
||||
(caller)->vertical_scrollbar_moved(caller);
|
||||
}
|
||||
|
||||
void callback_horizontal_scrollbar(twidget* caller)
|
||||
{
|
||||
gui2::get_parent<gui2::tscrollbar_container>
|
||||
(caller)->horizontal_scrollbar_moved(caller);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
tscrollbar_container::tscrollbar_container(const unsigned canvas_count)
|
||||
: tcontainer_(canvas_count)
|
||||
, state_(ENABLED)
|
||||
, vertical_scrollbar_mode_(SHOW_WHEN_NEEDED)
|
||||
, horizontal_scrollbar_mode_(SHOW_WHEN_NEEDED)
|
||||
, vertical_scrollbar_grid_(NULL)
|
||||
, horizontal_scrollbar_grid_(NULL)
|
||||
, vertical_scrollbar_(NULL)
|
||||
, horizontal_scrollbar_(NULL)
|
||||
, content_grid_(NULL)
|
||||
, content_(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
void tscrollbar_container::layout_init()
|
||||
{
|
||||
// Inherited.
|
||||
tcontainer_::layout_init();
|
||||
|
||||
assert(content_grid_);
|
||||
content_grid_->layout_init();
|
||||
}
|
||||
|
||||
void tscrollbar_container::layout_wrap(const unsigned maximum_width)
|
||||
{
|
||||
// Inherited.
|
||||
twidget::layout_wrap(maximum_width);
|
||||
|
||||
assert(content_grid_ && vertical_scrollbar_grid_);
|
||||
const unsigned offset = vertical_scrollbar_mode_ == HIDE
|
||||
? 0
|
||||
: vertical_scrollbar_grid_->get_best_size().x;
|
||||
|
||||
content_grid_->layout_wrap(maximum_width - offset);
|
||||
}
|
||||
|
||||
void tscrollbar_container::
|
||||
layout_use_vertical_scrollbar(const unsigned maximum_height)
|
||||
{
|
||||
// Inherited.
|
||||
twidget::layout_use_vertical_scrollbar(maximum_height);
|
||||
|
||||
tpoint size = get_best_size();
|
||||
|
||||
size.y = maximum_height;
|
||||
|
||||
// FIXME adjust for the step size of the scrollbar
|
||||
|
||||
set_layout_size(size);
|
||||
}
|
||||
|
||||
void tscrollbar_container::
|
||||
layout_use_horizontal_scrollbar(const unsigned maximum_width)
|
||||
{
|
||||
// Inherited.
|
||||
twidget::layout_use_horizontal_scrollbar(maximum_width);
|
||||
|
||||
tpoint size = get_best_size();
|
||||
|
||||
size.x = maximum_width;
|
||||
|
||||
set_layout_size(size);
|
||||
}
|
||||
|
||||
tpoint tscrollbar_container::calculate_best_size() const
|
||||
{
|
||||
log_scope2(gui_layout,
|
||||
std::string("tscrollbar_container ") + __func__);
|
||||
|
||||
/***** get vertical scrollbar size *****/
|
||||
const tpoint vertical_scrollbar =
|
||||
vertical_scrollbar_mode_ == HIDE
|
||||
? tpoint(0, 0)
|
||||
: vertical_scrollbar_grid_->get_best_size();
|
||||
|
||||
/***** get horizontal scrollbar size *****/
|
||||
const tpoint horizontal_scrollbar =
|
||||
horizontal_scrollbar_mode_ == HIDE
|
||||
? tpoint(0, 0)
|
||||
: horizontal_scrollbar_grid_->get_best_size();
|
||||
|
||||
/***** get content size *****/
|
||||
assert(content_grid_);
|
||||
const tpoint content = content_grid_->get_best_size();
|
||||
|
||||
const tpoint result(
|
||||
vertical_scrollbar.x +
|
||||
std::max(horizontal_scrollbar.x, content.x),
|
||||
horizontal_scrollbar.y +
|
||||
std::max(vertical_scrollbar.y, content.y));
|
||||
|
||||
DBG_G_L << "tscrollbar_container"
|
||||
<< " vertical_scrollbar " << vertical_scrollbar
|
||||
<< " horizontal_scrollbar " << horizontal_scrollbar
|
||||
<< " content " << content
|
||||
<< " result " << result
|
||||
<< ".\n";
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void tscrollbar_container::
|
||||
set_size(const tpoint& origin, const tpoint& size)
|
||||
{
|
||||
// Inherited.
|
||||
tcontainer_::set_size(origin, size);
|
||||
|
||||
// Set content size
|
||||
assert(content_ && content_grid_);
|
||||
|
||||
const tpoint content_origin = tpoint(
|
||||
content_->get_screen_x(),
|
||||
content_->get_screen_y());
|
||||
|
||||
const tpoint content_size = content_grid_->get_best_size();
|
||||
|
||||
content_grid_->set_size(content_origin, content_size);
|
||||
|
||||
// Set vertical scrollbar
|
||||
assert(vertical_scrollbar_);
|
||||
if(vertical_scrollbar_mode_ != HIDE) {
|
||||
vertical_scrollbar_->set_item_count(content_size.y);
|
||||
vertical_scrollbar_->set_visible_items(content_->get_height());
|
||||
}
|
||||
|
||||
// Set horizontal scrollbar
|
||||
assert(horizontal_scrollbar_);
|
||||
if(horizontal_scrollbar_mode_ != HIDE) {
|
||||
horizontal_scrollbar_->set_item_count(content_size.x);
|
||||
horizontal_scrollbar_->set_visible_items(content_->get_width());
|
||||
}
|
||||
}
|
||||
|
||||
void tscrollbar_container::draw_background(surface& frame_buffer)
|
||||
{
|
||||
// Inherited.
|
||||
tcontainer_::draw_background(frame_buffer);
|
||||
|
||||
/***** **** Draw content ***** *****/
|
||||
assert(content_ && content_grid_);
|
||||
|
||||
// Update the location depending on the scrollbars.
|
||||
if(vertical_scrollbar_mode_ != HIDE
|
||||
|| horizontal_scrollbar_mode_ != HIDE) {
|
||||
|
||||
assert(vertical_scrollbar_ && horizontal_scrollbar_);
|
||||
const int x_offset = horizontal_scrollbar_mode_ == HIDE
|
||||
? 0
|
||||
: horizontal_scrollbar_->get_item_position() *
|
||||
horizontal_scrollbar_->get_step_size();
|
||||
|
||||
const int y_offset = vertical_scrollbar_mode_ == HIDE
|
||||
? 0
|
||||
: vertical_scrollbar_->get_item_position() *
|
||||
vertical_scrollbar_->get_step_size();
|
||||
|
||||
|
||||
const tpoint content_size = content_grid_->get_best_size();
|
||||
|
||||
const tpoint content_origin = tpoint(
|
||||
content_->get_screen_x() - x_offset,
|
||||
content_->get_screen_y() - y_offset);
|
||||
|
||||
content_grid_->set_size(content_origin, content_size);
|
||||
}
|
||||
|
||||
// Make sure the content can't draw outside its canvas.
|
||||
clip_rect_setter clip_rect(frame_buffer, ::create_rect(
|
||||
content_->get_screen_x(),
|
||||
content_->get_screen_y(),
|
||||
content_->get_width(),
|
||||
content_->get_height()));
|
||||
|
||||
// Draw.
|
||||
content_grid_->draw_children(frame_buffer);
|
||||
}
|
||||
|
||||
void tscrollbar_container::draw_foreground(surface& frame_buffer)
|
||||
{
|
||||
// Inherited.
|
||||
tcontainer_::draw_foreground(frame_buffer);
|
||||
}
|
||||
|
||||
void tscrollbar_container::vertical_scrollbar_click(twidget* caller)
|
||||
{
|
||||
/** @todo Hack to capture the keyboard focus. */
|
||||
get_window()->keyboard_capture(this);
|
||||
|
||||
const std::map<std::string, tscrollbar_::tscroll>::const_iterator
|
||||
itor = scroll_lookup().find(caller->id());
|
||||
|
||||
assert(itor != scroll_lookup().end());
|
||||
vertical_scrollbar_->scroll(itor->second);
|
||||
|
||||
set_scrollbar_button_status();
|
||||
set_dirty();
|
||||
}
|
||||
|
||||
void tscrollbar_container::horizontal_scrollbar_click(twidget* caller)
|
||||
{
|
||||
/** @todo Hack to capture the keyboard focus. */
|
||||
get_window()->keyboard_capture(this);
|
||||
|
||||
const std::map<std::string, tscrollbar_::tscroll>::const_iterator
|
||||
itor = scroll_lookup().find(caller->id());
|
||||
|
||||
assert(itor != scroll_lookup().end());
|
||||
horizontal_scrollbar_->scroll(itor->second);
|
||||
|
||||
set_scrollbar_button_status();
|
||||
set_dirty();
|
||||
}
|
||||
|
||||
void tscrollbar_container::finalize_setup()
|
||||
{
|
||||
/***** Setup vertical scrollbar *****/
|
||||
|
||||
vertical_scrollbar_grid_ =
|
||||
find_widget<tgrid>("_vertical_scrollbar_grid", false, true);
|
||||
|
||||
vertical_scrollbar_ = vertical_scrollbar_grid_->
|
||||
find_widget<tscrollbar_>("_vertical_scrollbar", false, true);
|
||||
|
||||
vertical_scrollbar_->
|
||||
set_callback_positioner_move(callback_vertical_scrollbar);
|
||||
|
||||
/***** Setup horizontal scrollbar *****/
|
||||
horizontal_scrollbar_grid_ =
|
||||
find_widget<tgrid>("_horizontal_scrollbar_grid", false, true);
|
||||
|
||||
horizontal_scrollbar_ = horizontal_scrollbar_grid_->
|
||||
find_widget<tscrollbar_>("_horizontal_scrollbar", false, true);
|
||||
|
||||
horizontal_scrollbar_->
|
||||
set_callback_positioner_move(callback_horizontal_scrollbar);
|
||||
|
||||
/***** Setup the scrollbar buttons *****/
|
||||
typedef std::pair<std::string, tscrollbar_::tscroll> hack;
|
||||
foreach(const hack& item, scroll_lookup()) {
|
||||
|
||||
// Vertical.
|
||||
tbutton* button = vertical_scrollbar_grid_->
|
||||
find_widget<tbutton>(item.first, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_callback_mouse_left_click(
|
||||
callback_vertical_scrollbar_button);
|
||||
}
|
||||
|
||||
// Horizontal.
|
||||
button = horizontal_scrollbar_grid_->
|
||||
find_widget<tbutton>(item.first, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_callback_mouse_left_click(
|
||||
callback_horizontal_scrollbar_button);
|
||||
}
|
||||
}
|
||||
|
||||
/***** Setup the content *****/
|
||||
content_ = new tspacer();
|
||||
content_->set_definition("default");
|
||||
|
||||
content_grid_ = dynamic_cast<tgrid*>(
|
||||
grid().swap_child("_content_grid", content_, true));
|
||||
assert(content_grid_);
|
||||
|
||||
/***** Set the easy close status. *****/
|
||||
/** @todo needs more testing. */
|
||||
set_block_easy_close(get_visible()
|
||||
&& get_active() && does_block_easy_close());
|
||||
|
||||
/***** Let our subclasses initialize themselves. *****/
|
||||
finalize_subclass();
|
||||
}
|
||||
|
||||
void tscrollbar_container::
|
||||
set_vertical_scrollbar_mode(const tscrollbar_mode scrollbar_mode)
|
||||
{
|
||||
if(vertical_scrollbar_mode_ != scrollbar_mode) {
|
||||
vertical_scrollbar_mode_ = scrollbar_mode;
|
||||
show_vertical_scrollbar(vertical_scrollbar_mode_ != HIDE);
|
||||
}
|
||||
}
|
||||
|
||||
void tscrollbar_container::
|
||||
set_horizontal_scrollbar_mode(const tscrollbar_mode scrollbar_mode)
|
||||
{
|
||||
if(horizontal_scrollbar_mode_ != scrollbar_mode) {
|
||||
horizontal_scrollbar_mode_ = scrollbar_mode;
|
||||
show_horizontal_scrollbar(horizontal_scrollbar_mode_ != HIDE);
|
||||
}
|
||||
}
|
||||
|
||||
void tscrollbar_container::show_vertical_scrollbar(const bool /*show*/)
|
||||
{
|
||||
/** @todo implement the new visibility. */
|
||||
// vertical_scrollbar_grid_->set_visible(show);
|
||||
}
|
||||
|
||||
void tscrollbar_container::show_horizontal_scrollbar(const bool /*show*/)
|
||||
{
|
||||
/** @todo implement the new visibility. */
|
||||
// horizontal_scrollbar_grid_->set_visible(show);
|
||||
}
|
||||
|
||||
void tscrollbar_container::set_scrollbar_button_status()
|
||||
{
|
||||
if(true) { /** @todo scrollbar visibility. */
|
||||
/***** set scroll up button status *****/
|
||||
foreach(const std::string& name, button_up_names) {
|
||||
tbutton* button = vertical_scrollbar_grid_->
|
||||
find_widget<tbutton>(name, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_active(!vertical_scrollbar_->at_begin());
|
||||
}
|
||||
}
|
||||
|
||||
/***** set scroll down status *****/
|
||||
foreach(const std::string& name, button_down_names) {
|
||||
tbutton* button = vertical_scrollbar_grid_->
|
||||
find_widget<tbutton>(name, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_active(vertical_scrollbar_->at_end());
|
||||
}
|
||||
}
|
||||
|
||||
/***** Set the status if the scrollbars *****/
|
||||
vertical_scrollbar_->set_active( !(vertical_scrollbar_->at_begin()
|
||||
&& vertical_scrollbar_->at_end()));
|
||||
}
|
||||
|
||||
if(true) { /** @todo scrollbar visibility. */
|
||||
/***** Set scroll left button status *****/
|
||||
foreach(const std::string& name, button_up_names) {
|
||||
tbutton* button = horizontal_scrollbar_grid_->
|
||||
find_widget<tbutton>(name, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_active(!horizontal_scrollbar_->at_begin());
|
||||
}
|
||||
}
|
||||
|
||||
/***** Set scroll right button status *****/
|
||||
foreach(const std::string& name, button_down_names) {
|
||||
tbutton* button = horizontal_scrollbar_grid_->
|
||||
find_widget<tbutton>(name, false, false);
|
||||
|
||||
if(button) {
|
||||
button->set_active(horizontal_scrollbar_->at_end());
|
||||
}
|
||||
}
|
||||
|
||||
/***** Set the status if the scrollbars *****/
|
||||
horizontal_scrollbar_->set_active( !(horizontal_scrollbar_->at_begin()
|
||||
&& horizontal_scrollbar_->at_end()));
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace gui2
|
||||
|
||||
#endif
|
||||
|
||||
|
257
src/gui/widgets/scrollbar_container.hpp
Normal file
257
src/gui/widgets/scrollbar_container.hpp
Normal file
|
@ -0,0 +1,257 @@
|
|||
/* $Id$ */
|
||||
/*
|
||||
copyright (C) 2008 by mark de wever <koraq@xs4all.nl>
|
||||
part of the battle for wesnoth project http://www.wesnoth.org/
|
||||
|
||||
this program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the gnu general public license version 2
|
||||
or at your option any later version.
|
||||
this program is distributed in the hope that it will be useful,
|
||||
but without any warranty.
|
||||
|
||||
see the copying file for more details.
|
||||
*/
|
||||
|
||||
#ifndef GUI_WIDGETS_SCROLLBAR_CONTAINER_HPP_INCLUDED
|
||||
#define GUI_WIDGETS_SCROLLBAR_CONTAINER_HPP_INCLUDED
|
||||
|
||||
|
||||
#ifdef NEW_DRAW
|
||||
|
||||
#include "gui/widgets/container.hpp"
|
||||
|
||||
#include <boost/noncopyable.hpp>
|
||||
|
||||
namespace gui2 {
|
||||
|
||||
class tscrollbar_;
|
||||
class tspacer;
|
||||
|
||||
/**
|
||||
* Base class for creating containers with one or two scrollbar(s).
|
||||
*
|
||||
* For now users can't instanciate this class directly and needs to use small
|
||||
* wrapper classes. Maybe in the future users can use the class directly.
|
||||
*
|
||||
* @todo events are not yet send to the content grid.
|
||||
*/
|
||||
class tscrollbar_container
|
||||
: public tcontainer_
|
||||
, private boost::noncopyable
|
||||
{
|
||||
friend class tdebug_layout_graph;
|
||||
|
||||
friend class tbuilder_scroll_label;
|
||||
|
||||
public:
|
||||
|
||||
tscrollbar_container(const unsigned canvas_count);
|
||||
|
||||
~tscrollbar_container() { delete content_grid_; }
|
||||
|
||||
/** The way to handle the showing or hiding of the scrollbar. */
|
||||
enum tscrollbar_mode {
|
||||
SHOW, /**<
|
||||
* The scrollbar is always shown, whether
|
||||
* needed or not.
|
||||
*/
|
||||
HIDE, /**<
|
||||
* The scrollbar is never shown even not when
|
||||
* needed. There's also no space reserved for
|
||||
* the scrollbar.
|
||||
*/
|
||||
SHOW_WHEN_NEEDED /**<
|
||||
* The scrollbar is shown when the number of
|
||||
* items is larger as the visible items. The
|
||||
* space for the scrollbar is always
|
||||
* reserved, just in case it's needed after
|
||||
* the initial sizing (due to adding items).
|
||||
*/
|
||||
};
|
||||
|
||||
/***** ***** ***** ***** layout functions ***** ***** ***** *****/
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void layout_init();
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
bool can_wrap() const
|
||||
{
|
||||
// Note this function is called before the object is finalized.
|
||||
return content_grid_
|
||||
? content_grid_->can_wrap()
|
||||
: false;
|
||||
}
|
||||
|
||||
/** Inherited from twidget (not tcontainer_). */
|
||||
void layout_wrap(const unsigned maximum_width);
|
||||
|
||||
/** Inherited from twidget (not tcontainer_). */
|
||||
bool has_vertical_scrollbar() const
|
||||
{ return vertical_scrollbar_mode_ != HIDE; }
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void layout_use_vertical_scrollbar(const unsigned maximum_height);
|
||||
|
||||
/** Inherited from twidget (not tcontainer_). */
|
||||
bool has_horizontal_scrollbar() const
|
||||
{ return horizontal_scrollbar_mode_ != HIDE; }
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void layout_use_horizontal_scrollbar(const unsigned maximum_width);
|
||||
|
||||
private:
|
||||
/** Inherited from tcontainer_. */
|
||||
tpoint calculate_best_size() const;
|
||||
public:
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void set_size(const tpoint& origin, const tpoint& size);
|
||||
|
||||
/***** ***** ***** inherited ****** *****/
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
bool get_active() const { return state_ != DISABLED; }
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
unsigned get_state() const { return state_; }
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void draw_background(surface& frame_buffer);
|
||||
|
||||
/** Inherited from tcontainer_. */
|
||||
void draw_foreground(surface& frame_buffer);
|
||||
|
||||
/***** ***** ***** setters / getters for members ***** ****** *****/
|
||||
|
||||
void set_vertical_scrollbar_mode(const tscrollbar_mode scrollbar_mode);
|
||||
tscrollbar_mode get_vertical_scrollbar_mode() const
|
||||
{ return vertical_scrollbar_mode_; }
|
||||
|
||||
void set_horizontal_scrollbar_mode(const tscrollbar_mode scrollbar_mode);
|
||||
tscrollbar_mode get_horizontal_scrollbar_mode() const
|
||||
{ return horizontal_scrollbar_mode_; }
|
||||
|
||||
void vertical_scrollbar_click(twidget* caller);
|
||||
void horizontal_scrollbar_click(twidget* caller);
|
||||
|
||||
tgrid *content_grid() { return content_grid_; }
|
||||
const tgrid *content_grid() const { return content_grid_; }
|
||||
|
||||
/**
|
||||
* Callback when the scrollbar moves (NOTE maybe only one callback needed).
|
||||
* Maybe also make protected or private and add a friend.
|
||||
*/
|
||||
void vertical_scrollbar_moved(twidget* /*caller*/)
|
||||
{ set_scrollbar_button_status(); set_dirty(); }
|
||||
|
||||
void horizontal_scrollbar_moved(twidget* /*caller*/)
|
||||
{ set_scrollbar_button_status(); set_dirty(); }
|
||||
protected:
|
||||
|
||||
/*
|
||||
* The widget contains the following three grids.
|
||||
*
|
||||
* * _vertical_scrollbar_grid containing at least a widget named
|
||||
* _vertical_scrollbar
|
||||
*
|
||||
* * _horizontal_scrollbar_grid containing at least a widget named
|
||||
* _horizontal_scrollbar
|
||||
*
|
||||
* * _content_grid a grid which holds the contents of the area.
|
||||
*
|
||||
* NOTE maybe just hardcode these in the finalize phase...
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* Sets the status of the scrollbar buttons.
|
||||
*
|
||||
* This is needed after the scrollbar moves so the status of the buttons
|
||||
* will be active or inactive as needed.
|
||||
*/
|
||||
void set_scrollbar_button_status();
|
||||
|
||||
private:
|
||||
|
||||
/**
|
||||
* Possible states of the widget.
|
||||
*
|
||||
* Note the order of the states must be the same as defined in settings.hpp.
|
||||
*/
|
||||
enum tstate { ENABLED, DISABLED, COUNT };
|
||||
|
||||
/**
|
||||
* Current state of the widget.
|
||||
*
|
||||
* The state of the widget determines what to render and how the widget
|
||||
* reacts to certain 'events'.
|
||||
*/
|
||||
tstate state_;
|
||||
|
||||
/**
|
||||
* The mode of how to show the scrollbar.
|
||||
*
|
||||
* This value should only be modified before showing, doing it while
|
||||
* showing results in UB.
|
||||
*/
|
||||
tscrollbar_mode
|
||||
vertical_scrollbar_mode_,
|
||||
horizontal_scrollbar_mode_;
|
||||
|
||||
/** These are valid after finalize_setup(). */
|
||||
tgrid
|
||||
*vertical_scrollbar_grid_,
|
||||
*horizontal_scrollbar_grid_;
|
||||
|
||||
/** These are valid after finalize_setup(). */
|
||||
tscrollbar_
|
||||
*vertical_scrollbar_,
|
||||
*horizontal_scrollbar_;
|
||||
|
||||
/** The grid that holds the content. */
|
||||
tgrid *content_grid_;
|
||||
|
||||
/** Dummy spacer to hold the contents location. */
|
||||
tspacer *content_;
|
||||
|
||||
/** The builder needs to call us so we do our setup. */
|
||||
void finalize_setup();
|
||||
|
||||
/**
|
||||
* Function for the subclasses to do their setup.
|
||||
*
|
||||
* This function is called at the end of finalize_setup().
|
||||
*/
|
||||
virtual void finalize_subclass() {}
|
||||
|
||||
/**
|
||||
* Shows the vertical scrollbar.
|
||||
*
|
||||
* @param show If true the scrollbar is shown, hidden
|
||||
* otherwise.
|
||||
*/
|
||||
void show_vertical_scrollbar(const bool show);
|
||||
|
||||
/**
|
||||
* Shows the horizontal scrollbar.
|
||||
*
|
||||
* @param show If true the scrollbar is shown, hidden
|
||||
* otherwise.
|
||||
*/
|
||||
void show_horizontal_scrollbar(const bool show);
|
||||
|
||||
/** Inherited from tcontrol. */
|
||||
const std::string& get_control_type() const
|
||||
{
|
||||
static const std::string type = "scrollbar_container";
|
||||
return type;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
} // namespace gui2
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
|
@ -1013,6 +1013,9 @@ twidget* tbuilder_scroll_label::build() const
|
|||
<const tscroll_label_definition::tresolution>(widget->config());
|
||||
assert(conf);
|
||||
|
||||
#ifdef NEW_DRAW
|
||||
conf->grid->build(&widget->grid());
|
||||
#else
|
||||
tgrid* grid = dynamic_cast<tgrid*>(conf->grid->build());
|
||||
assert(grid);
|
||||
|
||||
|
@ -1021,7 +1024,7 @@ twidget* tbuilder_scroll_label::build() const
|
|||
tgrid::VERTICAL_GROW_SEND_TO_CLIENT
|
||||
| tgrid::HORIZONTAL_GROW_SEND_TO_CLIENT
|
||||
, 0);
|
||||
|
||||
#endif
|
||||
widget->finalize_setup();
|
||||
|
||||
DBG_GUI << "Window builder: placed scroll label '" << id << "' with defintion '"
|
||||
|
|
Loading…
Add table
Reference in a new issue