Pri Reader has problems.

This commit is contained in:
Bruce
2025-11-02 22:31:16 +08:00
parent b1d1a5670b
commit 733c2ca4f0
6 changed files with 1989 additions and 433 deletions

View File

@@ -100,72 +100,96 @@ template <typename E, typename TR = std::char_traits <E>, typename AL = std::all
} }
template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> bool IsNormalizeStringEquals (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false) template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> bool IsNormalizeStringEquals (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false)
{ {
auto skip_blank = [&] (auto &it, auto &end) auto _local_strlen = [] (const E *p) -> size_t {
{ size_t cnt = 0;
while (it != end && is_blank (*it)) ++ it; while (*(p + cnt)) { cnt ++; }
return cnt;
}; };
auto it_l = l.begin (), it_r = r.begin (); const E *pl = l.c_str ();
auto end_l = l.end (), end_r = r.end (); const E *pr = r.c_str ();
skip_blank (it_l, end_l); while (*pl && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (*pr && is_blank (*pr)) ++ pr;
while (it_l != end_l && it_r != end_r) const E *el = l.c_str () + _local_strlen (l.c_str ());
const E *er = r.c_str () + _local_strlen (r.c_str ());
while (el > pl && is_blank (*(el - 1))) --el;
while (er > pr && is_blank (*(er - 1))) --er;
while (pl < el && pr < er)
{ {
E ch_l = *it_l;
E ch_r = *it_r;
ch_l = l0km::tolower (ch_l);
ch_r = l0km::tolower (ch_r);
if (ch_l != ch_r) return false;
++ it_l;
++ it_r;
if (includemidblank) if (includemidblank)
{ {
if (is_blank (ch_l)) if (is_blank (*pl) && is_blank (*pr))
{ {
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++pr;
continue;
}
else if (is_blank (*pl))
{
while (pl < el && is_blank (*pl)) ++pl;
continue;
}
else if (is_blank (*pr))
{
while (pr < er && is_blank (*pr)) ++pr;
continue;
} }
} }
if (l0km::tolower (*pl) != l0km::tolower (*pr)) return false;
++ pl;
++ pr;
} }
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++ pr;
return it_l == end_l && it_r == end_r; return pl == el && pr == er;
} }
template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> int64_t NormalizeStringCompare (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false) template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> int64_t NormalizeStringCompare (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false)
{ {
auto skip_blank = [&] (auto &it, auto &end) auto _local_strlen = [] (const E *p) -> size_t {
{ size_t cnt = 0;
while (it != end && is_blank (*it)) ++ it; while (*(p + cnt)) { cnt ++; }
return cnt;
}; };
auto it_l = l.begin (), it_r = r.begin (); const E *pl = l.c_str ();
auto end_l = l.end (), end_r = r.end (); const E *pr = r.c_str ();
skip_blank (it_l, end_l); while (*pl && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (*pr && is_blank (*pr)) ++ pr;
while (it_l != end_l && it_r != end_r) const E *el = l.c_str () + _local_strlen (l.c_str ());
const E *er = r.c_str () + _local_strlen (r.c_str ());
while (el > pl && is_blank (*(el - 1))) -- el;
while (er > pr && is_blank (*(er - 1))) -- er;
while (pl < el && pr < er)
{ {
E ch_l = l0km::tolower (*it_l);
E ch_r = l0km::tolower (*it_r);
if (ch_l != ch_r) return ch_l < ch_r ? -1 : 1;
++ it_l;
++ it_r;
if (includemidblank) if (includemidblank)
{ {
if (is_blank (*it_l) || is_blank (*it_r)) if (is_blank (*pl) && is_blank (*pr))
{ {
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++pr;
if (it_l != end_l && it_r != end_r) continue;
{ }
ch_l = l0km::tolower (*it_l); else if (is_blank (*pl))
ch_r = l0km::tolower (*it_r); {
} while (pl < el && is_blank (*pl)) ++pl;
continue;
}
else if (is_blank (*pr))
{
while (pr < er && is_blank (*pr)) ++pr;
continue;
} }
} }
E chl = l0km::tolower (*pl);
E chr = l0km::tolower (*pr);
if (chl != chr) return (int64_t)chl - (int64_t)chr;
++ pl;
++ pr;
} }
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++ pr;
if (it_l == end_l && it_r == end_r) return 0; if (pl == el && pr == er) return 0;
if (it_l == end_l) return -1; if (pl == el) return -1;
return 1; if (pr == er) return 1;
return (int64_t)l0km::tolower (*pl) - (int64_t)l0km::tolower (*pr);
} }
template <typename CharT> bool IsNormalizeStringEquals (const CharT *l, const CharT *r, bool includemidblank = false) template <typename CharT> bool IsNormalizeStringEquals (const CharT *l, const CharT *r, bool includemidblank = false)
{ {

View File

@@ -28,31 +28,37 @@ namespace l0km
} }
inline char toupper (char ch) inline char toupper (char ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <char>> (loc).toupper (ch); return std::use_facet <std::ctype <char>> (loc).toupper (ch);
} }
inline char tolower (char ch) inline char tolower (char ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <char>> (loc).tolower (ch); return std::use_facet <std::ctype <char>> (loc).tolower (ch);
} }
inline wchar_t toupper (wchar_t ch) inline wchar_t toupper (wchar_t ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <wchar_t>> (loc).toupper (ch); return std::use_facet <std::ctype <wchar_t>> (loc).toupper (ch);
} }
inline wchar_t tolower (wchar_t ch) inline wchar_t tolower (wchar_t ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <wchar_t>> (loc).tolower (ch); return std::use_facet <std::ctype <wchar_t>> (loc).tolower (ch);
} }
inline int toupper (int ch) inline int toupper (int ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <int>> (loc).toupper (ch); return std::use_facet <std::ctype <int>> (loc).toupper (ch);
} }
inline int tolower (int ch) inline int tolower (int ch)
{ {
if (ch < -1) return ch;
static const std::locale loc; static const std::locale loc;
return std::use_facet <std::ctype <int>> (loc).tolower (ch); return std::use_facet <std::ctype <int>> (loc).tolower (ch);
} }
@@ -100,72 +106,96 @@ template <typename E, typename TR = std::char_traits <E>, typename AL = std::all
} }
template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> bool IsNormalizeStringEquals (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false) template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> bool IsNormalizeStringEquals (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false)
{ {
auto skip_blank = [&] (auto &it, auto &end) auto _local_strlen = [] (const E *p) -> size_t {
{ size_t cnt = 0;
while (it != end && is_blank (*it)) ++ it; while (*(p + cnt)) { cnt ++; }
return cnt;
}; };
auto it_l = l.begin (), it_r = r.begin (); const E *pl = l.c_str ();
auto end_l = l.end (), end_r = r.end (); const E *pr = r.c_str ();
skip_blank (it_l, end_l); while (*pl && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (*pr && is_blank (*pr)) ++ pr;
while (it_l != end_l && it_r != end_r) const E *el = l.c_str () + _local_strlen (l.c_str ());
const E *er = r.c_str () + _local_strlen (r.c_str ());
while (el > pl && is_blank (*(el - 1))) --el;
while (er > pr && is_blank (*(er - 1))) --er;
while (pl < el && pr < er)
{ {
E ch_l = *it_l;
E ch_r = *it_r;
ch_l = l0km::tolower (ch_l);
ch_r = l0km::tolower (ch_r);
if (ch_l != ch_r) return false;
++ it_l;
++ it_r;
if (includemidblank) if (includemidblank)
{ {
if (is_blank (ch_l)) if (is_blank (*pl) && is_blank (*pr))
{ {
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++pr;
continue;
}
else if (is_blank (*pl))
{
while (pl < el && is_blank (*pl)) ++pl;
continue;
}
else if (is_blank (*pr))
{
while (pr < er && is_blank (*pr)) ++pr;
continue;
} }
} }
if (l0km::tolower (*pl) != l0km::tolower (*pr)) return false;
++ pl;
++ pr;
} }
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++ pr;
return it_l == end_l && it_r == end_r; return pl == el && pr == er;
} }
template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> int64_t NormalizeStringCompare (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false) template <typename E, typename TR = std::char_traits <E>, typename AL = std::allocator <E>> int64_t NormalizeStringCompare (const std::basic_string <E, TR, AL> &l, const std::basic_string <E, TR, AL> &r, bool includemidblank = false)
{ {
auto skip_blank = [&] (auto &it, auto &end) auto _local_strlen = [] (const E *p) -> size_t {
{ size_t cnt = 0;
while (it != end && is_blank (*it)) ++ it; while (*(p + cnt)) { cnt ++; }
return cnt;
}; };
auto it_l = l.begin (), it_r = r.begin (); const E *pl = l.c_str ();
auto end_l = l.end (), end_r = r.end (); const E *pr = r.c_str ();
skip_blank (it_l, end_l); while (*pl && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (*pr && is_blank (*pr)) ++ pr;
while (it_l != end_l && it_r != end_r) const E *el = l.c_str () + _local_strlen (l.c_str ());
const E *er = r.c_str () + _local_strlen (r.c_str ());
while (el > pl && is_blank (*(el - 1))) -- el;
while (er > pr && is_blank (*(er - 1))) -- er;
while (pl < el && pr < er)
{ {
E ch_l = l0km::tolower (*it_l);
E ch_r = l0km::tolower (*it_r);
if (ch_l != ch_r) return ch_l < ch_r ? -1 : 1;
++ it_l;
++ it_r;
if (includemidblank) if (includemidblank)
{ {
if (is_blank (*it_l) || is_blank (*it_r)) if (is_blank (*pl) && is_blank (*pr))
{ {
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++pr;
if (it_l != end_l && it_r != end_r) continue;
{ }
ch_l = l0km::tolower (*it_l); else if (is_blank (*pl))
ch_r = l0km::tolower (*it_r); {
} while (pl < el && is_blank (*pl)) ++pl;
continue;
}
else if (is_blank (*pr))
{
while (pr < er && is_blank (*pr)) ++pr;
continue;
} }
} }
E chl = l0km::tolower (*pl);
E chr = l0km::tolower (*pr);
if (chl != chr) return (int64_t)chl - (int64_t)chr;
++ pl;
++ pr;
} }
skip_blank (it_l, end_l); while (pl < el && is_blank (*pl)) ++ pl;
skip_blank (it_r, end_r); while (pr < er && is_blank (*pr)) ++ pr;
if (it_l == end_l && it_r == end_r) return 0; if (pl == el && pr == er) return 0;
if (it_l == end_l) return -1; if (pl == el) return -1;
return 1; if (pr == er) return 1;
return (int64_t)l0km::tolower (*pl) - (int64_t)l0km::tolower (*pr);
} }
template <typename CharT> bool IsNormalizeStringEquals (const CharT *l, const CharT *r, bool includemidblank = false) template <typename CharT> bool IsNormalizeStringEquals (const CharT *l, const CharT *r, bool includemidblank = false)
{ {

File diff suppressed because it is too large Load Diff

View File

@@ -151,6 +151,7 @@
<ClInclude Include="priread.h" /> <ClInclude Include="priread.h" />
<ClInclude Include="stdafx.h" /> <ClInclude Include="stdafx.h" />
<ClInclude Include="targetver.h" /> <ClInclude Include="targetver.h" />
<ClInclude Include="themeinfo.h" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ClCompile Include="dllmain.cpp"> <ClCompile Include="dllmain.cpp">

View File

@@ -36,6 +36,9 @@
<ClInclude Include="localeex.h"> <ClInclude Include="localeex.h">
<Filter>头文件</Filter> <Filter>头文件</Filter>
</ClInclude> </ClInclude>
<ClInclude Include="themeinfo.h">
<Filter>头文件</Filter>
</ClInclude>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ClCompile Include="stdafx.cpp"> <ClCompile Include="stdafx.cpp">

40
priread/themeinfo.h Normal file
View File

@@ -0,0 +1,40 @@
#pragma once
#include <Windows.h>
bool IsHighContrastEnabled ()
{
HIGHCONTRAST hc = {sizeof (HIGHCONTRAST)};
if (SystemParametersInfo (SPI_GETHIGHCONTRAST, sizeof (hc), &hc, 0)) return (hc.dwFlags & HCF_HIGHCONTRASTON) != 0;
return false;
}
enum class HighContrastTheme
{
None,
Black,
White,
Other
};
HighContrastTheme GetHighContrastTheme ()
{
HIGHCONTRAST hc = {sizeof (HIGHCONTRAST)};
if (!SystemParametersInfo (SPI_GETHIGHCONTRAST, sizeof (hc), &hc, 0)) return HighContrastTheme::None;
if (!(hc.dwFlags & HCF_HIGHCONTRASTON)) return HighContrastTheme::None;
COLORREF bgColor = GetSysColor (COLOR_WINDOW);
COLORREF textColor = GetSysColor (COLOR_WINDOWTEXT);
int brightnessBg = (GetRValue (bgColor) + GetGValue (bgColor) + GetBValue (bgColor)) / 3;
int brightnessText = (GetRValue (textColor) + GetGValue (textColor) + GetBValue (textColor)) / 3;
if (brightnessBg < brightnessText) return HighContrastTheme::Black;
else if (brightnessBg > brightnessText) return HighContrastTheme::White;
else return HighContrastTheme::Other;
}
int GetDPI ()
{
HDC hDC = GetDC (NULL);
int DPI_A = (int)(((double)GetDeviceCaps (hDC, 118) / (double)GetDeviceCaps (hDC, 8)) * 100);
int DPI_B = (int)(((double)GetDeviceCaps (hDC, 88) / 96) * 100);
ReleaseDC (NULL, hDC);
if (DPI_A == 100) return DPI_B;
else if (DPI_B == 100) return DPI_A;
else if (DPI_A == DPI_B) return DPI_A;
else return 0;
}