Merge branch 'hotfix-1.5.5' into develop

This commit is contained in:
Jinhao
2017-12-01 17:56:06 +08:00
29 changed files with 529 additions and 333 deletions

View File

@@ -204,6 +204,11 @@ namespace nana
{
return (visible_state::invisible != visibility_);
}
bool caret::activated() const
{
return (visible_state::displayed == visibility_);
}
//end class caret
//struct basic_window
@@ -329,24 +334,18 @@ namespace nana
return false;
}
const basic_window* get_child_caret(const basic_window* wd, bool this_is_a_child)
{
if (this_is_a_child && wd->annex.caret_ptr)
return wd;
for (auto child : wd->children)
{
auto caret_wd = get_child_caret(child, true);
if (caret_wd)
return caret_wd;
}
return nullptr;
}
const basic_window * basic_window::child_caret() const
{
return get_child_caret(this, false);
for (auto child : children) {
//Only return the child who has activated caret.
if (child->annex.caret_ptr && child->annex.caret_ptr->activated())
return child;
auto caret = child->child_caret();
if (caret)
return caret;
}
return nullptr;
}
bool basic_window::is_draw_through() const

View File

@@ -151,7 +151,8 @@ namespace nana
arg.window_handle = reinterpret_cast<window>(wd);
if (emit(event_code::expose, wd, arg, false, get_thread_context()))
{
const core_window_t * caret_wd = (wd->annex.caret_ptr ? wd : wd->child_caret());
//Get the window who has the activated caret
const core_window_t * caret_wd = ((wd->annex.caret_ptr && wd->annex.caret_ptr->activated()) ? wd : wd->child_caret());
if (caret_wd)
{
if (exposed)

View File

@@ -245,22 +245,31 @@ namespace detail
_m_event_filter(evt_code, wd, thrd);
}
if(wd->other.upd_state == core_window_t::update_state::none)
wd->other.upd_state = core_window_t::update_state::lazy;
using update_state = basic_window::update_state;
if(wd->other.upd_state == update_state::none)
wd->other.upd_state = update_state::lazy;
_m_emit_core(evt_code, wd, false, arg, bForce__EmitInternal);
//A child of wd may not be drawn if it was out of wd's range before wd resized,
//so refresh all children of wd when a resized occurs.
if(ask_update || (event_code::resized == evt_code))
bool good_wd = false;
if(wd_manager().available(wd))
{
wd_manager().do_lazy_refresh(wd, false, (event_code::resized == evt_code));
//A child of wd may not be drawn if it was out of wd's range before wd resized,
//so refresh all children of wd when a resized occurs.
if(ask_update || (event_code::resized == evt_code) || (update_state::refreshed == wd->other.upd_state))
{
wd_manager().do_lazy_refresh(wd, false, (event_code::resized == evt_code));
}
else
wd->other.upd_state = update_state::none;
good_wd = true;
}
else if(wd_manager().available(wd))
wd->other.upd_state = core_window_t::update_state::none;
if(thrd) thrd->event_window = prev_wd;
return true;
return good_wd;
}
void assign_arg(arg_mouse& arg, basic_window* wd, unsigned msg, const XEvent& evt)

View File

