From 5be1b8e6e044cbd13ccc3e8fbbeab00ec576784b Mon Sep 17 00:00:00 2001 From: Nathan Woods Date: Sat, 31 Dec 2016 09:07:40 -0500 Subject: Introduced utf8proc and created wrapper code to expose a prettier API --- src/lib/util/unicode.cpp | 89 +++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 88 insertions(+), 1 deletion(-) (limited to 'src/lib/util/unicode.cpp') diff --git a/src/lib/util/unicode.cpp b/src/lib/util/unicode.cpp index a6c5515fbf6..b3e92e4094e 100644 --- a/src/lib/util/unicode.cpp +++ b/src/lib/util/unicode.cpp @@ -2,7 +2,7 @@ // copyright-holders:Aaron Giles /********************************************************************* - unicode.c + unicode.cpp Unicode related functions @@ -10,6 +10,12 @@ #include "unicode.h" +#ifdef _WIN32 +#define UTF8PROC_DLLEXPORT +#endif + +#include "utf8proc/utf8proc.h" + //------------------------------------------------- // uchar_isvalid - return true if a given @@ -345,6 +351,87 @@ int utf16f_from_uchar(char16_t *utf16string, size_t count, char32_t uchar) } +//------------------------------------------------- +// internal_normalize_unicode - uses utf8proc to +// normalize unicode +//------------------------------------------------- + +static std::string internal_normalize_unicode(const char *s, size_t length, unicode_normalization_form normalization_form, bool null_terminated) +{ + // convert the normalization form + int options; + switch (normalization_form) + { + case unicode_normalization_form::C: + options = UTF8PROC_STABLE | UTF8PROC_COMPOSE; + break; + case unicode_normalization_form::D: + options = UTF8PROC_STABLE | UTF8PROC_DECOMPOSE; + break; + case unicode_normalization_form::KC: + options = UTF8PROC_STABLE | UTF8PROC_COMPOSE | UTF8PROC_COMPAT; + break; + case unicode_normalization_form::KD: + options = UTF8PROC_STABLE | UTF8PROC_DECOMPOSE | UTF8PROC_COMPAT; + break; + default: + throw false; + } + + // was this null terminated? + if (null_terminated) + options |= UTF8PROC_NULLTERM; + + // invoke utf8proc + utf8proc_uint8_t *utf8proc_result; + utf8proc_ssize_t utf8proc_result_length = utf8proc_map((utf8proc_uint8_t *) s, length, &utf8proc_result, (utf8proc_option_t)options); + + // conver the result + std::string result; + if (utf8proc_result) + { + if (utf8proc_result_length > 0) + result = std::string((const char *)utf8proc_result, utf8proc_result_length); + free(utf8proc_result); + } + + return result; +} + + +//------------------------------------------------- +// normalize_unicode - uses utf8proc to normalize +// unicode +//------------------------------------------------- + +std::string normalize_unicode(const std::string &s, unicode_normalization_form normalization_form) +{ + return internal_normalize_unicode(s.c_str(), s.length(), normalization_form, false); +} + + +//------------------------------------------------- +// normalize_unicode - uses utf8proc to normalize +// unicode +//------------------------------------------------- + +std::string normalize_unicode(const char *s, unicode_normalization_form normalization_form) +{ + return internal_normalize_unicode(s, 0, normalization_form, true); +} + + +//------------------------------------------------- +// normalize_unicode - uses utf8proc to normalize +// unicode +//------------------------------------------------- + +std::string normalize_unicode(const char *s, size_t length, unicode_normalization_form normalization_form) +{ + return internal_normalize_unicode(s, length, normalization_form, false); +} + + //------------------------------------------------- // utf8_previous_char - return a pointer to the // previous character in a string -- cgit v1.2.3