sequence

The use of custom fonts on Android has been a common requirement and has recently been studied in depth.

I was going to write another article about Android font modification, but there was a lot to write, so I decided to break it down into several articles (maybe five). There will be some common Fonts replacement solutions, and finally some global Fonts replacement solutions, including the latest “Fonts in XML” solution.

I look forward to your continued attention.

This is the second in a series of posts that have already been published.

  • Android font change overview | opening

A, the opening

If you want to manipulate fonts, either using Android fonts or loading your own built-in.ttf(TureType) or.otf(OpenType) font files, you need to use Typeface.

This article takes a look at some of the source details of Typeface in isolation. This article may be a bit more boring in this series, but I think it’s an integral part of it, so I’ve covered it in a separate article.

Load a Typeface

Typeface details, to talk about the content is quite a lot, listen to me carefully.

2.1 Load fonts through AssetManager

Typeface. CreateFromAsset () is a Typeface object that can be retrieved by placing the required built-in font files in assets.

For example, now put a font.ttf file in the assets/fonts directory of your project.

/f-path.png

We can then load it when we need it, which is also a fairly common piece of code.

/f-createfont.png

Continue with the createFromAsset() source code.

/f-createassets.png

The code is simple and the logic is clear.

SFallbackFonts can’t be null, otherwise it will throw an exception. SFallbackFonts is not important, but I’ll talk about that later.

It relies on sDynamicTypefaceCache to keep threads safe. And createAssetUid() is used to retrieve the unique key for the font. With this unique key, the loaded font is retrieved from sDynamicTypefaceCache, and if not, a FontFamily object is created. Through FontFamily. AddFontFromAsset () method, which will join in this font file, finally through createFromFamiliesWithDefault (), create a font directly, Finally, it’s stored in sDynamicTypefaceCache as a cache.

CreateFromFamiliesWithDefault () method need to pass an array of FontFamily, itself also only will these FontFamily represent common extracted, NativeCreateFromArray () is eventually called, so efficiency shouldn’t be too much of a problem.

This also shows that, in fact, the font stored in assets directory will have a cache once it is loaded through Typeface, and then it will only be retrieved from the cache, without affecting performance.

SDynamicTypefaceCache is a cache based on Lru algorithm that stores up to 16 fonts.

/f-sdyna.png

2.2 Loading fonts from the file path

In addition to loading font files from assets, Typeface can also load font files stored elsewhere and provides a convenient Api.

/f-createfromfile.png

Finally, the font file is loaded through the absolute path, which is also easy to understand logic. As is the use of FontFamily, is to use as the createFromFamilyWithDefault ().

There is nothing new in these, so I won’t go through them in detail.

2.3 Obtaining a Font by font Name

As we know, Typeface can also manage some of the fonts that come with Android, and these fonts can also be loaded through Typeface if you want to retrieve them by passing in their names.

/f-createname.png

TextStyle is used to set the font parameters such as bold, italic, and so on.

This method, in fact, ends up calling an overload of another create() method, which we’ll explain in more detail later. It’s singled out because it involves a sSystemFontMap object.

SSystemFontMap is initialized in Typeface’s initialization method init().

/f-init.jpg

As you can see, it is actually through getSystemFontConfigLocation (), read the font file of local support, then load them at once, for the use of directly behind.

/f-getSystemFont.png

Uphold the tradition of the Linux, all configuration, are written in the file, it is read from the file directly, getSystemFontConfigLocation () method to get the path of the just a configuration, The fonts.xml file of the FONTS_CONFIG configuration is finally read.

2.4 Obtain a new Typeface through Typeface

This brings us to the aforementioned create() method, which passes in a Typeface object and appends a new effect to the original Typeface font class by setting the style.

/f-createtypeface.png

And this process does not require us to worry about efficiency. It also provides a sTypefaceCache cache for the system default fonts we used.

Other details of Typeface

This is basically enough to cover Typeface usage, but there are a few other details that can be singled out for additional explanation.

3.1 Initialization of Typeface

Typeface initialization is placed in a static block of code that initializes some commonly used system default fonts and stores them for easy use.

/f-static.png

The init() method is called to load the system’s native fonts and then initialize a series of native fonts, such as DEFAULT and SNAS_SERIF.

So if we just need to get a native font, just use some of the constant fonts initialized here.

It also defaults the DEFAULT font to an array of sDefaults, which preloads common styles like bold and italic.

Typeface also provides corresponding methods if you want to use it.

/f-defaultStyle.png

3.2 Typeface 中的 Style

The concept of Style has been mentioned before, which can be set through the Android :textStyle property, including bold, italic, etc.

In Typeface, these styles correspond to constants, and Typeface provides an Api to retrieve the current font style.

/f-fontStyle.png

3.3 Native methods in Typeface

In Typeface, all final operations to load fonts are native methods. Native methods are known for their efficiency, so you only need to ensure infrequent calls (Typeface is already cached and not frequently called), and basically there is no problem with efficiency.

/f-native.png

3.4 A brief introduction to FontFamily

FontFamily is used in many of the previous methods. It actually reads the data stream of the font file, and then loads the font via native method.

/f-addfont.png

The addFont() method, for example, takes the FileInputStream object, converts it into a ByteBuffer, and passes it to the native method nAddFont() to load the font.

This object, you can understand, there is no too complicated logic.

Four, summary

Now that I’ve covered all the contents of Typeface, I’m ready to use Typeface after reading this article.

To sum up:

  1. Typeface offers a range ofcreateXxx()Method is used to load fonts from different places.
  2. Typeface supports loading fonts from default fonts, font files, and assets.
  3. Typeface already supports font caching, so you don’t need to cache it again.
  4. Typeface ultimately calls native methods, so there are no efficiency issues.

The next trailer

In the next installment, we’ll look at some rough ways to replace global fonts. Some are on new projects, some are on existing mature projects. Looking forward to your continued attention.

In addition, there is a share about job-hopping recently, and I have some exclusive preferential activities here. If you’re interested, check out How I Got Offers from Hundreds of millions of App users.

Qr code. JPG

Like it or share it