@@ -601,40 +601,6 @@ namespace detail
::HeapFree(::GetProcessHeap(), 0, stru);
}
return true;
case nana::detail::messages::remote_thread_move_window:
{
auto * mw = reinterpret_cast<nana::detail::messages::move_window*>(wParam);
::RECT r;
::GetWindowRect(wd, &r);
if(mw->ignore & mw->Pos)
{
mw->x = r.left;
mw->y = r.top;
}
else
{
HWND owner = ::GetWindow(wd, GW_OWNER);
if(owner)
{
::RECT owr;
::GetWindowRect(owner, &owr);
::POINT pos = {owr.left, owr.top};
::ScreenToClient(owner, &pos);
mw->x += (owr.left - pos.x);
mw->y += (owr.top - pos.y);
}
}
if(mw->ignore & mw->Size)
{
mw->width = r.right - r.left;
mw->height = r.bottom - r.top;
}
::MoveWindow(wd, mw->x, mw->y, mw->width, mw->height, true);
delete mw;
}
return true;
case nana::detail::messages::remote_thread_set_window_pos:
::SetWindowPos(wd, reinterpret_cast<HWND>(wParam), 0, 0, 0, 0, static_cast<UINT>(lParam));
return true;
@@ -1652,18 +1618,21 @@ namespace detail
_m_event_filter(evt_code, wd, thrd);
}
if (wd->other.upd_state == core_window_t::update_state::none)
wd->other.upd_state = core_window_t::update_state::lazy;
using update_state = basic_window::update_state;
if (update_state::none == wd->other.upd_state)
wd->other.upd_state = update_state::lazy;
_m_emit_core(evt_code, wd, false, arg, bForce__EmitInternal);
bool good_wd = false;
if (wd_manager().available(wd))
{
if (ask_update)
//Ignore ask_update if update state is refreshed.
if (ask_update || (update_state::refreshed == wd->other.upd_state))
wd_manager().do_lazy_refresh(wd, false);
else
wd->other.upd_state = basic_window::update_state::none;
wd->other.upd_state = update_state::none;
good_wd = true;
}

View File

