【问题标题】:Unicode characters not displayed in TextView.setTextTextView.setText 中未显示 Unicode 字符
【发布时间】:2011-05-30 04:05:27
【问题描述】:

我无法让 TextView 正确动态地显示 unicode 字符,这让我很生气。我已将其精简到最低限度,但由 setText 填充的 TextView 仍然显示带有 unicode 字符的问号的菱形。从 strings.xml 填充的版本完美地显示了多字节字符。这是活动:

public class TestMultibyteActivity extends Activity
{
  /** Called when the activity is first created. */
  @Override
  public void onCreate( Bundle savedInstanceState )
  {
    super.onCreate( savedInstanceState );
    setContentView( R.layout.main );
    TextView textField = (TextView) findViewById( R.id.text_field );
    String str = "Tübingen systemportefølje";
    Log.d( "MULTIBYTE", str ); //note that this prints the multibyte chars correctly.
    //EDIT: oh crap, no it doesn't.  might be onto something here...
    textField.setText( str );
  }
}

这是布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
              android:orientation="vertical"
              android:layout_width="fill_parent"
              android:layout_height="fill_parent">
  <TextView android:id="@+id/text_field"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"/>
  <TextView android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:text="@string/unicodechars"/>
</LinearLayout>

这里是strings.xml:

<?xml version="1.0" encoding="utf-8"?>
<resources>
  <string name="app_name">TestMultibyteActivity</string>
  <string name="unicodechars">Tübingen systemportefølje</string>
</resources>

我正在用 ant 构建。这是我的 default.properties:

target=Google Inc.:Google APIs:8

这是我的 AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
      package="com.mycompany.android.multibyte"
      android:versionCode="1"
      android:versionName="1.0">
    <application android:label="@string/app_name" android:icon="@drawable/icon">
        <activity android:name="TestMultibyteActivity"
                  android:label="@string/app_name">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>
</manifest> 

我已经修改了我能想到的所有内容,但似乎 Unicode 字符被 CharSequence 接口分割,我不知道为什么。

