EDIT : Quindi è passato un po 'di tempo e vorrei aggiungere quello che penso sia il modo migliore per farlo, e tramite XML non meno!
Quindi, per prima cosa, vorrai creare una nuova classe che sovrascriva qualsiasi visualizzazione che desideri personalizzare. (ad esempio, vuoi un pulsante con un carattere tipografico personalizzato? Estendi Button
). Facciamo un esempio:
public class CustomButton extends Button {
private final static int ROBOTO = 0;
private final static int ROBOTO_CONDENSED = 1;
public CustomButton(Context context) {
super(context);
}
public CustomButton(Context context, AttributeSet attrs) {
super(context, attrs);
parseAttributes(context, attrs); //I'll explain this method later
}
public CustomButton(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
parseAttributes(context, attrs);
}
}
Ora, se non ne hai uno, aggiungi un documento XML sotto res/values/attrs.xml
e aggiungi:
<resources>
<!-- Define the values for the attribute -->
<attr name="typeface" format="enum">
<enum name="roboto" value="0"/>
<enum name="robotoCondensed" value="1"/>
</attr>
<!-- Tell Android that the class "CustomButton" can be styled,
and which attributes it supports -->
<declare-styleable name="CustomButton">
<attr name="typeface"/>
</declare-styleable>
</resources>
Ok, quindi con quello fuori mano, torniamo al parseAttributes()
metodo di prima:
private void parseAttributes(Context context, AttributeSet attrs) {
TypedArray values = context.obtainStyledAttributes(attrs, R.styleable.CustomButton);
//The value 0 is a default, but shouldn't ever be used since the attr is an enum
int typeface = values.getInt(R.styleable.CustomButton_typeface, 0);
switch(typeface) {
case ROBOTO: default:
//You can instantiate your typeface anywhere, I would suggest as a
//singleton somewhere to avoid unnecessary copies
setTypeface(roboto);
break;
case ROBOTO_CONDENSED:
setTypeface(robotoCondensed);
break;
}
values.recycle();
}
Ora sei pronto. Puoi aggiungere più attributi per qualsiasi cosa (potresti aggiungerne un altro per typefaceStyle - grassetto, corsivo, ecc.) Ma ora vediamo come usarlo:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:custom="http://schemas.android.com/apk/res/com.yourpackage.name"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<com.yourpackage.name.CustomButton
android:id="@+id/button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Click Me!"
custom:typeface="roboto" />
</LinearLayout>
La xmlns:custom
linea può davvero essere qualsiasi cosa, ma la convenzione è quella mostrata sopra. Ciò che conta è che sia unico ed è per questo che viene utilizzato il nome del pacchetto. Ora usi solo il custom:
prefisso per i tuoi attributi e il android:
prefisso per gli attributi Android.
Un'ultima cosa: se si desidera utilizzare questo in uno stile ( res/values/styles.xml
), è necessario non aggiungere la xmlns:custom
riga. Basta fare riferimento al nome dell'attributo senza prefisso:
<style name="MyStyle>
<item name="typeface">roboto</item>
</style>
(PREVIOUS ANSWER)
Utilizzo di un carattere tipografico personalizzato in Android
Questo dovrebbe aiutare. Fondamentalmente, non c'è modo di farlo in XML e, per quanto ne so, non c'è modo più semplice per farlo in codice. Puoi sempre avere un metodo setLayoutFont () che crea il carattere tipografico una volta, quindi esegue setTypeface () per ciascuno. Dovresti solo aggiornarlo ogni volta che aggiungi un nuovo elemento a un layout. Qualcosa come di seguito:
public void setLayoutFont() {
Typeface tf = Typeface.createFromAsset(
getBaseContext().getAssets(), "fonts/BPreplay.otf");
TextView tv1 = (TextView)findViewById(R.id.tv1);
tv1.setTypeface(tf);
TextView tv2 = (TextView)findViewById(R.id.tv2);
tv2.setTypeface(tf);
TextView tv3 = (TextView)findViewById(R.id.tv3);
tv3.setTypeface(tf);
}
EDIT : Quindi sono appena riuscito a implementare qualcosa del genere da solo, e il modo in cui ho finito per farlo è stato creare una funzione come questa:
public static void setLayoutFont(Typeface tf, TextView...params) {
for (TextView tv : params) {
tv.setTypeface(tf);
}
}
Quindi, usa questo metodo da onCreate () e passa tutti i TextView che desideri aggiornare:
Typeface tf = Typeface.createFromAsset(getAssets(), "fonts/BPreplay.otf");
//find views by id...
setLayoutFont(tf, tv1, tv2, tv3, tv4, tv5);
EDIT 9/5/12:
Quindi, poiché questo continua a ricevere visualizzazioni e voti, vorrei aggiungere un metodo molto migliore e più completo:
Typeface mFont = Typeface.createFromAsset(getAssets(), "fonts/BPreplay.otf");
ViewGroup root = (ViewGroup)findViewById(R.id.myrootlayout);
setFont(root, mFont);
/*
* Sets the font on all TextViews in the ViewGroup. Searches
* recursively for all inner ViewGroups as well. Just add a
* check for any other views you want to set as well (EditText,
* etc.)
*/
public void setFont(ViewGroup group, Typeface font) {
int count = group.getChildCount();
View v;
for(int i = 0; i < count; i++) {
v = group.getChildAt(i);
if(v instanceof TextView || v instanceof Button /*etc.*/)
((TextView)v).setTypeface(font);
else if(v instanceof ViewGroup)
setFont((ViewGroup)v, font);
}
}
Se gli passi la radice del tuo layout, controllerà ricorsivamente TextView
o vedrà Button
(o qualsiasi altra cosa che aggiungi a quell'istruzione if) all'interno di quel layout e imposterà il carattere senza che tu debba specificarli per ID. Questo ovviamente presuppone che tu voglia impostare il carattere per ogni vista.