@@ -863,30 +863,27 @@ namespace nana{
void native_interface::move_window(native_window_type wd, int x, int y)
{
#if defined(NANA_WINDOWS)
if(::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
::RECT r;
::GetWindowRect(reinterpret_cast<HWND>(wd), &r);
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
if(owner)
{
nana::detail::messages::move_window * mw = new nana::detail::messages::move_window;
mw->x = x;
mw->y = y;
mw->ignore = mw->Size;
::PostMessage(reinterpret_cast<HWND>(wd), nana::detail::messages::remote_thread_move_window, reinterpret_cast<WPARAM>(mw), 0);
::RECT owner_rect;
::GetWindowRect(owner, &owner_rect);
::POINT pos = {owner_rect.left, owner_rect.top};
::ScreenToClient(owner, &pos);
x += (owner_rect.left - pos.x);
y += (owner_rect.top - pos.y);
}
else
if (::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
{
::RECT r;
::GetWindowRect(reinterpret_cast<HWND>(wd), &r);
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
if(owner)
{
::RECT owner_rect;
::GetWindowRect(owner, &owner_rect);
::POINT pos = {owner_rect.left, owner_rect.top};
::ScreenToClient(owner, &pos);
x += (owner_rect.left - pos.x);
y += (owner_rect.top - pos.y);
}
nana::internal_revert_guard irg;
::MoveWindow(reinterpret_cast<HWND>(wd), x, y, r.right - r.left, r.bottom - r.top, true);
}
else
::MoveWindow(reinterpret_cast<HWND>(wd), x, y, r.right - r.left, r.bottom - r.top, true);
#elif defined(NANA_X11)
Display * disp = restrict::spec.open_display();
@@ -908,41 +905,36 @@ namespace nana{
#endif
}
void native_interface::move_window(native_window_type wd, const rectangle& r)
bool native_interface::move_window(native_window_type wd, const rectangle& r)
{
#if defined(NANA_WINDOWS)
if(::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
int x = r.x;
int y = r.y;
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
if(owner)
{
auto * mw = new nana::detail::messages::move_window;
mw->x = r.x;
mw->y = r.y;
mw->width = r.width;
mw->height = r.height;
mw->ignore = 0;
::PostMessage(reinterpret_cast<HWND>(wd), nana::detail::messages::remote_thread_move_window, reinterpret_cast<WPARAM>(mw), 0);
::RECT owner_rect;
::GetWindowRect(owner, &owner_rect);
::POINT pos = {owner_rect.left, owner_rect.top};
::ScreenToClient(owner, &pos);
x += (owner_rect.left - pos.x);
y += (owner_rect.top - pos.y);
}
else
{
int x = r.x;
int y = r.y;
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
if(owner)
{
::RECT owner_rect;
::GetWindowRect(owner, &owner_rect);
::POINT pos = {owner_rect.left, owner_rect.top};
::ScreenToClient(owner, &pos);
x += (owner_rect.left - pos.x);
y += (owner_rect.top - pos.y);
}
RECT client, wd_area;
::GetClientRect(reinterpret_cast<HWND>(wd), &client);
::GetWindowRect(reinterpret_cast<HWND>(wd), &wd_area);
unsigned ext_w = (wd_area.right - wd_area.left) - client.right;
unsigned ext_h = (wd_area.bottom - wd_area.top) - client.bottom;
::MoveWindow(reinterpret_cast<HWND>(wd), x, y, r.width + ext_w, r.height + ext_h, true);
RECT client, wd_area;
::GetClientRect(reinterpret_cast<HWND>(wd), &client);
::GetWindowRect(reinterpret_cast<HWND>(wd), &wd_area);
unsigned ext_w = (wd_area.right - wd_area.left) - client.right;
unsigned ext_h = (wd_area.bottom - wd_area.top) - client.bottom;
if (::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
{
nana::internal_revert_guard irg;
return (FALSE != ::MoveWindow(reinterpret_cast<HWND>(wd), x, y, r.width + ext_w, r.height + ext_h, true));
}
return (FALSE != ::MoveWindow(reinterpret_cast<HWND>(wd), x, y, r.width + ext_w, r.height + ext_h, true));
#elif defined(NANA_X11)
Display * disp = restrict::spec.open_display();
long supplied;
@@ -984,6 +976,7 @@ namespace nana{
::XSetWMNormalHints(disp, reinterpret_cast<Window>(wd), &hints);
::XMoveResizeWindow(disp, reinterpret_cast<Window>(wd), x, y, r.width, r.height);
return true;
#endif
}
@@ -1062,32 +1055,28 @@ namespace nana{
#endif
}
void native_interface::window_size(native_window_type wd, const size& sz)
bool native_interface::window_size(native_window_type wd, const size& sz)
{
#if defined(NANA_WINDOWS)
if(::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
::RECT r;
::GetWindowRect(reinterpret_cast<HWND>(wd), &r);
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
HWND parent = ::GetParent(reinterpret_cast<HWND>(wd));
if(parent && (parent != owner))
{
auto * mw = new nana::detail::messages::move_window;
mw->width = sz.width;
mw->height = sz.height;
mw->ignore = mw->Pos;
::PostMessage(reinterpret_cast<HWND>(wd), nana::detail::messages::remote_thread_move_window, reinterpret_cast<WPARAM>(mw), 0);
::POINT pos = {r.left, r.top};
::ScreenToClient(parent, &pos);
r.left = pos.x;
r.top = pos.y;
}
else
if (::GetWindowThreadProcessId(reinterpret_cast<HWND>(wd), 0) != ::GetCurrentThreadId())
{
::RECT r;
::GetWindowRect(reinterpret_cast<HWND>(wd), &r);
HWND owner = ::GetWindow(reinterpret_cast<HWND>(wd), GW_OWNER);
HWND parent = ::GetParent(reinterpret_cast<HWND>(wd));
if(parent && (parent != owner))
{
::POINT pos = {r.left, r.top};
::ScreenToClient(parent, &pos);
r.left = pos.x;
r.top = pos.y;
}
::MoveWindow(reinterpret_cast<HWND>(wd), r.left, r.top, static_cast<int>(sz.width), static_cast<int>(sz.height), true);
nana::internal_revert_guard irg;
return (FALSE != ::MoveWindow(reinterpret_cast<HWND>(wd), r.left, r.top, static_cast<int>(sz.width), static_cast<int>(sz.height), true));
}
return (FALSE != ::MoveWindow(reinterpret_cast<HWND>(wd), r.left, r.top, static_cast<int>(sz.width), static_cast<int>(sz.height), true));
#elif defined(NANA_X11)
auto disp = restrict::spec.open_display();
nana::detail::platform_scope_guard psg;
@@ -1104,6 +1093,7 @@ namespace nana{
::XSetWMNormalHints(disp, reinterpret_cast<Window>(wd), &hints);
}
::XResizeWindow(disp, reinterpret_cast<Window>(wd), sz.width, sz.height);
return true;
#endif
}

View File

@@ -219,8 +219,6 @@ namespace detail
Key first;
Value second;
key_value_rep() = default;
key_value_rep(const Key& k)
: first(k), second{}
{
@@ -258,15 +256,7 @@ namespace detail
std::vector<key_value_rep> table_;
};
//class window_manager
struct window_handle_deleter
{
void operator()(basic_window* wd) const
{
delete wd;
}
};
//class window_manager
//struct wdm_private_impl
struct window_manager::wdm_private_impl
{
@@ -506,7 +496,7 @@ namespace detail
if (impl_->wd_register.available(owner))
{
if (owner->flags.destroying)
throw std::runtime_error("the specified owner is destory");
throw std::runtime_error("the specified owner is destoryed");
#ifndef WIDGET_FRAME_DEPRECATED
native = (category::flags::frame == owner->other.category ?
@@ -953,24 +943,46 @@ namespace detail
if (wd->dimension == sz)
return false;
//Before resiz the window, creates the new graphics
paint::graphics graph;
paint::graphics root_graph;
if (category::flags::lite_widget != wd->other.category)
{
//If allocation fails, here throws std::bad_alloc.
graph.make(sz);
graph.typeface(wd->drawer.graphics.typeface());
if (category::flags::root == wd->other.category)
root_graph.make(sz);
}
auto pre_sz = wd->dimension;
wd->dimension = sz;
if(category::flags::lite_widget != wd->other.category)
{
bool graph_state = wd->drawer.graphics.empty();
wd->drawer.graphics.make(sz);
wd->drawer.graphics.swap(graph);
//It shall make a typeface_changed() call when the graphics state is changing.
//Because when a widget is created with zero-size, it may get some wrong result in typeface_changed() call
//Because when a widget is created with zero-size, it may get some wrong results in typeface_changed() call
//due to the invaliable graphics object.
if(graph_state != wd->drawer.graphics.empty())
wd->drawer.typeface_changed();
if(category::flags::root == wd->other.category)
{
wd->root_graph->make(sz);
//wd->root_graph->make(sz);
wd->root_graph->swap(root_graph);
if(false == passive)
native_interface::window_size(wd->root, sz + nana::size(wd->extra_width, wd->extra_height));
if (!native_interface::window_size(wd->root, sz + nana::size(wd->extra_width, wd->extra_height)))
{
wd->dimension = pre_sz;
wd->drawer.graphics.swap(graph);
wd->root_graph->swap(root_graph);
wd->drawer.typeface_changed();
return false;
}
}
#ifndef WIDGET_FRAME_DEPRECATED
else if(category::flags::frame == wd->other.category)

View File

@@ -1183,6 +1183,13 @@ namespace API
auto caret = _m_caret();
return (caret && caret->visible());
}
bool activated() const override
{
internal_scope_guard lock;
auto caret = _m_caret();
return (caret && caret->activated());
}
private:
caret_interface* _m_caret() const
{

View File

@@ -14,6 +14,7 @@
#include <nana/gui/widgets/scroll.hpp>
#include <nana/gui/layout_utility.hpp>
#include <nana/gui/screen.hpp>
namespace nana
{
@@ -198,16 +199,14 @@ namespace nana
return widget_;
}
void attach(widget* wd, nana::paint::graphics* graph)
void attach(widget& wd, nana::paint::graphics& graph)
{
if(wd)
{
widget_ = wd;
wd->events().mouse_wheel.connect_unignorable([this](const arg_wheel& arg){
scroll_items(arg.upwards);
});
}
if(graph) graph_ = graph;
widget_ = &wd;
wd.events().mouse_wheel.connect_unignorable([this](const arg_wheel& arg){
scroll_items(arg.upwards);
});
graph_ = &graph;
}
void detach()
@@ -219,9 +218,46 @@ namespace nana
{
if(module_)
{
std::size_t items = (module_->max_items <= module_->items.size() ? module_->max_items : module_->items.size());
std::size_t h = items * state_.renderer->item_pixels(*graph_);
widget_->size(size{ widget_->size().width, static_cast<unsigned>(h + 4) });
auto const items = (module_->max_items <= module_->items.size() ? module_->max_items : module_->items.size());
rectangle list_r{
0, 0,
widget_->size().width,
static_cast<unsigned>(items * state_.renderer->item_pixels(*graph_)) + 4
};
//Test if the listbox excesses the screen
screen scr;
auto & disp = scr.from_window(*widget_);
auto disp_r = disp.area();
point pos;
API::calc_screen_point(*widget_, pos);
list_r.position(pos);
if (widget_->size().width >= disp_r.width)
{
pos.x = 0;
list_r.width = disp_r.width;
}
else if (list_r.right() > disp_r.right())
pos.x = disp_r.right() - static_cast<int>(list_r.width);
if (list_r.height >= disp_r.height)
{
pos.y = 0;
list_r.height = disp_r.height;
}
else if (list_r.bottom() > disp_r.bottom())
pos.y = disp_r.bottom() - static_cast<int>(list_r.height);
API::calc_window_point(API::get_owner_window(*widget_), pos);
list_r.position(pos);
widget_->move(list_r);
}
}
@@ -312,36 +348,37 @@ namespace nana
void _m_open_scrollbar(widget_reference wd, bool v)
{
if(v)
if (!v)
{
if(scrollbar_.empty() && module_)
{
scrollbar_.create(wd, rectangle(static_cast<int>(wd.size().width - 18), 2, 16, wd.size().height - 4));
scrollbar_.amount(module_->items.size());
scrollbar_.range(module_->max_items);
scrollbar_.value(state_.offset_y);
auto & events = scrollbar_.events();
events.mouse_wheel.connect([this](const arg_wheel& arg)
{
scroll_items(arg.upwards);
});
auto fn = [this](const arg_mouse& arg)
{
if (arg.is_left_button() && (scrollbar_.value() != state_.offset_y))
{
state_.offset_y = static_cast<unsigned>(scrollbar_.value());
draw();
API::update_window(*widget_);
}
};
events.mouse_move.connect(fn);
events.mouse_up.connect(fn);
}
}
else
scrollbar_.close();
return;
}
if(scrollbar_.empty() && module_)
{
scrollbar_.create(wd, rectangle(static_cast<int>(wd.size().width - 18), 2, 16, wd.size().height - 4));
scrollbar_.amount(module_->items.size());
scrollbar_.range(module_->max_items);
scrollbar_.value(state_.offset_y);
auto & events = scrollbar_.events();
events.mouse_wheel.connect([this](const arg_wheel& arg)
{
scroll_items(arg.upwards);
});
auto fn = [this](const arg_mouse& arg)
{
if (arg.is_left_button() && (scrollbar_.value() != state_.offset_y))
{
state_.offset_y = static_cast<unsigned>(scrollbar_.value());
draw();
API::update_window(*widget_);
}
};
events.mouse_move.connect(fn);
events.mouse_up.connect(fn);
}
}
private:
widget * widget_{nullptr};
@@ -393,7 +430,7 @@ namespace nana
void trigger::attached(widget_reference widget, graph_reference graph)
{
drawer_->attach(&widget, &graph);
drawer_->attach(widget, graph);
}
void trigger::detached()

View File

@@ -3931,6 +3931,11 @@ namespace nana
essence_->content_view.reset(new widgets::skeletons::content_view{ widget.handle() });
essence_->resize_disp_area();
//Set the content_view wheel speed with the listbox scheme.
essence_->content_view->set_wheel_speed([this] {
return essence_->scheme_ptr->mouse_wheel.lines;
});
essence_->content_view->events().hover_outside = [this](const point& cur_pos) {
essence_->update_mouse_selection(cur_pos);
};
@@ -4166,16 +4171,17 @@ namespace nana
{
if (item_ptr->flags.selected != sel)
{
item_ptr->flags.selected = sel;
lister.emit_cs(abs_item_pos, true);
if (item_ptr->flags.selected)
if (sel)
{
//Deselects the previously selected item.
lister.cancel_others_if_single_enabled(true, abs_item_pos);
essence_->lister.latest_selected_abs = abs_item_pos;
}
else if (essence_->lister.latest_selected_abs == abs_item_pos)
essence_->lister.latest_selected_abs.set_both(npos);
item_ptr->flags.selected = sel;
lister.emit_cs(abs_item_pos, true);
}
}
else

View File

@@ -29,7 +29,6 @@ namespace nana
struct implement
{
widget* wdg_ptr{nullptr};
paint::graphics* graph_ptr{nullptr};
std::unique_ptr<content_measurer> measurer;
struct gradual_bground_tag
@@ -48,6 +47,23 @@ namespace nana
std::unique_ptr<element::bground> bground; //If it is not a null ptr, the widget is stretchable mode
bool stretchable{ false }; //If it is true, the widget is stretchable mode without changing aspect ratio.
}backimg;
void draw_background(paint::graphics& graph, const size& dimension)
{
if (!API::dev::copy_transparent_background(*wdg_ptr, graph))
{
auto const graph_size = graph.size();
if (dimension.width < graph_size.width || dimension.height < graph_size.height || backimg.image.alpha())
{
if (gradual_bground.gradual_from.invisible() || gradual_bground.gradual_to.invisible())
graph.rectangle(true, wdg_ptr->bgcolor());
else if (gradual_bground.gradual_from == gradual_bground.gradual_to)
graph.rectangle(true, gradual_bground.gradual_from);
else
graph.gradual_rectangle(::nana::rectangle{graph_size }, gradual_bground.gradual_from, gradual_bground.gradual_to, !gradual_bground.horizontal);
}
}
}
};
class content_measurer
@@ -88,32 +104,36 @@ namespace nana
delete impl_;
}
void drawer::attached(widget_reference& wdg, graph_reference graph)
void drawer::attached(widget_reference& wdg, graph_reference)
{
impl_->wdg_ptr = &wdg;
impl_->graph_ptr = &graph;
API::dev::set_measurer(wdg, impl_->measurer.get());
}
void drawer::refresh(graph_reference graph)
{
if (!graph.changed())
return;
auto graphsize = graph.size();
auto const graphsize = graph.size();
auto & backimg = impl_->backimg;
if (!backimg.bground)
{
if (backimg.image.empty())
{
impl_->draw_background(graph, {});
return;
}
auto valid_area = backimg.valid_area;
if (valid_area.empty())
valid_area.dimension(backimg.image.size());
//The position where the image to be drawn.
::nana::point pos;
if (backimg.stretchable)
{
auto fit_size = fit_zoom({ valid_area.width, valid_area.height }, graphsize);
::nana::point pos;
auto fit_size = fit_zoom(valid_area.dimension(), graphsize);
if (fit_size.width != graphsize.width)
{
@@ -142,15 +162,12 @@ namespace nana
}
}
_m_draw_background(fit_size.width, fit_size.height);
impl_->draw_background(graph, fit_size);
backimg.image.stretch(valid_area, graph, ::nana::rectangle{ pos, fit_size });
}
else
{
//The point in which position the image to be drawn.
::nana::point pos;
switch (backimg.align_horz)
{
case ::nana::align::left: break;
@@ -173,15 +190,14 @@ namespace nana
break;
}
_m_draw_background(valid_area.width, valid_area.height);
impl_->draw_background(graph, valid_area.dimension());
if ( ! backimg.image.empty())
backimg.image.paste(valid_area, graph, pos);
backimg.image.paste(valid_area, graph, pos);
}
}
else
{
_m_draw_background(graphsize.width, graphsize.height);
impl_->draw_background(graph, graphsize);
color invalid_clr_for_call;
backimg.bground->draw(graph, invalid_clr_for_call, invalid_clr_for_call, rectangle{ graphsize }, element_state::normal);
@@ -189,25 +205,6 @@ namespace nana
graph.setsta();
}
void drawer::_m_draw_background(unsigned w, unsigned h)
{
auto graph = impl_->graph_ptr;
if (graph && (!API::dev::copy_transparent_background(*impl_->wdg_ptr, *graph)))
{
if (w < graph->size().width || h < graph->size().height || impl_->backimg.image.alpha())
{
auto & bground = impl_->gradual_bground;
if (bground.gradual_from.invisible() || bground.gradual_to.invisible())
graph->rectangle(true, impl_->wdg_ptr->bgcolor());
else if (bground.gradual_from == bground.gradual_to)
graph->rectangle(true, bground.gradual_from);
else
graph->gradual_rectangle(::nana::rectangle{ graph->size() }, bground.gradual_from, bground.gradual_to, !bground.horizontal);
}
}
}
//end class drawer
}//end namespace picture
}//end namespace drawerbase
@@ -233,11 +230,7 @@ namespace nana
if (backimg.bground)
backimg.bground->image(backimg.image, true, valid_area);
if (handle())
{
get_drawer_trigger().impl_->graph_ptr->set_changed();
API::refresh_window(*this);
}
API::refresh_window(*this);
}
void picture::align(::nana::align horz, align_v vert)
@@ -252,18 +245,11 @@ namespace nana
backimg.align_horz = horz;
backimg.align_vert = vert;
if (handle())
{
get_drawer_trigger().impl_->graph_ptr->set_changed();
API::refresh_window(*this);
}
API::refresh_window(*this);
}
void picture::stretchable(unsigned left, unsigned top, unsigned right, unsigned bottom)
{
if (!handle())
return;
internal_scope_guard lock;
auto & backimg = get_drawer_trigger().impl_->backimg;
if (!backimg.bground)
@@ -275,11 +261,8 @@ namespace nana
backimg.bground->stretch_parts(left, top, right, bottom);
backimg.stretchable = false;
if (handle())
{
get_drawer_trigger().impl_->graph_ptr->set_changed();
API::refresh_window(*this);
}
API::refresh_window(*this);
}
void picture::stretchable(bool enables)
@@ -290,11 +273,7 @@ namespace nana
backimg.bground.reset();
backimg.stretchable = enables;
if (handle())
{
get_drawer_trigger().impl_->graph_ptr->set_changed();
API::refresh_window(*this);
}
API::refresh_window(*this);
}
void picture::set_gradual_background(const ::nana::color& from, const ::nana::color& to, bool horizontal)
@@ -303,11 +282,8 @@ namespace nana
bground.gradual_from = from;
bground.gradual_to = to;
bground.horizontal = horizontal;
if (handle())
{
get_drawer_trigger().impl_->graph_ptr->set_changed();
API::refresh_window(*this);
}
API::refresh_window(*this);
}
void picture::transparent(bool enabled)

View File

@@ -91,19 +91,26 @@ namespace nana
{
return value_px_;
}
bool value_px_sync()
{
if (widget_)
{
auto value_px = (widget_->size().width - border_px * 2) * value_ / max_;
if (value_px != value_px_)
{
value_px_ = value_px;
return true;
}
}
return false;
}
private:
void _m_try_refresh()
{
if (nullptr == widget_)
return;
auto value_px = (widget_->size().width - border_px * 2) * value_ / max_;
if (value_px != value_px_)
{
value_px_ = value_px;
if (value_px_sync())
API::refresh_window(*widget_);
}
}
private:
nana::progress * widget_{ nullptr };
@@ -144,6 +151,9 @@ namespace nana
auto rt_bground = rt_val;
if (false == progress_->unknown(nullptr))
{
//Sync the value_px otherwise the progress is incorrect when it is resized.
progress_->value_px_sync();
rt_bground.x = static_cast<int>(progress_->value_px()) + static_cast<int>(border_px);
rt_bground.width -= progress_->value_px();