【问题讨论】:

    标签: android


    【解决方案1】:

    不幸的是,您不能从 strings.xml AFAIK 中这样做。

    你只能做两件事之一。

    • 将java中的Unicode字符添加到XML文件中的String中:

      String str = "\u00A9" + getContext().getString(R.string.your_string);
      
    • 在 java 中输入 HTML 格式的文本:

      yourTextView.setText(Html.fromHtml("your chars"));
      

    希望这是有用的。

    【讨论】:

    【解决方案2】:

    我在尝试从映射到 Unicode 专用区域的自定义字体中显示 Unicode 字符时遇到问题。这是一个常见的区域,MaterialDesign 和 FontAwesome 等字体映射其图标字体字符。只是为了清楚起见,我在 android 版本 4.4.2 上对此进行了测试,所以在以后的版本中这可能不是问题(但可能是)。我已经尝试了“\uF151”、 的所有组合,还尝试了 Html.fromHtlm。这些技术都不能正确显示 Unicode 专用区域中的字符。如果我将自己保持在 \u00xx 范围内,它们对于在这些位置具有 Unicode 代码的字体都可以正常工作。 (我提到的两种字体没有任何符号映射到这些点位置)

    在使用 Microsoft 的字符映射检查字体时,我注意到当我为字体选择 Windows 英语字符集时,Unicode 专用区域空间中的字符没有显示。如果我选择了 Unicode 字符集,这些字符就会出现;在 Material Design 字体的情况下,如果我选择了日文字符集。

    为了让字符在 TextView 中显示,我所做的是将区域设置更改为日语,在 Textview 对象上调用 setText,将正确的私有区域 unicode 值传递给它,然后字符就会正确显示。所以这是我用来设置图标字体符号然后恢复为英文的代码:

        TextView tv = (TextView)findViewById(R.id.myTextViewObject);
        Typeface tf =  Typeface.createFromAsset(this.getAssets(), "material_design.ttf");
        tv.setTypeface(tf);
        String x = "\uE693";
    
        tv.setText(x);
        setDefaultLocale(getApplicationContext(),"en");
        tv.append("hello");
    

    这里是 setDefaultLocale 方法的代码:

    public static void setDefaultLocale(Context context, String locale) {
        Locale locJa = new Locale(locale.trim());
        Locale.setDefault(locJa);
    
        Configuration config = new Configuration();
        config.locale = locJa;
    
        context.getResources().updateConfiguration(config, context.getResources().getDisplayMetrics());
    
        locJa = null;
        config = null;
    }
    

    在 FontAwesome 的情况下,您必须选择繁体中文字符集才能访问 unicode 私有区域代码点。

    你可能会问,为什么我没有选择“Unicode”字符集? android 使用的字符集是基于当前语言环境的,我找不到选择 unicode 作为当前语言环境的方法。此外,我找不到将私有区域 unicode 映射到我现有的区域设置的方法。我也无法告诉您这是否是关于这些 True Type 字体是如何构建的问题,或者这是否是 Android 问题(尽管我认为应该有一个为什么要映射私有区域代码以在您现有的语言环境中使用)我了解到的是,所有 Unicode 代码点都映射到相同字体的所有语言环境中。这就是我认为很多人对支持 unicode 的字体感到困惑的地方。 windows 字符映射是我确定哪些字符点映射到哪个字符集的有用工具。

    【讨论】:

      【解决方案3】:

      可以通过这样一种简单的方式完成:

      str.replace("uoo26","&");
      

      【讨论】:

        【解决方案4】:

        接受的答案是正确的,但 Html.fromHtml 现在已弃用。所以你需要使用:

        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.N) {
                textView.setText(Html.fromHtml(user.getInput(), Html.FROM_HTML_MODE_LEGACY));
            } else {
                textView.setText(Html.fromHtml(user.getInput()));
            }
        

        【讨论】:

          【解决方案5】:

          我在这里尝试了所有其他答案,但无法解决我的问题。终于找到了:D

          StringEscapeUtils.unescapeJava("Your unicode string")
          

          【讨论】:

            【解决方案6】:

            如果你想显示来自 unicode 的文本。

            1. 第一步,从 unicode 中删除“\u”。例如:\u00A9 应该是“00A9”
            2. 然后,将“00A9”转换为整数。例如:val hexVal = Integer.parseInt("00A9", 16)
            3. 最后,将 Integer 转换为 char。 val char = hexVal.toChar().Then 显示字符。

            源代码:

             val builder = StringBuilder()
            listUnicodes.forEach 
             { uniCode ->
               val hexVal = Integer.parseInt(uniCode, 16)
               val char = hexVal.toChar()
               builder.append(char)        
            }
            return builder.toString()
            

            【讨论】:

              【解决方案7】:

              欢迎来到 kotlin 的世界,

              如果有人想以编程方式设置 UNICODE,您可以通过以下方式进行操作

              ?的Unicode字符是U+1F91A

              U+ 替换为 0x 使其变为 0x1F91A

              val unicodeChar = 0x1F91A.toChar() // unicode for ?
              

              对于上述问题,用户希望显示 "Tübingen systemportefølje"

              val char1 = 0x00FC.toChar()  // unicode for ü is U+00FC
              val char2 = 0x00F8.toChar() //  unicode for ø is U+00F8
              
              val name = StringBuilder("T")
                          .append(char1)
                          .append("bingen systemportef")
                          .append(char2)
                          .append("lje")
                          .toString()
              
              // OUTPUT name = "Tübingen systemportefølje"
              

              现在您可以将字符串设置为您的 Textview。

              对于动态字符串,您可以搜索以 0x 开头的模式并通过构造等效的 Unicode 图像来替换它。

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 2012-08-08
                • 1970-01-01
                • 2015-06-24
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                相关资源
                最近更新 更多