1
0
mirror of https://github.com/libretro/RetroArch synced 2024-07-05 09:48:42 +00:00

Add encoding_utf to libretro-common

This commit is contained in:
twinaphex 2015-11-16 07:24:21 +01:00
parent 2fe29f56be
commit 8918df95e1
4 changed files with 121 additions and 53 deletions

View File

@ -127,6 +127,7 @@ OBJ += frontend/frontend.o \
runloop_msg.o \
tasks/task_file_transfer.o \
content.o \
libretro-common/encodings/encoding_utf.o \
libretro-common/file/file_list.o \
libretro-common/file/dir_list.o \
libretro-common/file/retro_dirent.o \

View File

@ -14,9 +14,6 @@
* If not, see <http://www.gnu.org/licenses/>.
*/
#include <boolean.h>
#include <retro_inline.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/extensions/xf86vmode.h>
@ -25,58 +22,13 @@
#include <X11/extensions/Xinerama.h>
#endif
#include <boolean.h>
#include <retro_inline.h>
#include <encodings/utf.h>
#include "../keyboard_line.h"
#include "../input_keymaps.h"
static INLINE unsigned leading_ones(uint8_t c)
{
unsigned ones = 0;
while (c & 0x80)
{
ones++;
c <<= 1;
}
return ones;
}
/* Simple implementation. Assumes the sequence is
* properly synchronized and terminated. */
static size_t conv_utf8_utf32(uint32_t *out,
size_t out_chars, const char *in, size_t in_size)
{
unsigned i;
size_t ret = 0;
while (in_size && out_chars)
{
unsigned ones, extra, shift;
uint32_t c;
uint8_t first = *in++;
ones = leading_ones(first);
if (ones > 6 || ones == 1) /* Invalid or desync. */
break;
extra = ones ? ones - 1 : ones;
if (1 + extra > in_size) /* Overflow. */
break;
shift = (extra - 1) * 6;
c = (first & ((1 << (7 - ones)) - 1)) << (6 * extra);
for (i = 0; i < extra; i++, in++, shift -= 6)
c |= (*in & 0x3f) << shift;
*out++ = c;
in_size -= 1 + extra;
out_chars--;
ret++;
}
return ret;
}
void x11_handle_key_event(XEvent *event, XIC ic, bool filter)
{
int i;
@ -101,7 +53,7 @@ void x11_handle_key_event(XEvent *event, XIC ic, bool filter)
* which makes mbrtowc a bit impractical.
*
* Use custom UTF8 -> UTF-32 conversion. */
num = conv_utf8_utf32(chars, ARRAY_SIZE(chars), keybuf, num);
num = utf8_conv_utf32(chars, ARRAY_SIZE(chars), keybuf, num);
#else
(void)ic;
num = XLookupString(&event->xkey, keybuf, sizeof(keybuf), &keysym, NULL); /* ASCII only. */

View File

@ -0,0 +1,75 @@
/* Copyright (C) 2010-2015 The RetroArch team
*
* ---------------------------------------------------------------------------------------
* The following license statement only applies to this file (encodings_utf.c).
* ---------------------------------------------------------------------------------------
*
* Permission is hereby granted, free of charge,
* to any person obtaining a copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
* and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#include <stdint.h>
#include <stddef.h>
#include <retro_inline.h>
static INLINE unsigned leading_ones(uint8_t c)
{
unsigned ones = 0;
while (c & 0x80)
{
ones++;
c <<= 1;
}
return ones;
}
/* Simple implementation. Assumes the sequence is
* properly synchronized and terminated. */
size_t utf8_conv_utf32(uint32_t *out, size_t out_chars,
const char *in, size_t in_size)
{
unsigned i;
size_t ret = 0;
while (in_size && out_chars)
{
unsigned extra, shift;
uint32_t c;
uint8_t first = *in++;
unsigned ones = leading_ones(first);
if (ones > 6 || ones == 1) /* Invalid or desync. */
break;
extra = ones ? ones - 1 : ones;
if (1 + extra > in_size) /* Overflow. */
break;
shift = (extra - 1) * 6;
c = (first & ((1 << (7 - ones)) - 1)) << (6 * extra);
for (i = 0; i < extra; i++, in++, shift -= 6)
c |= (*in & 0x3f) << shift;
*out++ = c;
in_size -= 1 + extra;
out_chars--;
ret++;
}
return ret;
}

View File

@ -0,0 +1,40 @@
/* Copyright (C) 2010-2015 The RetroArch team
*
* ---------------------------------------------------------------------------------------
* The following license statement only applies to this file (utf.h).
* ---------------------------------------------------------------------------------------
*
* Permission is hereby granted, free of charge,
* to any person obtaining a copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation the rights to
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
* and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef _LIBRETRO_ENCODINGS_UTF_H
#define _LIBRETRO_ENCODINGS_UTF_H
#include <stdint.h>
#include <stddef.h>
#ifdef __cplusplus
extern "C" {
#endif
size_t utf8_conv_utf32(uint32_t *out, size_t out_chars,
const char *in, size_t in_size);
#ifdef __cplusplus
}
#endif
#endif