std::string_view
This commit is contained in:
parent
88d395353e
commit
ffee0e5a3b
@ -1,7 +1,7 @@
|
||||
/*
|
||||
* Paint Graphics Implementation
|
||||
* Nana C++ Library(http://www.nanapro.org)
|
||||
* Copyright(C) 2003-2017 Jinhao(cnjinhao@hotmail.com)
|
||||
* Copyright(C) 2003-2018 Jinhao(cnjinhao@hotmail.com)
|
||||
*
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or copy at
|
||||
@ -116,6 +116,12 @@ namespace nana
|
||||
#ifdef _nana_std_has_string_view
|
||||
::nana::size text_extent_size(std::string_view text) const;
|
||||
::nana::size text_extent_size(std::wstring_view text) const;
|
||||
|
||||
///Only supports the wide string, because it is very hard to specify the begin and end position in a UTF-8 string.
|
||||
::nana::size glyph_extent_size(std::wstring_view text, std::size_t begin, std::size_t end) const;
|
||||
|
||||
bool glyph_pixels(std::wstring_view text, unsigned* pxbuf) const;
|
||||
std::unique_ptr<unsigned[]> glyph_pixels(std::wstring_view text) const;
|
||||
#else
|
||||
::nana::size text_extent_size(const ::std::string&) const;
|
||||
::nana::size text_extent_size(const char*, std::size_t len) const;
|
||||
@ -124,11 +130,12 @@ namespace nana
|
||||
::nana::size text_extent_size(const ::std::wstring&) const; ///< Computes the width and height of the specified string of text.
|
||||
::nana::size text_extent_size(const wchar_t*, std::size_t length) const; ///< Computes the width and height of the specified string of text with the specified length.
|
||||
::nana::size text_extent_size(const ::std::wstring&, std::size_t length) const; ///< Computes the width and height of the specified string of text with the specified length.
|
||||
#endif
|
||||
|
||||
::nana::size glyph_extent_size(const wchar_t*, std::size_t length, std::size_t begin, std::size_t end) const;
|
||||
::nana::size glyph_extent_size(const ::std::wstring&, std::size_t length, std::size_t begin, std::size_t end) const;
|
||||
|
||||
bool glyph_pixels(const wchar_t *, std::size_t length, unsigned* pxbuf) const;
|
||||
#endif
|
||||
::nana::size bidi_extent_size(const std::wstring&) const;
|
||||
::nana::size bidi_extent_size(const std::string&) const;
|
||||
|
||||
|
@ -834,8 +834,12 @@ namespace nana{ namespace widgets
|
||||
if (str_w > pixels) //Indicates the splitting of ts string
|
||||
{
|
||||
std::size_t len = ts.end - ts.begin;
|
||||
#ifdef _nana_std_has_string_view
|
||||
auto pxbuf = editor_.graph_.glyph_pixels({ts.begin, len});
|
||||
#else
|
||||
std::unique_ptr<unsigned[]> pxbuf(new unsigned[len]);
|
||||
editor_.graph_.glyph_pixels(ts.begin, len, pxbuf.get());
|
||||
#endif
|
||||
|
||||
auto pxptr = pxbuf.get();
|
||||
auto pxend = pxptr + len;
|
||||
@ -3310,8 +3314,12 @@ namespace nana{ namespace widgets
|
||||
if (parser.entities().empty())
|
||||
return;
|
||||
|
||||
#ifdef _nana_std_has_string_view
|
||||
auto glyph_px = graph_.glyph_pixels({ str, len });
|
||||
#else
|
||||
std::unique_ptr<unsigned[]> glyph_px(new unsigned[len]);
|
||||
graph_.glyph_pixels(str, len, glyph_px.get());
|
||||
#endif
|
||||
auto glyphs = glyph_px.get();
|
||||
|
||||
auto px_h = line_height();
|
||||
@ -3561,8 +3569,12 @@ namespace nana{ namespace widgets
|
||||
unsigned select_pos = static_cast<unsigned>(ent_sbegin != ent.begin ? ent_sbegin - ent.begin : 0);
|
||||
unsigned select_len = static_cast<unsigned>(ent_send - ent_sbegin);
|
||||
|
||||
#ifdef _nana_std_has_string_view
|
||||
auto pxbuf = graph_.glyph_pixels({ ent.begin, static_cast<std::size_t>(len) });
|
||||
#else
|
||||
std::unique_ptr<unsigned[]> pxbuf{ new unsigned[len] };
|
||||
graph_.glyph_pixels(ent.begin, len, pxbuf.get());
|
||||
#endif
|
||||
|
||||
auto head_px = std::accumulate(pxbuf.get(), pxbuf.get() + select_pos, unsigned{});
|
||||
auto select_px = std::accumulate(pxbuf.get() + select_pos, pxbuf.get() + select_pos + select_len, unsigned{});
|
||||
@ -3636,7 +3648,11 @@ namespace nana{ namespace widgets
|
||||
auto len = static_cast<std::size_t>(ent.end - ent.begin);
|
||||
|
||||
std::unique_ptr<unsigned[]> pxbuf(new unsigned[len]);
|
||||
#ifdef _nana_std_has_string_view
|
||||
if (graph_.glyph_pixels({ent.begin, len}, pxbuf.get()))
|
||||
#else
|
||||
if (graph_.glyph_pixels(ent.begin, len, pxbuf.get()))
|
||||
#endif
|
||||
{
|
||||
const auto px_end = pxbuf.get() + len;
|
||||
|
||||
@ -3695,7 +3711,11 @@ namespace nana{ namespace widgets
|
||||
//Characters of some bidi languages may transform in a word.
|
||||
//RTL
|
||||
std::unique_ptr<unsigned[]> pxbuf(new unsigned[len]);
|
||||
#ifdef _nana_std_has_string_view
|
||||
graph_.glyph_pixels({ent.begin, len}, pxbuf.get());
|
||||
#else
|
||||
graph_.glyph_pixels(ent.begin, len, pxbuf.get());
|
||||
#endif
|
||||
return std::accumulate(pxbuf.get() + (target - ent.begin), pxbuf.get() + len, text_w);
|
||||
}
|
||||
//LTR
|
||||
|
@ -465,8 +465,116 @@ namespace paint
|
||||
{
|
||||
return detail::text_extent_size(impl_->handle, text.data(), text.length());
|
||||
}
|
||||
|
||||
|
||||
nana::size graphics::glyph_extent_size(std::wstring_view text, std::size_t begin, std::size_t end) const
|
||||
{
|
||||
end = std::clamp(end, static_cast<std::size_t>(0), static_cast<std::size_t>(text.size()));
|
||||
|
||||
if (nullptr == impl_->handle || text.empty() || begin >= end) return{};
|
||||
|
||||
nana::size sz;
|
||||
#if defined(NANA_WINDOWS)
|
||||
int * dx = new int[text.size()];
|
||||
|
||||
SIZE extents;
|
||||
::GetTextExtentExPoint(impl_->handle->context, text.data(), static_cast<int>(text.size()), 0, 0, dx, &extents);
|
||||
sz.width = dx[end - 1] - (begin ? dx[begin - 1] : 0);
|
||||
unsigned tab_pixels = impl_->handle->string.tab_length * impl_->handle->string.whitespace_pixels;
|
||||
const wchar_t * pend = text.data() + end;
|
||||
for (const wchar_t * p = text.data() + begin; p != pend; ++p)
|
||||
{
|
||||
if (*p == '\t')
|
||||
sz.width += tab_pixels;
|
||||
}
|
||||
sz.height = extents.cy;
|
||||
delete[] dx;
|
||||
#elif defined(NANA_X11)
|
||||
sz = text_extent_size(text.substr(begin, end - begin));
|
||||
#endif
|
||||
return sz;
|
||||
}
|
||||
|
||||
bool graphics::glyph_pixels(std::wstring_view text, unsigned* pxbuf) const
|
||||
{
|
||||
if (nullptr == impl_->handle || nullptr == impl_->handle->context || nullptr == pxbuf) return false;
|
||||
|
||||
if (text.empty()) return true;
|
||||
|
||||
unsigned tab_pixels = impl_->handle->string.tab_length * impl_->handle->string.whitespace_pixels;
|
||||
#if defined(NANA_WINDOWS)
|
||||
int * dx = new int[text.size()];
|
||||
SIZE extents;
|
||||
::GetTextExtentExPoint(impl_->handle->context, text.data(), static_cast<int>(text.size()), 0, 0, dx, &extents);
|
||||
|
||||
pxbuf[0] = (text[0] == '\t' ? tab_pixels : dx[0]);
|
||||
|
||||
for (std::size_t i = 1; i < text.size(); ++i)
|
||||
{
|
||||
pxbuf[i] = (text[i] == '\t' ? tab_pixels : dx[i] - dx[i - 1]);
|
||||
}
|
||||
delete[] dx;
|
||||
#elif defined(NANA_X11) && defined(NANA_USE_XFT)
|
||||
|
||||
auto disp = nana::detail::platform_spec::instance().open_display();
|
||||
auto xft = reinterpret_cast<XftFont*>(impl_->handle->font->native_handle());
|
||||
|
||||
XGlyphInfo extents;
|
||||
for (std::size_t i = 0; i < len; ++i)
|
||||
{
|
||||
if (text[i] != '\t')
|
||||
{
|
||||
FT_UInt glyphs = ::XftCharIndex(disp, xft, text[i]);
|
||||
::XftGlyphExtents(disp, xft, &glyphs, 1, &extents);
|
||||
pxbuf[i] = extents.xOff;
|
||||
}
|
||||
else
|
||||
pxbuf[i] = tab_pixels;
|
||||
}
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
std::unique_ptr<unsigned[]> graphics::glyph_pixels(std::wstring_view text) const
|
||||
{
|
||||
if (nullptr == impl_->handle || nullptr == impl_->handle->context) return {};
|
||||
|
||||
if (text.empty()) return std::unique_ptr<unsigned[]>{new unsigned[1]};
|
||||
|
||||
unsigned tab_pixels = impl_->handle->string.tab_length * impl_->handle->string.whitespace_pixels;
|
||||
#if defined(NANA_WINDOWS)
|
||||
int * dx = new int[text.size()];
|
||||
SIZE extents;
|
||||
::GetTextExtentExPoint(impl_->handle->context, text.data(), static_cast<int>(text.size()), 0, 0, dx, &extents);
|
||||
|
||||
auto pxbuf = std::unique_ptr<unsigned[]>{ new unsigned[text.size()] };
|
||||
|
||||
pxbuf[0] = (text[0] == '\t' ? tab_pixels : dx[0]);
|
||||
|
||||
for (std::size_t i = 1; i < text.size(); ++i)
|
||||
{
|
||||
pxbuf[i] = (text[i] == '\t' ? tab_pixels : dx[i] - dx[i - 1]);
|
||||
}
|
||||
delete[] dx;
|
||||
#elif defined(NANA_X11) && defined(NANA_USE_XFT)
|
||||
|
||||
auto disp = nana::detail::platform_spec::instance().open_display();
|
||||
auto xft = reinterpret_cast<XftFont*>(impl_->handle->font->native_handle());
|
||||
|
||||
XGlyphInfo extents;
|
||||
for (std::size_t i = 0; i < len; ++i)
|
||||
{
|
||||
if (text[i] != '\t')
|
||||
{
|
||||
FT_UInt glyphs = ::XftCharIndex(disp, xft, text[i]);
|
||||
::XftGlyphExtents(disp, xft, &glyphs, 1, &extents);
|
||||
pxbuf[i] = extents.xOff;
|
||||
}
|
||||
else
|
||||
pxbuf[i] = tab_pixels;
|
||||
}
|
||||
#endif
|
||||
return pxbuf;
|
||||
}
|
||||
#else
|
||||
::nana::size graphics::text_extent_size(const ::std::string& text) const
|
||||
{
|
||||
@ -498,11 +606,10 @@ namespace paint
|
||||
{
|
||||
return detail::text_extent_size(impl_->handle, str.c_str(), len);
|
||||
}
|
||||
#endif
|
||||
|
||||
nana::size graphics::glyph_extent_size(const wchar_t * str, std::size_t len, std::size_t begin, std::size_t end) const
|
||||
{
|
||||
if(len < end) end = len;
|
||||
if (len < end) end = len;
|
||||
if (nullptr == impl_->handle || nullptr == str || 0 == len || begin >= end) return{};
|
||||
|
||||
nana::size sz;
|
||||
@ -513,13 +620,13 @@ namespace paint
|
||||
sz.width = dx[end - 1] - (begin ? dx[begin - 1] : 0);
|
||||
unsigned tab_pixels = impl_->handle->string.tab_length * impl_->handle->string.whitespace_pixels;
|
||||
const wchar_t * pend = str + end;
|
||||
for(const wchar_t * p = str + begin; p != pend; ++p)
|
||||
for (const wchar_t * p = str + begin; p != pend; ++p)
|
||||
{
|
||||
if(*p == '\t')
|
||||
if (*p == '\t')
|
||||
sz.width += tab_pixels;
|
||||
}
|
||||
sz.height = extents.cy;
|
||||
delete [] dx;
|
||||
delete[] dx;
|
||||
#elif defined(NANA_X11)
|
||||
sz = text_extent_size(str + begin, end - begin);
|
||||
#endif
|
||||
@ -533,8 +640,8 @@ namespace paint
|
||||
|
||||
bool graphics::glyph_pixels(const wchar_t * str, std::size_t len, unsigned* pxbuf) const
|
||||
{
|
||||
if(nullptr == impl_->handle || nullptr == impl_->handle->context || nullptr == str || nullptr == pxbuf) return false;
|
||||
if(len == 0) return true;
|
||||
if (nullptr == impl_->handle || nullptr == impl_->handle->context || nullptr == str || nullptr == pxbuf) return false;
|
||||
if (len == 0) return true;
|
||||
|
||||
unsigned tab_pixels = impl_->handle->string.tab_length * impl_->handle->string.whitespace_pixels;
|
||||
#if defined(NANA_WINDOWS)
|
||||
@ -542,22 +649,22 @@ namespace paint
|
||||
SIZE extents;
|
||||
::GetTextExtentExPoint(impl_->handle->context, str, static_cast<int>(len), 0, 0, dx, &extents);
|
||||
|
||||
pxbuf[0] = (str[0] == '\t' ? tab_pixels : dx[0]);
|
||||
pxbuf[0] = (str[0] == '\t' ? tab_pixels : dx[0]);
|
||||
|
||||
for(std::size_t i = 1; i < len; ++i)
|
||||
for (std::size_t i = 1; i < len; ++i)
|
||||
{
|
||||
pxbuf[i] = (str[i] == '\t' ? tab_pixels : dx[i] - dx[i - 1]);
|
||||
}
|
||||
delete [] dx;
|
||||
delete[] dx;
|
||||
#elif defined(NANA_X11) && defined(NANA_USE_XFT)
|
||||
|
||||
auto disp = nana::detail::platform_spec::instance().open_display();
|
||||
auto xft = reinterpret_cast<XftFont*>(impl_->handle->font->native_handle());
|
||||
|
||||
XGlyphInfo extents;
|
||||
for(std::size_t i = 0; i < len; ++i)
|
||||
for (std::size_t i = 0; i < len; ++i)
|
||||
{
|
||||
if(str[i] != '\t')
|
||||
if (str[i] != '\t')
|
||||
{
|
||||
FT_UInt glyphs = ::XftCharIndex(disp, xft, str[i]);
|
||||
::XftGlyphExtents(disp, xft, &glyphs, 1, &extents);
|
||||
@ -570,6 +677,9 @@ namespace paint
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
nana::size graphics::bidi_extent_size(const std::wstring& str) const
|
||||
{
|
||||
nana::size sz;
|
||||
|
@ -236,7 +236,12 @@ namespace nana
|
||||
std::unique_ptr<unsigned[]> pixel_buf(new unsigned[len]);
|
||||
|
||||
//Find the char that should be splitted
|
||||
#ifdef _nana_std_has_string_view
|
||||
graph.glyph_pixels({ i.begin, len }, pixel_buf.get());
|
||||
#else
|
||||
graph.glyph_pixels(i.begin, len, pixel_buf.get());
|
||||
#endif
|
||||
|
||||
std::size_t idx_head = 0, idx_splitted;
|
||||
|
||||
do
|
||||
@ -456,7 +461,11 @@ namespace nana
|
||||
std::unique_ptr<unsigned[]> scope_res(new unsigned[len]);
|
||||
auto pxbuf = scope_res.get();
|
||||
//Find the char that should be splitted
|
||||
#ifdef _nana_std_has_string_view
|
||||
graph.glyph_pixels({ i.begin, len }, pxbuf);
|
||||
#else
|
||||
graph.glyph_pixels(i.begin, len, pxbuf);
|
||||
#endif
|
||||
std::size_t idx_head = 0, idx_splitted;
|
||||
|
||||
do
|
||||
@ -636,12 +645,15 @@ namespace nana
|
||||
|
||||
#ifdef _nana_std_has_string_view
|
||||
const auto ellipsis = graph_.text_extent_size(std::string_view{ "...", 3 }).width;
|
||||
|
||||
std::unique_ptr<unsigned[]> pixels(new unsigned[text.size()]);
|
||||
graph_.glyph_pixels({ text.c_str(), text.size() }, pixels.get());
|
||||
#else
|
||||
const auto ellipsis = graph_.text_extent_size("...", 3).width;
|
||||
#endif
|
||||
|
||||
std::unique_ptr<unsigned[]> pixels(new unsigned[text.size()]);
|
||||
graph_.glyph_pixels(text.c_str(), text.size(), pixels.get());
|
||||
#endif
|
||||
|
||||
std::size_t substr_len = 0;
|
||||
unsigned substr_px = 0;
|
||||
|
Loading…
x
Reference in New Issue
Block a user