Merge branch 'hotfix-1.7' into develop
This commit is contained in:
		
						commit
						a08e274088
					
				@ -108,11 +108,16 @@ namespace std {
 | 
			
		||||
	{
 | 
			
		||||
		using namespace experimental::filesystem;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
#ifndef __cpp_lib_experimental_filesystem
 | 
			
		||||
#   define __cpp_lib_experimental_filesystem 201406
 | 
			
		||||
#endif
 | 
			
		||||
} // std
 | 
			
		||||
 | 
			
		||||
#else
 | 
			
		||||
#   undef NANA_USING_STD_FILESYSTEM
 | 
			
		||||
#   define NANA_USING_STD_FILESYSTEM 1
 | 
			
		||||
	//Detects whether the compiler supports std::filesystem under current options
 | 
			
		||||
#	if ((defined(_MSC_VER) && (_MSC_VER >= 1912) && defined(_MSVC_LANG) && _MSVC_LANG >= 201703)) ||				\
 | 
			
		||||
		((__cplusplus >= 201703L) && \
 | 
			
		||||
			(defined(__clang__) && (__clang_major__ >= 7) ||		\
 | 
			
		||||
@ -125,14 +130,11 @@ namespace std {
 | 
			
		||||
				using namespace std::experimental::filesystem;
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
#		undef NANA_USING_STD_EXPERIMENTAL_FILESYSTEM
 | 
			
		||||
#		define NANA_USING_STD_EXPERIMENTAL_FILESYSTEM
 | 
			
		||||
#	endif
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
#ifndef __cpp_lib_experimental_filesystem
 | 
			
		||||
#   define __cpp_lib_experimental_filesystem 201406
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#if NANA_USING_NANA_FILESYSTEM
 | 
			
		||||
 | 
			
		||||
#include <string>
 | 
			
		||||
@ -558,7 +560,23 @@ namespace std {
 | 
			
		||||
#endif
 | 
			
		||||
	}
 | 
			
		||||
} // std
 | 
			
		||||
#else
 | 
			
		||||
 | 
			
		||||
//Implements the missing functions for various version of experimental/filesystem
 | 
			
		||||
#	if defined(NANA_USING_STD_EXPERIMENTAL_FILESYSTEM)
 | 
			
		||||
	namespace std
 | 
			
		||||
	{
 | 
			
		||||
		namespace filesystem
 | 
			
		||||
		{
 | 
			
		||||
			//Visual Studio 2017
 | 
			
		||||
			#if (defined(_MSC_VER) && (_MSC_VER > 1912)) ||	\
 | 
			
		||||
				(!defined(__clang__) && defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__ < 801))
 | 
			
		||||
			path weakly_canonical(const path& p);
 | 
			
		||||
			path weakly_canonical(const path& p, std::error_code& err);
 | 
			
		||||
			#endif
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
#	endif
 | 
			
		||||
 | 
			
		||||
#endif	//NANA_USING_NANA_FILESYSTEM
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -1,6 +1,6 @@
 | 
			
		||||
/*
 | 
			
		||||
 *	A Tree Container class implementation
 | 
			
		||||
 *	Copyright(C) 2003-2018 Jinhao(cnjinhao@hotmail.com)
 | 
			
		||||
 *	Copyright(C) 2003-2019 Jinhao(cnjinhao@hotmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 *	Distributed under the Boost Software License, Version 1.0.
 | 
			
		||||
 *	(See accompanying file LICENSE_1_0.txt or copy at
 | 
			
		||||
@ -193,6 +193,11 @@ namespace detail
 | 
			
		||||
			node_type* insert(const std::string& key, const element_type& elem)
 | 
			
		||||
			{
 | 
			
		||||
				auto node = _m_locate<true>(key);
 | 
			
		||||
 | 
			
		||||
				//Doesn't return the root node
 | 
			
		||||
				if (node == &root_)
 | 
			
		||||
					return nullptr;
 | 
			
		||||
 | 
			
		||||
				if(node)
 | 
			
		||||
					node->value.second = elem;
 | 
			
		||||
				return node;
 | 
			
		||||
@ -206,12 +211,14 @@ namespace detail
 | 
			
		||||
 | 
			
		||||
			node_type* find(const std::string& path) const
 | 
			
		||||
			{
 | 
			
		||||
				return _m_locate(path);
 | 
			
		||||
				auto p = _m_locate(path);
 | 
			
		||||
				return (&root_ == p ? nullptr : p);
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			node_type* ref(const std::string& path)
 | 
			
		||||
			{
 | 
			
		||||
				return _m_locate<true>(path);
 | 
			
		||||
				auto p = _m_locate<true>(path);
 | 
			
		||||
				return (&root_ == p ? nullptr : p);
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			unsigned indent_size(const node_type* node) const
 | 
			
		||||
@ -479,15 +486,16 @@ namespace detail
 | 
			
		||||
				return nullptr;
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			// foreach elements of key.
 | 
			
		||||
			// the root name "/" and "\\" are treated as a node. This is a feature that can easily support the UNIX-like path.
 | 
			
		||||
			template<typename Function>
 | 
			
		||||
			void _m_for_each(const ::std::string& key, Function function) const
 | 
			
		||||
			{
 | 
			
		||||
				if(key.size())
 | 
			
		||||
				{
 | 
			
		||||
					::std::string::size_type beg = 0;
 | 
			
		||||
					auto end = key.find_first_of("\\/");
 | 
			
		||||
				//Ignores separaters at the begin of key.
 | 
			
		||||
				::std::string::size_type beg = key.find_first_not_of("\\/");
 | 
			
		||||
				if (key.npos == beg)
 | 
			
		||||
					return;
 | 
			
		||||
 | 
			
		||||
				auto end = key.find_first_of("\\/", beg);
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
				while(end != ::std::string::npos)
 | 
			
		||||
				{
 | 
			
		||||
@ -515,7 +523,6 @@ namespace detail
 | 
			
		||||
 | 
			
		||||
				function(key.substr(beg, key.size() - beg));
 | 
			
		||||
			}
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			template<bool CreateIfNotExists>
 | 
			
		||||
			node_type* _m_locate(const ::std::string& key)
 | 
			
		||||
 | 
			
		||||
@ -1,7 +1,7 @@
 | 
			
		||||
/**
 | 
			
		||||
 *	A float_listbox Implementation
 | 
			
		||||
 *	Nana C++ Library(http://www.nanapro.org)
 | 
			
		||||
 *	Copyright(C) 2003-2015 Jinhao(cnjinhao@hotmail.com)
 | 
			
		||||
 *	Copyright(C) 2003-2019 Jinhao(cnjinhao@hotmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 *	Distributed under the Boost Software License, Version 1.0. 
 | 
			
		||||
 *	(See accompanying file LICENSE_1_0.txt or copy at 
 | 
			
		||||
@ -46,8 +46,10 @@ namespace nana
 | 
			
		||||
			class item_renderer
 | 
			
		||||
			{
 | 
			
		||||
			public:
 | 
			
		||||
				typedef widget&	widget_reference;
 | 
			
		||||
				typedef paint::graphics& graph_reference;
 | 
			
		||||
				using widget_reference = widget&;
 | 
			
		||||
				using graph_reference = paint::graphics&;
 | 
			
		||||
				using item_interface = float_listbox::item_interface;
 | 
			
		||||
 | 
			
		||||
				enum state_t{StateNone, StateHighlighted};
 | 
			
		||||
 | 
			
		||||
				virtual ~item_renderer() = default;
 | 
			
		||||
 | 
			
		||||
@ -480,6 +480,8 @@ namespace nana
 | 
			
		||||
		 */
 | 
			
		||||
		void scroll_into_view(item_proxy item);
 | 
			
		||||
 | 
			
		||||
		/// Gets the current hovered node.
 | 
			
		||||
		item_proxy hovered(bool exclude_expander) const;
 | 
			
		||||
	private:
 | 
			
		||||
		std::shared_ptr<scroll_operation_interface> _m_scroll_operation() override;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -1130,7 +1130,7 @@ namespace nana {	namespace experimental {	namespace filesystem
 | 
			
		||||
				::fclose(stream);
 | 
			
		||||
				return bytes;
 | 
			
		||||
			}
 | 
			
		||||
			ec.assign(static_cast<int>(::errno), std::generic_category());
 | 
			
		||||
			ec.assign(static_cast<int>(errno), std::generic_category());
 | 
			
		||||
#endif
 | 
			
		||||
			return static_cast<std::uintmax_t>(-1);
 | 
			
		||||
		}
 | 
			
		||||
@ -1265,7 +1265,7 @@ namespace std
 | 
			
		||||
			return p;  // p.is_absolute() is true
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		path absolute(const path& p, std::error_code& err)
 | 
			
		||||
		path absolute(const path& p, std::error_code& /*err*/)
 | 
			
		||||
		{
 | 
			
		||||
			return absolute(p);
 | 
			
		||||
		}
 | 
			
		||||
@ -1350,7 +1350,7 @@ namespace std
 | 
			
		||||
			{	//error
 | 
			
		||||
				if (nullptr == ec)
 | 
			
		||||
					throw (filesystem_error(
 | 
			
		||||
						"nana::filesystem::canonical", p,
 | 
			
		||||
						message, p,
 | 
			
		||||
						error_code(err_val, generic_category())));
 | 
			
		||||
				else
 | 
			
		||||
					ec->assign(err_val, system_category());
 | 
			
		||||
@ -1435,5 +1435,162 @@ namespace std
 | 
			
		||||
	}//end namespace filesystem
 | 
			
		||||
}//end namespace std
 | 
			
		||||
 | 
			
		||||
#else 	//NANA_USING_NANA_FILESYSTEM
 | 
			
		||||
#	if defined(NANA_USING_STD_EXPERIMENTAL_FILESYSTEM)
 | 
			
		||||
 | 
			
		||||
	//Defines the functions that are not provided by experimental/filesystem
 | 
			
		||||
	namespace std
 | 
			
		||||
	{
 | 
			
		||||
		namespace filesystem
 | 
			
		||||
		{
 | 
			
		||||
			#if (defined(_MSC_VER) && (_MSC_VER > 1912)) || \
 | 
			
		||||
				(!defined(__clang__) && defined(__GNUC__) && (__GNUC__ * 100 + __GNUC_MINOR__ < 801))
 | 
			
		||||
 | 
			
		||||
			namespace detail
 | 
			
		||||
			{
 | 
			
		||||
				bool try_throw(int err_val, const path& p, std::error_code* ec, const char* message)
 | 
			
		||||
				{
 | 
			
		||||
					if (0 == err_val)
 | 
			
		||||
					{
 | 
			
		||||
						if (ec) ec->clear();
 | 
			
		||||
					}
 | 
			
		||||
					else
 | 
			
		||||
					{	//error
 | 
			
		||||
						if (nullptr == ec)
 | 
			
		||||
							throw (filesystem_error(
 | 
			
		||||
								message, p,
 | 
			
		||||
								error_code(err_val, generic_category())));
 | 
			
		||||
						else
 | 
			
		||||
							ec->assign(err_val, system_category());
 | 
			
		||||
					}
 | 
			
		||||
					return err_val != 0;
 | 
			
		||||
				}
 | 
			
		||||
 | 
			
		||||
				path lexically_normal(path p)
 | 
			
		||||
				{
 | 
			
		||||
					if (p.empty())
 | 
			
		||||
						return p;
 | 
			
		||||
 | 
			
		||||
					std::vector<path> elements;
 | 
			
		||||
 | 
			
		||||
					while (!p.empty())
 | 
			
		||||
					{
 | 
			
		||||
						elements.emplace_back(p.filename());
 | 
			
		||||
						p.remove_filename();
 | 
			
		||||
					}
 | 
			
		||||
 | 
			
		||||
					auto start = elements.begin();
 | 
			
		||||
					auto last = elements.end();
 | 
			
		||||
					auto stop = last--;
 | 
			
		||||
					for (auto itr(start); itr != stop; ++itr)
 | 
			
		||||
					{
 | 
			
		||||
						// ignore "." except at start and last
 | 
			
		||||
						if (itr->native().size() == 1
 | 
			
		||||
							&& (itr->native())[0] == '.'
 | 
			
		||||
							&& itr != start
 | 
			
		||||
							&& itr != last) continue;
 | 
			
		||||
 | 
			
		||||
						// ignore a name and following ".."
 | 
			
		||||
						if (!p.empty()
 | 
			
		||||
							&& itr->native().size() == 2
 | 
			
		||||
							&& (itr->native())[0] == '.'
 | 
			
		||||
							&& (itr->native())[1] == '.') // dot dot
 | 
			
		||||
						{
 | 
			
		||||
							auto lf(p.filename().native());
 | 
			
		||||
							if (lf.size() > 0
 | 
			
		||||
								&& (lf.size() != 1
 | 
			
		||||
									|| (lf[0] != '.'
 | 
			
		||||
										&& (lf[0] != '/' && lf[0] != '\\')))
 | 
			
		||||
								&& (lf.size() != 2
 | 
			
		||||
									|| (lf[0] != '.'
 | 
			
		||||
										&& lf[1] != '.'
 | 
			
		||||
	#             ifdef NANA_WINDOWS
 | 
			
		||||
										&& lf[1] != ':'
 | 
			
		||||
	#             endif
 | 
			
		||||
										)
 | 
			
		||||
									)
 | 
			
		||||
								)
 | 
			
		||||
							{
 | 
			
		||||
								p.remove_filename();
 | 
			
		||||
								auto next = itr;
 | 
			
		||||
								if (p.empty() && ++next != stop
 | 
			
		||||
									&& next == last && last->string() == ".")
 | 
			
		||||
								{
 | 
			
		||||
									p /= ".";
 | 
			
		||||
								}
 | 
			
		||||
								continue;
 | 
			
		||||
							}
 | 
			
		||||
						}
 | 
			
		||||
 | 
			
		||||
						p /= *itr;
 | 
			
		||||
					};
 | 
			
		||||
 | 
			
		||||
					if (p.empty())
 | 
			
		||||
						p = ".";
 | 
			
		||||
					return p;
 | 
			
		||||
				}
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			path weakly_canonical(const path& p, std::error_code* err)
 | 
			
		||||
			{
 | 
			
		||||
				path head{ p };
 | 
			
		||||
 | 
			
		||||
				std::error_code tmp_err;
 | 
			
		||||
				std::vector<path> elements;
 | 
			
		||||
				while (!head.empty())
 | 
			
		||||
				{
 | 
			
		||||
					auto head_status = status(head, tmp_err);
 | 
			
		||||
 | 
			
		||||
					if (head_status.type() == file_type::unknown)
 | 
			
		||||
					{
 | 
			
		||||
						if (detail::try_throw(static_cast<int>(errc::invalid_argument), head, err, "nana::filesystem::weakly_canonical"))
 | 
			
		||||
							return path{};
 | 
			
		||||
					}
 | 
			
		||||
					if (head_status.type() != file_type::not_found)
 | 
			
		||||
						break;
 | 
			
		||||
 | 
			
		||||
					elements.emplace_back(head.filename());
 | 
			
		||||
					head.remove_filename();
 | 
			
		||||
				}
 | 
			
		||||
 | 
			
		||||
				bool tail_has_dots = false;
 | 
			
		||||
				path tail;
 | 
			
		||||
 | 
			
		||||
				for (auto & e : elements)
 | 
			
		||||
				{
 | 
			
		||||
					tail /= e;
 | 
			
		||||
					// for a later optimization, track if any dot or dot-dot elements are present
 | 
			
		||||
					if (e.native().size() <= 2
 | 
			
		||||
						&& e.native()[0] == '.'
 | 
			
		||||
						&& (e.native().size() == 1 || e.native()[1] == '.'))
 | 
			
		||||
						tail_has_dots = true;
 | 
			
		||||
				}
 | 
			
		||||
 | 
			
		||||
				if (head.empty())
 | 
			
		||||
					return detail::lexically_normal(p);
 | 
			
		||||
				head = canonical(head, tmp_err);
 | 
			
		||||
				if (detail::try_throw(tmp_err.value(), head, err, "nana::filesystem::weakly_canonical"))
 | 
			
		||||
					return path();
 | 
			
		||||
				return tail.empty()
 | 
			
		||||
					? head
 | 
			
		||||
					: (tail_has_dots  // optimization: only normalize if tail had dot or dot-dot element
 | 
			
		||||
						? detail::lexically_normal(head / tail)
 | 
			
		||||
						: head / tail);
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			path weakly_canonical(const path& p)
 | 
			
		||||
			{
 | 
			
		||||
				return weakly_canonical(p, nullptr);
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			path weakly_canonical(const path& p, std::error_code& err)
 | 
			
		||||
			{
 | 
			
		||||
				return weakly_canonical(p, &err);
 | 
			
		||||
			}
 | 
			
		||||
			#endif
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
#	endif
 | 
			
		||||
 | 
			
		||||
#endif //NANA_USING_NANA_FILESYSTEM
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -15,6 +15,7 @@
 | 
			
		||||
 *		Benjamin Navarro(pr#81)
 | 
			
		||||
 *		besh81(pr#130)
 | 
			
		||||
 *		dankan1890(pr#158)
 | 
			
		||||
 *		ErrorFlynn(pr#418)
 | 
			
		||||
 *
 | 
			
		||||
 */
 | 
			
		||||
#include <algorithm>
 | 
			
		||||
@ -5455,11 +5456,14 @@ namespace nana
 | 
			
		||||
			internal_scope_guard lock;
 | 
			
		||||
 | 
			
		||||
			if (_m_ess().lister.enable_ordered(enable))
 | 
			
		||||
			{
 | 
			
		||||
				_m_ess().update();
 | 
			
		||||
 | 
			
		||||
				return true;
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			return false;
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		void listbox::auto_draw(bool enabled) noexcept
 | 
			
		||||
		{
 | 
			
		||||
			internal_scope_guard lock;
 | 
			
		||||
 | 
			
		||||
@ -2371,6 +2371,19 @@ namespace nana
 | 
			
		||||
				API::refresh_window(*this);
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		treebox::item_proxy treebox::hovered(bool exclude_expander) const
 | 
			
		||||
		{
 | 
			
		||||
			internal_scope_guard lock;
 | 
			
		||||
			auto dw = &get_drawer_trigger();
 | 
			
		||||
			if (dw->impl()->node_state.pointed)
 | 
			
		||||
			{
 | 
			
		||||
				//Returns empty item_proxy if the mouse is on expander and exclude_expander is required.
 | 
			
		||||
				if (exclude_expander && (dw->impl()->node_state.comp_pointed == drawerbase::treebox::component::expander))
 | 
			
		||||
					return item_proxy{};
 | 
			
		||||
			}
 | 
			
		||||
			return item_proxy(const_cast<drawer_trigger_t*>(dw), dw->impl()->node_state.pointed);
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		std::shared_ptr<scroll_operation_interface> treebox::_m_scroll_operation()
 | 
			
		||||
		{
 | 
			
		||||
			internal_scope_guard lock;
 | 
			
		||||
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user