我需要使用特定的字体为我的整个应用程序。我有。ttf文件相同。 是否有可能将此设置为默认字体,在应用程序启动,然后在应用程序的其他地方使用它?当设置,我如何使用它在我的布局xml ?


当前回答

是的,可以将字体设置为整个应用程序。

实现这一点的最简单方法是将所需的字体打包到应用程序中。

要做到这一点,只需在项目根目录中创建一个assets/文件夹,并将您的字体(放在 TrueType,或TTF表单)。

例如,您可以创建资产/字体/并将您的TTF文件放在那里。

public class FontSampler extends Activity {
@Override
public void onCreate(Bundle icicle) {
super.onCreate(icicle);
setContentView(R.layout.main);
TextView tv=(TextView)findViewById(R.id.custom);

Typeface face=Typeface.createFromAsset(getAssets(), "fonts/HandmadeTypewriter.ttf");
tv.setTypeface(face);
}
}

其他回答

Tom的解决方案很好,但只适用于TextView和EditText。

如果你想覆盖大部分的视图(RadioGroup, TextView,复选框…),我创建了一个方法:

protected void changeChildrenFont(ViewGroup v, Typeface font){
    for(int i = 0; i < v.getChildCount(); i++){

        // For the ViewGroup, we'll have to use recursivity
        if(v.getChildAt(i) instanceof ViewGroup){
            changeChildrenFont((ViewGroup) v.getChildAt(i), font);
        }
        else{
            try {
                Object[] nullArgs = null;
                //Test wether setTypeface and getTypeface methods exists
                Method methodTypeFace = v.getChildAt(i).getClass().getMethod("setTypeface", new Class[] {Typeface.class, Integer.TYPE});
                //With getTypefaca we'll get back the style (Bold, Italic...) set in XML
                Method methodGetTypeFace = v.getChildAt(i).getClass().getMethod("getTypeface", new Class[] {});
                Typeface typeFace = ((Typeface)methodGetTypeFace.invoke(v.getChildAt(i), nullArgs));
                //Invoke the method and apply the new font with the defined style to the view if the method exists (textview,...)
                methodTypeFace.invoke(v.getChildAt(i), new Object[] {font, typeFace == null ? 0 : typeFace.getStyle()});
            }
            //Will catch the view with no such methods (listview...)
            catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}

该方法将返回视图集的XML样式(粗体,斜体…),并在它们存在时应用它们。

对于ListView,我总是创建一个适配器,并在getView中设置字体。

由于Android Oreo及其支持库(26.0.0)的发布,您可以轻松地做到这一点。这个答案在另一个问题中参考。

基本上你最终的风格是这样的:

<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
   <item name="fontFamily">@font/your_font</item> <!-- target android sdk versions < 26 and > 14 -->
</style>

虽然这并不适用于整个应用程序,但它适用于一个活动,并且可以重用于任何其他活动。我已经更新了我的代码,感谢@FR073N,以支持其他视图。我不确定的问题与按钮,RadioGroups等,因为这些类都扩展TextView,所以他们应该工作得很好。我为使用反射添加了一个布尔条件,因为它看起来非常笨拙,可能会显著降低性能。

注意:正如所指出的,这将不适用于动态内容!为此,可以用onCreateView或getView方法调用这个方法,但需要额外的努力。

/**
 * Recursively sets a {@link Typeface} to all
 * {@link TextView}s in a {@link ViewGroup}.
 */
public static final void setAppFont(ViewGroup mContainer, Typeface mFont, boolean reflect)
{
    if (mContainer == null || mFont == null) return;

    final int mCount = mContainer.getChildCount();

    // Loop through all of the children.
    for (int i = 0; i < mCount; ++i)
    {
        final View mChild = mContainer.getChildAt(i);
        if (mChild instanceof TextView)
        {
            // Set the font if it is a TextView.
            ((TextView) mChild).setTypeface(mFont);
        }
        else if (mChild instanceof ViewGroup)
        {
            // Recursively attempt another ViewGroup.
            setAppFont((ViewGroup) mChild, mFont);
        }
        else if (reflect)
        {
            try {
                Method mSetTypeface = mChild.getClass().getMethod("setTypeface", Typeface.class);
                mSetTypeface.invoke(mChild, mFont); 
            } catch (Exception e) { /* Do something... */ }
        }
    }
}

然后使用它,你可以这样做:

final Typeface mFont = Typeface.createFromAsset(getAssets(),
"fonts/MyFont.ttf"); 
final ViewGroup mContainer = (ViewGroup) findViewById(
android.R.id.content).getRootView();
HomeActivity.setAppFont(mContainer, mFont);

希望这能有所帮助。

为了改变textview的默认字体家族,重写textViewStyle在你的应用主题。

要在fontFamily中使用自定义字体,请使用支持库中的字体资源。

该功能是在Android 26中添加的,但通过supportlib向后移植到旧版本。

https://developer.android.com/guide/topics/resources/font-resource.html https://developer.android.com/guide/topics/ui/look-and-feel/fonts-in-xml.html#using-support-lib

package com.theeasylearn.demo.designdemo;
import android.content.Context;
import android.graphics.Typeface;
import android.util.AttributeSet;
import android.widget.TextView;

public class MyButton extends TextView {

    public MyButton(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        init();
    }

    public MyButton(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public MyButton(Context context) {
        super(context);
        init();
    }

    private void init() {

            Typeface tf =
                    Typeface.createFromAsset(
                            getContext().getAssets(), "angelina.TTF");
            setTypeface(tf);

    }

}