Merge branch 'besh81-develop-1.7' into develop-1.7

This commit is contained in:
Jinhao 2019-01-29 04:30:37 +08:00
commit 56f44e6479
3 changed files with 88 additions and 53 deletions

View File

@ -46,7 +46,7 @@ namespace nana{ namespace widgets{ namespace detail
}; };
/// A component set placer used for specifying component position and size. /// A component set placer used for specifying component position and size.
template<typename Component, typename ItemAttribute> template<typename Component, typename ItemAttribute, typename WidgetScheme>
class compset_placer class compset_placer
{ {
public: public:
@ -56,10 +56,22 @@ namespace nana{ namespace widgets{ namespace detail
/// A type of widget-defined item attribute. /// A type of widget-defined item attribute.
typedef ItemAttribute item_attribute_t; typedef ItemAttribute item_attribute_t;
/// Widget scheme.
typedef WidgetScheme widget_scheme_t;
widget_scheme_t * wdg_scheme_ptr_{ nullptr };
public: public:
/// The destrcutor. /// The destructor.
virtual ~compset_placer(){} virtual ~compset_placer(){}
/// Init the scheme pointer
void init_scheme(widget_scheme_t* wdg_scheme_ptr)
{
wdg_scheme_ptr_ = wdg_scheme_ptr;
}
/// Enable/Disable the specified component. /// Enable/Disable the specified component.
virtual void enable(component_t, bool) = 0; virtual void enable(component_t, bool) = 0;
virtual bool enabled(component_t) const = 0; virtual bool enabled(component_t) const = 0;

View File

@ -60,8 +60,26 @@ namespace nana
::std::string text; ::std::string text;
}; };
struct scheme
: public widget_geometrics
{
color_proxy item_bg_selected{ static_cast<color_rgb>(0xD5EFFC) }; ///< item selected: background color
color_proxy item_fg_selected{ static_cast<color_rgb>(0x99DEFD) }; ///< item selected: foreground color
color_proxy item_bg_highlighted{ static_cast<color_rgb>(0xE8F5FD) }; ///< item highlighted: background color
color_proxy item_fg_highlighted{ static_cast<color_rgb>(0xD8F0FA) }; ///< item highlighted: foreground color
color_proxy item_bg_selected_and_highlighted{ static_cast<color_rgb>(0xC4E8FA) }; ///< item selected and highlighted: background color
color_proxy item_fg_selected_and_highlighted{ static_cast<color_rgb>(0xB6E6FB) }; ///< item selected and highlighted: foreground color
unsigned item_offset{ 16 }; ///< item position displacement in pixels
unsigned text_offset{ 4 }; ///< text position displacement in pixels
unsigned icon_size{ 16 }; ///< icon size in pixels
unsigned crook_size{ 16 }; ///< crook size in pixels (TODO: the function that draw the crook doesn't scale the shape)
unsigned indent_displacement{ 18 }; ///< children position displacement in pixels (def=18 (before was 10))
};
typedef widgets::detail::compset<component, node_attribute> compset_interface; typedef widgets::detail::compset<component, node_attribute> compset_interface;
typedef widgets::detail::compset_placer<component, node_attribute> compset_placer_interface; typedef widgets::detail::compset_placer<component, node_attribute, scheme> compset_placer_interface;
class renderer_interface class renderer_interface
{ {
@ -353,7 +371,7 @@ namespace nana
/// \brief Displays a hierarchical list of items, such as the files and directories on a disk. /// \brief Displays a hierarchical list of items, such as the files and directories on a disk.
/// See also in [documentation](http://nanapro.org/en-us/documentation/widgets/treebox.htm) /// See also in [documentation](http://nanapro.org/en-us/documentation/widgets/treebox.htm)
class treebox class treebox
:public widget_object < category::widget_tag, drawerbase::treebox::trigger, drawerbase::treebox::treebox_events> :public widget_object <category::widget_tag, drawerbase::treebox::trigger, drawerbase::treebox::treebox_events, drawerbase::treebox::scheme>
{ {
public: public:
/// A type refers to the item and is also used to iterate through the nodes. /// A type refers to the item and is also used to iterate through the nodes.

View File

@ -238,11 +238,11 @@ namespace nana
switch (affect) switch (affect)
{ {
case 1: case 1:
pos_.x += impl_->shape.indent_pixels; pos_.x += impl_->data.scheme_ptr->indent_displacement;
break; break;
default: default:
if (affect >= 2) if (affect >= 2)
pos_.x -= impl_->shape.indent_pixels * (affect - 1); pos_.x -= impl_->data.scheme_ptr->indent_displacement * (affect - 1);
} }
auto & comp_placer = impl_->data.comp_placer; auto & comp_placer = impl_->data.comp_placer;
@ -301,6 +301,7 @@ namespace nana
{ {
nana::paint::graphics * graph; nana::paint::graphics * graph;
::nana::treebox * widget_ptr; ::nana::treebox * widget_ptr;
::nana::treebox::scheme_type* scheme_ptr;
trigger * trigger_ptr; trigger * trigger_ptr;
pat::cloneable<compset_placer_interface> comp_placer; pat::cloneable<compset_placer_interface> comp_placer;
@ -310,13 +311,11 @@ namespace nana
struct shape_tag struct shape_tag
{ {
nana::upoint border;
std::shared_ptr<nana::scroll<true>> scroll; std::shared_ptr<nana::scroll<true>> scroll;
mutable std::map<std::string, node_image_tag> image_table; mutable std::map<std::string, node_image_tag> image_table;
tree_cont_type::node_type * first; //The node at the top of screen tree_cont_type::node_type * first; //The node at the top of screen
int indent_pixels;
int offset_x; int offset_x;
}shape; }shape;
@ -356,7 +355,6 @@ namespace nana
data.stop_drawing = false; data.stop_drawing = false;
shape.first = nullptr; shape.first = nullptr;
shape.indent_pixels = 10;
shape.offset_x = 0; shape.offset_x = 0;
shape.scroll = std::make_shared<nana::scroll<true>>(); shape.scroll = std::make_shared<nana::scroll<true>>();
@ -451,7 +449,7 @@ namespace nana
data.graph->rectangle(true, data.widget_ptr->bgcolor()); data.graph->rectangle(true, data.widget_ptr->bgcolor());
//Draw tree //Draw tree
attr.tree_cont.for_each(shape.first, item_rendering_director(this, nana::point(static_cast<int>(attr.tree_cont.indent_size(shape.first) * shape.indent_pixels) - shape.offset_x, margin_top_bottom()))); attr.tree_cont.for_each(shape.first, item_rendering_director(this, nana::point(static_cast<int>(attr.tree_cont.indent_size(shape.first) * data.scheme_ptr->indent_displacement) - shape.offset_x, margin_top_bottom())));
if (!ignore_update) if (!ignore_update)
API::update_window(data.widget_ptr->handle()); API::update_window(data.widget_ptr->handle());
@ -711,7 +709,7 @@ namespace nana
case 3: case 3:
//param is the begin pos of an item in absolute. //param is the begin pos of an item in absolute.
{ {
int beg = static_cast<int>(tree.indent_size(node) * shape.indent_pixels) - shape.offset_x; int beg = static_cast<int>(tree.indent_size(node) * data.scheme_ptr->indent_displacement) - shape.offset_x;
int end = beg + static_cast<int>(node_w_pixels(node)); int end = beg + static_cast<int>(node_w_pixels(node));
bool take_adjust = false; bool take_adjust = false;
@ -910,7 +908,7 @@ namespace nana
bool track_mouse(int x, int y) bool track_mouse(int x, int y)
{ {
int xpos = attr.tree_cont.indent_size(shape.first) * shape.indent_pixels - shape.offset_x; int xpos = attr.tree_cont.indent_size(shape.first) * data.scheme_ptr->indent_displacement - shape.offset_x;
item_locator nl(this, xpos, x, y); item_locator nl(this, xpos, x, y);
attr.tree_cont.template for_each<item_locator&>(shape.first, nl); attr.tree_cont.template for_each<item_locator&>(shape.first, nl);
@ -1332,8 +1330,6 @@ namespace nana
class internal_placer class internal_placer
: public compset_placer_interface : public compset_placer_interface
{ {
static const unsigned item_offset = 16;
static const unsigned text_offset = 4;
private: private:
//Implement the compset_locator_interface //Implement the compset_locator_interface
@ -1342,10 +1338,10 @@ namespace nana
switch(comp) switch(comp)
{ {
case component_t::crook: case component_t::crook:
pixels_crook_ = (enabled ? 16 : 0); enable_crook_ = enabled;
break; break;
case component_t::icon: case component_t::icon:
pixels_icon_ = (enabled ? 16 : 0); enable_icon_ = enabled;
break; break;
default: default:
break; break;
@ -1357,9 +1353,9 @@ namespace nana
switch(comp) switch(comp)
{ {
case component_t::crook: case component_t::crook:
return (0 != pixels_crook_); return enable_crook_;
case component_t::icon: case component_t::icon:
return (0 != pixels_icon_); return enable_icon_;
default: default:
break; break;
} }
@ -1368,16 +1364,17 @@ namespace nana
virtual unsigned item_height(graph_reference graph) const override virtual unsigned item_height(graph_reference graph) const override
{ {
auto m = std::max((enable_crook_ ? wdg_scheme_ptr_->crook_size : 0), (enable_icon_ ? wdg_scheme_ptr_->icon_size : 0));
#ifdef _nana_std_has_string_view #ifdef _nana_std_has_string_view
return graph.text_extent_size(std::wstring_view{ L"jH{", 3 }).height + 8; return std::max(m, graph.text_extent_size(std::wstring_view{ L"jH{", 3 }).height + 8);
#else #else
return graph.text_extent_size(L"jH{", 3).height + 8; return std::max(m, graph.text_extent_size(L"jH{", 3).height + 8);
#endif #endif
} }
virtual unsigned item_width(graph_reference graph, const item_attribute_t& attr) const override virtual unsigned item_width(graph_reference graph, const item_attribute_t& attr) const override
{ {
return graph.text_extent_size(attr.text).width + pixels_crook_ + pixels_icon_ + (text_offset << 1) + item_offset; return graph.text_extent_size(attr.text).width + (enable_crook_ ? wdg_scheme_ptr_->crook_size : 0) + (enable_icon_ ? wdg_scheme_ptr_ ->icon_size: 0) + (wdg_scheme_ptr_->text_offset << 1) + wdg_scheme_ptr_->item_offset;
} }
// Locate a component through the specified coordinate. // Locate a component through the specified coordinate.
@ -1392,35 +1389,35 @@ namespace nana
case component_t::expander: case component_t::expander:
if(attr.has_children) if(attr.has_children)
{ {
r->width = item_offset; r->width = wdg_scheme_ptr_->item_offset;
return true; return true;
} }
return false; return false;
case component_t::bground: case component_t::bground:
return true; return true;
case component_t::crook: case component_t::crook:
if(pixels_crook_) if(enable_crook_)
{ {
r->x += item_offset; r->x += wdg_scheme_ptr_->item_offset;
r->width = pixels_crook_; r->width = wdg_scheme_ptr_->crook_size;
return true; return true;
} }
return false; return false;
case component_t::icon: case component_t::icon:
if(pixels_icon_) if(enable_icon_)
{ {
r->x += item_offset + pixels_crook_; r->x += wdg_scheme_ptr_->item_offset + (enable_crook_ ? wdg_scheme_ptr_->crook_size : 0);
r->y = 2; r->y = 2;
r->width = pixels_icon_; r->width = wdg_scheme_ptr_->icon_size;
r->height -= 2; r->height -= 2;
return true; return true;
} }
return false; return false;
case component_t::text: case component_t::text:
{ {
auto text_pos = item_offset + pixels_crook_ + pixels_icon_ + text_offset; auto text_pos = wdg_scheme_ptr_->item_offset + (enable_crook_ ? wdg_scheme_ptr_->crook_size : 0) + (enable_icon_ ? wdg_scheme_ptr_->icon_size : 0) + wdg_scheme_ptr_->text_offset;
r->x += text_pos; r->x += text_pos;
r->width -= (text_pos + text_offset); r->width -= (text_pos + wdg_scheme_ptr_->text_offset);
}; };
return true; return true;
default: default:
@ -1429,8 +1426,8 @@ namespace nana
return false; return false;
} }
private: private:
unsigned pixels_crook_{0}; bool enable_crook_{ false };
unsigned pixels_icon_{0}; bool enable_icon_{ false };
}; };
class internal_renderer class internal_renderer
@ -1449,37 +1446,42 @@ namespace nana
if(compset->comp_attribute(component::bground, attr)) if(compset->comp_attribute(component::bground, attr))
{ {
const ::nana::color color_table[][2] = { { { 0xE8, 0xF5, 0xFD }, { 0xD8, 0xF0, 0xFA } }, //highlighted auto scheme_ptr = static_cast<::nana::treebox::scheme_type*>(API::dev::get_scheme(window_handle_));
{ { 0xC4, 0xE8, 0xFA }, { 0xB6, 0xE6, 0xFB } }, //Selected and highlighted
{ { 0xD5, 0xEF, 0xFC }, {0x99, 0xDE, 0xFD } } //Selected but not highlighted
};
const ::nana::color *clrptr = nullptr; const ::nana::color_proxy *bg_ptr = nullptr, *fg_ptr = nullptr;
if(compset->item_attribute().mouse_pointed) if(compset->item_attribute().mouse_pointed)
{ {
if(compset->item_attribute().selected) if(compset->item_attribute().selected)
clrptr = color_table[1]; {
bg_ptr = &scheme_ptr->item_bg_selected_and_highlighted;
fg_ptr = &scheme_ptr->item_fg_selected_and_highlighted;
}
else else
clrptr = color_table[0]; {
bg_ptr = &scheme_ptr->item_bg_highlighted;
fg_ptr = &scheme_ptr->item_fg_highlighted;
}
} }
else if(compset->item_attribute().selected) else if(compset->item_attribute().selected)
clrptr = color_table[2]; {
bg_ptr = &scheme_ptr->item_bg_selected;
fg_ptr = &scheme_ptr->item_fg_selected;
}
if (clrptr) if(bg_ptr)
{ {
if (API::is_transparent_background(window_handle_)) if (API::is_transparent_background(window_handle_))
{ {
paint::graphics item_graph{ attr.area.dimension() }; paint::graphics item_graph{ attr.area.dimension() };
item_graph.rectangle(false, clrptr[1]); item_graph.rectangle(false, *fg_ptr);
item_graph.rectangle(rectangle{attr.area.dimension()}.pare_off(1), true, *clrptr); item_graph.rectangle(rectangle{ attr.area.dimension() }.pare_off(1), true, *bg_ptr);
graph.blend(attr.area, item_graph, attr.area.position(), 0.5); graph.blend(attr.area, item_graph, attr.area.position(), 0.5);
} }
else else
{ {
graph.rectangle(attr.area, false, clrptr[1]); graph.rectangle(attr.area, false, *fg_ptr);
graph.rectangle(attr.area.pare_off(1), true, *clrptr); graph.rectangle(attr.area.pare_off(1), true, *bg_ptr);
} }
} }
} }
@ -1531,7 +1533,7 @@ namespace nana
if((nullptr == img) || img->empty()) if((nullptr == img) || img->empty())
img = &(item_attr.icon_normal); img = &(item_attr.icon_normal);
if(! img->empty()) if(!img->empty())
{ {
auto size = img->size(); auto size = img->size();
if(size.width > attr.area.width || size.height > attr.area.height) if(size.width > attr.area.width || size.height > attr.area.height)
@ -1577,10 +1579,10 @@ namespace nana
switch(affect) switch(affect)
{ {
case 0: break; case 0: break;
case 1: item_pos_.x += static_cast<int>(node_desc.indent_pixels); break; case 1: item_pos_.x += static_cast<int>(impl_->data.scheme_ptr->indent_displacement); break;
default: default:
if(affect >= 2) if(affect >= 2)
item_pos_.x -= static_cast<int>(node_desc.indent_pixels) * (affect - 1); item_pos_.x -= static_cast<int>(impl_->data.scheme_ptr->indent_displacement) * (affect - 1);
} }
impl_->assign_node_attr(node_attr_, &node); impl_->assign_node_attr(node_attr_, &node);
@ -1942,7 +1944,10 @@ namespace nana
impl_->data.graph = &graph; impl_->data.graph = &graph;
widget.bgcolor(colors::white); widget.bgcolor(colors::white);
impl_->data.widget_ptr = static_cast< ::nana::treebox*>(&widget); impl_->data.widget_ptr = static_cast<::nana::treebox*>(&widget);
impl_->data.scheme_ptr = static_cast<::nana::treebox::scheme_type*>(API::dev::get_scheme(widget));
impl_->data.comp_placer->init_scheme(impl_->data.scheme_ptr);
widget.caption("nana treebox"); widget.caption("nana treebox");
} }
@ -1961,7 +1966,7 @@ namespace nana
{ {
auto & shape = impl_->shape; auto & shape = impl_->shape;
int xpos = impl_->attr.tree_cont.indent_size(shape.first) * shape.indent_pixels - shape.offset_x; int xpos = impl_->attr.tree_cont.indent_size(shape.first) * impl_->data.scheme_ptr->indent_displacement - shape.offset_x;
item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y); item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y);
impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl); impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl);
@ -1986,7 +1991,7 @@ namespace nana
{ {
auto & shape = impl_->shape; auto & shape = impl_->shape;
int xpos = impl_->attr.tree_cont.indent_size(shape.first) * shape.indent_pixels - shape.offset_x; int xpos = impl_->attr.tree_cont.indent_size(shape.first) * impl_->data.scheme_ptr->indent_displacement - shape.offset_x;
item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y); item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y);
impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl); impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl);
@ -2013,7 +2018,7 @@ namespace nana
{ {
auto & shape = impl_->shape; auto & shape = impl_->shape;
int xpos = impl_->attr.tree_cont.indent_size(shape.first) * shape.indent_pixels - shape.offset_x; int xpos = impl_->attr.tree_cont.indent_size(shape.first) * impl_->data.scheme_ptr->indent_displacement - shape.offset_x;
item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y); item_locator nl(impl_, xpos, arg.pos.x, arg.pos.y);
impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl); impl_->attr.tree_cont.for_each<item_locator&>(shape.first, nl);