| /* |
| * Copyright 2022 The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| package androidx.compose.ui.text.style |
| |
| import androidx.compose.ui.text.PlatformParagraphStyle |
| |
| /** |
| * The configuration for line height such as alignment of the line in the provided line height, |
| * whether to apply additional space as a result of line height to top of first line top and |
| * bottom of last line. |
| * |
| * The configuration is applied only when a line height is defined on the text. |
| * |
| * [trim] feature is available only when [PlatformParagraphStyle.includeFontPadding] is false. |
| * |
| * Please check [Trim] and [Alignment] for more description. |
| * |
| * @param alignment defines how to align the line in the space provided by the line height. |
| * @param trim defines whether the space that would be added to the top of first line, and |
| * bottom of the last line should be trimmed or not. This feature is available only when |
| * [PlatformParagraphStyle.includeFontPadding] is false. |
| */ |
| class LineHeightStyle( |
| val alignment: Alignment, |
| val trim: Trim |
| ) { |
| companion object { |
| /** |
| * The default configuration for [LineHeightStyle]: |
| * - alignment = [Alignment.Proportional] |
| * - trim = [Trim.Both] |
| */ |
| val Default = LineHeightStyle( |
| alignment = Alignment.Proportional, |
| trim = Trim.Both |
| ) |
| } |
| |
| override fun equals(other: Any?): Boolean { |
| if (this === other) return true |
| if (other !is LineHeightStyle) return false |
| |
| if (alignment != other.alignment) return false |
| if (trim != other.trim) return false |
| |
| return true |
| } |
| |
| override fun hashCode(): Int { |
| var result = alignment.hashCode() |
| result = 31 * result + trim.hashCode() |
| return result |
| } |
| |
| override fun toString(): String { |
| return "LineHeightStyle(" + |
| "alignment=$alignment, " + |
| "trim=$trim" + |
| ")" |
| } |
| |
| /** |
| * Defines whether the space that would be added to the top of first line, and bottom of the |
| * last line should be trimmed or not. This feature is available only when |
| * [PlatformParagraphStyle.includeFontPadding] is false. |
| */ |
| @kotlin.jvm.JvmInline |
| value class Trim private constructor(private val value: Int) { |
| |
| override fun toString(): String { |
| return when (value) { |
| FirstLineTop.value -> "LineHeightStyle.Trim.FirstLineTop" |
| LastLineBottom.value -> "LineHeightStyle.Trim.LastLineBottom" |
| Both.value -> "LineHeightStyle.Trim.Both" |
| None.value -> "LineHeightStyle.Trim.None" |
| else -> "Invalid" |
| } |
| } |
| |
| companion object { |
| private const val FlagTrimTop = 0x00000001 |
| private const val FlagTrimBottom = 0x00000010 |
| |
| /** |
| * Trim the space that would be added to the top of the first line as a result of the |
| * line height. Single line text is both the first and last line. This feature is |
| * available only when [PlatformParagraphStyle.includeFontPadding] is false. |
| * |
| * For example, when line height is 3.em, and [Alignment] is |
| * [Alignment.Center], the first line has 2.em height and the height from |
| * first line baseline to second line baseline is still 3.em: |
| * <pre> |
| * +--------+ |
| * | Line1 | |
| * | | |
| * |--------| |
| * | | |
| * | Line2 | |
| * | | |
| * +--------+ |
| * </pre> |
| */ |
| val FirstLineTop = Trim(FlagTrimTop) |
| |
| /** |
| * Trim the space that would be added to the bottom of the last line as a result of the |
| * line height. Single line text is both the first and last line. This feature is |
| * available only when [PlatformParagraphStyle.includeFontPadding] is false. |
| * |
| * For example, when line height is 3.em, and [Alignment] is |
| * [Alignment.Center], the last line has 2.em height and the height from |
| * first line baseline to second line baseline is still 3.em: |
| * <pre> |
| * +--------+ |
| * | | |
| * | Line1 | |
| * | | |
| * |--------| |
| * | | |
| * | Line2 | |
| * +--------+ |
| * </pre> |
| */ |
| val LastLineBottom = Trim(FlagTrimBottom) |
| |
| /** |
| * Trim the space that would be added to the top of the first line and bottom of the last |
| * line as a result of the line height. This feature is available only when |
| * [PlatformParagraphStyle.includeFontPadding] is false. |
| * |
| * For example, when line height is 3.em, and [Alignment] is |
| * [Alignment.Center], the first and last line has 2.em height and the height |
| * from first line baseline to second line baseline is still 3.em: |
| * <pre> |
| * +--------+ |
| * | Line1 | |
| * | | |
| * |--------| |
| * | | |
| * | Line2 | |
| * +--------+ |
| * </pre> |
| */ |
| val Both = Trim(FlagTrimTop or FlagTrimBottom) |
| |
| /** |
| * Do not trim first line top or last line bottom. |
| * |
| * For example, when line height is 3.em, and [Alignment] is |
| * [Alignment.Center], the first line height, last line height and the height |
| * from first line baseline to second line baseline are 3.em: |
| * <pre> |
| * +--------+ |
| * | | |
| * | Line1 | |
| * | | |
| * |--------| |
| * | | |
| * | Line2 | |
| * | | |
| * +--------+ |
| * </pre> |
| */ |
| val None = Trim(0) |
| } |
| |
| internal fun isTrimFirstLineTop(): Boolean { |
| return value and FlagTrimTop > 0 |
| } |
| |
| internal fun isTrimLastLineBottom(): Boolean { |
| return value and FlagTrimBottom > 0 |
| } |
| } |
| |
| /** |
| * Defines how to align the line in the space provided by the line height. |
| * |
| * @param topRatio the ratio of ascent to ascent+descent in percentage. Valid values are |
| * between 0f (inclusive) and 1f (inclusive). |
| */ |
| @kotlin.jvm.JvmInline |
| value class Alignment constructor(internal val topRatio: Float) { |
| |
| init { |
| check(topRatio in 0f..1f || topRatio == -1f) { |
| "topRatio should be in [0..1] range or -1" |
| } |
| } |
| |
| override fun toString(): String { |
| return when (topRatio) { |
| Top.topRatio -> "LineHeightStyle.Alignment.Top" |
| Center.topRatio -> "LineHeightStyle.Alignment.Center" |
| Proportional.topRatio -> "LineHeightStyle.Alignment.Proportional" |
| Bottom.topRatio -> "LineHeightStyle.Alignment.Bottom" |
| else -> "LineHeightStyle.Alignment(topPercentage = $topRatio)" |
| } |
| } |
| |
| companion object { |
| /** |
| * Align the line to the top of the space reserved for that line. This means that all extra |
| * space as a result of line height is applied to the bottom of the line. When the provided |
| * line height value is smaller than the actual line height, the line will still be aligned |
| * to the top, therefore the required difference will be subtracted from the bottom of the |
| * line. |
| * |
| * For example, when line height is 3.em, the lines are aligned to the top of 3.em |
| * height: |
| * <pre> |
| * +--------+ |
| * | Line1 | |
| * | | |
| * | | |
| * |--------| |
| * | Line2 | |
| * | | |
| * | | |
| * +--------+ |
| * </pre> |
| */ |
| val Top = Alignment(topRatio = 0f) |
| |
| /** |
| * Align the line to the center of the space reserved for the line. This configuration |
| * distributes additional space evenly between top and bottom of the line. |
| * |
| * For example, when line height is 3.em, the lines are aligned to the center of 3.em |
| * height: |
| * <pre> |
| * +--------+ |
| * | | |
| * | Line1 | |
| * | | |
| * |--------| |
| * | | |
| * | Line2 | |
| * | | |
| * +--------+ |
| * </pre> |
| */ |
| val Center = Alignment(topRatio = 0.5f) |
| |
| /** |
| * Align the line proportional to the ascent and descent values of the line. For example |
| * if ascent is 8 units of length, and descent is 2 units; an additional space of 10 units |
| * will be distributed as 8 units to top, and 2 units to the bottom of the line. This is |
| * the default behavior. |
| */ |
| val Proportional = Alignment(topRatio = -1f) |
| |
| /** |
| * Align the line to the bottom of the space reserved for that line. This means that all |
| * extra space as a result of line height is applied to the top of the line. When the |
| * provided line height value is smaller than the actual line height, the line will still |
| * be aligned to the bottom, therefore the required difference will be subtracted from the |
| * top of the line. |
| * |
| * For example, when line height is 3.em, the lines are aligned to the bottom of 3.em |
| * height: |
| * <pre> |
| * +--------+ |
| * | | |
| * | | |
| * | Line1 | |
| * |--------| |
| * | | |
| * | | |
| * | Line2 | |
| * +--------+ |
| * </pre> |
| */ |
| val Bottom = Alignment(topRatio = 1f) |
| } |
| } |
| } |