00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #include "xrb_utf8.hpp"
00012
00013 namespace Xrb
00014 {
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 char const *UTF8::NextCharacter (char const *current)
00037 {
00038 ASSERT1(current != NULL);
00039
00040 Uint8 const *bytes = reinterpret_cast<Uint8 const *>(current);
00041 if (*bytes == 0x00)
00042 return current;
00043 if (*bytes < 0x80)
00044 return current+1;
00045 if ((*bytes&0xE0) == 0xC0)
00046 return current+2;
00047 if ((*bytes&0xF0) == 0xE0)
00048 return current+3;
00049 if ((*bytes&0xF8) == 0xF0)
00050 return current+4;
00051
00052
00053 return current;
00054 }
00055
00056 bool UTF8::AreCharactersEqual (char const *const c0, char const *const c1)
00057 {
00058 return c0 != NULL && c1 != NULL && Unicode(c0) == Unicode(c1);
00059 }
00060
00061 Uint32 UTF8::Unicode (char const *sequence)
00062 {
00063 ASSERT1(sequence != NULL);
00064
00065 Uint8 const *bytes = reinterpret_cast<Uint8 const *>(sequence);
00066
00067 if (*bytes < 0x80)
00068 return static_cast<Uint32>(*bytes);
00069
00070 Uint32 retval;
00071 if (*bytes < 0xC2)
00072 return 0xFFFFFFFF;
00073 else if (*bytes < 0xE0)
00074 {
00075
00076 retval = *(bytes++)&0x1F;
00077 retval <<= 6;
00078 if (*bytes < 0x80 || *bytes > 0xBF)
00079 return 0xFFFFFFFF;
00080 retval |= *bytes&0x3F;
00081 }
00082 else if (*bytes == 0xE0)
00083 {
00084
00085 retval = *(bytes++)&0x1F;
00086 retval <<= 6;
00087 if (*bytes < 0xA0 || *bytes > 0xBF)
00088 return 0xFFFFFFFF;
00089 retval |= *(bytes++)&0x3F;
00090 retval <<= 6;
00091 if (*bytes < 0x80 || *bytes > 0xBF)
00092 return 0xFFFFFFFF;
00093 retval |= *bytes&0x3F;
00094 }
00095 else if (*bytes == 0xED)
00096 {
00097
00098 retval = *(bytes++)&0x0F;
00099 retval <<= 6;
00100 if (*bytes < 0x80 || *bytes > 0x9F)
00101 return 0xFFFFFFFF;
00102 retval |= *(bytes++)&0x3F;
00103 retval <<= 6;
00104 if (*bytes < 0x80 || *bytes > 0xBF)
00105 return 0xFFFFFFFF;
00106 retval |= *bytes&0x3F;
00107 }
00108 else if (*bytes < 0xF0)
00109 {
00110
00111 retval = *(bytes++)&0x0F;
00112 retval <<= 6;
00113 if (*bytes < 0x80 || *bytes > 0xBF)
00114 return 0xFFFFFFFF;
00115 retval |= *(bytes++)&0x3F;
00116 retval <<= 6;
00117 if (*bytes < 0x80 || *bytes > 0xBF)
00118 return 0xFFFFFFFF;
00119 retval |= *bytes&0x3F;
00120 }
00121 else if (*bytes == 0xF0)
00122 {
00123
00124 retval = *(bytes++)&0x07;
00125 retval <<= 6;
00126 if (*bytes < 0x90 || *bytes > 0xBF)
00127 return 0xFFFFFFFF;
00128 retval |= *(bytes++)&0x3F;
00129 retval <<= 6;
00130 if (*bytes < 0x80 || *bytes > 0xBF)
00131 return 0xFFFFFFFF;
00132 retval |= *(bytes++)&0x3F;
00133 retval <<= 6;
00134 if (*bytes < 0x80 || *bytes > 0xBF)
00135 return 0xFFFFFFFF;
00136 retval |= *bytes&0x3F;
00137 }
00138 else if (*bytes <= 0xF4)
00139 {
00140
00141 retval = *(bytes++)&0x07;
00142 retval <<= 6;
00143 if (*bytes < 0x80 || *bytes > 0xBF)
00144 return 0xFFFFFFFF;
00145 retval |= *(bytes++)&0x3F;
00146 retval <<= 6;
00147 if (*bytes < 0x80 || *bytes > 0xBF)
00148 return 0xFFFFFFFF;
00149 retval |= *(bytes++)&0x3F;
00150 retval <<= 6;
00151 if (*bytes < 0x80 || *bytes > 0xBF)
00152 return 0xFFFFFFFF;
00153 retval |= *bytes&0x3F;
00154 }
00155 else
00156 return 0xFFFFFFFF;
00157
00158 return retval;
00159 }
00160
00161 void UTF8::AppendSequence (std::string *const dest, Uint32 const unicode)
00162 {
00163 ASSERT1(dest != NULL);
00164
00165 if (unicode < 0x80)
00166 {
00167 *dest += static_cast<char>(unicode);
00168 }
00169 else if (unicode < 0x800)
00170 {
00171 *dest += static_cast<char>(0xC0|(unicode>>6));
00172 *dest += static_cast<char>(0x80|(unicode&0x3F));
00173 }
00174 else if (unicode < 0xD800)
00175 {
00176 *dest += static_cast<char>(0xE0|(unicode>>12));
00177 *dest += static_cast<char>(0x80|((unicode>>6)&0x3F));
00178 *dest += static_cast<char>(0x80|(unicode&0x3F));
00179 }
00180 else if (unicode < 0xE000)
00181 {
00182
00183 }
00184 else if (unicode < 0x10000)
00185 {
00186 *dest += static_cast<char>(0xE0|(unicode>>12));
00187 *dest += static_cast<char>(0x80|((unicode>>6)&0x3F));
00188 *dest += static_cast<char>(0x80|(unicode&0x3F));
00189 }
00190 else if (unicode < 0x110000)
00191 {
00192 *dest += static_cast<char>(0xF0|(unicode>>18));
00193 *dest += static_cast<char>(0x80|((unicode>>12)&0x3F));
00194 *dest += static_cast<char>(0x80|((unicode>>6)&0x3F));
00195 *dest += static_cast<char>(0x80|(unicode&0x3F));
00196 }
00197 else
00198 {
00199
00200 }
00201 }
00202
00203 }