2 * Copyright (C) 2014 The Android Open Source Project
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
17 #define LOG_TAG "Minikin"
18 #include <cutils/log.h>
21 #include "SkPathMeasure.h"
23 #include "TypefaceImpl.h"
25 #include "MinikinUtils.h"
29 FontStyle MinikinUtils::prepareMinikinPaint(MinikinPaint* minikinPaint, FontCollection** pFont,
30 const Paint* paint, TypefaceImpl* typeface) {
31 const TypefaceImpl* resolvedFace = TypefaceImpl_resolveDefault(typeface);
32 *pFont = resolvedFace->fFontCollection;
33 FontStyle resolved = resolvedFace->fStyle;
35 /* Prepare minikin FontStyle */
36 const std::string& langs = paint->getTextLocales();
37 FontLanguages minikinLangs(langs.c_str(), langs.size());
38 FontVariant minikinVariant = (paint->getFontVariant() == VARIANT_ELEGANT) ? VARIANT_ELEGANT
40 FontStyle minikinStyle(minikinLangs, minikinVariant, resolved.getWeight(), resolved.getItalic());
42 /* Prepare minikin Paint */
43 // Note: it would be nice to handle fractional size values (it would improve smooth zoom
44 // behavior), but historically size has been treated as an int.
45 // TODO: explore whether to enable fractional sizes, possibly when linear text flag is set.
46 minikinPaint->size = (int)paint->getTextSize();
47 minikinPaint->scaleX = paint->getTextScaleX();
48 minikinPaint->skewX = paint->getTextSkewX();
49 minikinPaint->letterSpacing = paint->getLetterSpacing();
50 minikinPaint->paintFlags = MinikinFontSkia::packPaintFlags(paint);
51 minikinPaint->fontFeatureSettings = paint->getFontFeatureSettings();
52 minikinPaint->hyphenEdit = HyphenEdit(paint->getHyphenEdit());
56 void MinikinUtils::doLayout(Layout* layout, const Paint* paint, int bidiFlags,
57 TypefaceImpl* typeface, const uint16_t* buf, size_t start, size_t count,
60 MinikinPaint minikinPaint;
61 FontStyle minikinStyle = prepareMinikinPaint(&minikinPaint, &font, paint, typeface);
62 layout->setFontCollection(font);
63 layout->doLayout(buf, start, count, bufSize, bidiFlags, minikinStyle, minikinPaint);
66 bool MinikinUtils::hasVariationSelector(TypefaceImpl* typeface, uint32_t codepoint, uint32_t vs) {
67 const TypefaceImpl* resolvedFace = TypefaceImpl_resolveDefault(typeface);
68 return resolvedFace->fFontCollection->hasVariationSelector(codepoint, vs);
71 float MinikinUtils::xOffsetForTextAlign(Paint* paint, const Layout& layout) {
72 switch (paint->getTextAlign()) {
73 case Paint::kCenter_Align:
74 return layout.getAdvance() * -0.5f;
76 case Paint::kRight_Align:
77 return -layout.getAdvance();
85 float MinikinUtils::hOffsetForTextAlign(Paint* paint, const Layout& layout, const SkPath& path) {
87 switch (paint->getTextAlign()) {
88 case Paint::kCenter_Align:
91 case Paint::kRight_Align:
97 SkPathMeasure measure(path, false);
98 return align * (layout.getAdvance() - measure.getLength());