mirror of
https://github.com/status-im/react-native.git
synced 2025-02-11 00:46:32 +00:00
Add support for shadows to RCTVirtualText
Summary: React provides properties to support shadows for Text, this diff implements it for Nodes. Reviewed By: ahmedre Differential Revision: D2817212
This commit is contained in:
parent
f98a288c2a
commit
76abec8894
@ -16,6 +16,7 @@ import android.text.Spannable;
|
|||||||
import android.text.SpannableStringBuilder;
|
import android.text.SpannableStringBuilder;
|
||||||
import android.text.TextUtils;
|
import android.text.TextUtils;
|
||||||
|
|
||||||
|
import com.facebook.react.bridge.ReadableMap;
|
||||||
import com.facebook.react.uimanager.PixelUtil;
|
import com.facebook.react.uimanager.PixelUtil;
|
||||||
import com.facebook.react.uimanager.annotations.ReactProp;
|
import com.facebook.react.uimanager.annotations.ReactProp;
|
||||||
import com.facebook.react.uimanager.ViewProps;
|
import com.facebook.react.uimanager.ViewProps;
|
||||||
@ -29,7 +30,13 @@ import com.facebook.react.uimanager.ViewProps;
|
|||||||
private static final String ITALIC = "italic";
|
private static final String ITALIC = "italic";
|
||||||
private static final String NORMAL = "normal";
|
private static final String NORMAL = "normal";
|
||||||
|
|
||||||
|
private static final String PROP_SHADOW_OFFSET = "textShadowOffset";
|
||||||
|
private static final String PROP_SHADOW_RADIUS = "textShadowRadius";
|
||||||
|
private static final String PROP_SHADOW_COLOR = "textShadowColor";
|
||||||
|
private static final int DEFAULT_TEXT_SHADOW_COLOR = 0x55000000;
|
||||||
|
|
||||||
private FontStylingSpan mFontStylingSpan = FontStylingSpan.INSTANCE;
|
private FontStylingSpan mFontStylingSpan = FontStylingSpan.INSTANCE;
|
||||||
|
private ShadowStyleSpan mShadowStyleSpan = ShadowStyleSpan.INSTANCE;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void performCollectText(SpannableStringBuilder builder) {
|
protected void performCollectText(SpannableStringBuilder builder) {
|
||||||
@ -49,6 +56,16 @@ import com.facebook.react.uimanager.ViewProps;
|
|||||||
end,
|
end,
|
||||||
Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
|
Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
|
||||||
|
|
||||||
|
if (mShadowStyleSpan.getColor() != 0 && mShadowStyleSpan.getRadius() != 0) {
|
||||||
|
mShadowStyleSpan.freeze();
|
||||||
|
|
||||||
|
builder.setSpan(
|
||||||
|
mShadowStyleSpan,
|
||||||
|
begin,
|
||||||
|
end,
|
||||||
|
Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0, childCount = getChildCount(); i < childCount; ++i) {
|
for (int i = 0, childCount = getChildCount(); i < childCount; ++i) {
|
||||||
FlatTextShadowNode child = (FlatTextShadowNode) getChildAt(i);
|
FlatTextShadowNode child = (FlatTextShadowNode) getChildAt(i);
|
||||||
child.applySpans(builder);
|
child.applySpans(builder);
|
||||||
@ -156,6 +173,42 @@ import com.facebook.react.uimanager.ViewProps;
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ReactProp(name = PROP_SHADOW_OFFSET)
|
||||||
|
public void setTextShadowOffset(@Nullable ReadableMap offsetMap) {
|
||||||
|
float dx = 0;
|
||||||
|
float dy = 0;
|
||||||
|
if (offsetMap != null) {
|
||||||
|
if (offsetMap.hasKey("width")) {
|
||||||
|
dx = PixelUtil.toPixelFromDIP(offsetMap.getDouble("width"));
|
||||||
|
}
|
||||||
|
if (offsetMap.hasKey("height")) {
|
||||||
|
dy = PixelUtil.toPixelFromDIP(offsetMap.getDouble("height"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!mShadowStyleSpan.offsetMatches(dx, dy)) {
|
||||||
|
getShadowSpan().setOffset(dx, dy);
|
||||||
|
notifyChanged(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@ReactProp(name = PROP_SHADOW_RADIUS)
|
||||||
|
public void setTextShadowRadius(float textShadowRadius) {
|
||||||
|
textShadowRadius = PixelUtil.toPixelFromDIP(textShadowRadius);
|
||||||
|
if (mShadowStyleSpan.getRadius() != textShadowRadius) {
|
||||||
|
getShadowSpan().setRadius(textShadowRadius);
|
||||||
|
notifyChanged(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@ReactProp(name = PROP_SHADOW_COLOR, defaultInt = DEFAULT_TEXT_SHADOW_COLOR, customType = "Color")
|
||||||
|
public void setTextShadowColor(int textShadowColor) {
|
||||||
|
if (mShadowStyleSpan.getColor() != textShadowColor) {
|
||||||
|
getShadowSpan().setColor(textShadowColor);
|
||||||
|
notifyChanged(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns font size for this node.
|
* Returns font size for this node.
|
||||||
* When called on RCTText, this value is never -1 (unset).
|
* When called on RCTText, this value is never -1 (unset).
|
||||||
@ -179,6 +232,13 @@ import com.facebook.react.uimanager.ViewProps;
|
|||||||
return mFontStylingSpan;
|
return mFontStylingSpan;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private final ShadowStyleSpan getShadowSpan() {
|
||||||
|
if (mShadowStyleSpan.isFrozen()) {
|
||||||
|
mShadowStyleSpan = mShadowStyleSpan.mutableCopy();
|
||||||
|
}
|
||||||
|
return mShadowStyleSpan;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return -1 if the input string is not a valid numeric fontWeight (100, 200, ..., 900), otherwise
|
* Return -1 if the input string is not a valid numeric fontWeight (100, 200, ..., 900), otherwise
|
||||||
* return the weight.
|
* return the weight.
|
||||||
|
@ -0,0 +1,74 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) 2015-present, Facebook, Inc.
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the BSD-style license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree. An additional grant
|
||||||
|
* of patent rights can be found in the PATENTS file in the same directory.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package com.facebook.react.flat;
|
||||||
|
|
||||||
|
import android.text.TextPaint;
|
||||||
|
import android.text.style.CharacterStyle;
|
||||||
|
|
||||||
|
/* package */ final class ShadowStyleSpan extends CharacterStyle {
|
||||||
|
|
||||||
|
/* package */ static final ShadowStyleSpan INSTANCE = new ShadowStyleSpan(0, 0, 0, 0, true);
|
||||||
|
|
||||||
|
private float mDx;
|
||||||
|
private float mDy;
|
||||||
|
private float mRadius;
|
||||||
|
private int mColor;
|
||||||
|
private boolean mFrozen;
|
||||||
|
|
||||||
|
private ShadowStyleSpan(float dx, float dy, float radius, int color, boolean frozen) {
|
||||||
|
mDx = dx;
|
||||||
|
mDy = dy;
|
||||||
|
mRadius = radius;
|
||||||
|
mColor = color;
|
||||||
|
mFrozen = frozen;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean offsetMatches(float dx, float dy) {
|
||||||
|
return mDx == dx && mDy == dy;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setOffset(float dx, float dy) {
|
||||||
|
mDx = dx;
|
||||||
|
mDy = dy;
|
||||||
|
}
|
||||||
|
|
||||||
|
public float getRadius() {
|
||||||
|
return mRadius;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setRadius(float radius) {
|
||||||
|
mRadius = radius;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getColor() {
|
||||||
|
return mColor;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setColor(int color) {
|
||||||
|
mColor = color;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* package */ ShadowStyleSpan mutableCopy() {
|
||||||
|
return new ShadowStyleSpan(mDx, mDy, mRadius, mColor, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* package */ boolean isFrozen() {
|
||||||
|
return mFrozen;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* package */ void freeze() {
|
||||||
|
mFrozen = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void updateDrawState(TextPaint textPaint) {
|
||||||
|
textPaint.setShadowLayer(mRadius, mDx, mDy, mColor);
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user