mirror of
https://gitee.com/openharmony/arkui_ace_engine
synced 2024-11-23 07:01:24 +00:00
commit
5a9bacccc1
@ -94,13 +94,6 @@ std::string SpanToHtml::ColorToHtml(const std::optional<Color>& value)
|
||||
return ToHtmlStyleFormat("color", color);
|
||||
}
|
||||
|
||||
std::string SpanToHtml::ColorToHtml(const std::optional<DynamicColor>& value)
|
||||
{
|
||||
auto color = value.value_or(DynamicColor(Color::BLACK)).ToColor().ColorToString();
|
||||
ToHtmlColor(color);
|
||||
return ToHtmlStyleFormat("color", color);
|
||||
}
|
||||
|
||||
std::string SpanToHtml::FontFamilyToHtml(const std::optional<std::vector<std::string>>& value)
|
||||
{
|
||||
return ToHtmlStyleFormat("font-family", GetFontFamilyInJson(value));
|
||||
|
@ -31,7 +31,6 @@ private:
|
||||
static std::string FontSizeToHtml(const std::optional<Dimension>& value);
|
||||
static std::string FontWeightToHtml(const std::optional<FontWeight>& value);
|
||||
static std::string ColorToHtml(const std::optional<Color>& value);
|
||||
static std::string ColorToHtml(const std::optional<DynamicColor>& value);
|
||||
static std::string FontFamilyToHtml(const std::optional<std::vector<std::string>>& value);
|
||||
static std::string TextDecorationToHtml(TextDecoration decoration);
|
||||
static std::string TextDecorationStyleToHtml(TextDecorationStyle decorationStyle);
|
||||
|
@ -79,7 +79,6 @@
|
||||
OHOS::Ace::ResourceWrapper::*;
|
||||
OHOS::Ace::NG::AppBarView::*;
|
||||
OHOS::Ace::Color::*;
|
||||
OHOS::Ace::DynamicColor::*;
|
||||
OHOS::Ace::NG::UIObserverHandler::*;
|
||||
OHOS::Ace::UIDisplaySync::*;
|
||||
OHOS::Ace::Dimension::*;
|
||||
|
@ -813,6 +813,7 @@ void JSRichEditor::SetTextChangeSpanResult(JSRef<JSObject>& resultObj,
|
||||
void JSRichEditor::SetSymbolChangeSpanResult(JSRef<JSObject>& resultObj,
|
||||
const NG::RichEditorAbstractSpanResult& spanResult)
|
||||
{
|
||||
resultObj->SetProperty<std::string>("value", spanResult.GetValue());
|
||||
resultObj->SetPropertyObject("symbolSpanStyle", CreateJSSymbolSpanStyleResult(spanResult.GetSymbolSpanStyle()));
|
||||
resultObj->SetPropertyObject("valueResource", CreateJSValueResource(spanResult.GetValueResource()));
|
||||
resultObj->SetPropertyObject("paragraphStyle", CreateJSParagraphStyle(spanResult.GetTextStyle()));
|
||||
@ -1093,7 +1094,7 @@ void JSRichEditor::SetPlaceholder(const JSCallbackInfo& info)
|
||||
JSRef<JSVal> colorVal = object->GetProperty("fontColor");
|
||||
Color fontColor;
|
||||
if (!colorVal->IsNull() && JSContainerBase::ParseJsColor(colorVal, fontColor)) {
|
||||
options.fontColor = DynamicColor(fontColor, ParseColorResourceId(colorVal));
|
||||
options.fontColor = fontColor;
|
||||
}
|
||||
}
|
||||
auto textTheme = pipelineContext->GetTheme<TextTheme>();
|
||||
@ -1175,18 +1176,15 @@ void JSRichEditor::SetCaretColor(const JSCallbackInfo& info)
|
||||
return;
|
||||
}
|
||||
Color color;
|
||||
DynamicColor dynamicColor;
|
||||
JSRef<JSVal> colorVal = info[0];
|
||||
if (!ParseJsColor(colorVal, color)) {
|
||||
auto pipeline = PipelineBase::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipeline);
|
||||
auto theme = pipeline->GetThemeManager()->GetTheme<NG::RichEditorTheme>();
|
||||
CHECK_NULL_VOID(theme);
|
||||
dynamicColor = theme->GetCaretColor();
|
||||
} else {
|
||||
dynamicColor = DynamicColor(color, ParseColorResourceId(colorVal));
|
||||
color = theme->GetCaretColor();
|
||||
}
|
||||
RichEditorModel::GetInstance()->SetCaretColor(dynamicColor);
|
||||
RichEditorModel::GetInstance()->SetCaretColor(color);
|
||||
}
|
||||
|
||||
void JSRichEditor::SetSelectedBackgroundColor(const JSCallbackInfo& info)
|
||||
@ -1196,18 +1194,15 @@ void JSRichEditor::SetSelectedBackgroundColor(const JSCallbackInfo& info)
|
||||
return;
|
||||
}
|
||||
Color selectedColor;
|
||||
DynamicColor dynamicSelectedColor;
|
||||
JSRef<JSVal> colorVal = info[0];
|
||||
if (!ParseJsColor(colorVal, selectedColor)) {
|
||||
auto pipeline = PipelineBase::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipeline);
|
||||
auto theme = pipeline->GetThemeManager()->GetTheme<NG::RichEditorTheme>();
|
||||
CHECK_NULL_VOID(theme);
|
||||
dynamicSelectedColor = theme->GetSelectedBackgroundColor();
|
||||
} else {
|
||||
dynamicSelectedColor = DynamicColor(selectedColor, ParseColorResourceId(colorVal));
|
||||
selectedColor = theme->GetSelectedBackgroundColor();
|
||||
}
|
||||
RichEditorModel::GetInstance()->SetSelectedBackgroundColor(dynamicSelectedColor);
|
||||
RichEditorModel::GetInstance()->SetSelectedBackgroundColor(selectedColor);
|
||||
}
|
||||
|
||||
void JSRichEditor::SetEnterKeyType(const JSCallbackInfo& info)
|
||||
@ -1272,18 +1267,6 @@ void JSRichEditor::SetOnSubmit(const JSCallbackInfo& info)
|
||||
CreateJsRichEditorCommonEvent(info);
|
||||
}
|
||||
|
||||
std::optional<uint32_t> JSRichEditor::ParseColorResourceId(JSRef<JSVal> colorVal)
|
||||
{
|
||||
CHECK_NULL_RETURN(colorVal->IsObject(), std::nullopt);
|
||||
JSRef<JSObject> jsObj = JSRef<JSObject>::Cast(colorVal);
|
||||
JSViewAbstract::CompleteResourceObject(jsObj);
|
||||
JSRef<JSVal> resId = jsObj->GetProperty("id");
|
||||
CHECK_NULL_RETURN(resId->IsNumber(), std::nullopt);
|
||||
auto type = jsObj->GetPropertyValue<int32_t>("type", -1);
|
||||
CHECK_NULL_RETURN(type == static_cast<int32_t>(ResourceType::COLOR), std::nullopt);
|
||||
return resId->ToNumber<uint32_t>();
|
||||
}
|
||||
|
||||
void JSRichEditor::SetEnableKeyboardOnFocus(const JSCallbackInfo& info)
|
||||
{
|
||||
CHECK_NULL_VOID(info.Length() > 0);
|
||||
@ -1295,6 +1278,28 @@ void JSRichEditor::SetEnableKeyboardOnFocus(const JSCallbackInfo& info)
|
||||
RichEditorModel::GetInstance()->SetRequestKeyboardOnFocus(jsValue->ToBoolean());
|
||||
}
|
||||
|
||||
void JSRichEditor::SetEnableHapticFeedback(const JSCallbackInfo& info)
|
||||
{
|
||||
CHECK_NULL_VOID(info.Length() > 0);
|
||||
auto jsValue = info[0];
|
||||
if (jsValue->IsUndefined() || !jsValue->IsBoolean()) {
|
||||
RichEditorModel::GetInstance()->SetEnableHapticFeedback(true);
|
||||
return;
|
||||
}
|
||||
RichEditorModel::GetInstance()->SetEnableHapticFeedback(jsValue->ToBoolean());
|
||||
}
|
||||
|
||||
void JSRichEditor::SetBarState(const JSCallbackInfo& info)
|
||||
{
|
||||
CHECK_NULL_VOID(info.Length() > 0);
|
||||
auto jsValue = info[0];
|
||||
CHECK_NULL_VOID(!jsValue->IsUndefined() && jsValue->IsNumber());
|
||||
int32_t barState = jsValue->ToNumber<int32_t>();
|
||||
CHECK_NULL_VOID(barState >= static_cast<int32_t>(DisplayMode::OFF));
|
||||
CHECK_NULL_VOID(barState <= static_cast<int32_t>(DisplayMode::ON));
|
||||
RichEditorModel::GetInstance()->SetBarState(static_cast<DisplayMode>(barState));
|
||||
}
|
||||
|
||||
void JSRichEditor::JSBind(BindingTarget globalObj)
|
||||
{
|
||||
JSClass<JSRichEditor>::Declare("RichEditor");
|
||||
@ -1336,6 +1341,8 @@ void JSRichEditor::JSBind(BindingTarget globalObj)
|
||||
JSClass<JSRichEditor>::StaticMethod("onCopy", &JSRichEditor::SetOnCopy);
|
||||
JSClass<JSRichEditor>::StaticMethod("editMenuOptions", &JSRichEditor::EditMenuOptions);
|
||||
JSClass<JSRichEditor>::StaticMethod("enableKeyboardOnFocus", &JSRichEditor::SetEnableKeyboardOnFocus);
|
||||
JSClass<JSRichEditor>::StaticMethod("enableHapticFeedback", &JSRichEditor::SetEnableHapticFeedback);
|
||||
JSClass<JSRichEditor>::StaticMethod("barState", &JSRichEditor::SetBarState);
|
||||
JSClass<JSRichEditor>::InheritAndBind<JSViewAbstract>(globalObj);
|
||||
}
|
||||
|
||||
@ -1397,19 +1404,17 @@ void JSRichEditorController::ParseJsSymbolSpanStyle(
|
||||
const JSRef<JSObject>& styleObject, TextStyle& style, struct UpdateSpanStyle& updateSpanStyle)
|
||||
{
|
||||
ContainerScope scope(instanceId_ < 0 ? Container::CurrentId() : instanceId_);
|
||||
updateSpanStyle.isSymbolStyle = true;
|
||||
JSRef<JSVal> fontColor = styleObject->GetProperty("fontColor");
|
||||
std::vector<Color> symbolColor;
|
||||
if (!fontColor->IsNull() && JSContainerBase::ParseJsSymbolColor(fontColor, symbolColor)) {
|
||||
updateSpanStyle.updateSymbolColor = symbolColor;
|
||||
style.SetSymbolColorList(symbolColor);
|
||||
updateSpanStyle.useThemeFontColor = false;
|
||||
}
|
||||
JSRef<JSVal> fontSize = styleObject->GetProperty("fontSize");
|
||||
CalcDimension size;
|
||||
if (!fontSize->IsNull() && JSContainerBase::ParseJsDimensionFpNG(fontSize, size, false) &&
|
||||
!FontSizeRangeIsNegative(size) && size.Unit() != DimensionUnit::PERCENT) {
|
||||
updateSpanStyle.updateFontSize = size;
|
||||
updateSpanStyle.updateSymbolFontSize = size;
|
||||
style.SetFontSize(size);
|
||||
} else if (FontSizeRangeIsNegative(size) || size.Unit() == DimensionUnit::PERCENT) {
|
||||
auto theme = JSContainerBase::GetTheme<TextTheme>();
|
||||
@ -1417,15 +1422,13 @@ void JSRichEditorController::ParseJsSymbolSpanStyle(
|
||||
size = theme->GetTextStyle().GetFontSize();
|
||||
style.SetFontSize(size);
|
||||
}
|
||||
ParseJsLineHeightLetterSpacingTextStyle(styleObject, style, updateSpanStyle, true);
|
||||
ParseJsFontFeatureTextStyle(styleObject, style, updateSpanStyle);
|
||||
JSRef<JSVal> fontWeight = styleObject->GetProperty("fontWeight");
|
||||
std::string weight;
|
||||
if (!fontWeight->IsNull() && (fontWeight->IsNumber() || JSContainerBase::ParseJsString(fontWeight, weight))) {
|
||||
if (fontWeight->IsNumber()) {
|
||||
weight = std::to_string(fontWeight->ToNumber<int32_t>());
|
||||
}
|
||||
updateSpanStyle.updateFontWeight = ConvertStrToFontWeight(weight);
|
||||
updateSpanStyle.updateSymbolFontWeight = ConvertStrToFontWeight(weight);
|
||||
style.SetFontWeight(ConvertStrToFontWeight(weight));
|
||||
}
|
||||
JSRef<JSVal> renderingStrategy = styleObject->GetProperty("renderingStrategy");
|
||||
@ -1441,7 +1444,7 @@ void JSRichEditorController::ParseJsSymbolSpanStyle(
|
||||
JSRef<JSVal> effectStrategy = styleObject->GetProperty("effectStrategy");
|
||||
uint32_t symbolEffectStrategy;
|
||||
if (!effectStrategy->IsNull() && JSContainerBase::ParseJsInteger(effectStrategy, symbolEffectStrategy)) {
|
||||
updateSpanStyle.updateSymbolEffectStrategy = symbolEffectStrategy;
|
||||
updateSpanStyle.updateSymbolEffectStrategy = 0;
|
||||
style.SetEffectStrategy(0);
|
||||
}
|
||||
}
|
||||
@ -2036,12 +2039,6 @@ bool JSRichEditorController::ParseParagraphStyle(const JSRef<JSObject>& styleObj
|
||||
CalcDimension height;
|
||||
JSContainerBase::ParseJsDimensionVp(widthVal, width);
|
||||
JSContainerBase::ParseJsDimensionVp(heightVal, height);
|
||||
if (width.Unit() == DimensionUnit::PERCENT) {
|
||||
width = Dimension(0.0);
|
||||
}
|
||||
if (height.Unit() == DimensionUnit::PERCENT) {
|
||||
height = Dimension(0.0);
|
||||
}
|
||||
style.leadingMargin->size = NG::LeadingMarginSize(width, height);
|
||||
} else if (sizeVal->IsUndefined()) {
|
||||
std::string resWidthStr;
|
||||
@ -2089,7 +2086,8 @@ void JSRichEditorController::UpdateSpanStyle(const JSCallbackInfo& info)
|
||||
imageStyle = ParseJsImageSpanAttribute(richEditorImageStyle);
|
||||
}
|
||||
if (!richEditorSymbolSpanStyle->IsUndefined()) {
|
||||
ParseJsSymbolSpanStyle(richEditorSymbolSpanStyle, textStyle, updateSpanStyle_);
|
||||
TextStyle symbolTextStyle;
|
||||
ParseJsSymbolSpanStyle(richEditorSymbolSpanStyle, symbolTextStyle, updateSpanStyle_);
|
||||
}
|
||||
|
||||
auto controller = controllerWeak_.Upgrade();
|
||||
@ -2242,9 +2240,9 @@ void JSRichEditorBaseController::ParseJsTextStyle(
|
||||
JSRef<JSVal> fontColor = styleObject->GetProperty("fontColor");
|
||||
Color textColor;
|
||||
if (!fontColor->IsNull() && JSContainerBase::ParseJsColor(fontColor, textColor)) {
|
||||
DynamicColor dynamicColor = DynamicColor(textColor, JSRichEditor::ParseColorResourceId(fontColor));
|
||||
style.SetTextColor(dynamicColor);
|
||||
updateSpanStyle.updateTextColor = dynamicColor;
|
||||
style.SetTextColor(textColor);
|
||||
updateSpanStyle.updateTextColor = textColor;
|
||||
updateSpanStyle.useThemeFontColor = false;
|
||||
}
|
||||
JSRef<JSVal> fontSize = styleObject->GetProperty("fontSize");
|
||||
CalcDimension size;
|
||||
@ -2362,9 +2360,8 @@ void JSRichEditorBaseController::ParseTextDecoration(
|
||||
JSRef<JSVal> color = decorationObject->GetProperty("color");
|
||||
Color decorationColor;
|
||||
if (!color->IsNull() && JSContainerBase::ParseJsColor(color, decorationColor)) {
|
||||
DynamicColor dynamicColor = DynamicColor(decorationColor, JSRichEditor::ParseColorResourceId(color));
|
||||
updateSpanStyle.updateTextDecorationColor = dynamicColor;
|
||||
style.SetTextDecorationColor(dynamicColor);
|
||||
updateSpanStyle.updateTextDecorationColor = decorationColor;
|
||||
style.SetTextDecorationColor(decorationColor);
|
||||
updateSpanStyle.useThemeDecorationColor = false;
|
||||
}
|
||||
JSRef<JSVal> textDecorationStyle = decorationObject->GetProperty("style");
|
||||
@ -2373,10 +2370,11 @@ void JSRichEditorBaseController::ParseTextDecoration(
|
||||
static_cast<TextDecorationStyle>(textDecorationStyle->ToNumber<int32_t>());
|
||||
style.SetTextDecorationStyle(static_cast<TextDecorationStyle>(textDecorationStyle->ToNumber<int32_t>()));
|
||||
}
|
||||
updateSpanStyle.isInitDecoration = true;
|
||||
}
|
||||
if (!updateSpanStyle.updateTextDecorationColor.has_value() && updateSpanStyle.updateTextColor.has_value()) {
|
||||
updateSpanStyle.updateTextDecorationColor = style.GetDynamicTextColor();
|
||||
style.SetTextDecorationColor(style.GetDynamicTextColor());
|
||||
updateSpanStyle.updateTextDecorationColor = style.GetTextColor();
|
||||
style.SetTextDecorationColor(style.GetTextColor());
|
||||
}
|
||||
}
|
||||
|
||||
@ -2401,7 +2399,8 @@ void JSRichEditorBaseController::GetTypingStyle(const JSCallbackInfo& info)
|
||||
ContainerScope scope(instanceId_ < 0 ? Container::CurrentId() : instanceId_);
|
||||
auto controller = controllerWeak_.Upgrade();
|
||||
CHECK_NULL_VOID(controller);
|
||||
auto style = CreateTypingStyleResult(typingStyle_);
|
||||
auto typingStyle = controller->GetTypingStyle();
|
||||
auto style = CreateTypingStyleResult(typingStyle.value_or(UpdateSpanStyle()));
|
||||
info.SetReturnValue(JSRef<JSVal>::Cast(style));
|
||||
}
|
||||
|
||||
@ -2448,7 +2447,7 @@ JSRef<JSObject> JSRichEditorBaseController::CreateTypingStyleResult(const struct
|
||||
decorationObj->SetProperty<int32_t>("style",
|
||||
static_cast<int32_t>(typingStyle.updateTextDecorationStyle.value()));
|
||||
}
|
||||
if (typingStyle.updateTextDecoration.has_value() || typingStyle.updateTextDecorationColor.has_value()) {
|
||||
if (typingStyle.isInitDecoration) {
|
||||
tyingStyleObj->SetPropertyObject("decoration", decorationObj);
|
||||
}
|
||||
if (typingStyle.updateTextShadows.has_value()) {
|
||||
|
@ -78,10 +78,11 @@ public:
|
||||
static std::optional<NG::MarginProperty> ParseMarginAttr(JsiRef<JSVal> marginAttr);
|
||||
static CalcDimension ParseLengthMetrics(const JSRef<JSObject>& obj);
|
||||
static void EditMenuOptions(const JSCallbackInfo& info);
|
||||
static std::optional<uint32_t> ParseColorResourceId(JSRef<JSVal> colorVal);
|
||||
static void SetEnableKeyboardOnFocus(const JSCallbackInfo& info);
|
||||
static void SetEnableHapticFeedback(const JSCallbackInfo& info);
|
||||
static JSRef<JSArray> CreateJsTextShadowObjectArray(const TextStyleResult& textStyleResult);
|
||||
static JSRef<JSArray> CreateJsTextShadowObjectArray(const std::vector<Shadow>& textShadows);
|
||||
static void SetBarState(const JSCallbackInfo& info);
|
||||
private:
|
||||
static void CreateTextStyleObj(JSRef<JSObject>& textStyleObj, const NG::RichEditorAbstractSpanResult& spanResult);
|
||||
static void CreateImageStyleObj(JSRef<JSObject>& imageStyleObj, JSRef<JSObject>& spanResultObj,
|
||||
|
@ -5532,6 +5532,7 @@ bool JSViewAbstract::ParseJsObjColorFromResource(const JSRef<JSObject> &jsObj, C
|
||||
}
|
||||
if (type == static_cast<int32_t>(ResourceType::COLOR)) {
|
||||
result = resourceWrapper->GetColor(resId->ToNumber<uint32_t>());
|
||||
result.SetResourceId(resId->ToNumber<uint32_t>());
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
|
@ -38,8 +38,8 @@ class ACE_EXPORT RichEditorModelImpl : public RichEditorModel {
|
||||
void SetTextDetectEnable(bool value) override {}
|
||||
void SetSupportPreviewText(bool value) override {}
|
||||
void SetTextDetectConfig(const TextDetectConfig& textDetectConfig) override {}
|
||||
void SetSelectedBackgroundColor(const DynamicColor& selectedColor) override {}
|
||||
void SetCaretColor(const DynamicColor& color) override {}
|
||||
void SetSelectedBackgroundColor(const Color& selectedColor) override {}
|
||||
void SetCaretColor(const Color& color) override {}
|
||||
void SetOnEditingChange(std::function<void(const bool&)>&& func) override {}
|
||||
void SetOnSubmit(std::function<void(int32_t, NG::TextFieldCommonEvent&)>&& func) override {}
|
||||
void SetEnterKeyType(TextInputAction value) override {}
|
||||
|
@ -606,66 +606,15 @@ bool Color::IsOpacityValid(double value)
|
||||
return value >= MIN_RGBA_OPACITY && value <= MAX_RGBA_OPACITY;
|
||||
}
|
||||
|
||||
DynamicColor::DynamicColor(const Color& color)
|
||||
{
|
||||
SetValue(color.GetValue());
|
||||
}
|
||||
|
||||
DynamicColor::DynamicColor(const Color& color, std::optional<uint32_t> resId) : resourceId(resId)
|
||||
{
|
||||
SetValue(color.GetValue());
|
||||
}
|
||||
|
||||
DynamicColor::DynamicColor(const Color& color, uint32_t resId) : resourceId(resId)
|
||||
{
|
||||
SetValue(color.GetValue());
|
||||
}
|
||||
|
||||
void DynamicColor::UpdateColorByResourceId()
|
||||
void Color::UpdateColorByResourceId()
|
||||
{
|
||||
#ifndef ACE_UNITTEST
|
||||
CHECK_NULL_VOID(resourceId);
|
||||
CHECK_NULL_VOID(resourceId_ != 0);
|
||||
auto resourceAdapter = ResourceManager::GetInstance().GetResourceAdapter();
|
||||
CHECK_NULL_VOID(resourceAdapter);
|
||||
auto newColor = resourceAdapter->GetColor(resourceId.value());
|
||||
auto newColor = resourceAdapter->GetColor(resourceId_);
|
||||
SetValue(newColor.GetValue());
|
||||
#endif
|
||||
}
|
||||
|
||||
Color DynamicColor::ToColor() const
|
||||
{
|
||||
return Color(GetValue());
|
||||
}
|
||||
|
||||
std::string DynamicColor::ToString() const
|
||||
{
|
||||
std::string ret = "color=";
|
||||
ret += Color::ToString();
|
||||
ret += ", resourceId=";
|
||||
ret += resourceId ? std::to_string(resourceId.value()) : "nullopt";
|
||||
return ret;
|
||||
}
|
||||
|
||||
DynamicColor& DynamicColor::operator=(const Color& rhs)
|
||||
{
|
||||
SetValue(rhs.GetValue());
|
||||
return *this;
|
||||
}
|
||||
|
||||
bool DynamicColor::operator==(const DynamicColor& rhs) const
|
||||
{
|
||||
if (this->GetValue() != rhs.GetValue()) {
|
||||
return false;
|
||||
}
|
||||
if (!this->resourceId && !rhs.resourceId) {
|
||||
return true;
|
||||
}
|
||||
return this->resourceId && rhs.resourceId && *(this->resourceId) == *(rhs.resourceId);
|
||||
}
|
||||
|
||||
bool DynamicColor::operator!=(const DynamicColor& rhs) const
|
||||
{
|
||||
return !operator==(rhs);
|
||||
}
|
||||
|
||||
} // namespace OHOS::Ace
|
||||
|
@ -55,6 +55,8 @@ class ACE_FORCE_EXPORT Color {
|
||||
public:
|
||||
Color() = default;
|
||||
constexpr explicit Color(uint32_t value) : colorValue_(ColorParam { .value = value }) {}
|
||||
constexpr explicit Color(uint32_t value, uint32_t resId)
|
||||
: colorValue_(ColorParam { .value = value }), resourceId_(resId) {}
|
||||
~Color() = default;
|
||||
|
||||
static Color FromARGB(uint8_t alpha, uint8_t red, uint8_t green, uint8_t blue);
|
||||
@ -95,6 +97,16 @@ public:
|
||||
return colorValue_.value;
|
||||
}
|
||||
|
||||
void SetResourceId(uint32_t id)
|
||||
{
|
||||
resourceId_ = id;
|
||||
}
|
||||
|
||||
uint32_t GetResourceId() const
|
||||
{
|
||||
return resourceId_;
|
||||
}
|
||||
|
||||
uint8_t GetAlpha() const
|
||||
{
|
||||
return colorValue_.argb.alpha;
|
||||
@ -115,6 +127,8 @@ public:
|
||||
return colorValue_.argb.blue;
|
||||
}
|
||||
|
||||
void UpdateColorByResourceId();
|
||||
|
||||
bool operator==(const Color& color) const
|
||||
{
|
||||
return colorValue_.value == color.GetValue();
|
||||
@ -139,7 +153,7 @@ public:
|
||||
|
||||
std::string ToString() const;
|
||||
|
||||
protected:
|
||||
private:
|
||||
constexpr explicit Color(ColorParam colorValue) : colorValue_(colorValue) {}
|
||||
|
||||
static double ConvertGammaToLinear(uint8_t value);
|
||||
@ -162,24 +176,7 @@ protected:
|
||||
|
||||
float CalculateBlend(float alphaLeft, float alphaRight, float valueLeft, float valueRight) const;
|
||||
ColorParam colorValue_ { .value = 0xff000000 };
|
||||
};
|
||||
|
||||
class ACE_FORCE_EXPORT DynamicColor : public Color {
|
||||
public:
|
||||
DynamicColor() {}
|
||||
DynamicColor(const Color& color);
|
||||
DynamicColor(const Color& color, std::optional<uint32_t> resId);
|
||||
DynamicColor(const Color& color, uint32_t resId);
|
||||
|
||||
void UpdateColorByResourceId();
|
||||
std::string ToString() const;
|
||||
Color ToColor() const;
|
||||
|
||||
DynamicColor& operator=(const Color& rhs);
|
||||
bool operator==(const DynamicColor& rhs) const;
|
||||
bool operator!=(const DynamicColor& rhs) const;
|
||||
|
||||
std::optional<uint32_t> resourceId = std::nullopt;
|
||||
uint32_t resourceId_ = 0;
|
||||
};
|
||||
|
||||
namespace StringUtils {
|
||||
|
@ -237,6 +237,11 @@ public:
|
||||
return blurRadius_ > 0.0 || spreadRadius_ > 0.0 || offset_ != Offset::Zero();
|
||||
}
|
||||
|
||||
void UpdateColorByResourceId()
|
||||
{
|
||||
color_.UpdateColorByResourceId();
|
||||
}
|
||||
|
||||
private:
|
||||
float lightHeight_ = LIGHT_HEIGHT;
|
||||
float lightRadius_ = LIGHT_RADIUS;
|
||||
|
@ -80,6 +80,8 @@ void TextStyle::UpdateColorByResourceId()
|
||||
{
|
||||
textColor_.UpdateColorByResourceId();
|
||||
textDecorationColor_.UpdateColorByResourceId();
|
||||
std::for_each(renderColors_.begin(), renderColors_.end(), [](Color& cl) { cl.UpdateColorByResourceId(); });
|
||||
std::for_each(textShadows_.begin(), textShadows_.end(), [](Shadow& sd) { sd.UpdateColorByResourceId(); });
|
||||
}
|
||||
|
||||
std::string TextStyle::ToString() const
|
||||
|
@ -368,11 +368,6 @@ public:
|
||||
enableVariableFontWeight_ = enableVariableFontWeight;
|
||||
}
|
||||
const Color GetTextColor() const
|
||||
{
|
||||
return textColor_.ToColor();
|
||||
}
|
||||
|
||||
const DynamicColor GetDynamicTextColor() const
|
||||
{
|
||||
return textColor_;
|
||||
}
|
||||
@ -382,11 +377,6 @@ public:
|
||||
textColor_ = textColor;
|
||||
}
|
||||
|
||||
void SetTextColor(const DynamicColor& textColor)
|
||||
{
|
||||
textColor_ = textColor;
|
||||
}
|
||||
|
||||
TextDecoration GetTextDecoration() const
|
||||
{
|
||||
return textDecoration_;
|
||||
@ -408,16 +398,11 @@ public:
|
||||
}
|
||||
|
||||
const Color GetTextDecorationColor() const
|
||||
{
|
||||
return textDecorationColor_.ToColor();
|
||||
}
|
||||
|
||||
const DynamicColor GetDynamicTextDecorationColor() const
|
||||
{
|
||||
return textDecorationColor_;
|
||||
}
|
||||
|
||||
void SetTextDecorationColor(const DynamicColor& textDecorationColor)
|
||||
void SetTextDecorationColor(const Color& textDecorationColor)
|
||||
{
|
||||
textDecorationColor_ = textDecorationColor;
|
||||
}
|
||||
@ -811,8 +796,8 @@ private:
|
||||
TextCase textCase_ { TextCase::NORMAL };
|
||||
EllipsisMode ellipsisMode_ = EllipsisMode::TAIL;
|
||||
LineBreakStrategy lineBreakStrategy_ { LineBreakStrategy::GREEDY };
|
||||
DynamicColor textColor_ { Color::BLACK };
|
||||
DynamicColor textDecorationColor_ { Color::BLACK };
|
||||
Color textColor_ { Color::BLACK };
|
||||
Color textDecorationColor_ { Color::BLACK };
|
||||
uint32_t maxLines_ = UINT32_MAX;
|
||||
int32_t variableFontWeight_ = 0;
|
||||
bool hasHeightOverride_ = false;
|
||||
|
@ -1046,4 +1046,13 @@ void SelectContentOverlayManager::SetIsHandleLineShow(bool isShow)
|
||||
CHECK_NULL_VOID(pattern);
|
||||
pattern->SetIsHandleLineShow(isShow);
|
||||
}
|
||||
|
||||
void SelectContentOverlayManager::MarkHandleDirtyNode(PropertyChangeFlag flag)
|
||||
{
|
||||
auto pattern = GetSelectHandlePattern(WeakClaim(this));
|
||||
CHECK_NULL_VOID(pattern);
|
||||
auto host = pattern->GetHost();
|
||||
CHECK_NULL_VOID(host);
|
||||
host->MarkDirtyNode(flag);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -90,6 +90,7 @@ public:
|
||||
void UpdateViewPort();
|
||||
void SetHandleCircleIsShow(bool isFirst, bool isShow);
|
||||
void SetIsHandleLineShow(bool isShow);
|
||||
void MarkHandleDirtyNode(PropertyChangeFlag flag);
|
||||
|
||||
private:
|
||||
void SetHolder(const RefPtr<SelectOverlayHolder>& holder);
|
||||
|
@ -76,12 +76,14 @@ float ParagraphManager::GetTextWidthIncludeIndent() const
|
||||
{
|
||||
float res = 0.0f;
|
||||
for (auto &&info : paragraphs_) {
|
||||
auto width = info.paragraph->GetTextWidth();
|
||||
auto paragraph = info.paragraph;
|
||||
CHECK_NULL_RETURN(paragraph, 0.0f);
|
||||
auto width = paragraph->GetTextWidth();
|
||||
res = std::max(res, width);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
float ParagraphManager::GetLongestLineWithIndent() const
|
||||
{
|
||||
float res = 0.0f;
|
||||
@ -241,7 +243,7 @@ LineMetrics ParagraphManager::GetLineMetricsByRectF(RectF rect, int32_t paragrap
|
||||
|
||||
TextLineMetrics ParagraphManager::GetLineMetrics(size_t lineNumber)
|
||||
{
|
||||
if (lineNumber > GetLineCount() - 1) {
|
||||
if (GetLineCount() == 0 || lineNumber > GetLineCount() - 1) {
|
||||
TAG_LOGE(AceLogTag::ACE_TEXT,
|
||||
"GetLineMetrics failed, lineNumber is greater than max lines:%{public}zu", lineNumber);
|
||||
return TextLineMetrics();
|
||||
@ -251,7 +253,7 @@ TextLineMetrics ParagraphManager::GetLineMetrics(size_t lineNumber)
|
||||
size_t lineNumberParam = lineNumber;
|
||||
for (auto &&info : paragraphs_) {
|
||||
auto lineCount = info.paragraph->GetLineCount();
|
||||
if (lineNumber > lineCount - 1) {
|
||||
if (lineCount > 0 && lineNumber > lineCount - 1) {
|
||||
lineNumber -= lineCount;
|
||||
paragraphsHeight += info.paragraph->GetHeight();
|
||||
auto lastLineMetrics = info.paragraph->GetLineMetrics(lineCount - 1);
|
||||
|
@ -53,6 +53,13 @@ void RichEditorBaseController::SetTypingStyle(std::optional<struct UpdateSpanSty
|
||||
richEditorPattern->SetTypingStyle(typingStyle, textStyle);
|
||||
}
|
||||
|
||||
std::optional<struct UpdateSpanStyle> RichEditorBaseController::GetTypingStyle()
|
||||
{
|
||||
auto richEditorPattern = AceType::DynamicCast<RichEditorPattern>(pattern_.Upgrade());
|
||||
CHECK_NULL_RETURN(richEditorPattern, {});
|
||||
return richEditorPattern->GetTypingStyle();
|
||||
}
|
||||
|
||||
void RichEditorBaseController::CloseSelectionMenu()
|
||||
{
|
||||
auto richEditorPattern = pattern_.Upgrade();
|
||||
|
@ -31,6 +31,7 @@ public:
|
||||
int32_t GetCaretOffset() override;
|
||||
bool SetCaretOffset(int32_t caretPosition) override;
|
||||
void SetTypingStyle(std::optional<struct UpdateSpanStyle> typingStyle, std::optional<TextStyle> textStyle) override;
|
||||
std::optional<struct UpdateSpanStyle> GetTypingStyle() override;
|
||||
void CloseSelectionMenu() override;
|
||||
bool IsEditing() override;
|
||||
void StopEditing() override;
|
||||
|
@ -92,7 +92,7 @@ SelectionInfo RichEditorController::GetSelectionSpansInfo()
|
||||
end = richEditorPattern->GetCaretPosition();
|
||||
}
|
||||
TAG_LOGI(AceLogTag::ACE_RICH_TEXT, "GetSelection, start, range=[%{public}d,%{public}d]", start, end);
|
||||
SelectionInfo value = richEditorPattern->GetSpansInfo(start, end, GetSpansMethod::ONSELECT);
|
||||
SelectionInfo value = richEditorPattern->GetSpansInfo(start, end, GetSpansMethod::GETSPANS);
|
||||
TAG_LOGI(AceLogTag::ACE_RICH_TEXT, "GetSelection end");
|
||||
return value;
|
||||
}
|
||||
|
@ -366,6 +366,11 @@ void RichEditorDeleteValue::SetRichEditorDeleteSpans(const RichEditorAbstractSpa
|
||||
richEditorDeleteSpans_.emplace_back(deleteSpan);
|
||||
}
|
||||
|
||||
void RichEditorDeleteValue::ResetRichEditorDeleteSpans()
|
||||
{
|
||||
richEditorDeleteSpans_.clear();
|
||||
}
|
||||
|
||||
const std::list<RichEditorAbstractSpanResult>& RichEditorDeleteValue::GetRichEditorDeleteSpans() const
|
||||
{
|
||||
return richEditorDeleteSpans_;
|
||||
|
@ -210,6 +210,7 @@ public:
|
||||
void SetLength(int32_t length);
|
||||
int32_t GetLength() const;
|
||||
void SetRichEditorDeleteSpans(const RichEditorAbstractSpanResult& deleteSpan);
|
||||
void ResetRichEditorDeleteSpans();
|
||||
const std::list<RichEditorAbstractSpanResult>& GetRichEditorDeleteSpans() const;
|
||||
|
||||
private:
|
||||
|
@ -103,59 +103,59 @@ void RichEditorLayoutAlgorithm::CopySpanStyle(RefPtr<SpanItem> source, RefPtr<Sp
|
||||
}
|
||||
}
|
||||
|
||||
std::optional<SizeF> RichEditorLayoutAlgorithm::MeasureEmptyContentSize(
|
||||
const LayoutConstraintF& contentConstraint, LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
auto host = layoutWrapper->GetHostNode();
|
||||
CHECK_NULL_RETURN(host, {});
|
||||
auto pipeline = host->GetContext();
|
||||
CHECK_NULL_RETURN(pipeline, {});
|
||||
auto richEditorTheme = pipeline->GetTheme<RichEditorTheme>();
|
||||
CHECK_NULL_RETURN(richEditorTheme, {});
|
||||
auto defaultCaretHeight = richEditorTheme->GetDefaultCaretHeight().ConvertToPx();
|
||||
auto width = contentConstraint.selfIdealSize.Width().value_or(contentConstraint.maxSize.Width());
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_RETURN(pattern, {});
|
||||
auto presetParagraph = pattern->GetPresetParagraph();
|
||||
if (!presetParagraph) {
|
||||
pattern->PreferredParagraph();
|
||||
}
|
||||
auto contentHeight = defaultCaretHeight;
|
||||
presetParagraph = pattern->GetPresetParagraph();
|
||||
if (presetParagraph) {
|
||||
contentHeight = presetParagraph->GetHeight();
|
||||
}
|
||||
return SizeF(width, static_cast<float>(contentHeight));
|
||||
}
|
||||
|
||||
std::optional<SizeF> RichEditorLayoutAlgorithm::MeasureContentSize(
|
||||
const LayoutConstraintF& contentConstraint, LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
auto layoutProperty = DynamicCast<TextLayoutProperty>(layoutWrapper->GetLayoutProperty());
|
||||
CHECK_NULL_RETURN(layoutProperty, {});
|
||||
TextStyle textStyle;
|
||||
ConstructTextStyles(contentConstraint, layoutWrapper, textStyle);
|
||||
CHECK_NULL_RETURN(BuildParagraph(textStyle, layoutProperty, contentConstraint, layoutWrapper), {});
|
||||
pManager_->SetParagraphs(GetParagraphs());
|
||||
return SizeF(pManager_->GetMaxWidth(), pManager_->GetHeight());
|
||||
}
|
||||
|
||||
std::optional<SizeF> RichEditorLayoutAlgorithm::MeasureContent(
|
||||
const LayoutConstraintF& contentConstraint, LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
ACE_SCOPED_TRACE("RichEditorMeasureContent");
|
||||
pManager_->Reset();
|
||||
SetPlaceholder(layoutWrapper);
|
||||
if (spans_.empty()) {
|
||||
auto pipeline = PipelineContext::GetCurrentContext();
|
||||
CHECK_NULL_RETURN(pipeline, std::nullopt);
|
||||
auto richEditorTheme = pipeline->GetTheme<RichEditorTheme>();
|
||||
CHECK_NULL_RETURN(richEditorTheme, std::nullopt);
|
||||
auto defaultCaretHeight = richEditorTheme->GetDefaultCaretHeight().ConvertToPx();
|
||||
auto width = contentConstraint.selfIdealSize.Width().value_or(contentConstraint.maxSize.Width());
|
||||
auto host = layoutWrapper->GetHostNode();
|
||||
CHECK_NULL_RETURN(host, std::nullopt);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_RETURN(pattern, std::nullopt);
|
||||
auto presetParagraph = pattern->GetPresetParagraph();
|
||||
if (!presetParagraph) {
|
||||
pattern->PreferredParagraph();
|
||||
}
|
||||
auto contentHeight = defaultCaretHeight;
|
||||
presetParagraph = pattern->GetPresetParagraph();
|
||||
if (presetParagraph) {
|
||||
contentHeight = presetParagraph->GetHeight();
|
||||
}
|
||||
return SizeF(width, static_cast<float>(contentHeight));
|
||||
}
|
||||
|
||||
auto layoutProperty = DynamicCast<TextLayoutProperty>(layoutWrapper->GetLayoutProperty());
|
||||
CHECK_NULL_RETURN(layoutProperty, std::nullopt);
|
||||
TextStyle textStyle;
|
||||
ConstructTextStyles(contentConstraint, layoutWrapper, textStyle);
|
||||
if (!BuildParagraph(textStyle, layoutProperty, contentConstraint, layoutWrapper)) {
|
||||
return std::nullopt;
|
||||
}
|
||||
pManager_->SetParagraphs(GetParagraphs());
|
||||
SizeF res;
|
||||
float textHeight = 0.0f;
|
||||
textHeight = pManager_->GetHeight();
|
||||
res.SetWidth(pManager_->GetMaxWidth());
|
||||
res.SetHeight(textHeight);
|
||||
res.AddHeight(shadowOffset_);
|
||||
if (Negative(res.Height()) || Negative(res.Width())) {
|
||||
return std::nullopt;
|
||||
}
|
||||
UpdateRichTextRect(res, textHeight, layoutWrapper);
|
||||
auto contentHeight = res.Height();
|
||||
if (contentConstraint.selfIdealSize.Height().has_value()) {
|
||||
contentHeight = std::min(contentHeight, contentConstraint.selfIdealSize.Height().value());
|
||||
} else {
|
||||
contentHeight = std::min(contentHeight, contentConstraint.maxSize.Height());
|
||||
}
|
||||
auto optionalTextSize = spans_.empty()
|
||||
? MeasureEmptyContentSize(contentConstraint, layoutWrapper)
|
||||
: MeasureContentSize(contentConstraint, layoutWrapper);
|
||||
CHECK_NULL_RETURN(optionalTextSize, {});
|
||||
SizeF res = optionalTextSize.value();
|
||||
res.AddHeight(spans_.empty() ? 0 : shadowOffset_);
|
||||
CHECK_NULL_RETURN(res.IsNonNegative(), {});
|
||||
UpdateRichTextRect(optionalTextSize.value(), layoutWrapper);
|
||||
auto maxHeight = contentConstraint.selfIdealSize.Height().value_or(contentConstraint.maxSize.Height());
|
||||
auto contentHeight = std::min(res.Height(), maxHeight);
|
||||
return SizeF(res.Width(), contentHeight);
|
||||
}
|
||||
|
||||
@ -193,27 +193,26 @@ bool RichEditorLayoutAlgorithm::CreateParagraph(
|
||||
return UpdateParagraphBySpan(layoutWrapper, paraStyle, maxWidth, textStyle);
|
||||
}
|
||||
|
||||
void RichEditorLayoutAlgorithm::UpdateRichTextRect(
|
||||
const SizeF& res, const float& textHeight, LayoutWrapper* layoutWrapper)
|
||||
RefPtr<RichEditorPattern> RichEditorLayoutAlgorithm::GetRichEditorPattern(LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
CHECK_NULL_RETURN(layoutWrapper, nullptr);
|
||||
auto host = layoutWrapper->GetHostNode();
|
||||
CHECK_NULL_VOID(host);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
if (pattern->IsShowPlaceholder()) {
|
||||
richTextRect_.SetSize(SizeF(0.0f, 0.0f));
|
||||
} else {
|
||||
richTextRect_.SetSize(SizeF(res.Width(), textHeight));
|
||||
}
|
||||
CHECK_NULL_RETURN(host, nullptr);
|
||||
return host->GetPattern<RichEditorPattern>();
|
||||
}
|
||||
|
||||
void RichEditorLayoutAlgorithm::SetPlaceholder(LayoutWrapper* layoutWrapper)
|
||||
void RichEditorLayoutAlgorithm::UpdateRichTextRect(const SizeF& textSize, LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
auto host = layoutWrapper->GetHostNode();
|
||||
CHECK_NULL_VOID(host);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
auto pattern = GetRichEditorPattern(layoutWrapper);
|
||||
CHECK_NULL_VOID(pattern);
|
||||
pattern->SetPlaceholder(spans_);
|
||||
richTextRect_.SetSize(pattern->IsShowPlaceholder() ? SizeF() : textSize);
|
||||
}
|
||||
|
||||
bool RichEditorLayoutAlgorithm::SetPlaceholder(LayoutWrapper* layoutWrapper)
|
||||
{
|
||||
auto pattern = GetRichEditorPattern(layoutWrapper);
|
||||
CHECK_NULL_RETURN(pattern, false);
|
||||
return pattern->SetPlaceholder(spans_);
|
||||
}
|
||||
|
||||
float RichEditorLayoutAlgorithm::GetShadowOffset(const std::list<RefPtr<SpanItem>>& group)
|
||||
|
@ -57,12 +57,15 @@ private:
|
||||
const TextStyle& textStyle, const std::string& content, LayoutWrapper* layoutWrapper) const override;
|
||||
RefPtr<SpanItem> GetFirstTextSpanItem() const;
|
||||
float GetShadowOffset(const std::list<RefPtr<SpanItem>>& group) override;
|
||||
void UpdateRichTextRect(const SizeF& res, const float& textHeight, LayoutWrapper* layoutWrapper);
|
||||
void UpdateRichTextRect(const SizeF& textSize, LayoutWrapper* layoutWrapper);
|
||||
RefPtr<RichEditorPattern> GetRichEditorPattern(LayoutWrapper* layoutWrapper);
|
||||
|
||||
void SetPlaceholder(LayoutWrapper* layoutWrapper);
|
||||
bool SetPlaceholder(LayoutWrapper* layoutWrapper);
|
||||
|
||||
void CopySpanStyle(RefPtr<SpanItem> source, RefPtr<SpanItem> target);
|
||||
void AppendNewLineSpan();
|
||||
std::optional<SizeF> MeasureContentSize(const LayoutConstraintF& constraint, LayoutWrapper* layoutWrapper);
|
||||
std::optional<SizeF> MeasureEmptyContentSize(const LayoutConstraintF& constraint, LayoutWrapper* layoutWrapper);
|
||||
|
||||
const std::list<RefPtr<SpanItem>>& GetSpans() const
|
||||
{
|
||||
|
@ -27,6 +27,7 @@ public:
|
||||
~RichEditorLayoutProperty() override;
|
||||
ACE_DISALLOW_COPY_AND_MOVE(RichEditorLayoutProperty);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITHOUT_GROUP(PreviewTextStyle, std::string, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITHOUT_GROUP(DisplayMode, DisplayMode, PROPERTY_UPDATE_MEASURE);
|
||||
};
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
||||
|
@ -81,9 +81,6 @@ struct UpdateSpanStyle {
|
||||
|
||||
updateLineHeight.reset();
|
||||
updateLetterSpacing.reset();
|
||||
updateSymbolColor.reset();
|
||||
updateSymbolRenderingStrategy.reset();
|
||||
updateSymbolEffectStrategy.reset();
|
||||
|
||||
updateImageWidth.reset();
|
||||
updateImageHeight.reset();
|
||||
@ -93,25 +90,28 @@ struct UpdateSpanStyle {
|
||||
borderRadius.reset();
|
||||
useThemeFontColor = true;
|
||||
useThemeDecorationColor = true;
|
||||
isSymbolStyle = false;
|
||||
isInitDecoration = false;
|
||||
|
||||
updateSymbolColor.reset();
|
||||
updateSymbolFontSize.reset();
|
||||
updateSymbolFontWeight.reset();
|
||||
updateSymbolRenderingStrategy.reset();
|
||||
updateSymbolEffectStrategy.reset();
|
||||
}
|
||||
|
||||
std::optional<DynamicColor> updateTextColor = std::nullopt;
|
||||
std::optional<Color> updateTextColor = std::nullopt;
|
||||
std::optional<CalcDimension> updateFontSize = std::nullopt;
|
||||
std::optional<FontStyle> updateItalicFontStyle = std::nullopt;
|
||||
std::optional<FontWeight> updateFontWeight = std::nullopt;
|
||||
std::optional<std::vector<std::string>> updateFontFamily = std::nullopt;
|
||||
std::optional<TextDecoration> updateTextDecoration = std::nullopt;
|
||||
std::optional<DynamicColor> updateTextDecorationColor = std::nullopt;
|
||||
std::optional<Color> updateTextDecorationColor = std::nullopt;
|
||||
std::optional<TextDecorationStyle> updateTextDecorationStyle = std::nullopt;
|
||||
std::optional<std::vector<Shadow>> updateTextShadows = std::nullopt;
|
||||
std::optional<NG::FONT_FEATURES_LIST> updateFontFeature = std::nullopt;
|
||||
|
||||
std::optional<CalcDimension> updateLineHeight = std::nullopt;
|
||||
std::optional<CalcDimension> updateLetterSpacing = std::nullopt;
|
||||
std::optional<std::vector<Color>> updateSymbolColor = std::nullopt;
|
||||
std::optional<uint32_t> updateSymbolRenderingStrategy = std::nullopt;
|
||||
std::optional<uint32_t> updateSymbolEffectStrategy = std::nullopt;
|
||||
|
||||
std::optional<CalcDimension> updateImageWidth = std::nullopt;
|
||||
std::optional<CalcDimension> updateImageHeight = std::nullopt;
|
||||
@ -122,8 +122,31 @@ struct UpdateSpanStyle {
|
||||
std::optional<OHOS::Ace::NG::BorderRadiusProperty> borderRadius = std::nullopt;
|
||||
bool useThemeFontColor = true;
|
||||
bool useThemeDecorationColor = true;
|
||||
bool isInitDecoration = false;
|
||||
|
||||
bool isSymbolStyle = false;
|
||||
std::optional<std::vector<Color>> updateSymbolColor = std::nullopt;
|
||||
std::optional<CalcDimension> updateSymbolFontSize = std::nullopt;
|
||||
std::optional<FontWeight> updateSymbolFontWeight = std::nullopt;
|
||||
std::optional<uint32_t> updateSymbolRenderingStrategy = std::nullopt;
|
||||
std::optional<uint32_t> updateSymbolEffectStrategy = std::nullopt;
|
||||
|
||||
void UpdateColorByResourceId()
|
||||
{
|
||||
if (updateTextColor) {
|
||||
updateTextColor->UpdateColorByResourceId();
|
||||
}
|
||||
if (updateTextDecorationColor) {
|
||||
updateTextDecorationColor->UpdateColorByResourceId();
|
||||
}
|
||||
if (updateTextShadows) {
|
||||
auto& shadows = updateTextShadows.value();
|
||||
std::for_each(shadows.begin(), shadows.end(), [](Shadow& sd) { sd.UpdateColorByResourceId(); });
|
||||
}
|
||||
if (updateSymbolColor) {
|
||||
auto& colors = updateSymbolColor.value();
|
||||
std::for_each(colors.begin(), colors.end(), [](Color& cl) { cl.UpdateColorByResourceId(); });
|
||||
}
|
||||
}
|
||||
|
||||
std::string ToString() const
|
||||
{
|
||||
@ -145,7 +168,6 @@ struct UpdateSpanStyle {
|
||||
JSON_STRING_PUT_OPTIONAL_STRINGABLE(jsonValue, borderRadius);
|
||||
JSON_STRING_PUT_BOOL(jsonValue, useThemeFontColor);
|
||||
JSON_STRING_PUT_BOOL(jsonValue, useThemeDecorationColor);
|
||||
JSON_STRING_PUT_BOOL(jsonValue, isSymbolStyle);
|
||||
return jsonValue->ToString();
|
||||
}
|
||||
};
|
||||
@ -194,8 +216,8 @@ struct TextSpanOptions : SpanOptionBase {
|
||||
std::optional<TextStyle> style;
|
||||
std::optional<UpdateParagraphStyle> paraStyle;
|
||||
UserGestureOptions userGestureOption;
|
||||
bool useThemeFontColor = false;
|
||||
bool useThemeDecorationColor = false;
|
||||
bool useThemeFontColor = true;
|
||||
bool useThemeDecorationColor = true;
|
||||
|
||||
std::string ToString() const
|
||||
{
|
||||
@ -230,7 +252,7 @@ struct PlaceholderOptions {
|
||||
std::optional<std::string> value;
|
||||
std::optional<FontWeight> fontWeight;
|
||||
std::optional<Dimension> fontSize;
|
||||
std::optional<DynamicColor> fontColor;
|
||||
std::optional<Color> fontColor;
|
||||
std::optional<FontStyle> fontStyle;
|
||||
std::vector<std::string> fontFamilies;
|
||||
|
||||
@ -267,6 +289,7 @@ public:
|
||||
virtual bool SetCaretOffset(int32_t caretPosition) = 0;
|
||||
virtual void SetTypingStyle(std::optional<struct UpdateSpanStyle> typingStyle,
|
||||
std::optional<TextStyle> textStyle) = 0;
|
||||
virtual std::optional<struct UpdateSpanStyle> GetTypingStyle() = 0;
|
||||
virtual void CloseSelectionMenu() = 0;
|
||||
virtual bool IsEditing() = 0;
|
||||
virtual void StopEditing() = 0;
|
||||
@ -330,8 +353,8 @@ public:
|
||||
virtual void SetTextDetectEnable(bool value) = 0;
|
||||
virtual void SetSupportPreviewText(bool value) = 0;
|
||||
virtual void SetTextDetectConfig(const TextDetectConfig& textDetectConfig) = 0;
|
||||
virtual void SetSelectedBackgroundColor(const DynamicColor& selectedColor) = 0;
|
||||
virtual void SetCaretColor(const DynamicColor& color) = 0;
|
||||
virtual void SetSelectedBackgroundColor(const Color& selectedColor) = 0;
|
||||
virtual void SetCaretColor(const Color& color) = 0;
|
||||
virtual void SetOnEditingChange(std::function<void(const bool&)>&& func) = 0;
|
||||
virtual void SetEnterKeyType(TextInputAction value) = 0;
|
||||
virtual void SetOnSubmit(std::function<void(int32_t, NG::TextFieldCommonEvent&)>&& func) = 0;
|
||||
@ -342,6 +365,8 @@ public:
|
||||
virtual void SetSelectionMenuOptions(
|
||||
const NG::OnCreateMenuCallback&& onCreateMenuCallback, const NG::OnMenuItemClickCallback&& onMenuItemClick) {}
|
||||
virtual void SetRequestKeyboardOnFocus(bool needToRequest) {}
|
||||
virtual void SetEnableHapticFeedback(bool isEnabled) {}
|
||||
virtual void SetBarState(DisplayMode mode) {}
|
||||
virtual void SetImagePreviewMenuParam(std::function<void()>& buildFunc, const NG::SelectMenuParam& menuParam) {}
|
||||
private:
|
||||
static std::unique_ptr<RichEditorModel> instance_;
|
||||
|
@ -307,7 +307,7 @@ void RichEditorModelNG::SetTextDetectEnable(FrameNode* frameNode, bool value)
|
||||
richEditorPattern->SetTextDetectEnable(value);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetSelectedBackgroundColor(const DynamicColor& selectedColor)
|
||||
void RichEditorModelNG::SetSelectedBackgroundColor(const Color& selectedColor)
|
||||
{
|
||||
auto frameNode = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
CHECK_NULL_VOID(frameNode);
|
||||
@ -316,14 +316,14 @@ void RichEditorModelNG::SetSelectedBackgroundColor(const DynamicColor& selectedC
|
||||
pattern->SetSelectedBackgroundColor(selectedColor);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetSelectedBackgroundColor(FrameNode* frameNode, const DynamicColor& selectedColor)
|
||||
void RichEditorModelNG::SetSelectedBackgroundColor(FrameNode* frameNode, const Color& selectedColor)
|
||||
{
|
||||
auto pattern = frameNode->GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
pattern->SetSelectedBackgroundColor(selectedColor);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetCaretColor(const DynamicColor& color)
|
||||
void RichEditorModelNG::SetCaretColor(const Color& color)
|
||||
{
|
||||
auto frameNode = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
CHECK_NULL_VOID(frameNode);
|
||||
@ -332,7 +332,7 @@ void RichEditorModelNG::SetCaretColor(const DynamicColor& color)
|
||||
pattern->SetCaretColor(color);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetCaretColor(FrameNode* frameNode, const DynamicColor& color)
|
||||
void RichEditorModelNG::SetCaretColor(FrameNode* frameNode, const Color& color)
|
||||
{
|
||||
auto pattern = frameNode->GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
@ -459,6 +459,10 @@ void RichEditorModelNG::SetRequestKeyboardOnFocus(FrameNode* frameNode, bool nee
|
||||
richEditorPattern->SetRequestKeyboardOnFocus(needToRequest);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetBarState(DisplayMode mode)
|
||||
{
|
||||
ACE_UPDATE_LAYOUT_PROPERTY(RichEditorLayoutProperty, DisplayMode, mode);
|
||||
}
|
||||
void RichEditorModelNG::SetImagePreviewMenuParam(std::function<void()>& buildFunc, const SelectMenuParam& menuParam)
|
||||
{
|
||||
auto richEditorPattern = ViewStackProcessor::GetInstance()->GetMainFrameNodePattern<RichEditorPattern>();
|
||||
@ -474,4 +478,11 @@ void RichEditorModelNG::SetImagePreviewMenuParam(FrameNode* frameNode,
|
||||
CHECK_NULL_VOID(richEditorPattern);
|
||||
richEditorPattern->SetImagePreviewMenuParam(buildFunc, menuParam);
|
||||
}
|
||||
|
||||
void RichEditorModelNG::SetEnableHapticFeedback(bool isEnabled)
|
||||
{
|
||||
auto richEditorPattern = ViewStackProcessor::GetInstance()->GetMainFrameNodePattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(richEditorPattern);
|
||||
richEditorPattern->SetEnableHapticFeedback(isEnabled);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -41,8 +41,8 @@ public:
|
||||
void SetTextDetectEnable(bool value) override;
|
||||
void SetSupportPreviewText(bool value) override;
|
||||
void SetTextDetectConfig(const TextDetectConfig& textDetectConfig) override;
|
||||
void SetSelectedBackgroundColor(const DynamicColor& selectedColor) override;
|
||||
void SetCaretColor(const DynamicColor& color) override;
|
||||
void SetSelectedBackgroundColor(const Color& selectedColor) override;
|
||||
void SetCaretColor(const Color& color) override;
|
||||
void SetOnEditingChange(std::function<void(const bool&)>&& func) override;
|
||||
void SetOnWillChange(std::function<bool(const RichEditorChangeValue&)>&& func) override;
|
||||
void SetOnDidChange(std::function<void(const RichEditorChangeValue&)>&& func) override;
|
||||
@ -51,6 +51,8 @@ public:
|
||||
void SetSelectionMenuOptions(const OnCreateMenuCallback&& onCreateMenuCallback,
|
||||
const OnMenuItemClickCallback&& onMenuItemClick) override;
|
||||
void SetRequestKeyboardOnFocus(bool needToRequest) override;
|
||||
void SetEnableHapticFeedback(bool isEnabled) override;
|
||||
void SetBarState(DisplayMode mode) override;
|
||||
void SetImagePreviewMenuParam(std::function<void()>& buildFunc, const SelectMenuParam& menuParam) override;
|
||||
|
||||
static void SetTextDetectEnable(FrameNode* frameNode, bool value);
|
||||
@ -60,12 +62,12 @@ public:
|
||||
static void SetOnDidIMEInput(FrameNode* frameNode, std::function<void(const TextRange&)>&& callback);
|
||||
static void SetCopyOption(FrameNode* frameNode, CopyOptions& copyOptions);
|
||||
static void SetOnSelectionChange(FrameNode* frameNode, std::function<void(const BaseEventInfo*)>&& callback);
|
||||
static void SetCaretColor(FrameNode* frameNode, const DynamicColor& color);
|
||||
static void SetCaretColor(FrameNode* frameNode, const Color& color);
|
||||
static void SetOnSelect(FrameNode* frameNode, std::function<void(const BaseEventInfo*)>&& callback);
|
||||
static void SetOnReady(FrameNode* frameNode, std::function<void()>&& callback);
|
||||
static void SetOnDeleteComplete(FrameNode* frameNode, std::function<void()>&& callback);
|
||||
static void SetOnEditingChange(FrameNode* frameNode, std::function<void(const bool&)>&& callback);
|
||||
static void SetSelectedBackgroundColor(FrameNode* frameNode, const DynamicColor& selectedColor);
|
||||
static void SetSelectedBackgroundColor(FrameNode* frameNode, const Color& selectedColor);
|
||||
static void SetOnPaste(FrameNode* frameNode, std::function<void(NG::TextCommonEvent&)>&& func);
|
||||
static void SetOnCut(FrameNode* frameNode, std::function<void(NG::TextCommonEvent&)>&& func);
|
||||
static void SetOnCopy(FrameNode* frameNode, std::function<void(NG::TextCommonEvent&)>&& func);
|
||||
@ -77,7 +79,6 @@ public:
|
||||
static void SetRequestKeyboardOnFocus(FrameNode* frameNode, bool needToRequest);
|
||||
static void SetImagePreviewMenuParam(FrameNode* frameNode,
|
||||
std::function<void()>& buildFunc, const SelectMenuParam& menuParam);
|
||||
|
||||
private:
|
||||
void SetDraggable(bool draggable);
|
||||
bool isStyledStringMode_ = false;
|
||||
|
@ -192,8 +192,7 @@ void RichEditorOverlayModifier::PaintCaret(DrawingContext& drawingContext) const
|
||||
canvas.AttachPen(pen);
|
||||
float midPosX = offset.GetX() + caretWidth / 2;
|
||||
float startPosY = offset.GetY();
|
||||
float endPosY = LessOrEqual(offset.GetY() + caretHeight, contentRect_.value().Bottom())
|
||||
? offset.GetY() + caretHeight : contentRect_.value().Bottom();
|
||||
float endPosY = startPosY + caretHeight;
|
||||
float roundCapRadius = caretWidth / 2;
|
||||
canvas.DrawLine(RSPoint(midPosX, startPosY + roundCapRadius), RSPoint(midPosX, endPosY - roundCapRadius));
|
||||
canvas.DetachPen();
|
||||
@ -204,6 +203,8 @@ void RichEditorOverlayModifier::PaintScrollBar(DrawingContext& context)
|
||||
{
|
||||
auto scrollBarOverlayModifier = scrollBarOverlayModifier_.Upgrade();
|
||||
CHECK_NULL_VOID(scrollBarOverlayModifier);
|
||||
auto pattern = DynamicCast<RichEditorPattern>(pattern_.Upgrade());
|
||||
CHECK_NULL_VOID(!pattern || pattern->GetBarDisplayMode() != DisplayMode::OFF);
|
||||
scrollBarOverlayModifier->onDraw(context);
|
||||
}
|
||||
|
||||
@ -221,21 +222,14 @@ void RichEditorOverlayModifier::onDraw(DrawingContext& drawingContext)
|
||||
auto richEditorPattern = AceType::DynamicCast<RichEditorPattern>(pattern_.Upgrade());
|
||||
CHECK_NULL_VOID(richEditorPattern);
|
||||
auto contentRect = richEditorPattern->GetTextContentRect();
|
||||
if (!contentRect.IsEmpty()) {
|
||||
auto pipeline = PipelineContext::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipeline);
|
||||
auto richEditorTheme = pipeline->GetTheme<RichEditorTheme>();
|
||||
auto defaultCaretHeight = richEditorTheme->GetDefaultCaretHeight().ConvertToPx();
|
||||
if (contentRect.Height() < defaultCaretHeight) {
|
||||
contentRect.SetHeight(defaultCaretHeight);
|
||||
}
|
||||
drawingContext.canvas.ClipRect(ToRSRect(contentRect), RSClipOp::INTERSECT);
|
||||
}
|
||||
|
||||
drawingContext.canvas.ClipRect(ToRSRect(contentRect), RSClipOp::INTERSECT);
|
||||
PaintCaret(drawingContext);
|
||||
PaintPreviewTextDecoration(drawingContext);
|
||||
SetSelectedColor(selectedBackgroundColor_->Get());
|
||||
TextOverlayModifier::onDraw(drawingContext);
|
||||
drawingContext.canvas.Restore();
|
||||
|
||||
PaintScrollBar(drawingContext);
|
||||
PaintEdgeEffect(frameSize_->Get(), drawingContext.canvas);
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -52,6 +52,7 @@
|
||||
#include "core/components_ng/pattern/text/text_base.h"
|
||||
#include "core/components_ng/pattern/text/text_pattern.h"
|
||||
#include "core/components_ng/pattern/text_field/text_field_model.h"
|
||||
#include "core/text/text_emoji_processor.h"
|
||||
|
||||
#ifndef ACE_UNITTEST
|
||||
#ifdef ENABLE_STANDARD_INPUT
|
||||
@ -108,12 +109,26 @@ enum class RecordType { DEL_FORWARD = 0, DEL_BACKWARD = 1, INSERT = 2, UNDO = 3,
|
||||
enum class SelectorAdjustPolicy { INCLUDE = 0, EXCLUDE };
|
||||
enum class HandleType { FIRST = 0, SECOND };
|
||||
enum class SelectType { SELECT_FORWARD = 0, SELECT_BACKWARD, SELECT_NOTHING };
|
||||
enum class CaretAffinityPolicy { DEFAULT = 0, UPSTREAM_FIRST, DOWNSTREAM_FIRST };
|
||||
enum class OperationType { DEFAULT = 0, DRAG, IME };
|
||||
const std::map<std::pair<HandleType, SelectorAdjustPolicy>, MoveDirection> SELECTOR_ADJUST_DIR_MAP = {
|
||||
{{ HandleType::FIRST, SelectorAdjustPolicy::INCLUDE }, MoveDirection::BACKWARD },
|
||||
{{ HandleType::FIRST, SelectorAdjustPolicy::EXCLUDE }, MoveDirection::FORWARD },
|
||||
{{ HandleType::SECOND, SelectorAdjustPolicy::INCLUDE }, MoveDirection::FORWARD },
|
||||
{{ HandleType::SECOND, SelectorAdjustPolicy::EXCLUDE }, MoveDirection::BACKWARD }
|
||||
};
|
||||
struct CaretOffsetInfo {
|
||||
// caret front offset info
|
||||
OffsetF caretOffsetUp;
|
||||
// caret end offset info
|
||||
OffsetF caretOffsetDown;
|
||||
// caret position offset info
|
||||
OffsetF caretOffsetLine;
|
||||
float caretHeightUp = 0.0f;
|
||||
float caretHeightDown = 0.0f;
|
||||
float caretHeightLine = 0.0f;
|
||||
};
|
||||
enum class PositionType { DEFAULT, PARAGRAPH_START, PARAGRAPH_END, LINE_START, LINE_END };
|
||||
|
||||
|
||||
class RichEditorPattern
|
||||
@ -173,7 +188,7 @@ public:
|
||||
bool isTouchCaret = false;
|
||||
bool isMoveCaret = false;
|
||||
Offset touchDownOffset;
|
||||
const Dimension minDinstance = 5.0_vp;
|
||||
const Dimension minDistance = 5.0_vp;
|
||||
|
||||
void Reset()
|
||||
{
|
||||
@ -199,6 +214,9 @@ public:
|
||||
return;
|
||||
}
|
||||
pattern->isModifyingContent_ = false;
|
||||
auto host = pattern->GetHost();
|
||||
CHECK_NULL_VOID(host);
|
||||
host->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
|
||||
}
|
||||
private:
|
||||
WeakPtr<RichEditorPattern> pattern_;
|
||||
@ -341,7 +359,7 @@ public:
|
||||
const struct UpdateSpanStyle& updateSpanStyle, const TextStyle& textStyle, int32_t length);
|
||||
void DeleteBackwardInStyledString(int32_t length);
|
||||
void DeleteForwardInStyledString(int32_t length, bool isIME = true);
|
||||
void DeleteValueInStyledString(int32_t start, int32_t length, bool isIME = true);
|
||||
void DeleteValueInStyledString(int32_t start, int32_t length, bool isIME = true, bool isUpdateCaret = true);
|
||||
|
||||
bool BeforeStyledStringChange(int32_t start, int32_t length, const std::string& string);
|
||||
bool BeforeStyledStringChange(int32_t start, int32_t length, const RefPtr<SpanString>& styledString);
|
||||
@ -360,22 +378,20 @@ public:
|
||||
|
||||
void UpdateEditingValue(const std::shared_ptr<TextEditingValue>& value, bool needFireChangeEvent = true) override;
|
||||
void PerformAction(TextInputAction action, bool forceCloseKeyboard = true) override;
|
||||
bool IsIMEOperation(OperationType operationType);
|
||||
void InsertValue(const std::string& insertValue, bool isIME = false) override;
|
||||
void InsertValueOperation(
|
||||
const std::string& insertValue, OperationRecord* const record = nullptr, bool isIME = true);
|
||||
void InsertValueByOperationType(const std::string& insertValue,
|
||||
OperationType operationType = OperationType::DEFAULT);
|
||||
void InsertValueOperation(const std::string& insertValue, OperationRecord* const record = nullptr,
|
||||
OperationType operationType = OperationType::IME);
|
||||
void DeleteSelectOperation(OperationRecord* const record);
|
||||
void DeleteByRange(OperationRecord* const record, int32_t start, int32_t end);
|
||||
void InsertValueAfterBeforeSpan(RefPtr<SpanNode>& spanNodeBefore, RefPtr<SpanNode>& spanNode,
|
||||
const TextInsertValueInfo& info, const std::string& insertValue, bool isIME = true);
|
||||
void InsertDiffStyleValueInSpan(
|
||||
RefPtr<SpanNode>& spanNode, const TextInsertValueInfo& info, const std::string& insertValue, bool isIME = true);
|
||||
void InsertValueWithoutSpan(
|
||||
RefPtr<SpanNode>& spanNode, const TextInsertValueInfo& info, const std::string& insertValue, bool isIME = true);
|
||||
void InsertValueByPaste(const std::string& insertValue);
|
||||
bool IsLineSeparatorInLast(RefPtr<SpanNode>& spanNode);
|
||||
void InsertValueToSpanNode(
|
||||
RefPtr<SpanNode>& spanNode, const std::string& insertValue, const TextInsertValueInfo& info);
|
||||
void SpanNodeFission(RefPtr<SpanNode>& spanNode, const std::string& insertValue, const TextInsertValueInfo& info);
|
||||
void SpanNodeFission(RefPtr<SpanNode>& spanNode);
|
||||
void CreateTextSpanNode(
|
||||
RefPtr<SpanNode>& spanNode, const TextInsertValueInfo& info, const std::string& insertValue, bool isIME = true);
|
||||
@ -390,6 +406,7 @@ public:
|
||||
std::wstring DeleteForwardOperation(int32_t length);
|
||||
void SetInputMethodStatus(bool keyboardShown) override;
|
||||
bool ClickAISpan(const PointF& textOffset, const AISpan& aiSpan) override;
|
||||
WindowMode GetWindowMode();
|
||||
void NotifyKeyboardClosedByUser() override
|
||||
{
|
||||
TAG_LOGI(AceLogTag::ACE_RICH_TEXT, "KeyboardClosedByUser");
|
||||
@ -399,13 +416,10 @@ public:
|
||||
{
|
||||
TAG_LOGI(AceLogTag::ACE_RICH_TEXT, "KeyboardClosed");
|
||||
CHECK_NULL_VOID(HasFocus());
|
||||
auto pipelineContext = PipelineBase::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipelineContext);
|
||||
auto windowManager = pipelineContext->GetWindowManager();
|
||||
CHECK_NULL_VOID(windowManager);
|
||||
|
||||
// lost focus in floating window mode
|
||||
if (windowManager->GetWindowMode() == WindowMode::WINDOW_MODE_FLOATING) {
|
||||
auto windowMode = GetWindowMode();
|
||||
if (windowMode == WindowMode::WINDOW_MODE_FLOATING) {
|
||||
FocusHub::LostFocusToViewRoot();
|
||||
}
|
||||
}
|
||||
@ -416,6 +430,7 @@ public:
|
||||
void HandleOnUndoAction() override;
|
||||
void HandleOnRedoAction() override;
|
||||
void CursorMove(CaretMoveIntent direction) override;
|
||||
bool BeforeStatusCursorMove(bool isLeft);
|
||||
bool CursorMoveLeft();
|
||||
bool CursorMoveRight();
|
||||
bool CursorMoveUp();
|
||||
@ -426,15 +441,32 @@ public:
|
||||
bool CursorMoveToParagraphEnd();
|
||||
bool CursorMoveHome();
|
||||
bool CursorMoveEnd();
|
||||
void CalcLineSidesIndexByPosition(int32_t& startIndex, int32_t& endIndex);
|
||||
RectF CalcLineInfoByPosition();
|
||||
CaretOffsetInfo GetCaretOffsetInfoByPosition(int32_t position = -1);
|
||||
int32_t CalcMoveUpPos(float& leadingMarginOffset);
|
||||
int32_t CalcMoveDownPos(float& leadingMarginOffset);
|
||||
int32_t CalcLineBeginPosition();
|
||||
float GetTextThemeFontSize();
|
||||
int32_t CalcLineEndPosition();
|
||||
int32_t CalcLineEndPosition(int32_t index = -1);
|
||||
bool CursorMoveLineBegin();
|
||||
bool CursorMoveLineEnd();
|
||||
void HandleSelectFontStyle(KeyCode code) override;
|
||||
void HandleSelectFontStyleWrapper(KeyCode code, TextStyle& spanStyle);
|
||||
void HandleOnShowMenu() override;
|
||||
int32_t HandleSelectPosition(bool isForward);
|
||||
int32_t HandleSelectParagraghPos(bool direction);
|
||||
PositionType GetPositionTypeFromLine();
|
||||
int32_t HandleSelectWrapper(CaretMoveIntent direction, int32_t fixedPos);
|
||||
void AIDeleteComb(int32_t start, int32_t end, int32_t& aiPosition, bool direction);
|
||||
bool HandleOnDeleteComb(bool backward) override;
|
||||
int32_t GetLeftWordPosition(int32_t caretPosition);
|
||||
int32_t GetRightWordPosition(int32_t caretPosition);
|
||||
int32_t GetParagraphBeginPosition(int32_t caretPosition);
|
||||
int32_t GetParagraphEndPosition(int32_t caretPosition);
|
||||
int32_t CaretPositionSelectEmoji(CaretMoveIntent direction);
|
||||
void HandleSelect(CaretMoveIntent direction) override;
|
||||
void SetCaretPositionWithAffinity(PositionWithAffinity positionWithAffinity);
|
||||
bool SetCaretPosition(int32_t pos, bool needNotifyImf = true);
|
||||
int32_t GetCaretPosition();
|
||||
int32_t GetTextContentLength() override;
|
||||
@ -457,15 +489,30 @@ public:
|
||||
void CloseSelectionMenu();
|
||||
bool SetCaretOffset(int32_t caretPosition);
|
||||
void ResetFirstNodeStyle();
|
||||
void DoDeleteActions(const RichEditorDeleteValue& info);
|
||||
bool DoDeleteActions(int32_t currentPosition, int32_t length, RichEditorDeleteValue& info);
|
||||
|
||||
void UpdateSpanStyle(int32_t start, int32_t end, const TextStyle& textStyle, const ImageSpanAttribute& imageStyle);
|
||||
std::string GetContentBySpans();
|
||||
ResultObject TextEmojiSplit(int32_t& start, int32_t end, std::string& content);
|
||||
SelectionInfo GetEmojisBySelect(int32_t start, int32_t end);
|
||||
void MixTextEmojiUpdateStyle(int32_t start, int32_t end, TextStyle textStyle, ImageSpanAttribute imageStyle);
|
||||
void SetSelectSpanStyle(int32_t start, int32_t end, KeyCode code, bool isStart);
|
||||
void GetSelectSpansPositionInfo(
|
||||
int32_t& start, int32_t& end, SpanPositionInfo& startPositionSpanInfo, SpanPositionInfo& endPositionSpanInfo);
|
||||
std::list<RefPtr<UINode>>::const_iterator GetSpanNodeIter(int32_t index);
|
||||
std::list<SpanPosition> GetSelectSpanSplit(
|
||||
SpanPositionInfo& startPositionSpanInfo, SpanPositionInfo& endPositionSpanInfo);
|
||||
std::list<SpanPosition> GetSelectSpanInfo(int32_t start, int32_t end);
|
||||
bool IsTextSpanFromResult(int32_t& start, int32_t& end, KeyCode code);
|
||||
void UpdateSelectSpanStyle(int32_t start, int32_t end, KeyCode code);
|
||||
bool SymbolSpanUpdateStyle(RefPtr<SpanNode>& spanNode, struct UpdateSpanStyle updateSpanStyle, TextStyle textStyle);
|
||||
void SetUpdateSpanStyle(struct UpdateSpanStyle updateSpanStyle);
|
||||
struct UpdateSpanStyle GetUpdateSpanStyle();
|
||||
void UpdateParagraphStyle(int32_t start, int32_t end, const struct UpdateParagraphStyle& style);
|
||||
void UpdateParagraphStyle(RefPtr<SpanNode> spanNode, const struct UpdateParagraphStyle& style);
|
||||
std::vector<ParagraphInfo> GetParagraphInfo(int32_t start, int32_t end);
|
||||
void SetTypingStyle(std::optional<struct UpdateSpanStyle> typingStyle, std::optional<TextStyle> textStyle);
|
||||
std::optional<struct UpdateSpanStyle> GetTypingStyle();
|
||||
int32_t AddImageSpan(const ImageSpanOptions& options, bool isPaste = false, int32_t index = -1,
|
||||
bool updateCaret = true);
|
||||
int32_t AddTextSpan(TextSpanOptions options, bool isPaste = false, int32_t index = -1);
|
||||
@ -503,6 +550,7 @@ public:
|
||||
bool JudgeContentDraggable();
|
||||
std::pair<OffsetF, float> CalculateCaretOffsetAndHeight();
|
||||
std::pair<OffsetF, float> CalculateEmptyValueCaretRect();
|
||||
TextAlign GetTextAlignByDirection();
|
||||
void RemoveEmptySpan(std::set<int32_t, std::greater<int32_t>>& deleteSpanIndexs);
|
||||
void RemoveEmptySpanItems();
|
||||
void RemoveEmptySpanNodes();
|
||||
@ -730,21 +778,22 @@ public:
|
||||
return isShowPlaceholder_;
|
||||
}
|
||||
|
||||
void SetPlaceholder(std::vector<std::list<RefPtr<SpanItem>>>& spanItemList);
|
||||
bool SetPlaceholder(std::vector<std::list<RefPtr<SpanItem>>>& spanItemList);
|
||||
|
||||
void SetCaretColor(const DynamicColor& caretColor)
|
||||
void SetCaretColor(const Color& caretColor)
|
||||
{
|
||||
caretColor_ = caretColor;
|
||||
IF_TRUE(SelectOverlayIsOn(), selectOverlay_->UpdateHandleColor());
|
||||
}
|
||||
|
||||
DynamicColor GetCaretColor();
|
||||
Color GetCaretColor();
|
||||
|
||||
void SetSelectedBackgroundColor(const DynamicColor& selectedBackgroundColor)
|
||||
void SetSelectedBackgroundColor(const Color& selectedBackgroundColor)
|
||||
{
|
||||
selectedBackgroundColor_ = selectedBackgroundColor;
|
||||
}
|
||||
|
||||
DynamicColor GetSelectedBackgroundColor();
|
||||
Color GetSelectedBackgroundColor();
|
||||
|
||||
void SetCustomKeyboardOption(bool supportAvoidance);
|
||||
|
||||
@ -794,6 +843,8 @@ public:
|
||||
|
||||
OffsetF GetTextPaintOffset() const override;
|
||||
OffsetF GetPaintRectGlobalOffset() const;
|
||||
// original local point to transformed global point.
|
||||
void HandlePointWithTransform(OffsetF& point);
|
||||
|
||||
float GetCrossOverHeight() const;
|
||||
|
||||
@ -807,6 +858,7 @@ public:
|
||||
void AdjustSelector(int32_t& start, int32_t& end, SelectorAdjustPolicy policy = SelectorAdjustPolicy::INCLUDE);
|
||||
bool AdjustSelectorForSymbol(int32_t& index, HandleType handleType, SelectorAdjustPolicy policy);
|
||||
bool AdjustSelectorForEmoji(int32_t& index, HandleType handleType, SelectorAdjustPolicy policy);
|
||||
EmojiRelation GetEmojiRelation(int index);
|
||||
void UpdateSelector(int32_t start, int32_t end);
|
||||
void UpdateSelectionType(const SelectionInfo& textSelectInfo);
|
||||
std::list<RefPtr<SpanItem>>::iterator GetSpanIter(int32_t index);
|
||||
@ -857,12 +909,18 @@ public:
|
||||
}
|
||||
|
||||
TextStyle GetDefaultTextStyle();
|
||||
void SetEnableHapticFeedback(bool isEnabled)
|
||||
{
|
||||
isEnableHapticFeedback_ = isEnabled;
|
||||
}
|
||||
|
||||
void SetRequestKeyboardOnFocus(bool needToRequest)
|
||||
{
|
||||
needToRequestKeyboardOnFocus_ = needToRequest;
|
||||
}
|
||||
|
||||
bool IsTextEditableForStylus() const override;
|
||||
|
||||
NG::DragDropInfo HandleDragStart(const RefPtr<Ace::DragEvent>& event, const std::string& extraParams);
|
||||
|
||||
void RequestFocusWhenSelected()
|
||||
@ -875,12 +933,16 @@ public:
|
||||
isOnlyRequestFocus_ = true;
|
||||
}
|
||||
|
||||
bool IsTextEditableForStylus() const override;
|
||||
DisplayMode GetBarDisplayMode()
|
||||
{
|
||||
return barDisplayMode_.value_or(DisplayMode::AUTO);
|
||||
}
|
||||
|
||||
void SetImagePreviewMenuParam(std::function<void()>& builder, const SelectMenuParam& menuParam);
|
||||
|
||||
protected:
|
||||
bool CanStartAITask() override;
|
||||
|
||||
template<typename T>
|
||||
RefPtr<T> GetTheme()
|
||||
{
|
||||
@ -934,10 +996,12 @@ private:
|
||||
void UpdateImageStyle(RefPtr<FrameNode>& imageNode, const ImageSpanAttribute& imageStyle);
|
||||
void UpdateImageAttribute(RefPtr<FrameNode>& imageNode, const ImageSpanAttribute& imageStyle);
|
||||
void InitTouchEvent();
|
||||
void InitPanEvent();
|
||||
bool SelectOverlayIsOn();
|
||||
void HandleLongPress(GestureEvent& info);
|
||||
void HandleDoubleClickOrLongPress(GestureEvent& info);
|
||||
void HandleDoubleClickOrLongPress(GestureEvent& info, RefPtr<FrameNode> host);
|
||||
void StartVibratorByLongPress();
|
||||
std::string GetPositionSpansText(int32_t position, int32_t& startSpan);
|
||||
void FireOnSelect(int32_t selectStart, int32_t selectEnd);
|
||||
void FireOnSelectionChange(const int32_t caretPosition);
|
||||
@ -952,12 +1016,13 @@ private:
|
||||
void HandleMouseRightButton(const MouseInfo& info);
|
||||
void HandleMouseEvent(const MouseInfo& info);
|
||||
void HandleTouchEvent(const TouchEventInfo& info);
|
||||
void HandleTouchDown(const Offset& offset);
|
||||
void HandleTouchDown(const TouchEventInfo& info);
|
||||
void HandleTouchUp();
|
||||
void HandleTouchUpAfterLongPress();
|
||||
void HandleTouchMove(const Offset& offset);
|
||||
void UpdateCaretByTouchMove(const Offset& offset);
|
||||
Offset AdjustLocalOffsetOnMoveEvent(const Offset& originalOffset);
|
||||
void StartVibratorByIndexChange(int32_t currentIndex, int32_t preIndex);
|
||||
void InitLongPressEvent(const RefPtr<GestureEventHub>& gestureHub);
|
||||
void UseHostToUpdateTextFieldManager();
|
||||
void UpdateTextFieldManager(const Offset& offset, float height);
|
||||
@ -973,11 +1038,10 @@ private:
|
||||
std::string GetPlaceHolderInJson() const;
|
||||
std::string GetTextColorInJson(const std::optional<Color>& value) const;
|
||||
void FillPreviewMenuInJson(const std::unique_ptr<JsonValue>& jsonValue) const override;
|
||||
void InsertValueInSpanOffset(const TextInsertValueInfo& info, std::wstring& text, const std::wstring& insertValue);
|
||||
void ResetSelectionAfterAddSpan(bool isPaste);
|
||||
void SetResultObjectText(ResultObject& resultObject, const RefPtr<SpanItem>& spanItem) override;
|
||||
SelectionInfo GetAdjustedSelectionInfo(const SelectionInfo& textSelectInfo);
|
||||
void ResetAfterTextChange() override {};
|
||||
void ResetAfterTextChange() override {};
|
||||
void InitPlaceholderSpansMap(
|
||||
RefPtr<SpanItem>& newSpanItem, const RefPtr<SpanItem>& spanItem, size_t& index, size_t& placeholderGains);
|
||||
void ReplacePlaceholderWithCustomSpan(const RefPtr<SpanItem>& spanItem, size_t& index, size_t& textIndex);
|
||||
@ -985,7 +1049,9 @@ private:
|
||||
void ReplacePlaceholderWithImageSpan(const RefPtr<SpanItem>& spanItem, size_t& index, size_t& textIndex);
|
||||
void AddDragFrameNodeToManager(const RefPtr<FrameNode>& frameNode)
|
||||
{
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
auto host = GetHost();
|
||||
CHECK_NULL_VOID(host);
|
||||
auto context = host->GetContext();
|
||||
CHECK_NULL_VOID(context);
|
||||
auto dragDropManager = context->GetDragDropManager();
|
||||
CHECK_NULL_VOID(dragDropManager);
|
||||
@ -994,7 +1060,9 @@ private:
|
||||
|
||||
void RemoveDragFrameNodeFromManager(const RefPtr<FrameNode>& frameNode)
|
||||
{
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
auto host = GetHost();
|
||||
CHECK_NULL_VOID(host);
|
||||
auto context = host->GetContext();
|
||||
CHECK_NULL_VOID(context);
|
||||
auto dragDropManager = context->GetDragDropManager();
|
||||
CHECK_NULL_VOID(dragDropManager);
|
||||
@ -1077,10 +1145,11 @@ private:
|
||||
void UpdateScrollStateAfterLayout(bool shouldDisappear);
|
||||
void ScheduleAutoScroll(AutoScrollParam param);
|
||||
void OnAutoScroll(AutoScrollParam param);
|
||||
void StopAutoScroll();
|
||||
void StopAutoScroll(bool hideBarImmediately = true);
|
||||
void AutoScrollByEdgeDetection(AutoScrollParam param, OffsetF offset, EdgeDetectionStrategy strategy);
|
||||
float CalcDragSpeed(float hotAreaStart, float hotAreaEnd, float point);
|
||||
float MoveTextRect(float offset);
|
||||
void SetNeedMoveCaretToContentRect();
|
||||
void MoveCaretToContentRect();
|
||||
void MoveCaretToContentRect(const OffsetF& caretOffset, float caretHeight);
|
||||
void MoveCaretToContentRect(float offset, int32_t source);
|
||||
@ -1098,7 +1167,8 @@ private:
|
||||
void AdjustCursorPosition(int32_t& pos);
|
||||
void AdjustPlaceholderSelection(int32_t& start, int32_t& end, const Offset& pos);
|
||||
bool AdjustWordSelection(int32_t& start, int32_t& end);
|
||||
bool IsTouchBeforeCaret(int32_t caretPos, const Offset& touchPos);
|
||||
bool IsTouchAtLineEnd(int32_t caretPos, const Offset& textOffset);
|
||||
bool IsTouchBeforeCaret(int32_t caretPos, const Offset& textOffset);
|
||||
bool IsClickBoundary(const int32_t position);
|
||||
|
||||
bool IsReachTop()
|
||||
@ -1138,12 +1208,14 @@ private:
|
||||
void AddSpanByPasteData(const RefPtr<SpanString>& spanString);
|
||||
void CompleteStyledString(RefPtr<SpanString>& spanString);
|
||||
void InsertStyledStringByPaste(const RefPtr<SpanString>& spanString);
|
||||
void HandleOnDragInsertStyledString(const RefPtr<SpanString>& spanString);
|
||||
void AddSpansByPaste(const std::list<RefPtr<NG::SpanItem>>& spans);
|
||||
TextSpanOptions GetTextSpanOptions(const RefPtr<SpanItem>& spanItem);
|
||||
void HandleOnCopyStyledString();
|
||||
void HandleOnDragDropStyledString(const RefPtr<OHOS::Ace::DragEvent>& event);
|
||||
void NotifyExitTextPreview();
|
||||
void ProcessInsertValue(const std::string& insertValue, bool isIME = false, bool calledbyImf = false);
|
||||
void ProcessInsertValue(const std::string& insertValue, OperationType operationType = OperationType::DEFAULT,
|
||||
bool calledbyImf = false);
|
||||
void FinishTextPreviewInner();
|
||||
void UpdateSelectionByTouchMove(const Offset& offset);
|
||||
void MoveCaretAnywhere(const Offset& touchOffset);
|
||||
@ -1211,6 +1283,7 @@ private:
|
||||
int32_t caretPosition_ = 0;
|
||||
int32_t caretSpanIndex_ = -1;
|
||||
long long timestamp_ = 0;
|
||||
CaretAffinityPolicy caretAffinityPolicy_ = CaretAffinityPolicy::DEFAULT;
|
||||
OffsetF selectionMenuOffsetByMouse_;
|
||||
OffsetF selectionMenuOffsetClick_;
|
||||
OffsetF lastClickOffset_;
|
||||
@ -1223,6 +1296,7 @@ private:
|
||||
std::vector<OperationRecord> redoOperationRecords_;
|
||||
|
||||
RefPtr<TouchEventImpl> touchListener_;
|
||||
RefPtr<PanEvent> panEvent_;
|
||||
struct UpdateSpanStyle updateSpanStyle_;
|
||||
CancelableCallback<void()> caretTwinklingTask_;
|
||||
RefPtr<RichEditorController> richEditorController_;
|
||||
@ -1232,8 +1306,8 @@ private:
|
||||
std::optional<struct UpdateSpanStyle> typingStyle_;
|
||||
std::optional<TextStyle> typingTextStyle_;
|
||||
std::list<ResultObject> dragResultObjects_;
|
||||
std::optional<DynamicColor> caretColor_;
|
||||
std::optional<DynamicColor> selectedBackgroundColor_;
|
||||
std::optional<Color> caretColor_;
|
||||
std::optional<Color> selectedBackgroundColor_;
|
||||
std::function<void()> customKeyboardBuilder_;
|
||||
std::function<void(int32_t)> caretChangeListener_;
|
||||
RefPtr<OverlayManager> keyboardOverlay_;
|
||||
@ -1290,8 +1364,10 @@ private:
|
||||
std::queue<std::function<void()>> tasks_;
|
||||
bool isModifyingContent_ = false;
|
||||
bool needToRequestKeyboardOnFocus_ = true;
|
||||
std::unordered_map<std::string, RefPtr<SpanItem>> placeholderSpansMap_;
|
||||
bool isEnableHapticFeedback_ = true;
|
||||
std::optional<DisplayMode> barDisplayMode_ = std::nullopt;
|
||||
std::shared_ptr<OneStepDragParam> oneStepDragParam_ = nullptr;
|
||||
std::unordered_map<std::string, RefPtr<SpanItem>> placeholderSpansMap_;
|
||||
std::queue<WeakPtr<ImageSpanNode>> dirtyImageNodes;
|
||||
bool isImageSelfResponseEvent_ = true;
|
||||
};
|
||||
|
@ -24,11 +24,13 @@
|
||||
#include "core/components_ng/manager/select_content_overlay/select_content_overlay_manager.h"
|
||||
#include "core/components_ng/pattern/select_overlay/select_overlay_property.h"
|
||||
#include "core/components_ng/pattern/rich_editor/rich_editor_pattern.h"
|
||||
#include "core/components/text_overlay/text_overlay_theme.h"
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
namespace {
|
||||
constexpr float BOX_EPSILON = 0.5f;
|
||||
constexpr float DOUBLE = 2.0f;
|
||||
constexpr SelectOverlayDirtyFlag UPDATE_HANDLE_COLOR_FLAG = 101;
|
||||
}
|
||||
|
||||
bool RichEditorSelectOverlay::PreProcessOverlay(const OverlayRequest& request)
|
||||
@ -186,9 +188,11 @@ void RichEditorSelectOverlay::UpdateSelectorOnHandleMove(const OffsetF& handleOf
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
auto& textSelector = pattern->textSelector_;
|
||||
auto currentHandleIndex = pattern->GetHandleIndex(Offset(handleOffset.GetX(), handleOffset.GetY()));
|
||||
auto preHandleIndex = isFirst ? textSelector.baseOffset : textSelector.destinationOffset;
|
||||
pattern->StartVibratorByIndexChange(currentHandleIndex, preHandleIndex);
|
||||
pattern->SetCaretPosition(currentHandleIndex);
|
||||
if (isFirst) {
|
||||
pattern->HandleSelectionChange(currentHandleIndex, textSelector.destinationOffset);
|
||||
pattern->HandleSelectionChange(currentHandleIndex, initSelector_.second);
|
||||
} else {
|
||||
pattern->SetCaretPosition(currentHandleIndex);
|
||||
if (IsSingleHandle()) {
|
||||
@ -196,7 +200,7 @@ void RichEditorSelectOverlay::UpdateSelectorOnHandleMove(const OffsetF& handleOf
|
||||
pattern->CalcAndRecordLastClickCaretInfo(Offset(textOffset.GetX(), textOffset.GetY()));
|
||||
textSelector.Update(currentHandleIndex);
|
||||
} else {
|
||||
pattern->HandleSelectionChange(textSelector.baseOffset, currentHandleIndex);
|
||||
pattern->HandleSelectionChange(initSelector_.first, currentHandleIndex);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -215,14 +219,14 @@ void RichEditorSelectOverlay::OnHandleMoveDone(const RectF& handleRect, bool isF
|
||||
auto selectEnd = std::max(textSelector.baseOffset, textSelector.destinationOffset);
|
||||
pattern->FireOnSelect(selectStart, selectEnd);
|
||||
if (!IsSingleHandle()) {
|
||||
pattern->SetCaretPosition(selectEnd);
|
||||
pattern->SetCaretPositionWithAffinity({ selectEnd, TextAffinity::UPSTREAM });
|
||||
}
|
||||
pattern->StopAutoScroll();
|
||||
pattern->magnifierController_->RemoveMagnifierFrameNode();
|
||||
if (!IsSingleHandle() && textSelector.StartEqualToDest()) {
|
||||
HideMenu();
|
||||
CloseOverlay(true, CloseReason::CLOSE_REASON_NORMAL);
|
||||
pattern->StartTwinkling();
|
||||
IF_TRUE(pattern->IsEditing(), pattern->StartTwinkling());
|
||||
return;
|
||||
}
|
||||
auto overlayManager = GetManager<SelectContentOverlayManager>();
|
||||
@ -290,10 +294,7 @@ void RichEditorSelectOverlay::OnUpdateSelectOverlayInfo(SelectOverlayInfo& selec
|
||||
auto responseType = pattern->textResponseType_.value_or(TextResponseType::NONE);
|
||||
auto& firstHandle = pattern->textSelector_.firstHandle;
|
||||
auto& secondHandle = pattern->textSelector_.secondHandle;
|
||||
if (!usingMouse && responseType == TextResponseType::LONG_PRESS && pattern->sourceType_ != SourceType::MOUSE) {
|
||||
selectInfo.firstHandle.paintRect = firstHandle;
|
||||
selectInfo.secondHandle.paintRect = secondHandle;
|
||||
} else {
|
||||
if (usingMouse && pattern->sourceType_ == SourceType::MOUSE) {
|
||||
if (responseType == TextResponseType::LONG_PRESS) {
|
||||
pattern->SetTextResponseType(TextResponseType::RIGHT_CLICK);
|
||||
responseType = TextResponseType::RIGHT_CLICK;
|
||||
@ -301,6 +302,9 @@ void RichEditorSelectOverlay::OnUpdateSelectOverlayInfo(SelectOverlayInfo& selec
|
||||
selectInfo.isUsingMouse = true;
|
||||
selectInfo.rightClickOffset = pattern->GetSelectionMenuOffset();
|
||||
pattern->ResetIsMousePressed();
|
||||
} else {
|
||||
selectInfo.firstHandle.paintRect = firstHandle;
|
||||
selectInfo.secondHandle.paintRect = secondHandle;
|
||||
}
|
||||
selectInfo.menuInfo.responseType = static_cast<int32_t>(responseType);
|
||||
selectInfo.menuInfo.editorType = static_cast<int32_t>(pattern->GetEditorType());
|
||||
@ -401,7 +405,6 @@ void RichEditorSelectOverlay::OnCloseOverlay(OptionMenuType menuType, CloseReaso
|
||||
IF_TRUE(needResetSelection, pattern->ResetSelection());
|
||||
IF_TRUE(isHoldByOther, pattern->CloseSelectOverlay());
|
||||
if (isBackPressed) {
|
||||
pattern->ResetSelection();
|
||||
if (pattern->IsEditing()) {
|
||||
TAG_LOGI(AceLogTag::ACE_RICH_TEXT, "only show caret for edit state");
|
||||
pattern->isCursorAlwaysDisplayed_ = false;
|
||||
@ -475,14 +478,13 @@ void RichEditorSelectOverlay::OnHandleMoveStart(const GestureEvent& event, bool
|
||||
isHandleMoving_ = true;
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
initSelector_ = { pattern->textSelector_.GetTextStart(), pattern->textSelector_.GetTextEnd() };
|
||||
pattern->ChangeHandleHeight(event, isFirst, IsOverlayMode());
|
||||
auto manager = GetManager<SelectContentOverlayManager>();
|
||||
CHECK_NULL_VOID(manager);
|
||||
manager->MarkInfoChange(isFirst ? DIRTY_FIRST_HANDLE : DIRTY_SECOND_HANDLE);
|
||||
manager->SetHandleCircleIsShow(isFirst, false);
|
||||
if (IsSingleHandle()) {
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
pattern->ShowCaretWithoutTwinkling();
|
||||
manager->SetIsHandleLineShow(false);
|
||||
}
|
||||
@ -517,7 +519,7 @@ void RichEditorSelectOverlay::UpdateSelectOverlayOnAreaChanged()
|
||||
|
||||
void RichEditorSelectOverlay::SwitchCaretState()
|
||||
{
|
||||
CHECK_NULL_VOID(IsSingleHandle());
|
||||
CHECK_NULL_VOID(IsSingleHandle() && !isHandleMoving_);
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
auto singleHandlePaintRect = pattern->textSelector_.secondHandle;
|
||||
@ -580,4 +582,40 @@ void RichEditorSelectOverlay::OnAfterSelectOverlayShow(bool isCreate)
|
||||
}
|
||||
}
|
||||
|
||||
float RichEditorSelectOverlay::GetHandleHotZoneRadius()
|
||||
{
|
||||
auto hotZoneRadius = 0.0f;
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_RETURN(pattern, hotZoneRadius);
|
||||
auto host = pattern->GetHost();
|
||||
CHECK_NULL_RETURN(host, hotZoneRadius);
|
||||
auto pipeline = host->GetContext();
|
||||
CHECK_NULL_RETURN(pipeline, hotZoneRadius);
|
||||
auto theme = pipeline->GetTheme<TextOverlayTheme>();
|
||||
CHECK_NULL_RETURN(theme, hotZoneRadius);
|
||||
hotZoneRadius = theme->GetHandleHotZoneRadius().ConvertToPx();
|
||||
return hotZoneRadius;
|
||||
}
|
||||
|
||||
void RichEditorSelectOverlay::OnHandleMarkInfoChange(
|
||||
std::shared_ptr<SelectOverlayInfo> info, SelectOverlayDirtyFlag flag)
|
||||
{
|
||||
CHECK_NULL_VOID((flag & UPDATE_HANDLE_COLOR_FLAG) == UPDATE_HANDLE_COLOR_FLAG);
|
||||
CHECK_NULL_VOID(info);
|
||||
|
||||
auto manager = GetManager<SelectContentOverlayManager>();
|
||||
CHECK_NULL_VOID(manager);
|
||||
auto pattern = GetPattern<RichEditorPattern>();
|
||||
CHECK_NULL_VOID(pattern);
|
||||
info->handlerColor = pattern->caretColor_;
|
||||
manager->MarkHandleDirtyNode(PROPERTY_UPDATE_RENDER);
|
||||
}
|
||||
|
||||
void RichEditorSelectOverlay::UpdateHandleColor()
|
||||
{
|
||||
auto manager = GetManager<SelectContentOverlayManager>();
|
||||
CHECK_NULL_VOID(manager);
|
||||
manager->MarkInfoChange(UPDATE_HANDLE_COLOR_FLAG);
|
||||
}
|
||||
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -51,6 +51,8 @@ public:
|
||||
void OnCloseOverlay(OptionMenuType menuType, CloseReason reason, RefPtr<OverlayInfo> info = nullptr) override;
|
||||
void OnHandleGlobalTouchEvent(SourceType sourceType, TouchType touchType, bool touchInside = true) override;
|
||||
void OnHandleLevelModeChanged(HandleLevelMode mode) override;
|
||||
void OnHandleMarkInfoChange(std::shared_ptr<SelectOverlayInfo> info, SelectOverlayDirtyFlag flag) override;
|
||||
void UpdateHandleColor();
|
||||
std::optional<SelectOverlayInfo> GetSelectOverlayInfo();
|
||||
bool IsSingleHandleShow();
|
||||
void UpdateMenuOffset();
|
||||
@ -72,6 +74,7 @@ public:
|
||||
{
|
||||
return isHandleMoving_;
|
||||
}
|
||||
float GetHandleHotZoneRadius();
|
||||
|
||||
private:
|
||||
void RemoveAreaChangeInner();
|
||||
@ -83,6 +86,7 @@ private:
|
||||
std::pair<TextSpanType, TextResponseType> lastSelectResponseComb_;
|
||||
bool needRefreshMenu_ = false;
|
||||
bool handleIsHidden_ = true;
|
||||
std::pair<int32_t, int32_t> initSelector_ = { 0, 0 };
|
||||
|
||||
ACE_DISALLOW_COPY_AND_MOVE(RichEditorSelectOverlay);
|
||||
};
|
||||
|
@ -30,6 +30,7 @@ namespace OHOS::Ace::NG {
|
||||
namespace {
|
||||
constexpr Color DEFAULT_TEXT_COLOR = Color(0xe5000000);
|
||||
constexpr float DRAG_BACKGROUND_OPACITY = 0.95f;
|
||||
constexpr float DEFAULT_TEXT_SIZE = 16.0f;
|
||||
} // namespace
|
||||
|
||||
class RichEditorTheme : public virtual Theme {
|
||||
@ -88,6 +89,7 @@ public:
|
||||
theme->richeditorShowHandle_ = StringUtils::StringToInt(showHandle);
|
||||
theme->textStyle_.SetTextColor(pattern->GetAttr<Color>("default_text_color", DEFAULT_TEXT_COLOR));
|
||||
theme->textStyle_.SetTextDecorationColor(pattern->GetAttr<Color>("default_text_color", DEFAULT_TEXT_COLOR));
|
||||
theme->textStyle_.SetFontSize(Dimension(DEFAULT_TEXT_SIZE, DimensionUnit::FP));
|
||||
theme->aiWriteBundleName_ = pattern->GetAttr<std::string>("rich_editor_writting_bundle_name", "");
|
||||
theme->aiWriteAbilityName_ = pattern->GetAttr<std::string>("rich_editor_writting_ability_name", "");
|
||||
theme->aiWriteIsSupport_ = pattern->GetAttr<std::string>("rich_editor_writting_is_support", "");
|
||||
|
@ -89,7 +89,9 @@ struct SymbolSpanStyle {
|
||||
for (const auto& color : style.GetSymbolColorList()) {
|
||||
symbolColor += color.ColorToString() + ",";
|
||||
}
|
||||
symbolColor = symbolColor.substr(0, symbolColor.size() - 1);
|
||||
if (symbolColor.size() > 0) {
|
||||
symbolColor = symbolColor.substr(0, symbolColor.size() - 1);
|
||||
}
|
||||
symbolColor = symbolColor.empty() ? DEFAULT_SYMBOL_COLOR.ColorToString() : symbolColor;
|
||||
|
||||
fontFeature = style.GetFontFeatures();
|
||||
|
@ -206,9 +206,7 @@ RefPtr<FrameNode> ServiceCollaborationMenuAceHelper::CreateMainMenuItem(
|
||||
menuItemProperty->UpdatePadding({ .right = CalcLength(2.0f), .top = CalcLength(0.0f) });
|
||||
auto renderContext = menuItemNode->GetRenderContext();
|
||||
CHECK_NULL_RETURN(renderContext, nullptr);
|
||||
BorderRadiusProperty border;
|
||||
border.SetRadius(menuTheme->GetInnerBorderRadius());
|
||||
renderContext->UpdateBorderRadius(border);
|
||||
renderContext->UpdateBorderRadius(BorderRadiusProperty(menuTheme->GetMenuDefaultInnerRadius()));
|
||||
auto row = FrameNode::CreateFrameNode(V2::ROW_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
|
||||
AceType::MakeRefPtr<LinearLayoutPattern>(false));
|
||||
CHECK_NULL_RETURN(row, nullptr);
|
||||
@ -227,7 +225,10 @@ RefPtr<FrameNode> ServiceCollaborationMenuAceHelper::CreateMainMenuItem(
|
||||
rowContext->UpdateBorderColor(borderColorProperty);
|
||||
rowProperty->UpdateCalcMinSize(
|
||||
CalcSize(CalcLength(static_cast<float>(MENUITEM_WIDTH)), CalcLength(static_cast<float>(MENUITEM_HEIGHT))));
|
||||
PaddingProperty rowpadding {.right = CalcLength(static_cast<float>(PANDDING_ZERO))};
|
||||
PaddingProperty rowpadding { .right = CalcLength(static_cast<float>(PANDDING_ZERO)) };
|
||||
if (Container::GreatOrEqualAPITargetVersion(PlatformVersion::VERSION_TWELVE)) {
|
||||
rowpadding.top = CalcLength(menuTheme->GetMenuItemVerticalPadding().ConvertToPx());
|
||||
}
|
||||
rowProperty->UpdatePadding(rowpadding);
|
||||
MarginProperty margin;
|
||||
margin.bottom = CalcLength(static_cast<float>(ROW_PADDING));
|
||||
@ -273,9 +274,7 @@ RefPtr<FrameNode> ServiceCollaborationMenuAceHelper::CreateDeviceMenuItem(
|
||||
CHECK_NULL_RETURN(menuItemNode, nullptr);
|
||||
auto renderContext = menuItemNode->GetRenderContext();
|
||||
CHECK_NULL_RETURN(renderContext, nullptr);
|
||||
BorderRadiusProperty border;
|
||||
border.SetRadius(menuTheme->GetInnerBorderRadius());
|
||||
renderContext->UpdateBorderRadius(border);
|
||||
renderContext->UpdateBorderRadius(BorderRadiusProperty(menuTheme->GetMenuDefaultInnerRadius()));
|
||||
auto row = FrameNode::CreateFrameNode(V2::ROW_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
|
||||
AceType::MakeRefPtr<LinearLayoutPattern>(false));
|
||||
CHECK_NULL_RETURN(row, nullptr);
|
||||
@ -284,10 +283,11 @@ RefPtr<FrameNode> ServiceCollaborationMenuAceHelper::CreateDeviceMenuItem(
|
||||
MarginProperty margin;
|
||||
margin.top = CalcLength(static_cast<float>(MENUITEM_MARGIN));
|
||||
margin.bottom = CalcLength(static_cast<float>(MENUITEM_MARGIN));
|
||||
auto size = CalcSize();
|
||||
size.SetHeight(CalcLength(static_cast<float>(MENUITEM_HEIGHT)));
|
||||
rowProperty->UpdateMargin(margin);
|
||||
rowProperty->UpdateUserDefinedIdealSize(size);
|
||||
auto menuHeight = Container::GreatOrEqualAPITargetVersion(PlatformVersion::VERSION_TWELVE)
|
||||
? menuTheme->GetMenuChildMinHeight().ConvertToPx()
|
||||
: menuTheme->GetOptionMinHeight().ConvertToPx();
|
||||
rowProperty->UpdateCalcMinSize(CalcSize(std::nullopt, CalcLength(menuHeight)));
|
||||
CreateStartIcon(icon, row);
|
||||
CreateText(value, row, richTheme->GetMenuTextColor(), false);
|
||||
row->MountToParent(menuItemNode);
|
||||
@ -388,22 +388,24 @@ RefPtr<FrameNode> ServiceCollaborationMenuAceHelper::CreateSubDeviceMenuOnCol(
|
||||
auto subMenu = MenuView::Create(column, SUB_MENU_ID, SUN_MENU_TAG, param);
|
||||
auto inputHub = subMenu->GetOrCreateInputEventHub();
|
||||
CHECK_NULL_RETURN(inputHub, nullptr);
|
||||
auto mouseTask = [this, weak = AceType::WeakClaim(AceType::RawPtr(menuWrapper))](bool isHover) {
|
||||
auto mouseTask = [weakHelper = WeakClaim(this), weakMenuWrapper = WeakClaim(RawPtr(menuWrapper))](bool isHover) {
|
||||
auto helper = weakHelper.Upgrade();
|
||||
CHECK_NULL_VOID(helper);
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "mouseTask, isHover=%{public}d", isHover);
|
||||
auto menuWrapper = weak.Upgrade();
|
||||
if (isHover) {
|
||||
subMenuIsHover_ = true;
|
||||
helper->subMenuIsHover_ = true;
|
||||
return;
|
||||
}
|
||||
subMenuIsHover_ = false;
|
||||
helper->subMenuIsHover_ = false;
|
||||
ContainerScope scope(Container::CurrentIdSafely());
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
CHECK_NULL_VOID(context);
|
||||
auto cancelableCallback = [this, weak2 = AceType::WeakClaim(AceType::RawPtr(menuWrapper)),
|
||||
instanceId = Container::CurrentIdSafely()] {
|
||||
auto menuWrapper = weak2.Upgrade();
|
||||
auto cancelableCallback = [weakHelper, weakMenuWrapper, instanceId = Container::CurrentIdSafely()] {
|
||||
auto helper = weakHelper.Upgrade();
|
||||
auto menuWrapper = weakMenuWrapper.Upgrade();
|
||||
CHECK_NULL_VOID(helper && menuWrapper);
|
||||
ContainerScope scope(instanceId);
|
||||
RemoveSubmenu(menuWrapper);
|
||||
helper->RemoveSubmenu(menuWrapper);
|
||||
};
|
||||
auto taskExecutor = context->GetTaskExecutor();
|
||||
CHECK_NULL_VOID(taskExecutor);
|
||||
@ -421,41 +423,44 @@ void ServiceCollaborationMenuAceHelper::SubMeunMountToMainMenu(
|
||||
{
|
||||
auto inputHub = menuNode->GetOrCreateInputEventHub();
|
||||
CHECK_NULL_VOID(inputHub);
|
||||
auto mouseTask = [this, &menuNode, wrapper = AceType::WeakClaim(AceType::RawPtr(menuWrapper)),
|
||||
subDeviceMenuCreator, node = AceType::WeakClaim(AceType::RawPtr(menuNode))](bool isHover) {
|
||||
auto menuItemNode = node.Upgrade();
|
||||
auto menuWrapper = wrapper.Upgrade();
|
||||
auto mouseTask = [weakHelper = WeakClaim(this), weakMenuWrapper = WeakClaim(RawPtr(menuWrapper)),
|
||||
weakMenuNode = WeakClaim(RawPtr(menuNode)), subDeviceMenuCreator](bool isHover) {
|
||||
auto menuItemNode = weakMenuNode.Upgrade();
|
||||
auto menuWrapper = weakMenuWrapper.Upgrade();
|
||||
auto helper = weakHelper.Upgrade();
|
||||
CHECK_NULL_VOID(menuItemNode && menuWrapper && helper);
|
||||
if (isHover) {
|
||||
mainMenuIsHover_ = true;
|
||||
if (!subMenuIsShow_) {
|
||||
helper->mainMenuIsHover_ = true;
|
||||
if (!helper->subMenuIsShow_) {
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "create SubMenu enter.1");
|
||||
auto subMenu = subDeviceMenuCreator();
|
||||
CHECK_NULL_VOID(subMenu);
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "create SubMenu enter.2");
|
||||
auto submenuPattern = subMenu->GetPattern<MenuPattern>();
|
||||
CHECK_NULL_VOID(submenuPattern);
|
||||
submenuPattern->SetParentMenuItem(menuItemNode);
|
||||
subMenu->MountToParent(menuWrapper);
|
||||
auto menuProps = subMenu->GetLayoutProperty<MenuLayoutProperty>();
|
||||
OffsetF position;
|
||||
auto frameSize = menuItemNode->GetGeometryNode()->GetMarginFrameSize();
|
||||
position = menuItemNode->GetPaintRectOffset() + OffsetF(frameSize.Width(), 0.0);
|
||||
OffsetF position = menuItemNode->GetPaintRectOffset() + OffsetF(frameSize.Width(), 0.0);
|
||||
menuProps->UpdateMenuOffset(position);
|
||||
subMenu->MarkDirtyNode(PROPERTY_UPDATE_MEASURE_SELF_AND_CHILD);
|
||||
subMenuIsShow_ = true;
|
||||
helper->subMenuIsShow_ = true;
|
||||
}
|
||||
return;
|
||||
}
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "remove SubMenu enter.");
|
||||
mainMenuIsHover_ = false;
|
||||
helper->mainMenuIsHover_ = false;
|
||||
// timeout 100ms to RemoveChild
|
||||
ContainerScope scope(Container::CurrentIdSafely());
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
CHECK_NULL_VOID(context);
|
||||
auto cancelableCallback = [this, weak = AceType::WeakClaim(AceType::RawPtr(menuWrapper)),
|
||||
instanceId = Container::CurrentIdSafely()] {
|
||||
auto menuWrapper = weak.Upgrade();
|
||||
auto cancelableCallback = [weakHelper, weakMenuWrapper, instanceId = Container::CurrentIdSafely()] {
|
||||
auto menuWrapper = weakMenuWrapper.Upgrade();
|
||||
auto helper = weakHelper.Upgrade();
|
||||
ContainerScope scope(instanceId);
|
||||
if (!subMenuIsHover_) {
|
||||
SubMenuDown(menuWrapper);
|
||||
if (!helper->subMenuIsHover_) {
|
||||
helper->SubMenuDown(menuWrapper);
|
||||
}
|
||||
};
|
||||
auto taskExecutor = context->GetTaskExecutor();
|
||||
@ -499,6 +504,56 @@ void ServiceCollaborationAceCallback::CreateText(const std::string& value, const
|
||||
textNode->MarkModifyDone();
|
||||
}
|
||||
|
||||
void ServiceCollaborationAceCallback::AddMouseEventToEndIcon(const RefPtr<FrameNode>& iconNode)
|
||||
{
|
||||
auto inputHub = iconNode->GetOrCreateInputEventHub();
|
||||
CHECK_NULL_VOID(inputHub);
|
||||
auto gestureHub = iconNode->GetOrCreateGestureEventHub();
|
||||
CHECK_NULL_VOID(gestureHub);
|
||||
auto mouseTask = [weakHelper = WeakClaim(this), node = WeakClaim(RawPtr(iconNode))](bool isHover) {
|
||||
auto helper = weakHelper.Upgrade();
|
||||
auto iconNode = node.Upgrade();
|
||||
CHECK_NULL_VOID(helper && iconNode);
|
||||
auto iconContext = iconNode->GetRenderContext();
|
||||
CHECK_NULL_VOID(iconContext);
|
||||
auto pipeline = PipelineBase::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipeline);
|
||||
auto theme = pipeline->GetTheme<SelectTheme>();
|
||||
CHECK_NULL_VOID(theme);
|
||||
if (isHover) {
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "hover");
|
||||
helper->endIconIsHover_ = isHover;
|
||||
iconContext->UpdateBackgroundColor(theme->GetHoverColor());
|
||||
} else {
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "leave");
|
||||
helper->endIconIsHover_ = isHover;
|
||||
iconContext->UpdateBackgroundColor(Color::TRANSPARENT);
|
||||
}
|
||||
};
|
||||
auto touchCallback = [weakHelper = WeakClaim(this), node = WeakClaim(RawPtr(iconNode))]
|
||||
(const TouchEventInfo& info) {
|
||||
auto helper = weakHelper.Upgrade();
|
||||
auto iconNode = node.Upgrade();
|
||||
CHECK_NULL_VOID(helper && iconNode);
|
||||
auto iconContext = iconNode->GetRenderContext();
|
||||
CHECK_NULL_VOID(iconContext);
|
||||
auto pipeline = PipelineBase::GetCurrentContext();
|
||||
CHECK_NULL_VOID(pipeline);
|
||||
auto theme = pipeline->GetTheme<SelectTheme>();
|
||||
auto touchType = info.GetTouches().front().GetTouchType();
|
||||
if (touchType == TouchType::DOWN) {
|
||||
iconContext->UpdateBackgroundColor(theme->GetClickedColor());
|
||||
}
|
||||
if (touchType == TouchType::UP) {
|
||||
iconContext->UpdateBackgroundColor(helper->endIconIsHover_ ? theme->GetHoverColor() : Color::TRANSPARENT);
|
||||
}
|
||||
};
|
||||
auto mouseEvent = MakeRefPtr<InputEvent>(std::move(mouseTask));
|
||||
auto touchEvent = MakeRefPtr<TouchEventImpl>(std::move(touchCallback));
|
||||
inputHub->AddOnHoverEvent(mouseEvent);
|
||||
gestureHub->AddTouchEvent(touchEvent);
|
||||
}
|
||||
|
||||
void ServiceCollaborationAceCallback::CreateEndIcon(const std::string& icon, const RefPtr<FrameNode>& parent)
|
||||
{
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "enter, icon is %{public}s", icon.c_str());
|
||||
@ -520,6 +575,10 @@ void ServiceCollaborationAceCallback::CreateEndIcon(const std::string& icon, con
|
||||
CalcLength(static_cast<float>(ENDICON_SIZE), DimensionUnit::VP)
|
||||
)
|
||||
);
|
||||
iconProperty->UpdatePadding({ .left = CalcLength(static_cast<float>(ICON_PADDING), DimensionUnit::VP),
|
||||
.right = CalcLength(static_cast<float>(ICON_PADDING), DimensionUnit::VP),
|
||||
.top = CalcLength(static_cast<float>(ICON_PADDING), DimensionUnit::VP),
|
||||
.bottom = CalcLength(static_cast<float>(ICON_PADDING), DimensionUnit::VP) });
|
||||
iconProperty->UpdateAlignment(Alignment::CENTER_LEFT);
|
||||
MarginProperty margin;
|
||||
margin.right = CalcLength(static_cast<float>(ENDICON_MARGIN));
|
||||
@ -527,18 +586,24 @@ void ServiceCollaborationAceCallback::CreateEndIcon(const std::string& icon, con
|
||||
margin.top = CalcLength(static_cast<float>(ENDICON_MARGIN_TOP));
|
||||
margin.bottom = CalcLength(static_cast<float>(ENDICON_MARGIN));
|
||||
iconProperty->UpdateMargin(margin);
|
||||
auto clickEvent = AceType::MakeRefPtr<ClickEvent>([this](GestureEvent& callback) {
|
||||
auto clickEvent = AceType::MakeRefPtr<ClickEvent>([weakCallback = WeakClaim(this)](GestureEvent& event) {
|
||||
auto callback = weakCallback.Upgrade();
|
||||
CHECK_NULL_VOID(callback);
|
||||
ContainerScope scope(Container::CurrentIdSafely());
|
||||
RemovePopupNode();
|
||||
callback->RemovePopupNode();
|
||||
});
|
||||
auto gestureHub = iconNode->GetOrCreateGestureEventHub();
|
||||
gestureHub->AddClickEvent(clickEvent);
|
||||
iconNode->MountToParent(parent);
|
||||
iconNode->MarkModifyDone();
|
||||
auto iconContext = iconNode->GetRenderContext();
|
||||
CHECK_NULL_VOID(iconContext);
|
||||
BorderRadiusProperty border(Dimension(static_cast<float>(ICON_BORDER_RADIUS), DimensionUnit::VP));
|
||||
iconContext->UpdateBorderRadius(border);
|
||||
AddMouseEventToEndIcon(iconNode);
|
||||
}
|
||||
|
||||
void ServiceCollaborationAceCallback::CreateStartIcon(
|
||||
const std::string& icon, const RefPtr<FrameNode>& parent)
|
||||
void ServiceCollaborationAceCallback::CreateStartIcon(const std::string& icon, const RefPtr<FrameNode>& parent)
|
||||
{
|
||||
TAG_LOGI(AceLogTag::ACE_MENU, "enter, icon is %{public}s", icon.c_str());
|
||||
auto iconPipeline = PipelineBase::GetCurrentContextSafely();
|
||||
@ -659,10 +724,12 @@ int32_t ServiceCollaborationAceCallback::OnEvent(uint32_t code, uint32_t eventId
|
||||
position_ = AceType::DynamicCast<RichEditorPattern>(info_->pattern.Upgrade())->GetCaretRect().GetOffset();
|
||||
auto popupParam = GetPopupParam(true, onStateChange_);
|
||||
auto pattern = AceType::DynamicCast<RichEditorPattern>(info_->pattern.Upgrade());
|
||||
std::function<void(int32_t)> func = [this](int32_t num) {
|
||||
if (!isTransmit_) {
|
||||
RemovePopupNode();
|
||||
info_ = nullptr;
|
||||
std::function<void(int32_t)> func = [weak = WeakClaim(this)](int32_t num) {
|
||||
auto callback = weak.Upgrade();
|
||||
CHECK_NULL_VOID(callback);
|
||||
if (!callback->isTransmit_) {
|
||||
callback->RemovePopupNode();
|
||||
callback->info_ = nullptr;
|
||||
}
|
||||
};
|
||||
pattern->RegisiterCaretChangeListener(std::move(func));
|
||||
@ -693,12 +760,7 @@ int32_t ServiceCollaborationAceCallback::OnEvent(uint32_t code, uint32_t eventId
|
||||
CHECK_NULL_RETURN(toastPipeline, -1);
|
||||
auto overlay = toastPipeline->GetOverlayManager();
|
||||
CHECK_NULL_RETURN(overlay, -1);
|
||||
auto toastInfo = NG::ToastInfo { .message = category,
|
||||
.duration = 2000,
|
||||
.bottom = "",
|
||||
.isRightToLeft = true
|
||||
};
|
||||
overlay->ShowToast(toastInfo);
|
||||
overlay->ShowToast({ .message = category, .duration = 2000, .alignment = -1 });
|
||||
info_ = nullptr;
|
||||
return 0;
|
||||
}
|
||||
@ -712,6 +774,7 @@ RefPtr<PixelMap> ServiceCollaborationAceCallback::CreatePixelMap(void *buffer, u
|
||||
TAG_LOGE(AceLogTag::ACE_MENU, "CreateImageSource from buffer failed.");
|
||||
return nullptr;
|
||||
}
|
||||
CHECK_NULL_RETURN(imageSource, nullptr);
|
||||
Media::DecodeOptions decodeOpts;
|
||||
std::shared_ptr<Media::PixelMap> pixelMap = imageSource->CreatePixelMap(decodeOpts, errorCode);
|
||||
if (errorCode != 0) {
|
||||
@ -727,7 +790,6 @@ int32_t ServiceCollaborationAceCallback::OnDataCallback(uint32_t code, uint32_t
|
||||
uint32_t dataLength, std::unique_ptr<char[]>& data)
|
||||
{
|
||||
CHECK_NULL_RETURN(menuHelper_, -1);
|
||||
auto& photoCount = menuHelper_->photoCount_;
|
||||
ContainerScope scope(Container::CurrentIdSafely());
|
||||
CHECK_NULL_RETURN(info_, -1);
|
||||
isTransmit_ = true;
|
||||
@ -737,22 +799,24 @@ int32_t ServiceCollaborationAceCallback::OnDataCallback(uint32_t code, uint32_t
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
CHECK_NULL_RETURN(context, -1);
|
||||
CancelableCallback<void()> caretTwinklingTask;
|
||||
caretTwinklingTask.Reset([this, code, weak = imagePix, instanceId = Container::CurrentIdSafely(), &photoCount] {
|
||||
CHECK_NULL_VOID(weak);
|
||||
CHECK_NULL_VOID(info_);
|
||||
auto richEditorPattern = AceType::DynamicCast<RichEditorPattern>(info_->pattern.Upgrade());
|
||||
caretTwinklingTask.Reset([weakCallback = WeakClaim(this), code, imagePix,
|
||||
instanceId = Container::CurrentIdSafely(), weakHelper = WeakClaim(RawPtr(menuHelper_))] {
|
||||
auto callback = weakCallback.Upgrade();
|
||||
auto helper = weakHelper.Upgrade();
|
||||
CHECK_NULL_VOID(callback && imagePix && callback->info_);
|
||||
auto richEditorPattern = DynamicCast<RichEditorPattern>(callback->info_->pattern.Upgrade());
|
||||
CHECK_NULL_VOID(richEditorPattern);
|
||||
ContainerScope scope(instanceId);
|
||||
ImageSpanOptions options;
|
||||
options.imagePixelMap = weak;
|
||||
options.offset = richEditorPattern->GetCaretPosition() + photoCount;
|
||||
auto width = weak->GetWidth();
|
||||
auto height = weak->GetHeight();
|
||||
photoCount++;
|
||||
options.imagePixelMap = imagePix;
|
||||
options.offset = richEditorPattern->GetCaretPosition() + helper->photoCount_;
|
||||
auto width = imagePix->GetWidth();
|
||||
auto height = imagePix->GetHeight();
|
||||
helper->photoCount_++;
|
||||
ImageSpanAttribute attr = {
|
||||
.size = ImageSpanSize{ .width = CalcDimension(width), .height = CalcDimension(height) } };
|
||||
options.imageAttribute = attr;
|
||||
if (!info_->pattern.Upgrade()) {
|
||||
if (!callback->info_->pattern.Upgrade()) {
|
||||
TAG_LOGE(AceLogTag::ACE_MENU, "info_->pattern.Upgrade() is nullptr.");
|
||||
return;
|
||||
}
|
||||
@ -761,10 +825,10 @@ int32_t ServiceCollaborationAceCallback::OnDataCallback(uint32_t code, uint32_t
|
||||
}
|
||||
richEditorPattern->AddImageSpan(options, false, 0, false);
|
||||
if (code == SEND_PHOTO_SUCCESS) {
|
||||
richEditorPattern->SetCaretPosition(richEditorPattern->GetCaretPosition() + photoCount);
|
||||
RemovePopupNode();
|
||||
isTransmit_ = false;
|
||||
info_ = nullptr;
|
||||
richEditorPattern->SetCaretPosition(richEditorPattern->GetCaretPosition() + helper->photoCount_);
|
||||
callback->RemovePopupNode();
|
||||
callback->isTransmit_ = false;
|
||||
callback->info_ = nullptr;
|
||||
}
|
||||
});
|
||||
auto taskExecutor = context->GetTaskExecutor();
|
||||
|
@ -34,7 +34,8 @@ enum ServiceCollaborationCode {
|
||||
|
||||
class FrameNode;
|
||||
struct SelectOverlayInfo;
|
||||
class ACE_FORCE_EXPORT ServiceCollaborationMenuAceHelper {
|
||||
class ACE_FORCE_EXPORT ServiceCollaborationMenuAceHelper : public virtual AceType {
|
||||
DECLARE_ACE_TYPE(ServiceCollaborationMenuAceHelper, AceType);
|
||||
public:
|
||||
void CreateText(const std::string& value, const RefPtr<FrameNode>& parent, const Color& color, bool needMargin);
|
||||
void CreateHeaderText(const std::string& value, const RefPtr<FrameNode>& parent);
|
||||
@ -86,7 +87,8 @@ private:
|
||||
static constexpr char SUN_MENU_TAG[33] = "SelectOverlayMenuByRightClickSub";
|
||||
};
|
||||
|
||||
class ACE_FORCE_EXPORT ServiceCollaborationAceCallback {
|
||||
class ACE_FORCE_EXPORT ServiceCollaborationAceCallback : public virtual AceType {
|
||||
DECLARE_ACE_TYPE(ServiceCollaborationAceCallback, AceType);
|
||||
public:
|
||||
RefPtr<FrameNode> CreateCustomPopUpNode(const std::string& value, const std::string& icon);
|
||||
void CreateText(const std::string& value, const RefPtr<FrameNode>& parent);
|
||||
@ -98,7 +100,8 @@ public:
|
||||
int32_t OnDataCallback(uint32_t code, uint32_t collaborationId,
|
||||
uint32_t dataLength, std::unique_ptr<char[]>& data);
|
||||
RefPtr<PixelMap> CreatePixelMap(void *buffer, uint32_t code, uint32_t dataLength);
|
||||
void SetMenuHelper(std::shared_ptr<ServiceCollaborationMenuAceHelper> menuHelper)
|
||||
void AddMouseEventToEndIcon(const RefPtr<FrameNode>& iconNode);
|
||||
void SetMenuHelper(RefPtr<ServiceCollaborationMenuAceHelper> menuHelper)
|
||||
{
|
||||
menuHelper_ = menuHelper;
|
||||
}
|
||||
@ -116,21 +119,25 @@ public:
|
||||
OffsetF position_;
|
||||
RefPtr<FrameNode> row_;
|
||||
bool isTransmit_;
|
||||
std::shared_ptr<ServiceCollaborationMenuAceHelper> menuHelper_;
|
||||
RefPtr<ServiceCollaborationMenuAceHelper> menuHelper_;
|
||||
std::shared_ptr<SelectOverlayInfo> info_;
|
||||
std::string ability_;
|
||||
bool endIconIsHover_ = false;
|
||||
|
||||
private:
|
||||
static constexpr int32_t TEXT_MAX_WIDTH = 500;
|
||||
static constexpr int32_t TEXT_MAX_HIGHT = 456;
|
||||
static constexpr int32_t TEXT_FONT_SIZE = 14;
|
||||
static constexpr int32_t TEXT_MARGIN_TOP = 14;
|
||||
static constexpr int32_t TEXT_MARGIN_BOTTOM = 12;
|
||||
static constexpr int32_t ENDICON_SIZE = 18;
|
||||
static constexpr int32_t ENDICON_SIZE = 36;
|
||||
static constexpr int32_t ENDICON_MARGIN = 12;
|
||||
static constexpr int32_t ENDICON_MARGIN_TOP = 13;
|
||||
static constexpr int32_t STARTICON_SIZE = 24;
|
||||
static constexpr int32_t STARTICON_MARGIN = 12;
|
||||
static constexpr int32_t TARGET_SPACE = 8;
|
||||
static constexpr int32_t ICON_BORDER_RADIUS = 18;
|
||||
static constexpr int32_t ICON_PADDING = 9;
|
||||
static constexpr uint32_t ICON_COLOR = 0x99000000;
|
||||
};
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -456,13 +456,13 @@ public:
|
||||
}
|
||||
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(FontSize, Dimension);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextColor, DynamicColor);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextColor, Color);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(ItalicFontStyle, Ace::FontStyle);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(FontWeight, FontWeight);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(FontFamily, std::vector<std::string>);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextDecoration, TextDecoration);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextDecorationStyle, TextDecorationStyle);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextDecorationColor, DynamicColor);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextDecorationColor, Color);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(FontFeature, FONT_FEATURES_LIST);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextCase, TextCase);
|
||||
DEFINE_SPAN_FONT_STYLE_ITEM(TextShadow, std::vector<Shadow>);
|
||||
|
@ -65,7 +65,7 @@ public:
|
||||
|
||||
ACE_DEFINE_PROPERTY_GROUP(FontStyle, FontStyle);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, FontSize, Dimension, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, TextColor, DynamicColor, PROPERTY_UPDATE_MEASURE_SELF);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, TextColor, Color, PROPERTY_UPDATE_MEASURE_SELF);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, TextShadow, std::vector<Shadow>, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, ItalicFontStyle, Ace::FontStyle, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP(FontStyle, FontWeight, FontWeight, PROPERTY_UPDATE_MEASURE);
|
||||
@ -111,7 +111,7 @@ public:
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP_ITEM(
|
||||
PlaceholderFontStyle, FontSize, PlaceholderFontSize, Dimension, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP_ITEM(
|
||||
PlaceholderFontStyle, TextColor, PlaceholderTextColor, DynamicColor, PROPERTY_UPDATE_MEASURE_SELF);
|
||||
PlaceholderFontStyle, TextColor, PlaceholderTextColor, Color, PROPERTY_UPDATE_MEASURE_SELF);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP_ITEM(
|
||||
PlaceholderFontStyle, ItalicFontStyle, PlaceholderItalicFontStyle, Ace::FontStyle, PROPERTY_UPDATE_MEASURE);
|
||||
ACE_DEFINE_PROPERTY_ITEM_WITH_GROUP_ITEM(
|
||||
|
@ -828,6 +828,7 @@ protected:
|
||||
|
||||
OffsetF parentGlobalOffset_;
|
||||
std::optional<TextResponseType> textResponseType_;
|
||||
MouseFormat currentMouseStyle_ = MouseFormat::DEFAULT;
|
||||
|
||||
struct SubComponentInfoEx {
|
||||
std::optional<AISpan> aiSpan;
|
||||
|
@ -200,4 +200,22 @@ std::string GetSymbolEffectOptionsInJson(const std::optional<SymbolEffectOptions
|
||||
}
|
||||
return text;
|
||||
}
|
||||
|
||||
void FontStyle::UpdateColorByResourceId()
|
||||
{
|
||||
if (propTextColor) {
|
||||
propTextColor->UpdateColorByResourceId();
|
||||
}
|
||||
if (propTextDecorationColor) {
|
||||
propTextDecorationColor->UpdateColorByResourceId();
|
||||
}
|
||||
if (propTextShadow) {
|
||||
auto& shadows = propTextShadow.value();
|
||||
std::for_each(shadows.begin(), shadows.end(), [](Shadow& sd) { sd.UpdateColorByResourceId(); });
|
||||
}
|
||||
if (propSymbolColorList) {
|
||||
auto& colors = propSymbolColorList.value();
|
||||
std::for_each(colors.begin(), colors.end(), [](Color& cl) { cl.UpdateColorByResourceId(); });
|
||||
}
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -151,7 +151,7 @@ constexpr Dimension TEXT_DEFAULT_FONT_SIZE = 16.0_fp;
|
||||
using FONT_FEATURES_LIST = std::list<std::pair<std::string, int32_t>>;
|
||||
struct FontStyle {
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(FontSize, Dimension);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextColor, DynamicColor);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextColor, Color);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextShadow, std::vector<Shadow>);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(ItalicFontStyle, Ace::FontStyle);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(FontWeight, FontWeight);
|
||||
@ -160,13 +160,13 @@ struct FontStyle {
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(FontFamily, std::vector<std::string>);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(FontFeature, FONT_FEATURES_LIST);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextDecoration, TextDecoration);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextDecorationColor, DynamicColor);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextDecorationColor, Color);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextDecorationStyle, TextDecorationStyle);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(TextCase, TextCase);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(AdaptMinFontSize, Dimension);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(AdaptMaxFontSize, Dimension);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(LetterSpacing, Dimension);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(ForegroundColor, DynamicColor);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(ForegroundColor, Color);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(SymbolColorList, std::vector<Color>);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(SymbolRenderingStrategy, uint32_t);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(SymbolEffectStrategy, uint32_t);
|
||||
@ -174,15 +174,7 @@ struct FontStyle {
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(MinFontScale, float);
|
||||
ACE_DEFINE_PROPERTY_GROUP_ITEM(MaxFontScale, float);
|
||||
|
||||
void UpdateColorByResourceId()
|
||||
{
|
||||
if (propTextColor) {
|
||||
propTextColor->UpdateColorByResourceId();
|
||||
}
|
||||
if (propTextDecorationColor) {
|
||||
propTextDecorationColor->UpdateColorByResourceId();
|
||||
}
|
||||
}
|
||||
void UpdateColorByResourceId();
|
||||
};
|
||||
|
||||
struct TextLineStyle {
|
||||
|
@ -17,16 +17,24 @@ ace_unittest("rich_editor_test_ng") {
|
||||
type = "new"
|
||||
sources = [
|
||||
"rich_editor_base_test_ng.cpp",
|
||||
"rich_editor_base_testone_ng.cpp",
|
||||
"rich_editor_change_callback_test_ng.cpp",
|
||||
"rich_editor_click_test_ng.cpp",
|
||||
"rich_editor_click_testone_ng.cpp",
|
||||
"rich_editor_common_test_ng.cpp",
|
||||
"rich_editor_content_modifier_test_ng.cpp",
|
||||
"rich_editor_drag_test_ng.cpp",
|
||||
"rich_editor_edit_test_ng.cpp",
|
||||
"rich_editor_edit_testone_ng.cpp",
|
||||
"rich_editor_keyboard_shortcut_test_ng.cpp",
|
||||
"rich_editor_overlay_test_ng.cpp",
|
||||
"rich_editor_pattern_test_ng.cpp",
|
||||
"rich_editor_pattern_testfour_ng.cpp",
|
||||
"rich_editor_pattern_testone_ng.cpp",
|
||||
"rich_editor_pattern_testthree_ng.cpp",
|
||||
"rich_editor_pattern_testtwo_ng.cpp",
|
||||
"rich_editor_preview_text_test_ng.cpp",
|
||||
"rich_editor_span_test.cpp",
|
||||
"rich_editor_styled_string_test_ng.cpp",
|
||||
]
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -575,13 +575,11 @@ HWTEST_F(RichEditorChangeCallbackTestNg, ChangeTextCallbackTest008, TestSize.Lev
|
||||
*/
|
||||
isWillCalled = false;
|
||||
isDidCalled = false;
|
||||
originalCount = 0;
|
||||
replacedCount = 0;
|
||||
afterCount = 0;
|
||||
richEditorPattern->HandleOnRedoAction();
|
||||
EXPECT_EQ(isWillCalled, true);
|
||||
EXPECT_EQ(isDidCalled, true);
|
||||
EXPECT_EQ(originalCount, 1);
|
||||
EXPECT_EQ(replacedCount, 0);
|
||||
EXPECT_EQ(afterCount, 0);
|
||||
}
|
||||
|
@ -24,8 +24,6 @@ int32_t testAboutToIMEInput = 0;
|
||||
int32_t testOnIMEInputComplete = 0;
|
||||
int32_t testAboutToDelete = 0;
|
||||
int32_t testOnDeleteComplete = 0;
|
||||
const Dimension LETTER_SPACING_2 = Dimension(12, DimensionUnit::PX);
|
||||
const Dimension LINE_HEIGHT_VALUE_2 = Dimension(30, DimensionUnit::PX);
|
||||
const Dimension IMAGE_WIDTH = 50.0_vp;
|
||||
const Dimension IMAGE_HEIGHT = 50.0_vp;
|
||||
const ImageSpanSize TEST_IMAGE_SIZE_1 = { .width = 50.0_vp, .height = 50.0_vp };
|
||||
@ -193,7 +191,7 @@ HWTEST_F(RichEditorClickTestNg, HandleMouseLeftButton002, TestSize.Level1)
|
||||
std::vector<TextSpanType> selectType = { TextSpanType::TEXT, TextSpanType::IMAGE, TextSpanType::MIXED };
|
||||
SelectOverlayInfo selectInfo;
|
||||
selectInfo.isUsingMouse = true;
|
||||
for (int32_t i = 0; i < static_cast<int32_t>(selectType.size()); i++) {
|
||||
for (size_t i = 0; i < selectType.size(); i++) {
|
||||
richEditorPattern->selectedType_ = selectType[i];
|
||||
richEditorPattern->HandleMouseLeftButton(mouseInfo);
|
||||
EXPECT_NE(richEditorPattern->selectionMenuOffsetByMouse_.GetX(),
|
||||
@ -214,13 +212,12 @@ HWTEST_F(RichEditorClickTestNg, HandleMouseLeftButton002, TestSize.Level1)
|
||||
return;
|
||||
};
|
||||
richEditorPattern->mouseStatus_ = MouseStatus::MOVE;
|
||||
for (int32_t i = 0; i < static_cast<int32_t>(selectType.size()); i++) {
|
||||
for (size_t i = 0; i < selectType.size(); i++) {
|
||||
richEditorPattern->selectedType_ = selectType[i];
|
||||
auto key = std::make_pair(selectType[i], TextResponseType::SELECTED_BY_MOUSE);
|
||||
std::shared_ptr<SelectionMenuParams> params1 = std::make_shared<SelectionMenuParams>(
|
||||
selectType[i], buildFunc, onAppear, onDisappear, TextResponseType::SELECTED_BY_MOUSE);
|
||||
richEditorPattern->selectionMenuMap_[key] = params1;
|
||||
richEditorPattern->mouseStatus_ = MouseStatus::MOVE;
|
||||
richEditorPattern->HandleMouseLeftButton(mouseInfo);
|
||||
EXPECT_EQ(richEditorPattern->selectionMenuOffsetByMouse_.GetX(),
|
||||
static_cast<float>(mouseInfo.GetGlobalLocation().GetX()));
|
||||
@ -483,6 +480,9 @@ HWTEST_F(RichEditorClickTestNg, MouseRightFocus001, TestSize.Level1)
|
||||
AddImageSpan();
|
||||
richEditorPattern->spans_.push_front(AceType::MakeRefPtr<SpanItem>());
|
||||
richEditorPattern->spans_.push_front(AceType::MakeRefPtr<SpanItem>());
|
||||
auto it = richEditorPattern->spans_.front();
|
||||
it->content = "test";
|
||||
it->position = 4;
|
||||
richEditorPattern->caretPosition_ = richEditorPattern->GetTextContentLength();
|
||||
richEditorPattern->moveLength_ = 0;
|
||||
MouseInfo info;
|
||||
@ -490,66 +490,11 @@ HWTEST_F(RichEditorClickTestNg, MouseRightFocus001, TestSize.Level1)
|
||||
richEditorPattern->textSelector_.destinationOffset = 0;
|
||||
richEditorPattern->MouseRightFocus(info);
|
||||
EXPECT_EQ(richEditorPattern->caretPosition_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorController018
|
||||
* @tc.desc: test UpdateSymbolStyle
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestNg, RichEditorController018, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. get richEditorController
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto richEditorController = richEditorPattern->GetRichEditorController();
|
||||
ASSERT_NE(richEditorController, nullptr);
|
||||
|
||||
/**
|
||||
* @tc.steps: step2. initalize symbol span properties
|
||||
*/
|
||||
TextStyle style;
|
||||
style.SetFontSize(FONT_SIZE_VALUE);
|
||||
style.SetLineHeight(LINE_HEIGHT_VALUE);
|
||||
style.SetLetterSpacing(LETTER_SPACING);
|
||||
SymbolSpanOptions options;
|
||||
options.symbolId = SYMBOL_ID;
|
||||
options.style = style;
|
||||
|
||||
/**
|
||||
* @tc.steps: step3. add symbol span
|
||||
*/
|
||||
auto index1 = richEditorController->AddSymbolSpan(options);
|
||||
EXPECT_EQ(index1, 0);
|
||||
|
||||
/**
|
||||
* @tc.steps: step4. test UpdateSymbolStyle
|
||||
*/
|
||||
struct UpdateSpanStyle updateSpanStyle;
|
||||
updateSpanStyle.updateLineHeight = LINE_HEIGHT_VALUE_2;
|
||||
updateSpanStyle.updateLetterSpacing = LETTER_SPACING_2;
|
||||
updateSpanStyle.isSymbolStyle = true;
|
||||
richEditorController->SetUpdateSpanStyle(updateSpanStyle);
|
||||
|
||||
ImageSpanAttribute imageStyle;
|
||||
style.SetLineHeight(LINE_HEIGHT_VALUE_2);
|
||||
style.SetLetterSpacing(LETTER_SPACING_2);
|
||||
|
||||
richEditorController->UpdateSpanStyle(0, 2, style, imageStyle);
|
||||
|
||||
/**
|
||||
* @tc.steps: step5. test symbol span style
|
||||
*/
|
||||
auto newSpan1 = AceType::DynamicCast<SpanNode>(richEditorNode_->GetChildAtIndex(0));
|
||||
ASSERT_NE(newSpan1, nullptr);
|
||||
EXPECT_EQ(newSpan1->GetFontSize(), FONT_SIZE_VALUE);
|
||||
EXPECT_EQ(newSpan1->GetLineHeight(), LINE_HEIGHT_VALUE_2);
|
||||
EXPECT_EQ(newSpan1->GetLetterSpacing(), LETTER_SPACING_2);
|
||||
|
||||
ClearSpan();
|
||||
richEditorPattern->textSelector_.baseOffset = 0;
|
||||
richEditorPattern->textSelector_.destinationOffset = 1;
|
||||
richEditorPattern->MouseRightFocus(info);
|
||||
EXPECT_EQ(richEditorPattern->caretPosition_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -1099,29 +1044,6 @@ HWTEST_F(RichEditorClickTestNg, HandleBlurEvent, TestSize.Level1)
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.destinationOffset, -1);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CreateAndShowSingleHandle
|
||||
* @tc.desc: test CreateAndShowSingleHandle
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestNg, CreateAndShowSingleHandle, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. create richEditorPattern
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
richEditorPattern->caretPosition_ = -1;
|
||||
|
||||
/**
|
||||
* @tc.steps: step2. Construct GestureEvent data and call CreatAndShowSingleHandle
|
||||
*/
|
||||
ASSERT_NE(richEditorPattern->selectOverlay_, nullptr);
|
||||
richEditorPattern->CreateAndShowSingleHandle();
|
||||
EXPECT_TRUE(richEditorPattern->selectOverlay_->IsSingleHandle());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: JudgeContentDraggable
|
||||
* @tc.desc: test JudgeContentDraggable
|
||||
@ -1144,33 +1066,4 @@ HWTEST_F(RichEditorClickTestNg, JudgeContentDraggable, TestSize.Level1)
|
||||
bool testSelectAreaVisible = richEditorPattern->JudgeContentDraggable();
|
||||
EXPECT_FALSE(testSelectAreaVisible);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorKeyBoardShortCuts207 about Handle Select FontStyle
|
||||
* @tc.desc: test the text font style
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestNg, RichEditorKeyBoardShortCuts207, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. get richEditor pattern and controller
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto richEditorController = richEditorPattern->GetRichEditorController();
|
||||
ASSERT_NE(richEditorController, nullptr);
|
||||
|
||||
/**
|
||||
* @tc.steps: step2. add different type span and select
|
||||
*/
|
||||
AddSpan(INIT_VALUE_1);
|
||||
AddImageSpan();
|
||||
AddSpan(INIT_VALUE_2);
|
||||
EXPECT_EQ(richEditorNode_->GetChildren().size(), 3);
|
||||
|
||||
richEditorPattern->textSelector_.Update(4, 10);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 10);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
@ -0,0 +1,167 @@
|
||||
/*
|
||||
* Copyright (c) 2024 Huawei Device Co., Ltd.
|
||||
* 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.
|
||||
*/
|
||||
#include "test/unittest/core/pattern/rich_editor/rich_editor_common_test_ng.h"
|
||||
|
||||
using namespace testing;
|
||||
using namespace testing::ext;
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
|
||||
class RichEditorClickTestOneNg : public RichEditorCommonTestNg {
|
||||
public:
|
||||
void SetUp() override;
|
||||
void TearDown() override;
|
||||
static void TearDownTestSuite();
|
||||
};
|
||||
|
||||
void RichEditorClickTestOneNg::SetUp()
|
||||
{
|
||||
MockPipelineContext::SetUp();
|
||||
MockContainer::SetUp();
|
||||
MockContainer::Current()->taskExecutor_ = AceType::MakeRefPtr<MockTaskExecutor>();
|
||||
auto* stack = ViewStackProcessor::GetInstance();
|
||||
auto nodeId = stack->ClaimNodeId();
|
||||
richEditorNode_ = FrameNode::GetOrCreateFrameNode(
|
||||
V2::RICH_EDITOR_ETS_TAG, nodeId, []() { return AceType::MakeRefPtr<RichEditorPattern>(); });
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
richEditorPattern->InitScrollablePattern();
|
||||
richEditorPattern->SetRichEditorController(AceType::MakeRefPtr<RichEditorController>());
|
||||
richEditorPattern->GetRichEditorController()->SetPattern(AceType::WeakClaim(AceType::RawPtr(richEditorPattern)));
|
||||
richEditorPattern->CreateNodePaintMethod();
|
||||
richEditorNode_->GetGeometryNode()->SetContentSize({});
|
||||
}
|
||||
|
||||
void RichEditorClickTestOneNg::TearDown()
|
||||
{
|
||||
richEditorNode_ = nullptr;
|
||||
MockParagraph::TearDown();
|
||||
}
|
||||
|
||||
void RichEditorClickTestOneNg::TearDownTestSuite()
|
||||
{
|
||||
TestNG::TearDownTestSuite();
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleClickEvent002
|
||||
* @tc.desc: test RichEditorPattern HandleClickEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestOneNg, HandleClickEvent002, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
GestureEvent info;
|
||||
info.localLocation_ = Offset(0, 0);
|
||||
ParagraphStyle paragraphStyle;
|
||||
auto paragraph = Paragraph::Create(paragraphStyle, FontCollection::Current());
|
||||
richEditorPattern->pManager_->AddParagraph({ .paragraph = paragraph, .paragraphStyle = paragraphStyle });
|
||||
auto focusHub = richEditorNode_->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
richEditorPattern->GetFocusHub()->focusType_ = FocusType::DISABLE;
|
||||
richEditorPattern->dataDetectorAdapter_->hasClickedAISpan_ = true;
|
||||
richEditorPattern->HandleClickEvent(info);
|
||||
EXPECT_EQ(richEditorPattern->caretPosition_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleSingleClickEvent001
|
||||
* @tc.desc: test RichEditorPattern HandleSingleClickEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestOneNg, HandleSingleClickEvent001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
RichEditorPattern::OperationRecord record;
|
||||
richEditorPattern->DeleteSelectOperation(&record);
|
||||
|
||||
RectF rect(0, 0, 5, 5);
|
||||
richEditorPattern->CreateHandles();
|
||||
richEditorPattern->textSelector_.Update(0, 5);
|
||||
richEditorPattern->selectOverlay_->OnHandleMoveDone(rect, true);
|
||||
|
||||
GestureEvent info;
|
||||
info.localLocation_ = Offset(0, 0);
|
||||
ParagraphStyle paragraphStyle;
|
||||
auto paragraph = Paragraph::Create(paragraphStyle, FontCollection::Current());
|
||||
richEditorPattern->pManager_->AddParagraph({ .paragraph = paragraph, .paragraphStyle = paragraphStyle });
|
||||
auto focusHub = richEditorNode_->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
richEditorPattern->isMousePressed_ = true;
|
||||
|
||||
richEditorPattern->dataDetectorAdapter_->hasClickedAISpan_ = true;
|
||||
richEditorPattern->dataDetectorAdapter_->pressedByLeftMouse_ = true;
|
||||
richEditorPattern->HandleSingleClickEvent(info);
|
||||
|
||||
richEditorPattern->dataDetectorAdapter_->hasClickedAISpan_ = false;
|
||||
richEditorPattern->dataDetectorAdapter_->pressedByLeftMouse_ = false;
|
||||
richEditorPattern->HandleSingleClickEvent(info);
|
||||
|
||||
richEditorPattern->dataDetectorAdapter_->hasClickedAISpan_ = true;
|
||||
richEditorPattern->dataDetectorAdapter_->pressedByLeftMouse_ = false;
|
||||
richEditorPattern->HandleSingleClickEvent(info);
|
||||
|
||||
richEditorPattern->dataDetectorAdapter_->hasClickedAISpan_ = false;
|
||||
richEditorPattern->dataDetectorAdapter_->pressedByLeftMouse_ = true;
|
||||
richEditorPattern->HandleSingleClickEvent(info);
|
||||
EXPECT_EQ(richEditorPattern->caretPosition_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: ClickAISpan001
|
||||
* @tc.desc: test RichEditorPattern ClickAISpan
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestOneNg, ClickAISpan001, TestSize.Level1)
|
||||
{
|
||||
AISpan aiSpan;
|
||||
aiSpan.start = 0;
|
||||
aiSpan.end = 10;
|
||||
aiSpan.content = "1234567";
|
||||
aiSpan.type = TextDataDetectType::PHONE_NUMBER;
|
||||
PointF textOffset = PointF(100, 100);
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
bool res = richEditorPattern->ClickAISpan(textOffset, aiSpan);
|
||||
EXPECT_EQ(res, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleLongPress001
|
||||
* @tc.desc: test RichEditorPattern HandleLongPress
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorClickTestOneNg, HandleLongPress001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
GestureEvent info;
|
||||
info.localLocation_ = Offset(0, 0);
|
||||
auto focusHub = richEditorNode_->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
richEditorPattern->HandleLongPress(info);
|
||||
focusHub->focusType_ = FocusType::DISABLE;
|
||||
richEditorPattern->HandleLongPress(info);
|
||||
ASSERT_EQ(richEditorPattern->caretUpdateType_, CaretUpdateType::NONE);
|
||||
}
|
||||
|
||||
} // namespace OHOS::Ace::NG
|
@ -119,29 +119,29 @@ void RichEditorCommonTestNg::ClearSpan()
|
||||
void RichEditorCommonTestNg::InitAdjustObject(MockDataDetectorMgr& mockDataDetectorMgr)
|
||||
{
|
||||
EXPECT_CALL(mockDataDetectorMgr, GetCursorPosition(_, _))
|
||||
.WillRepeatedly([](const std::string& text, int8_t offset) -> int8_t {
|
||||
if (text.empty()) {
|
||||
return DEFAULT_RETURN_VALUE;
|
||||
}
|
||||
if (text.length() <= WORD_LIMIT_LEN) {
|
||||
return WORD_LIMIT_RETURN;
|
||||
} else {
|
||||
return BEYOND_LIMIT_RETURN;
|
||||
}
|
||||
});
|
||||
.WillRepeatedly([](const std::string &text, int8_t offset) -> int8_t {
|
||||
if (text.empty()) {
|
||||
return DEFAULT_RETURN_VALUE;
|
||||
}
|
||||
if (text.length() <= WORD_LIMIT_LEN) {
|
||||
return WORD_LIMIT_RETURN;
|
||||
} else {
|
||||
return BEYOND_LIMIT_RETURN;
|
||||
}
|
||||
});
|
||||
|
||||
EXPECT_CALL(mockDataDetectorMgr, GetWordSelection(_, _))
|
||||
.WillRepeatedly([](const std::string& text, int8_t offset) -> std::vector<int8_t> {
|
||||
if (text.empty()) {
|
||||
return std::vector<int8_t> { -1, -1 };
|
||||
}
|
||||
.WillRepeatedly([](const std::string &text, int8_t offset) -> std::vector<int8_t> {
|
||||
if (text.empty()) {
|
||||
return std::vector<int8_t> { -1, -1 };
|
||||
}
|
||||
|
||||
if (text.length() <= WORD_LIMIT_LEN) {
|
||||
return std::vector<int8_t> { 2, 3 };
|
||||
} else {
|
||||
return std::vector<int8_t> { 0, 2 };
|
||||
}
|
||||
});
|
||||
if (text.length() <= WORD_LIMIT_LEN) {
|
||||
return std::vector<int8_t> { 2, 3 };
|
||||
} else {
|
||||
return std::vector<int8_t> { 0, 2 };
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void RichEditorCommonTestNg::RequestFocus()
|
||||
@ -172,7 +172,8 @@ void RichEditorCommonTestNg::OnDrawVerify(
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto contentRect = richEditorNode_->GetGeometryNode()->GetContentRect();
|
||||
richEditorNode_->GetGeometryNode()->SetContentSize({100, 100});
|
||||
if (SelectSpanType::TYPESPAN == type) {
|
||||
AddSpan(text);
|
||||
} else if (SelectSpanType::TYPEIMAGE == type) {
|
||||
@ -247,5 +248,6 @@ void RichEditorCommonTestNg::OnDrawVerify(
|
||||
*/
|
||||
ret = controller->GetShowMagnifier();
|
||||
EXPECT_FALSE(ret);
|
||||
richEditorNode_->GetGeometryNode()->SetContentSize(contentRect.GetSize());
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
@ -43,6 +43,7 @@
|
||||
#include "base/window/drag_window.h"
|
||||
#include "core/components/common/layout/constants.h"
|
||||
#include "core/components/common/properties/text_style.h"
|
||||
#include "core/components/text_overlay/text_overlay_theme.h"
|
||||
#include "core/components_ng/base/frame_node.h"
|
||||
#include "core/components_ng/base/geometry_node.h"
|
||||
#include "core/components_ng/base/view_abstract_model.h"
|
||||
@ -174,6 +175,8 @@ const SymbolSpanOptions SYMBOL_SPAN_OPTIONS_1 = {
|
||||
.style = TEXT_STYLE_1,
|
||||
.resourceObject = nullptr
|
||||
};
|
||||
auto BUILDER_NODE_1 = FrameNode::GetOrCreateFrameNode(V2::ROW_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
|
||||
[]() { return AceType::MakeRefPtr<LinearLayoutPattern>(false); });
|
||||
} // namespace
|
||||
|
||||
struct TestCursorItem {
|
||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -102,6 +102,156 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, OnKeyEvent001, TestSize.Level1)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorKeyBoardShortCuts001 about cursor move
|
||||
* @tc.desc: test the cursor move line start
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts001, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. get richEditor pattern
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
/**
|
||||
* @tc.steps: step2. get richEditor controller
|
||||
*/
|
||||
auto richEditorController = richEditorPattern->GetRichEditorController();
|
||||
ASSERT_NE(richEditorController, nullptr);
|
||||
/**
|
||||
* @tc.steps: step2. add text span
|
||||
*/
|
||||
richEditorPattern->paragraphs_.minParagraphFontSize = 19.0;
|
||||
EXPECT_EQ(richEditorPattern->paragraphs_.minParagraphFontSize.value(), 19.0);
|
||||
TextSpanOptions textOptions;
|
||||
textOptions.value = INIT_VALUE_3;
|
||||
richEditorController->AddTextSpan(textOptions);
|
||||
EXPECT_EQ(textOptions.value.length(), richEditorPattern->GetTextContentLength());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::Left);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 19);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::LeftWord);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 19);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::RightWord);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 20);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::ParagraghBegin);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 0);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::ParagraghEnd);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), textOptions.value.length());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::Home);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 0);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::End);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), textOptions.value.length());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::LineBegin);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorKeyBoardShortCuts002 about cursor move
|
||||
* @tc.desc: test the cursor move line end and down
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts002, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. get richEditor pattern
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
richEditorPattern->paragraphs_.minParagraphFontSize = 19.0;
|
||||
EXPECT_EQ(richEditorPattern->paragraphs_.minParagraphFontSize.value(), 19.0);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
auto paragraph = MockParagraph::GetOrCreateMockParagraph();
|
||||
TestParagraphItem testParagraphItem = {
|
||||
.start = 0, .end = 6, .indexOffsetMap = { { 0, Offset(0, 5) }, { 6, Offset(50, 0) } }
|
||||
};
|
||||
richEditorPattern->paragraphs_.AddParagraph({ .paragraph = paragraph, .start = 0, .end = 6 });
|
||||
CaretMetricsF metricsDown;
|
||||
CaretMetricsF metricsUp;
|
||||
for (const auto& [index, offset] : testParagraphItem.indexOffsetMap) {
|
||||
metricsDown.offset.SetX(offset.GetX());
|
||||
metricsDown.offset.SetY(offset.GetY());
|
||||
metricsUp.offset.SetX(offset.GetX());
|
||||
metricsUp.offset.SetY(offset.GetY());
|
||||
EXPECT_CALL(*paragraph, GetGlyphIndexByCoordinate(_, _)).WillRepeatedly(Return(6));
|
||||
EXPECT_CALL(*paragraph, GetMaxWidth).WillRepeatedly(Return(150));
|
||||
EXPECT_CALL(*paragraph, GetHeight).WillRepeatedly(Return(50));
|
||||
EXPECT_CALL(*paragraph, ComputeOffsetForCaretDownstream(index, _, _))
|
||||
.WillRepeatedly(DoAll(SetArgReferee<1>(metricsDown), Return(true)));
|
||||
EXPECT_CALL(*paragraph, ComputeOffsetForCaretUpstream(index, _, _))
|
||||
.WillRepeatedly(DoAll(SetArgReferee<1>(metricsUp), Return(true)));
|
||||
}
|
||||
richEditorPattern->SetCaretPosition(0);
|
||||
richEditorPattern->CursorMove(CaretMoveIntent::LineEnd);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 6);
|
||||
richEditorPattern->SetCaretPosition(0);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::LineEnd);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 6);
|
||||
richEditorPattern->SetCaretPosition(0);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::Down);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 6);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorKeyBoardShortCuts101 about Handle select
|
||||
* @tc.desc: test the select move position
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts101, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. get richEditor pattern
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
/**
|
||||
* @tc.steps: step2. get richEditor controller
|
||||
*/
|
||||
auto richEditorController = richEditorPattern->GetRichEditorController();
|
||||
ASSERT_NE(richEditorController, nullptr);
|
||||
richEditorPattern->paragraphs_.minParagraphFontSize = 19.0;
|
||||
EXPECT_EQ(richEditorPattern->paragraphs_.minParagraphFontSize.value(), 19.0);
|
||||
/**
|
||||
* @tc.steps: step2. add text span
|
||||
*/
|
||||
TextSpanOptions textOptions;
|
||||
textOptions.value = INIT_VALUE_3;
|
||||
richEditorController->AddTextSpan(textOptions);
|
||||
EXPECT_EQ(textOptions.value.length(), richEditorPattern->GetTextContentLength());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::Left);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), 19);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::Right);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 21);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::LeftWord);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), 19);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::RightWord);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 21);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::ParagraghBegin);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), 0);
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::ParagraghEnd);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), textOptions.value.length());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::LineBegin);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorKeyBoardShortCuts101 about Handle select
|
||||
* @tc.desc: test the select move position, up
|
||||
@ -170,6 +320,10 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts201, TestS
|
||||
richEditorController->AddTextSpan(textOptions);
|
||||
EXPECT_EQ(textOptions.value.length(), richEditorPattern->GetTextContentLength());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->HandleOnDeleteComb(true);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 20);
|
||||
richEditorPattern->HandleOnDeleteComb(false);
|
||||
EXPECT_EQ(richEditorPattern->GetCaretPosition(), 20);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -202,6 +356,8 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts202, TestS
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->textSelector_.Update(4, 20);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), 4);
|
||||
richEditorPattern->HandleSelectFontStyle(KeyCode::KEY_B);
|
||||
EXPECT_EQ(richEditorPattern->GetUpdateSpanStyle().updateFontWeight, Ace::FontWeight::BOLD);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -234,6 +390,8 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts203, TestS
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->textSelector_.Update(4, 20);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextEnd(), 20);
|
||||
richEditorPattern->HandleSelectFontStyle(KeyCode::KEY_I);
|
||||
EXPECT_EQ(richEditorPattern->GetUpdateSpanStyle().updateItalicFontStyle, OHOS::Ace::FontStyle::ITALIC);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -265,6 +423,8 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, RichEditorKeyBoardShortCuts204, TestS
|
||||
EXPECT_EQ(textOptions.value.length(), richEditorPattern->GetTextContentLength());
|
||||
richEditorPattern->SetCaretPosition(20);
|
||||
richEditorPattern->textSelector_.Update(4, 20);
|
||||
richEditorPattern->HandleSelectFontStyle(KeyCode::KEY_U);
|
||||
EXPECT_EQ(richEditorPattern->GetUpdateSpanStyle().updateTextDecoration, TextDecoration::UNDERLINE);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -329,30 +489,6 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, BeforeChangeText101, TestSize.Level1)
|
||||
EXPECT_EQ(ret, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetTextThemeFontSize101
|
||||
* @tc.desc: test GetTextThemeFontSize
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorKeyboardShortcutTestNg, GetTextThemeFontSize101, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. declare and init variables and call function.
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
ASSERT_NE(context, nullptr);
|
||||
auto themeManager = AceType::MakeRefPtr<MockThemeManager>();
|
||||
context->SetThemeManager(themeManager);
|
||||
EXPECT_CALL(*themeManager, GetTheme(_)).WillRepeatedly(Return(AceType::MakeRefPtr<TextTheme>()));
|
||||
auto theme = context->GetTheme<TextTheme>();
|
||||
ASSERT_NE(theme, nullptr);
|
||||
auto ret = richEditorPattern->GetTextThemeFontSize();
|
||||
EXPECT_NE(ret, 0.0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleTripleClickEvent
|
||||
* @tc.desc: test HandleTripleClickEvent001
|
||||
@ -592,31 +728,6 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, HandleOnDragDrop001, TestSize.Level1)
|
||||
EXPECT_NE(event->GetData(), nullptr);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CalcLineEndPosition001
|
||||
* @tc.desc: test CalcLineEndPosition
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorKeyboardShortcutTestNg, CalcLineEndPosition001, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. declare and init variables.
|
||||
*/
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
richEditorPattern->CreateNodePaintMethod();
|
||||
EXPECT_NE(richEditorPattern->contentMod_, nullptr);
|
||||
EXPECT_NE(richEditorPattern->overlayMod_, nullptr);
|
||||
/**
|
||||
* @tc.steps: step2. change parameter and call function.
|
||||
*/
|
||||
richEditorPattern->richTextRect_.y_ = 10.0f;
|
||||
richEditorPattern->contentRect_.y_ = 20.0f;
|
||||
auto ret = richEditorPattern->CalcLineEndPosition();
|
||||
EXPECT_EQ(ret, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetDeletedSpan001
|
||||
* @tc.desc: test GetDeletedSpan
|
||||
@ -892,7 +1003,7 @@ HWTEST_F(RichEditorKeyboardShortcutTestNg, GetSelectArea101, TestSize.Level1)
|
||||
TestParagraphRect paragraphRect = { .start = 0, .end = 6, .rects = { { 0.0, 10.0, 200.0, 200.0 } } };
|
||||
TestParagraphItem paragraphItem = { .start = 0, .end = 6, .testParagraphRects = { paragraphRect } };
|
||||
AddParagraph(paragraphItem);
|
||||
richEditorPattern->textSelector_ = TextSelector(10, 50);
|
||||
richEditorPattern->textSelector_ = TextSelector(0, 6);
|
||||
richEditorPattern->contentRect_ = { 0.0, 10.0, 500.0, 500.0 };
|
||||
richEditorPattern->isShowPlaceholder_ = true;
|
||||
auto res = richEditorPattern->GetSelectArea();
|
||||
|
@ -934,7 +934,18 @@ HWTEST_F(RichEditorOverlayTestNg, SingleHandle003, TestSize.Level1)
|
||||
auto touchOffset = Offset(0, 0);
|
||||
AceType::DynamicCast<RichEditorOverlayModifier>(richEditorPattern->overlayMod_)
|
||||
->SetCaretOffsetAndHeight(OffsetF(0, 0), 50.0f);
|
||||
richEditorPattern->HandleTouchDown(touchOffset);
|
||||
auto themeManager = AceType::MakeRefPtr<MockThemeManager>();
|
||||
MockPipelineContext::GetCurrent()->SetThemeManager(themeManager);
|
||||
auto textOverlayTheme = AceType::MakeRefPtr<TextOverlayTheme>();
|
||||
textOverlayTheme->handleDiameter_ = 14.0_vp;
|
||||
EXPECT_CALL(*themeManager, GetTheme(_)).WillRepeatedly(Return(textOverlayTheme));
|
||||
TouchEventInfo touchEventInfo("");
|
||||
TouchLocationInfo touchLocationInfo(0);
|
||||
touchLocationInfo.touchType_ = TouchType::DOWN;
|
||||
touchLocationInfo.localLocation_ = touchOffset;
|
||||
touchEventInfo.AddTouchLocationInfo(std::move(touchLocationInfo));
|
||||
touchEventInfo.SetSourceTool(SourceTool::FINGER);
|
||||
richEditorPattern->HandleTouchDown(touchEventInfo);
|
||||
EXPECT_TRUE(richEditorPattern->moveCaretState_.isTouchCaret);
|
||||
/**
|
||||
* @tc.steps: step4. move caret position by touch move
|
||||
@ -1509,4 +1520,236 @@ HWTEST_F(RichEditorOverlayTestNg, IsSelectLineHeadAndUseLeadingMargin001, TestSi
|
||||
bool ret =richEditorPattern->paragraphs_.IsSelectLineHeadAndUseLeadingMargin(0);
|
||||
EXPECT_EQ(ret, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg001
|
||||
* @tc.desc: Test onDraw.
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg001, TestSize.Level1)
|
||||
{
|
||||
auto themeManager = AceType::MakeRefPtr<MockThemeManager>();
|
||||
MockPipelineContext::GetCurrent()->SetThemeManager(themeManager);
|
||||
auto richEditorTheme = AceType::MakeRefPtr<RichEditorTheme>();
|
||||
EXPECT_CALL(*themeManager, GetTheme(_)).WillRepeatedly(Return(richEditorTheme));
|
||||
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
EdgeEffect edgeEffect;
|
||||
auto scrollEdgeEffect = AceType::MakeRefPtr<ScrollEdgeEffect>(edgeEffect);
|
||||
auto scrollBarModifier = AceType::MakeRefPtr<ScrollBarOverlayModifier>();
|
||||
auto richEditorOverlayModifier = AceType::MakeRefPtr<RichEditorOverlayModifier>(
|
||||
richEditorPattern, AceType::WeakClaim(AceType::RawPtr(scrollBarModifier)), scrollEdgeEffect);
|
||||
ASSERT_NE(richEditorOverlayModifier, nullptr);
|
||||
|
||||
Testing::MockCanvas rsCanvas;
|
||||
EXPECT_CALL(rsCanvas, AttachPen(_)).WillRepeatedly(ReturnRef(rsCanvas));
|
||||
EXPECT_CALL(rsCanvas, DetachPen()).WillRepeatedly(ReturnRef(rsCanvas));
|
||||
DrawingContext context { rsCanvas, CONTEXT_WIDTH_VALUE, CONTEXT_HEIGHT_VALUE };
|
||||
|
||||
richEditorOverlayModifier->previewTextStyle_ = PreviewTextStyle::NORMAL;
|
||||
richEditorPattern->contentRect_ = RectF(0, 0, 10.0f, 10.0f);
|
||||
richEditorOverlayModifier->showPreviewTextDecoration_ = AceType::MakeRefPtr<PropertyBool>(1);
|
||||
richEditorOverlayModifier->caretVisible_ = AceType::MakeRefPtr<PropertyBool>(1);
|
||||
richEditorOverlayModifier->caretOffset_ = AceType::MakeRefPtr<PropertyOffsetF>(OffsetF(50, 30));
|
||||
richEditorOverlayModifier->caretWidth_ = AceType::MakeRefPtr<PropertyFloat>(10.0f);
|
||||
richEditorOverlayModifier->caretHeight_ = AceType::MakeRefPtr<PropertyFloat>(10.0f);
|
||||
richEditorOverlayModifier->contentRect_ = RectF(0, 0, 10.0, 10.0);
|
||||
richEditorOverlayModifier->onDraw(context);
|
||||
EXPECT_EQ(richEditorPattern->contentRect_.Height(), 10.0f);
|
||||
|
||||
richEditorPattern->contentRect_ = RectF(0, 0, 10.0f, 50.0f);
|
||||
richEditorOverlayModifier->contentRect_ = RectF(0, 0, 100.0, 10.0);
|
||||
richEditorOverlayModifier->onDraw(context);
|
||||
richEditorOverlayModifier->contentRect_ = RectF(0, 0, 100.0, 100.0);
|
||||
richEditorOverlayModifier->onDraw(context);
|
||||
EXPECT_EQ(richEditorPattern->contentRect_.Height(), 50.0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg002
|
||||
* @tc.desc: Test UpdateScrollBar.
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg002, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
EdgeEffect edgeEffect;
|
||||
auto scrollEdgeEffect = AceType::MakeRefPtr<ScrollEdgeEffect>(edgeEffect);
|
||||
auto scrollBarModifier = AceType::MakeRefPtr<ScrollBarOverlayModifier>();
|
||||
auto richEditorOverlayModifier = AceType::MakeRefPtr<RichEditorOverlayModifier>(
|
||||
richEditorPattern, AceType::WeakClaim(AceType::RawPtr(scrollBarModifier)), scrollEdgeEffect);
|
||||
ASSERT_NE(richEditorOverlayModifier, nullptr);
|
||||
|
||||
auto geometryNode = AceType::MakeRefPtr<GeometryNode>();
|
||||
auto renderContext = RenderContext::Create();
|
||||
ASSERT_NE(geometryNode, nullptr);
|
||||
auto paintProperty = richEditorPattern->CreatePaintProperty();
|
||||
ASSERT_NE(geometryNode, nullptr);
|
||||
auto paintWrapper = AceType::MakeRefPtr<PaintWrapper>(renderContext, geometryNode, paintProperty);
|
||||
ASSERT_NE(paintWrapper, nullptr);
|
||||
|
||||
richEditorPattern->InitScrollablePattern();
|
||||
richEditorOverlayModifier->UpdateScrollBar(AceType::RawPtr(paintWrapper));
|
||||
|
||||
auto scrollBar = richEditorPattern->GetScrollBar();
|
||||
ASSERT_NE(scrollBar, nullptr);
|
||||
scrollBar->isScrollable_ = true;
|
||||
richEditorOverlayModifier->UpdateScrollBar(AceType::RawPtr(paintWrapper));
|
||||
scrollBar->positionModeUpdate_ = true;
|
||||
richEditorOverlayModifier->UpdateScrollBar(AceType::RawPtr(paintWrapper));
|
||||
EXPECT_EQ(scrollBar->GetHoverAnimationType(), HoverAnimationType::NONE);
|
||||
EXPECT_EQ(scrollBar->GetOpacityAnimationType(), OpacityAnimationType::NONE);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg003
|
||||
* @tc.desc: test OnHandleMove
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg003, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto focusHub = richEditorPattern->GetHost()->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
focusHub->currentFocus_ = true;
|
||||
AddImageSpan();
|
||||
|
||||
richEditorPattern->ShowSelectOverlay(
|
||||
richEditorPattern->textSelector_.firstHandle, richEditorPattern->textSelector_.secondHandle, false);
|
||||
|
||||
richEditorPattern->selectOverlay_->hasTransform_ = false;
|
||||
richEditorPattern->selectOverlay_->SetHandleLevelMode(HandleLevelMode::EMBED);
|
||||
richEditorPattern->selectOverlay_->OnHandleMove(RectF(1.0f, 0.0f, 10.0f, 10.0f), true);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.firstHandle.GetOffset().GetX(), 1.0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg004
|
||||
* @tc.desc: test CheckHandleVisible
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg004, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto geometryNode = richEditorNode_->GetGeometryNode();
|
||||
ASSERT_NE(geometryNode, nullptr);
|
||||
geometryNode->SetContentSize(SizeF(BUILDER_WIDTH, BUILDER_HEIGHT));
|
||||
|
||||
richEditorPattern->selectOverlay_->enableHandleLevel_ = true;
|
||||
richEditorPattern->selectOverlay_->SetHandleLevelMode(HandleLevelMode::EMBED);
|
||||
auto isShow1 = richEditorPattern->selectOverlay_->CheckHandleVisible(RectF(0.0f, 0.0f, 10.0f, 10.0f));
|
||||
EXPECT_EQ(isShow1, true);
|
||||
|
||||
richEditorPattern->selectOverlay_->isSingleHandle_ = true;
|
||||
auto isShow2 = richEditorPattern->selectOverlay_->CheckHandleVisible(RectF(0.0f, 0.0f, 10.0f, 10.0f));
|
||||
EXPECT_EQ(isShow2, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg005
|
||||
* @tc.desc: test UpdateSelectorOnHandleMove
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg005, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
richEditorPattern->selectOverlay_->isSingleHandle_ = false;
|
||||
richEditorPattern->selectOverlay_->UpdateSelectorOnHandleMove(OffsetF(50.0f, 50.0f), false);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.destinationOffset, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg007
|
||||
* @tc.desc: test OnMenuItemAction
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg007, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto focusHub = richEditorPattern->GetHost()->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
focusHub->currentFocus_ = false;
|
||||
|
||||
richEditorPattern->textDetectEnable_ = true;
|
||||
richEditorPattern->selectOverlay_->OnMenuItemAction(OptionMenuActionId::DISAPPEAR, OptionMenuType::MOUSE_MENU);
|
||||
EXPECT_TRUE(richEditorPattern->GetTextDetectEnable());
|
||||
EXPECT_FALSE(richEditorPattern->HasFocus());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg008
|
||||
* @tc.desc: test OnCloseOverlay
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg008, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto focusHub = richEditorPattern->GetHost()->GetOrCreateFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
focusHub->currentFocus_ = false;
|
||||
|
||||
richEditorPattern->textDetectEnable_ = true;
|
||||
richEditorPattern->isEditing_ = true;
|
||||
auto info = AceType::MakeRefPtr<OverlayInfo>();
|
||||
richEditorPattern->selectOverlay_->OnCloseOverlay(
|
||||
OptionMenuType::MOUSE_MENU, CloseReason::CLOSE_REASON_BACK_PRESSED, info);
|
||||
EXPECT_EQ(richEditorPattern->caretTwinkling_, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg009
|
||||
* @tc.desc: test OnHandleLevelModeChanged
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg009, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto selectOverlay = richEditorPattern->selectOverlay_;
|
||||
ASSERT_NE(selectOverlay, nullptr);
|
||||
selectOverlay->handleLevelMode_ = HandleLevelMode::EMBED;
|
||||
selectOverlay->OnHandleLevelModeChanged(HandleLevelMode::OVERLAY);
|
||||
EXPECT_EQ(selectOverlay->handleLevelMode_, HandleLevelMode::OVERLAY);
|
||||
|
||||
selectOverlay->handleLevelMode_ = HandleLevelMode::OVERLAY;
|
||||
selectOverlay->OnHandleLevelModeChanged(HandleLevelMode::EMBED);
|
||||
EXPECT_EQ(selectOverlay->handleLevelMode_, HandleLevelMode::EMBED);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorOverlayTestNg010
|
||||
* @tc.desc: test OnAncestorNodeChanged
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorOverlayTestNg, RichEditorOverlayTestNg010, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
FrameNodeChangeInfoFlag flag = FRAME_NODE_CHANGE_GEOMETRY_CHANGE;
|
||||
richEditorPattern->selectOverlay_->OnAncestorNodeChanged(flag);
|
||||
EXPECT_EQ(richEditorPattern->selectOverlay_->IsAncestorNodeGeometryChange(flag), true);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
@ -297,6 +297,44 @@ HWTEST_F(RichEditorPatternTestNg, RichEditorPatternTestCloseCustomKeyboard001, T
|
||||
richEditorPattern->customKeyboardBuilder_ = oldFunc;
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorPatternTestUpdatePreviewText001
|
||||
* @tc.desc: test UpdatePreviewText
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestNg, RichEditorPatternTestUpdatePreviewText001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
std::string previewTextValue = INIT_VALUE_1;
|
||||
PreviewRange previewRange;
|
||||
previewRange.start = -1;
|
||||
previewRange.end = -1;
|
||||
richEditorPattern->SetPreviewText(PREVIEW_TEXT_VALUE1, previewRange);
|
||||
|
||||
previewRange.start = -1;
|
||||
previewRange.end = -1;
|
||||
EXPECT_EQ(richEditorPattern->UpdatePreviewText(previewTextValue, previewRange), true);
|
||||
|
||||
previewRange.start = 0;
|
||||
previewRange.end = -1;
|
||||
EXPECT_EQ(richEditorPattern->UpdatePreviewText(previewTextValue, previewRange), false);
|
||||
|
||||
previewRange.start = -1;
|
||||
previewRange.end = 0;
|
||||
EXPECT_EQ(richEditorPattern->UpdatePreviewText(previewTextValue, previewRange), false);
|
||||
|
||||
previewRange.start = 0;
|
||||
previewRange.end = 0;
|
||||
EXPECT_EQ(richEditorPattern->UpdatePreviewText(previewTextValue, previewRange), true);
|
||||
|
||||
previewRange.start = richEditorPattern->previewTextRecord_.startOffset;
|
||||
previewRange.end = richEditorPattern->previewTextRecord_.endOffset;
|
||||
EXPECT_EQ(richEditorPattern->UpdatePreviewText(previewTextValue, previewRange), false);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorPatternTestInsertDiffStyleValueInSpan001
|
||||
* @tc.desc: test InsertDiffStyleValueInSpan
|
||||
@ -309,36 +347,59 @@ HWTEST_F(RichEditorPatternTestNg, RichEditorPatternTestInsertDiffStyleValueInSpa
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto spanNode = AceType::MakeRefPtr<SpanNode>(testSpanNodeId);
|
||||
ASSERT_NE(spanNode, nullptr);
|
||||
|
||||
|
||||
TextInsertValueInfo info;
|
||||
std::string insertValue;
|
||||
struct UpdateSpanStyle typingStyle;
|
||||
TextStyle textStyle(5);
|
||||
richEditorPattern->SetTypingStyle(typingStyle, textStyle);
|
||||
|
||||
richEditorPattern->InsertDiffStyleValueInSpan(spanNode, info, insertValue, false);
|
||||
ASSERT_EQ(richEditorPattern->moveLength_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorPatternTestSpanNodeFission001
|
||||
* @tc.desc: test SpanNodeFission
|
||||
* @tc.name: RichEditorPatternTestCreateTextSpanNode001
|
||||
* @tc.desc: test CreateTextSpanNode
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestNg, RichEditorPatternTestSpanNodeFission001, TestSize.Level1)
|
||||
HWTEST_F(RichEditorPatternTestNg, RichEditorPatternTestCreateTextSpanNode001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto spanNode = AceType::MakeRefPtr<SpanNode>(testSpanNodeId);
|
||||
ASSERT_NE(spanNode, nullptr);
|
||||
RefPtr<SpanNode> spanNode;
|
||||
|
||||
std::string insertValue;
|
||||
TextInsertValueInfo info;
|
||||
std::string insertValue;
|
||||
UpdateSpanStyle updateSpanStyle;
|
||||
TextStyle textStyle;
|
||||
|
||||
richEditorPattern->SpanNodeFission(spanNode, insertValue, info);
|
||||
ASSERT_EQ(spanNode->GetSpanItem()->position, -1);
|
||||
updateSpanStyle.useThemeFontColor = false;
|
||||
|
||||
insertValue = "hello\n";
|
||||
richEditorPattern->SpanNodeFission(spanNode, insertValue, info);
|
||||
ASSERT_EQ(spanNode->GetSpanItem()->position, 0);
|
||||
auto typingStyle = richEditorPattern->typingStyle_;
|
||||
auto typingTextStyle = richEditorPattern->typingTextStyle_;
|
||||
|
||||
richEditorPattern->typingStyle_ = std::nullopt;
|
||||
richEditorPattern->typingTextStyle_ = std::nullopt;
|
||||
richEditorPattern->CreateTextSpanNode(spanNode, info, insertValue, false);
|
||||
EXPECT_EQ(spanNode->GetSpanItem()->useThemeDecorationColor, true);
|
||||
|
||||
richEditorPattern->typingStyle_ = updateSpanStyle;
|
||||
richEditorPattern->CreateTextSpanNode(spanNode, info, insertValue, false);
|
||||
EXPECT_EQ(spanNode->GetSpanItem()->useThemeDecorationColor, true);
|
||||
|
||||
richEditorPattern->typingStyle_ = std::nullopt;
|
||||
richEditorPattern->typingTextStyle_ = textStyle;
|
||||
richEditorPattern->CreateTextSpanNode(spanNode, info, insertValue, false);
|
||||
EXPECT_EQ(spanNode->GetSpanItem()->useThemeDecorationColor, true);
|
||||
|
||||
richEditorPattern->typingStyle_ = updateSpanStyle;
|
||||
richEditorPattern->CreateTextSpanNode(spanNode, info, insertValue, false);
|
||||
EXPECT_EQ(spanNode->GetSpanItem()->useThemeDecorationColor, true);
|
||||
|
||||
richEditorPattern->typingStyle_ = typingStyle;
|
||||
richEditorPattern->typingTextStyle_ = typingTextStyle;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -625,7 +686,7 @@ HWTEST_F(RichEditorPatternTestNg, HandleCursorOnDragMoved001, TestSize.Level1)
|
||||
*/
|
||||
richEditorPattern->isCursorAlwaysDisplayed_ = false;
|
||||
richEditorPattern->HandleCursorOnDragMoved(notifyDragEvent);
|
||||
EXPECT_EQ(richEditorPattern->isCursorAlwaysDisplayed_, false);
|
||||
EXPECT_EQ(richEditorPattern->isCursorAlwaysDisplayed_, true);
|
||||
}
|
||||
|
||||
/**
|
||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,639 @@
|
||||
/*
|
||||
* Copyright (c) 2024 Huawei Device Co., Ltd.
|
||||
* 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.
|
||||
*/
|
||||
#include "test/mock/base/mock_task_executor.h"
|
||||
#include "test/mock/core/common/mock_clipboard.h"
|
||||
#include "test/unittest/core/pattern/rich_editor/rich_editor_common_test_ng.h"
|
||||
|
||||
using namespace testing;
|
||||
using namespace testing::ext;
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
namespace {
|
||||
constexpr uint32_t RECORD_MAX_LENGTH = 20;
|
||||
constexpr int32_t SYMBOL_SPAN_LENGTH = 2;
|
||||
const std::string TEST_INSERT_LINE_SPACE = " ";
|
||||
} // namespace
|
||||
|
||||
class RichEditorPatternTestThreeNg : public RichEditorCommonTestNg {
|
||||
public:
|
||||
void SetUp() override;
|
||||
void TearDown() override;
|
||||
static void TearDownTestSuite();
|
||||
RefPtr<RichEditorPattern> GetRichEditorPattern();
|
||||
};
|
||||
|
||||
void RichEditorPatternTestThreeNg::SetUp()
|
||||
{
|
||||
MockPipelineContext::SetUp();
|
||||
MockContainer::SetUp();
|
||||
MockContainer::Current()->taskExecutor_ = AceType::MakeRefPtr<MockTaskExecutor>();
|
||||
auto* stack = ViewStackProcessor::GetInstance();
|
||||
auto nodeId = stack->ClaimNodeId();
|
||||
richEditorNode_ = FrameNode::GetOrCreateFrameNode(
|
||||
V2::RICH_EDITOR_ETS_TAG, nodeId, []() { return AceType::MakeRefPtr<RichEditorPattern>(); });
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
richEditorPattern->SetRichEditorController(AceType::MakeRefPtr<RichEditorController>());
|
||||
richEditorPattern->GetRichEditorController()->SetPattern(AceType::WeakClaim(AceType::RawPtr(richEditorPattern)));
|
||||
richEditorPattern->CreateNodePaintMethod();
|
||||
richEditorNode_->GetGeometryNode()->SetContentSize({});
|
||||
}
|
||||
|
||||
void RichEditorPatternTestThreeNg::TearDown()
|
||||
{
|
||||
richEditorNode_ = nullptr;
|
||||
MockParagraph::TearDown();
|
||||
}
|
||||
|
||||
void RichEditorPatternTestThreeNg::TearDownTestSuite()
|
||||
{
|
||||
TestNG::TearDownTestSuite();
|
||||
}
|
||||
|
||||
RefPtr<RichEditorPattern> RichEditorPatternTestThreeNg::GetRichEditorPattern()
|
||||
{
|
||||
CHECK_NULL_RETURN(richEditorNode_, nullptr);
|
||||
return richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: SetInputMethodStatus001
|
||||
* @tc.desc: test SetInputMethodStatus
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, SetInputMethodStatus001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
#if defined(OHOS_STANDARD_SYSTEM) && !defined(PREVIEW)
|
||||
richEditorPattern->SetInputMethodStatus(true);
|
||||
EXPECT_TRUE(richEditorPattern->imeShown_);
|
||||
richEditorPattern->SetInputMethodStatus(false);
|
||||
EXPECT_FALSE(richEditorPattern->imeShown_);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CursorMoveRight001
|
||||
* @tc.desc: test CursorMoveRight
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CursorMoveRight001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
richEditorPattern->CursorMoveRight();
|
||||
EXPECT_TRUE(richEditorPattern->caretVisible_);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CursorMoveLeftAndRightWord001
|
||||
* @tc.desc: test CursorMoveLeftWord and CursorMoveRightWord
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CursorMoveLeftWord001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_FALSE(richEditorPattern->CursorMoveLeftWord());
|
||||
EXPECT_FALSE(richEditorPattern->CursorMoveRightWord());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CursorMoveToParagraphBegin001
|
||||
* @tc.desc: test CursorMoveToParagraphBegin
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CursorMoveToParagraphBegin001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_FALSE(richEditorPattern->CursorMoveToParagraphBegin());
|
||||
AddSpan(TEST_INSERT_LINE_SEP);
|
||||
richEditorPattern->caretPosition_ = 1;
|
||||
EXPECT_TRUE(richEditorPattern->CursorMoveToParagraphBegin());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CursorMoveEnd001
|
||||
* @tc.desc: test CursorMoveToParagraphBegin
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CursorMoveEnd001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_FALSE(richEditorPattern->CursorMoveToParagraphBegin());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetLeftWordPosition001
|
||||
* @tc.desc: test GetLeftWordPosition
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, GetLeftWordPosition001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_EQ(richEditorPattern->GetLeftWordPosition(richEditorPattern->caretPosition_), 0);
|
||||
AddSpan(INIT_VALUE_1 + TEST_INSERT_LINE_SPACE);
|
||||
EXPECT_EQ(richEditorPattern->GetLeftWordPosition(richEditorPattern->GetTextContentLength()), 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetRightWordPosition001
|
||||
* @tc.desc: test GetRightWordPosition
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, GetRightWordPosition001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_EQ(richEditorPattern->GetLeftWordPosition(richEditorPattern->caretPosition_), 0);
|
||||
AddSpan(INIT_VALUE_1 + TEST_INSERT_LINE_SPACE);
|
||||
EXPECT_EQ(richEditorPattern->GetRightWordPosition(richEditorPattern->GetTextContentLength()),
|
||||
richEditorPattern->GetTextContentLength());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleSelect001
|
||||
* @tc.desc: test HandleSelect
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleSelect001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_EQ(richEditorPattern->GetLeftWordPosition(richEditorPattern->caretPosition_), 0);
|
||||
AddSpan(INIT_VALUE_1 + TEST_INSERT_LINE_SPACE);
|
||||
richEditorPattern->HandleSelect(CaretMoveIntent::Home);
|
||||
EXPECT_EQ(richEditorPattern->textSelector_.GetTextStart(), richEditorPattern->textSelector_.GetStart());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleOnEscape001
|
||||
* @tc.desc: test HandleOnEscape
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleOnEscape001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
EXPECT_FALSE(richEditorPattern->HandleOnEscape());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleOnUndoAction001
|
||||
* @tc.desc: test HandleOnUndoAction
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleOnUndoAction001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
RichEditorPattern::OperationRecord firstRecord;
|
||||
firstRecord.addText = "first Record helloWorld";
|
||||
firstRecord.deleteText = "helloWorld";
|
||||
richEditorPattern->operationRecords_.emplace_back(firstRecord);
|
||||
richEditorPattern->redoOperationRecords_.clear();
|
||||
for (uint32_t count = 0; count < RECORD_MAX_LENGTH; ++count) {
|
||||
RichEditorPattern::OperationRecord emptyRecord;
|
||||
richEditorPattern->redoOperationRecords_.emplace_back(emptyRecord);
|
||||
}
|
||||
richEditorPattern->HandleOnUndoAction();
|
||||
EXPECT_TRUE(richEditorPattern->operationRecords_.empty());
|
||||
|
||||
RichEditorPattern::OperationRecord secondRecord;
|
||||
secondRecord.addText = "second Record helloWorld";
|
||||
secondRecord.deleteCaretPostion = 3;
|
||||
richEditorPattern->operationRecords_.clear();
|
||||
richEditorPattern->operationRecords_.emplace_back(secondRecord);
|
||||
richEditorPattern->HandleOnUndoAction();
|
||||
EXPECT_TRUE(richEditorPattern->operationRecords_.empty());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleOnRedoAction001
|
||||
* @tc.desc: test HandleOnRedoAction
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleOnRedoAction001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
richEditorPattern->HandleOnRedoAction();
|
||||
RichEditorPattern::OperationRecord firstRecord;
|
||||
firstRecord.addText = "first Record helloWorld";
|
||||
firstRecord.deleteCaretPostion = 3;
|
||||
richEditorPattern->redoOperationRecords_.emplace_back(firstRecord);
|
||||
richEditorPattern->HandleOnRedoAction();
|
||||
EXPECT_TRUE(richEditorPattern->redoOperationRecords_.empty());
|
||||
|
||||
RichEditorPattern::OperationRecord secondRecord;
|
||||
secondRecord.addText = "second Record helloWorld";
|
||||
secondRecord.deleteText = "helloWorld";
|
||||
richEditorPattern->redoOperationRecords_.clear();
|
||||
richEditorPattern->redoOperationRecords_.emplace_back(secondRecord);
|
||||
richEditorPattern->HandleOnRedoAction();
|
||||
EXPECT_TRUE(richEditorPattern->redoOperationRecords_.empty());
|
||||
|
||||
RichEditorPattern::OperationRecord thridRecord;
|
||||
thridRecord.deleteText = "helloWorld";
|
||||
thridRecord.beforeCaretPosition = 10;
|
||||
thridRecord.afterCaretPosition = 15;
|
||||
richEditorPattern->redoOperationRecords_.clear();
|
||||
richEditorPattern->redoOperationRecords_.emplace_back(thridRecord);
|
||||
richEditorPattern->HandleOnRedoAction();
|
||||
EXPECT_TRUE(richEditorPattern->redoOperationRecords_.empty());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CalcDeleteValueObj001
|
||||
* @tc.desc: test CalcDeleteValueObj delete unicode
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CalcDeleteValueObj001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
auto spans = richEditorPattern->GetSpanItemChildren();
|
||||
ASSERT_FALSE(spans.empty());
|
||||
auto spanItem = spans.back();
|
||||
ASSERT_NE(spanItem, nullptr);
|
||||
spanItem->unicode = 1;
|
||||
|
||||
RichEditorDeleteValue info;
|
||||
int32_t currentPosition = INIT_VALUE_1.size() - 2;
|
||||
int32_t length = 2;
|
||||
richEditorPattern->CalcDeleteValueObj(currentPosition, length, info);
|
||||
EXPECT_EQ(info.GetLength(), SYMBOL_SPAN_LENGTH);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: CalcDeleteValueObj001
|
||||
* @tc.desc: test CalcDeleteValueObj delete builder span
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, CalcDeleteValueObj002, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
auto spans = richEditorPattern->GetSpanItemChildren();
|
||||
ASSERT_FALSE(spans.empty());
|
||||
auto spanItem = spans.back();
|
||||
ASSERT_NE(spanItem, nullptr);
|
||||
int32_t currentPosition = INIT_VALUE_1.size() - 2;
|
||||
spanItem->placeholderIndex = currentPosition;
|
||||
|
||||
RichEditorDeleteValue info;
|
||||
int32_t length = 2;
|
||||
richEditorPattern->CalcDeleteValueObj(currentPosition, length, info);
|
||||
EXPECT_EQ(info.GetRichEditorDeleteSpans().size(), 1);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetSpanNodeBySpanItem001
|
||||
* @tc.desc: test GetSpanNodeBySpanItem
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, GetSpanNodeBySpanItem001, TestSize.Level2)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
ASSERT_EQ(richEditorPattern->GetSpanNodeBySpanItem(nullptr), nullptr);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: DeleteValueSetImageSpan001
|
||||
* @tc.desc: test DeleteValueSetImageSpan
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, DeleteValueSetImageSpan001, TestSize.Level1)
|
||||
{
|
||||
AddImageSpan();
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
auto imageNode = AceType::DynamicCast<FrameNode>(richEditorNode_->GetLastChild());
|
||||
ASSERT_NE(imageNode, nullptr);
|
||||
auto imageLayoutProperty = imageNode->GetLayoutProperty<ImageLayoutProperty>();
|
||||
ASSERT_NE(imageLayoutProperty, nullptr);
|
||||
imageLayoutProperty->UpdateImageFit(ImageFit::FILL);
|
||||
imageLayoutProperty->UpdateVerticalAlign(VerticalAlign::CENTER);
|
||||
|
||||
RichEditorAbstractSpanResult spanResult;
|
||||
spanResult.SetSpanIndex(richEditorNode_->GetChildIndexById(imageNode->GetId()));
|
||||
|
||||
auto spans = richEditorPattern->GetSpanItemChildren();
|
||||
ASSERT_FALSE(spans.empty());
|
||||
auto imageSpanItem = AceType::DynamicCast<ImageSpanItem>(spans.back());
|
||||
ASSERT_NE(imageSpanItem, nullptr);
|
||||
richEditorPattern->DeleteValueSetImageSpan(imageSpanItem, spanResult);
|
||||
EXPECT_EQ(spanResult.GetObjectFit(), ImageFit::FILL);
|
||||
EXPECT_EQ(spanResult.GetVerticalAlign(), VerticalAlign::CENTER);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleOnCopyStyledString001
|
||||
* @tc.desc: test HandleOnCopyStyledString
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleOnCopyStyledString001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
|
||||
richEditorPattern->OnModifyDone();
|
||||
richEditorPattern->SetSpanStringMode(true);
|
||||
richEditorPattern->OnCopyOperation();
|
||||
ASSERT_NE(richEditorPattern->GetClipboard(), nullptr);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: OnCopyOperationExt001
|
||||
* @tc.desc: test OnCopyOperationExt
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, OnCopyOperationExt001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(INIT_VALUE_1);
|
||||
|
||||
richEditorPattern->OnModifyDone();
|
||||
auto clipboard = richEditorPattern->GetClipboard();
|
||||
ASSERT_NE(clipboard, nullptr);
|
||||
auto pasteDataMix = clipboard->CreatePasteDataMix();
|
||||
richEditorPattern->OnCopyOperationExt(pasteDataMix);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: ClearContent001
|
||||
* @tc.desc: test ClearContent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, ClearContent001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto placeholderSpanNode = PlaceholderSpanNode::GetOrCreateSpanNode(V2::PLACEHOLDER_SPAN_ETS_TAG,
|
||||
ElementRegister::GetInstance()->MakeUniqueId(), []() { return AceType::MakeRefPtr<PlaceholderSpanPattern>(); });
|
||||
auto placeholderSpanItem = placeholderSpanNode->GetSpanItem();
|
||||
ASSERT_NE(placeholderSpanItem, nullptr);
|
||||
placeholderSpanItem->content = " ";
|
||||
placeholderSpanNode->MountToParent(richEditorNode_);
|
||||
richEditorPattern->ClearContent(placeholderSpanNode);
|
||||
EXPECT_TRUE(placeholderSpanItem->content.empty());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: UpdateTextFieldManager001
|
||||
* @tc.desc: test UpdateTextFieldManager
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, UpdateTextFieldManager001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
ASSERT_NE(context, nullptr);
|
||||
context->taskExecutor_ = AceType::MakeRefPtr<MockTaskExecutor>();
|
||||
auto taskExecutor = context->GetTaskExecutor();
|
||||
ASSERT_NE(taskExecutor, nullptr);
|
||||
auto textFieldManager = AceType::MakeRefPtr<TextFieldManagerNG>();
|
||||
textFieldManager->SetHeight(20);
|
||||
context->SetTextFieldManager(textFieldManager);
|
||||
|
||||
auto theme = AceType::MakeRefPtr<MockThemeManager>();
|
||||
context->SetThemeManager(theme);
|
||||
EXPECT_CALL(*theme, GetTheme(_)).WillRepeatedly(Return(AceType::MakeRefPtr<RichEditorTheme>()));
|
||||
auto focusHub = richEditorPattern->GetFocusHub();
|
||||
ASSERT_NE(focusHub, nullptr);
|
||||
focusHub->currentFocus_ = true;
|
||||
Offset Offset = { 1, 4 };
|
||||
richEditorPattern->isTextChange_ = true;
|
||||
richEditorPattern->UpdateTextFieldManager(Offset, 1.0f);
|
||||
EXPECT_NE(textFieldManager->GetOnFocusTextField().Upgrade(), nullptr);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: OnDirtyLayoutWrapperSwap001
|
||||
* @tc.desc: test OnDirtyLayoutWrapperSwap
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, OnDirtyLayoutWrapperSwap001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto rendenContext = richEditorNode_->GetRenderContext();
|
||||
ASSERT_NE(rendenContext, nullptr);
|
||||
rendenContext->UpdateClipEdge(false);
|
||||
auto geometryNode = richEditorNode_->GetGeometryNode();
|
||||
ASSERT_NE(geometryNode, nullptr);
|
||||
auto globalOffset = OffsetF(15.0f, 3.0f);
|
||||
geometryNode->SetFrameSize(SizeF(20.0f, 5.0f));
|
||||
geometryNode->SetFrameOffset(globalOffset);
|
||||
|
||||
auto layoutWrapper = AceType::MakeRefPtr<LayoutWrapperNode>(
|
||||
richEditorNode_, AceType::MakeRefPtr<GeometryNode>(), richEditorNode_->GetLayoutProperty());
|
||||
ASSERT_NE(layoutWrapper, nullptr);
|
||||
auto layoutAlgorithm = AceType::DynamicCast<RichEditorLayoutAlgorithm>(richEditorPattern->CreateLayoutAlgorithm());
|
||||
ASSERT_NE(layoutAlgorithm, nullptr);
|
||||
layoutAlgorithm->parentGlobalOffset_ = globalOffset;
|
||||
layoutWrapper->SetLayoutAlgorithm(AceType::MakeRefPtr<LayoutAlgorithmWrapper>(layoutAlgorithm));
|
||||
DirtySwapConfig config;
|
||||
richEditorPattern->baselineOffset_ = 6.0f;
|
||||
richEditorPattern->CreateNodePaintMethod();
|
||||
auto ret = richEditorPattern->OnDirtyLayoutWrapperSwap(layoutWrapper, config);
|
||||
EXPECT_FALSE(ret);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleUserGestureEvent001
|
||||
* @tc.desc: test HandleUserGestureEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleUserGestureEvent001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
AddSpan(EXCEPT_VALUE);
|
||||
ASSERT_FALSE(richEditorPattern->spans_.empty());
|
||||
auto firstSpanItem = richEditorPattern->spans_.front();
|
||||
ASSERT_NE(firstSpanItem, nullptr);
|
||||
firstSpanItem->leadingMargin = std::make_optional<NG::LeadingMargin>();
|
||||
auto paragraph = MockParagraph::GetOrCreateMockParagraph();
|
||||
ASSERT_NE(paragraph, nullptr);
|
||||
richEditorPattern->paragraphs_.AddParagraph({ .paragraph = paragraph, .start = 0, .end = 10 });
|
||||
|
||||
std::vector<RectF> rects { RectF(0, 0, 5, 5) };
|
||||
EXPECT_CALL(*paragraph, GetRectsForRange(_, _, _)).WillRepeatedly(SetArgReferee<THIRD_PARAM>(rects));
|
||||
EXPECT_CALL(*paragraph, GetHeight).WillRepeatedly(Return(50));
|
||||
GestureEvent info;
|
||||
info.SetLocalLocation(Offset(3, 3));
|
||||
richEditorPattern->contentRect_ = RectF(0, 0, 20.0, 20.0);
|
||||
auto gestureFunc = [](RefPtr<SpanItem> item, GestureEvent& info) -> bool { return true; };
|
||||
EXPECT_TRUE(richEditorPattern->HandleUserGestureEvent(info, std::move(gestureFunc)));
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleTouchEvent001
|
||||
* @tc.desc: test HandleTouchEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleTouchEvent001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
TouchEventInfo touchEventInfo("");
|
||||
TouchLocationInfo touchLocationInfo(0);
|
||||
touchLocationInfo.touchType_ = TouchType::DOWN;
|
||||
touchLocationInfo.localLocation_ = Offset(0.0f, 0.0f);
|
||||
touchEventInfo.AddTouchLocationInfo(std::move(touchLocationInfo));
|
||||
richEditorPattern->HandleTouchEvent(touchEventInfo);
|
||||
auto touchInfo = touchEventInfo.GetTouches().front();
|
||||
auto touchType = touchInfo.GetTouchType();
|
||||
EXPECT_EQ(touchType, TouchType::DOWN);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleTouchEvent002
|
||||
* @tc.desc: test HandleTouchEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleTouchEvent002, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
TouchEventInfo touchEventInfo("");
|
||||
TouchLocationInfo touchLocationInfo(0);
|
||||
touchLocationInfo.touchType_ = TouchType::UP;
|
||||
touchLocationInfo.localLocation_ = Offset(0.0f, 0.0f);
|
||||
touchEventInfo.AddTouchLocationInfo(std::move(touchLocationInfo));
|
||||
richEditorPattern->HandleTouchEvent(touchEventInfo);
|
||||
auto touchInfo = touchEventInfo.GetTouches().front();
|
||||
auto touchType = touchInfo.GetTouchType();
|
||||
EXPECT_EQ(touchType, TouchType::UP);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleTouchEvent003
|
||||
* @tc.desc: test HandleTouchEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleTouchEvent003, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
TouchEventInfo touchEventInfo("");
|
||||
TouchLocationInfo touchLocationInfo(0);
|
||||
touchLocationInfo.touchType_ = TouchType::MOVE;
|
||||
touchLocationInfo.localLocation_ = Offset(0.0f, 0.0f);
|
||||
touchEventInfo.AddTouchLocationInfo(std::move(touchLocationInfo));
|
||||
richEditorPattern->HandleTouchEvent(touchEventInfo);
|
||||
auto touchInfo = touchEventInfo.GetTouches().front();
|
||||
auto touchType = touchInfo.GetTouchType();
|
||||
EXPECT_EQ(touchType, TouchType::MOVE);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: HandleTouchEvent004
|
||||
* @tc.desc: test HandleTouchEvent
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, HandleTouchEvent004, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
TouchEventInfo touchEventInfo("");
|
||||
TouchLocationInfo touchLocationInfo(0);
|
||||
touchLocationInfo.touchType_ = TouchType::UNKNOWN;
|
||||
touchLocationInfo.localLocation_ = Offset(0.0f, 0.0f);
|
||||
touchEventInfo.AddTouchLocationInfo(std::move(touchLocationInfo));
|
||||
richEditorPattern->HandleTouchEvent(touchEventInfo);
|
||||
auto touchInfo = touchEventInfo.GetTouches().front();
|
||||
auto touchType = touchInfo.GetTouchType();
|
||||
EXPECT_EQ(touchType, TouchType::UNKNOWN);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetRightWordPosition002
|
||||
* @tc.desc: test GetRightWordPosition
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, GetRightWordPosition002, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
std::string firstText = "text";
|
||||
AddSpan(firstText);
|
||||
std::string space = " ";
|
||||
std::string secondText = "content";
|
||||
AddSpan(space + secondText);
|
||||
auto initCaretPosition = firstText.size();
|
||||
EXPECT_EQ(richEditorPattern->GetRightWordPosition(initCaretPosition), initCaretPosition + space.size());
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetRightWordPosition003
|
||||
* @tc.desc: test GetRightWordPosition
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, GetRightWordPosition003, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
std::string firstText = "Text ";
|
||||
AddSpan(firstText);
|
||||
std::string secondText = "Content\n";
|
||||
AddSpan(secondText);
|
||||
AddSpan(INIT_VALUE_3);
|
||||
|
||||
auto initCaretPosition = firstText.size() + secondText.size() - 1;
|
||||
EXPECT_EQ(richEditorPattern->GetRightWordPosition(initCaretPosition), initCaretPosition + 1);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: InitScrollablePattern001
|
||||
* @tc.desc: test InitScrollablePattern when update padding property
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPatternTestThreeNg, InitScrollablePattern001, TestSize.Level1)
|
||||
{
|
||||
auto richEditorPattern = GetRichEditorPattern();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
auto layoutProperty = richEditorPattern->GetLayoutProperty<RichEditorLayoutProperty>();
|
||||
ASSERT_NE(layoutProperty, nullptr);
|
||||
auto theme = AceType::MakeRefPtr<MockThemeManager>();
|
||||
auto context = PipelineContext::GetCurrentContext();
|
||||
ASSERT_NE(context, nullptr);
|
||||
context->SetThemeManager(theme);
|
||||
EXPECT_CALL(*theme, GetTheme(_)).WillRepeatedly(Return(AceType::MakeRefPtr<RichEditorTheme>()));
|
||||
PaddingProperty padding;
|
||||
padding.top = CalcLength(10);
|
||||
padding.left = CalcLength(10);
|
||||
padding.right = CalcLength(10);
|
||||
padding.bottom = CalcLength(10);
|
||||
layoutProperty->UpdatePadding(padding);
|
||||
richEditorPattern->InitScrollablePattern();
|
||||
EXPECT_TRUE(IsEqual(richEditorPattern->richTextRect_.GetOffset(), OffsetF(10.0f, 10.0f)));
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
File diff suppressed because it is too large
Load Diff
@ -218,4 +218,21 @@ HWTEST_F(RichEditorPreviewTextTestNg, FinishTextPreview002, TestSize.Level1)
|
||||
EXPECT_EQ((*it)->content, PREVIEW_TEXT_VALUE1);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetPreviewTextInfo001
|
||||
* @tc.desc: test RichEditorPattern GetPreviewTextInfo
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorPreviewTextTestNg, GetPreviewTextInfo001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
PreviewTextInfo info = richEditorPattern->GetPreviewTextInfo();
|
||||
ASSERT_EQ(richEditorPattern->previewTextRecord_.previewContent.empty(), true);
|
||||
|
||||
richEditorPattern->previewTextRecord_.previewContent = "abc";
|
||||
info = richEditorPattern->GetPreviewTextInfo();
|
||||
ASSERT_EQ(richEditorPattern->previewTextRecord_.previewContent.empty(), false);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
1083
test/unittest/core/pattern/rich_editor/rich_editor_span_test.cpp
Normal file
1083
test/unittest/core/pattern/rich_editor/rich_editor_span_test.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@ -973,4 +973,68 @@ HWTEST_F(RichEditorStyledStringTestNg, GetSelection001, TestSize.Level1)
|
||||
auto testRangeInfo = styledStringController->GetSelection();
|
||||
ASSERT_EQ(testRangeInfo.start_, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: InsertValueInStyledString001
|
||||
* @tc.desc: test RichEditorPattern InsertValueInStyledString
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorStyledStringTestNg, InsertValueInStyledString001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
|
||||
TextStyle style;
|
||||
style.SetLineHeight(LINE_HEIGHT_VALUE);
|
||||
style.SetLetterSpacing(LETTER_SPACING);
|
||||
style.SetFontFeatures(TEXT_FONTFEATURE);
|
||||
|
||||
UpdateSpanStyle updateSpanStyle;
|
||||
|
||||
std::string content = "TEST123";
|
||||
richEditorPattern->isSpanStringMode_ = true;
|
||||
richEditorPattern->styledString_ = AceType::MakeRefPtr<MutableSpanString>(content);
|
||||
|
||||
richEditorPattern->typingStyle_ = std::nullopt;
|
||||
richEditorPattern->typingTextStyle_ = std::nullopt;
|
||||
richEditorPattern->InsertValueInStyledString("abc");
|
||||
|
||||
richEditorPattern->typingStyle_ = std::nullopt;
|
||||
richEditorPattern->typingTextStyle_ = style;
|
||||
richEditorPattern->InsertValueInStyledString("abc");
|
||||
|
||||
richEditorPattern->typingStyle_ = updateSpanStyle;
|
||||
richEditorPattern->typingTextStyle_ = std::nullopt;
|
||||
richEditorPattern->InsertValueInStyledString("abc");
|
||||
|
||||
richEditorPattern->typingStyle_ = updateSpanStyle;
|
||||
richEditorPattern->typingTextStyle_ = style;
|
||||
richEditorPattern->InsertValueInStyledString("abc");
|
||||
|
||||
ASSERT_EQ(richEditorPattern->typingTextStyle_.has_value(), true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: DeleteValueInStyledString001
|
||||
* @tc.desc: test RichEditorPattern DeleteValueInStyledString
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorStyledStringTestNg, DeleteValueInStyledString001, TestSize.Level1)
|
||||
{
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(richEditorPattern, nullptr);
|
||||
richEditorPattern->styledString_ = AceType::MakeRefPtr<MutableSpanString>("abc");
|
||||
richEditorPattern->caretVisible_ = false;
|
||||
richEditorPattern->previewLongPress_ = true;
|
||||
richEditorPattern->DeleteValueInStyledString(0, 10, true);
|
||||
richEditorPattern->previewLongPress_ = false;
|
||||
richEditorPattern->DeleteValueInStyledString(0, 10, true);
|
||||
richEditorPattern->previewLongPress_ = true;
|
||||
richEditorPattern->DeleteValueInStyledString(0, 10, false);
|
||||
richEditorPattern->previewLongPress_ = false;
|
||||
richEditorPattern->DeleteValueInStyledString(0, 10, false);
|
||||
ASSERT_EQ(!richEditorPattern->BeforeStyledStringChange(0, 10, ""), false);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
||||
|
@ -3701,7 +3701,6 @@ HWTEST_F(RichEditorTestNg, RichEditorController012, TestSize.Level1)
|
||||
updateSpanStyle.updateSymbolColor = SYMBOL_COLOR_LIST_2;
|
||||
updateSpanStyle.updateSymbolRenderingStrategy = RENDER_STRATEGY_MULTI_COLOR;
|
||||
updateSpanStyle.updateSymbolEffectStrategy = EFFECT_STRATEGY_SCALE;
|
||||
updateSpanStyle.isSymbolStyle = true;
|
||||
richEditorController->SetUpdateSpanStyle(updateSpanStyle);
|
||||
|
||||
ImageSpanAttribute imageStyle;
|
||||
|
@ -15,5 +15,8 @@ import("//foundation/arkui/ace_engine/test/unittest/ace_unittest.gni")
|
||||
|
||||
ace_unittest("rich_editor_drag_test_ng") {
|
||||
type = "new"
|
||||
sources = [ "rich_editor_drag_test_ng.cpp" ]
|
||||
sources = [
|
||||
"rich_editor_drag_paint_method_test_ng.cpp",
|
||||
"rich_editor_drag_test_ng.cpp",
|
||||
]
|
||||
}
|
||||
|
@ -0,0 +1,121 @@
|
||||
/*
|
||||
* Copyright (c) 2023 Huawei Device Co., Ltd.
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#include "rich_editor_drag_paint_method_test_ng.h"
|
||||
|
||||
#include "test/mock/core/common/mock_container.h"
|
||||
#include "test/mock/core/pipeline/mock_pipeline_context.h"
|
||||
#include "test/mock/core/render/mock_canvas_image.h"
|
||||
#include "core/components_ng/base/view_stack_processor.h"
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
namespace {
|
||||
constexpr float ROOT_WIDTH = 400.f;
|
||||
constexpr float ROOT_HEIGHT = 800.f;
|
||||
}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::SetUpTestSuite()
|
||||
{
|
||||
TestNG::SetUpTestSuite();
|
||||
MockPipelineContext::SetUp();
|
||||
MockContainer::SetUp();
|
||||
}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::TearDownTestSuite()
|
||||
{
|
||||
TestNG::TearDownTestSuite();
|
||||
MockPipelineContext::TearDown();
|
||||
MockContainer::TearDown();
|
||||
}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::SetUp() {}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::TearDown()
|
||||
{
|
||||
frameNode_ = nullptr;
|
||||
pattern_ = nullptr;
|
||||
dragNode_ = nullptr;
|
||||
}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::ClearSpan()
|
||||
{
|
||||
ASSERT_NE(frameNode_, nullptr);
|
||||
ASSERT_NE(pattern_, nullptr);
|
||||
frameNode_->children_.clear();
|
||||
pattern_->spans_.clear();
|
||||
pattern_->caretPosition_ = 0;
|
||||
}
|
||||
|
||||
void RichEditorDragPaintMethodTestNG::InitDate()
|
||||
{
|
||||
ViewAbstract::SetWidth(CalcLength(ROOT_WIDTH));
|
||||
ViewAbstract::SetHeight(CalcLength(ROOT_HEIGHT));
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
model.SetTextDetectEnable(true);
|
||||
frameNode_ = AceType::DynamicCast<FrameNode>(ViewStackProcessor::GetInstance()->Finish());
|
||||
pattern_ = frameNode_->GetPattern<RichEditorPattern>();
|
||||
RefPtr<TextDragOverlayModifier> textGragOverlayModifier =
|
||||
AceType::MakeRefPtr<TextDragOverlayModifier>(pattern_);
|
||||
RefPtr<RichEditorDragContentModifier> richContentModifier =
|
||||
AceType::MakeRefPtr<RichEditorDragContentModifier>();
|
||||
RichEditorDragInfo info;
|
||||
richGragPaintMethod_ =
|
||||
AceType::MakeRefPtr<RichEditorDragPaintMethod>(pattern_, textGragOverlayModifier, richContentModifier, info);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: UpdateContentModifier001
|
||||
* @tc.desc: Test function UpdateContentModifier.
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragPaintMethodTestNG, UpdateContentModifier001, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. Init frameNode_ 、pattern_ and richGragPaintMethod_.
|
||||
*/
|
||||
InitDate();
|
||||
|
||||
/**
|
||||
* @tc.steps: step2. call function UpdateContentModifier.
|
||||
*/
|
||||
RefPtr<GeometryNode> geometryNode = AceType::MakeRefPtr<GeometryNode>();
|
||||
ASSERT_NE(geometryNode, nullptr);
|
||||
RefPtr<RenderContext> renderContext = RenderContext::Create();
|
||||
auto paintProperty = pattern_->CreatePaintProperty();
|
||||
auto paintWrapper = AceType::MakeRefPtr<PaintWrapper>(renderContext, geometryNode, paintProperty);
|
||||
richGragPaintMethod_->UpdateContentModifier(AceType::RawPtr(paintWrapper));
|
||||
EXPECT_TRUE(richGragPaintMethod_->overlayModifier_ != nullptr);
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: GetContentModifier001
|
||||
* @tc.desc: Test function GetContentModifier.
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragPaintMethodTestNG, GetContentModifier001, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. Init frameNode_ 、pattern_ and richGragPaintMethod_.
|
||||
*/
|
||||
InitDate();
|
||||
|
||||
/**
|
||||
* @tc.steps: step2. call function GetContentModifier.
|
||||
*/
|
||||
auto testContentModifier = richGragPaintMethod_->GetContentModifier(nullptr);
|
||||
ASSERT_NE(testContentModifier, nullptr);
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright (c) 2023 Huawei Device Co., Ltd.
|
||||
* 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.
|
||||
*/
|
||||
#ifndef FOUNDATION_ACE_TEST_UNITTEST_CORE_PATTERN_RICH_EDITOR_DRAG_PAINT_METHOD_TEST_NG_H
|
||||
#define FOUNDATION_ACE_TEST_UNITTEST_CORE_PATTERN_RICH_EDITOR_DRAG_PAINT_METHOD_TEST_NG_H
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "test/unittest/core/pattern/test_ng.h"
|
||||
|
||||
#include "base/memory/ace_type.h"
|
||||
#include "base/memory/referenced.h"
|
||||
|
||||
#include "core/components_ng/pattern/text/span_model_ng.h"
|
||||
#include "frameworks/core/components_ng/pattern/rich_editor/rich_editor_model_ng.h"
|
||||
#include "frameworks/core/components_ng/pattern/rich_editor/rich_editor_pattern.h"
|
||||
#include "frameworks/core/components_ng/pattern/rich_editor_drag/rich_editor_drag_paint_method.h"
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
class RichEditorDragPaintMethodTestNG : public TestNG {
|
||||
public:
|
||||
using Callback = std::function<void (RichEditorModelNG& model)>;
|
||||
static void SetUpTestSuite();
|
||||
static void TearDownTestSuite();
|
||||
void SetUp() override;
|
||||
void TearDown() override;
|
||||
void InitDate();
|
||||
void ClearSpan();
|
||||
RefPtr<FrameNode> frameNode_;
|
||||
RefPtr<RichEditorPattern> pattern_;
|
||||
RefPtr<FrameNode> dragNode_;
|
||||
RefPtr<RichEditorDragPaintMethod> richGragPaintMethod_;
|
||||
};
|
||||
} // namespace OHOS::Ace::NG
|
||||
#endif
|
@ -12,134 +12,244 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
#include "test/unittest/core/pattern/rich_editor/rich_editor_common_test_ng.h"
|
||||
|
||||
#include "rich_editor_drag_test_ng.h"
|
||||
|
||||
#include "test/mock/core/common/mock_container.h"
|
||||
#include "test/mock/core/pipeline/mock_pipeline_context.h"
|
||||
#include "test/mock/core/render/mock_canvas_image.h"
|
||||
#include "core/components_ng/base/view_stack_processor.h"
|
||||
|
||||
#define private public
|
||||
#define protected public
|
||||
using namespace testing;
|
||||
using namespace testing::ext;
|
||||
|
||||
namespace OHOS::Ace::NG {
|
||||
namespace {
|
||||
using namespace testing;
|
||||
using namespace testing::ext;
|
||||
constexpr float ROOT_WIDTH = 400.f;
|
||||
constexpr float ROOT_HEIGHT = 800.f;
|
||||
const std::string IMAGE_VALUE = "image1";
|
||||
const std::string BUNDLE_NAME = "bundleName";
|
||||
const std::string MODULE_NAME = "moduleName";
|
||||
int32_t testOnReadyEvent = 0;
|
||||
int32_t testAboutToIMEInput = 0;
|
||||
int32_t testOnIMEInputComplete = 0;
|
||||
int32_t testAboutToDelete = 0;
|
||||
int32_t testOnDeleteComplete = 0;
|
||||
} // namespace
|
||||
|
||||
void RichEditorDragTestNG::SetUpTestSuite()
|
||||
class RichEditorDragTestNg : public RichEditorCommonTestNg {
|
||||
public:
|
||||
void SetUp() override;
|
||||
void TearDown() override;
|
||||
static void TearDownTestSuite();
|
||||
};
|
||||
|
||||
void RichEditorDragTestNg::SetUp()
|
||||
{
|
||||
TestNG::SetUpTestSuite();
|
||||
MockPipelineContext::SetUp();
|
||||
MockContainer::SetUp();
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::TearDownTestSuite()
|
||||
{
|
||||
TestNG::TearDownTestSuite();
|
||||
MockPipelineContext::TearDown();
|
||||
MockContainer::TearDown();
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::SetUp() {}
|
||||
|
||||
void RichEditorDragTestNG::TearDown()
|
||||
{
|
||||
frameNode_ = nullptr;
|
||||
pattern_ = nullptr;
|
||||
dragNode_ = nullptr;
|
||||
dragPattern_ = nullptr;
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::CreateRichEditor(Callback&& callback, uint32_t childSpanNum)
|
||||
{
|
||||
ViewAbstract::SetWidth(CalcLength(ROOT_WIDTH));
|
||||
ViewAbstract::SetHeight(CalcLength(ROOT_HEIGHT));
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
if (callback) {
|
||||
callback(model);
|
||||
}
|
||||
CreateDragNodeWithImageSpan(childSpanNum);
|
||||
FlushLayoutTask(frameNode_);
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::CreateDragNodeWithImageSpan(uint32_t childSpanNum)
|
||||
{
|
||||
frameNode_ = AceType::DynamicCast<FrameNode>(ViewStackProcessor::GetInstance()->Finish());
|
||||
pattern_ = frameNode_->GetPattern<RichEditorPattern>();
|
||||
for (uint32_t index = 0; index < childSpanNum; ++index) {
|
||||
AddImageSpan();
|
||||
}
|
||||
|
||||
auto children = frameNode_->GetChildren();
|
||||
std::list<RefPtr<FrameNode>> imageChildren;
|
||||
for (const auto& child : children) {
|
||||
auto node = AceType::DynamicCast<FrameNode>(child);
|
||||
if (!node) {
|
||||
continue;
|
||||
}
|
||||
auto image = node->GetPattern<ImagePattern>();
|
||||
if (image) {
|
||||
imageChildren.emplace_back(node);
|
||||
}
|
||||
}
|
||||
pattern_->dragNode_ = RichEditorDragPattern::CreateDragNode(frameNode_, imageChildren);
|
||||
dragNode_ = pattern_->dragNode_;
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::AddImageSpan()
|
||||
{
|
||||
ASSERT_NE(pattern_, nullptr);
|
||||
MockContainer::Current()->taskExecutor_ = AceType::MakeRefPtr<MockTaskExecutor>();
|
||||
auto* stack = ViewStackProcessor::GetInstance();
|
||||
auto nodeId = stack->ClaimNodeId();
|
||||
auto imageNode = FrameNode::GetOrCreateFrameNode(
|
||||
V2::IMAGE_ETS_TAG, nodeId, []() { return AceType::MakeRefPtr<ImagePattern>(); });
|
||||
auto imageLayoutProperty = imageNode->GetLayoutProperty<ImageLayoutProperty>();
|
||||
ASSERT_NE(imageLayoutProperty, nullptr);
|
||||
ImageSourceInfo imageInfo(IMAGE_VALUE, BUNDLE_NAME, MODULE_NAME);
|
||||
imageLayoutProperty->UpdateImageSourceInfo(imageInfo);
|
||||
imageNode->MountToParent(frameNode_, frameNode_->children_.size());
|
||||
auto spanItem = AceType::MakeRefPtr<ImageSpanItem>();
|
||||
spanItem->content = " ";
|
||||
spanItem->placeholderIndex = 0;
|
||||
pattern_->spans_.emplace_back(spanItem);
|
||||
int32_t spanTextLength = 0;
|
||||
for (auto& span : pattern_->spans_) {
|
||||
spanTextLength += StringUtils::ToWstring(span->content).length();
|
||||
span->position = spanTextLength;
|
||||
}
|
||||
richEditorNode_ = FrameNode::GetOrCreateFrameNode(
|
||||
V2::RICH_EDITOR_ETS_TAG, nodeId, []() { return AceType::MakeRefPtr<RichEditorPattern>(); });
|
||||
ASSERT_NE(richEditorNode_, nullptr);
|
||||
auto richEditorPattern = richEditorNode_->GetPattern<RichEditorPattern>();
|
||||
richEditorPattern->InitScrollablePattern();
|
||||
richEditorPattern->SetRichEditorController(AceType::MakeRefPtr<RichEditorController>());
|
||||
richEditorPattern->GetRichEditorController()->SetPattern(AceType::WeakClaim(AceType::RawPtr(richEditorPattern)));
|
||||
richEditorPattern->CreateNodePaintMethod();
|
||||
richEditorNode_->GetGeometryNode()->SetContentSize({});
|
||||
}
|
||||
|
||||
void RichEditorDragTestNG::ClearSpan()
|
||||
void RichEditorDragTestNg::TearDown()
|
||||
{
|
||||
ASSERT_NE(frameNode_, nullptr);
|
||||
ASSERT_NE(pattern_, nullptr);
|
||||
frameNode_->children_.clear();
|
||||
pattern_->spans_.clear();
|
||||
pattern_->caretPosition_ = 0;
|
||||
richEditorNode_ = nullptr;
|
||||
testOnReadyEvent = 0;
|
||||
testAboutToIMEInput = 0;
|
||||
testOnIMEInputComplete = 0;
|
||||
testAboutToDelete = 0;
|
||||
testOnDeleteComplete = 0;
|
||||
MockParagraph::TearDown();
|
||||
}
|
||||
|
||||
void RichEditorDragTestNg::TearDownTestSuite()
|
||||
{
|
||||
TestNG::TearDownTestSuite();
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorDragTestNG001
|
||||
* @tc.desc: Test FolderStackTestNG properties & ToJsonValue.
|
||||
* @tc.name: RichEditorDragTest001
|
||||
* @tc.desc: test the drag of RichEditor without developer's onDragStart function
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragTestNG, RichEditorDragTestNG001, TestSize.Level1)
|
||||
HWTEST_F(RichEditorDragTestNg, RichEditorDragTest001, TestSize.Level1)
|
||||
{
|
||||
/**
|
||||
* @tc.steps: step1. Init FolderStack node with Aniamtion/AutoHalfFold props false, itemId not null.
|
||||
*/
|
||||
CreateRichEditor([](RichEditorModelNG model) {
|
||||
model.SetTextDetectEnable(true);
|
||||
});
|
||||
EXPECT_TRUE(true);
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
auto host = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
ASSERT_NE(host, nullptr);
|
||||
host->draggable_ = true;
|
||||
auto eventHub = host->GetEventHub<EventHub>();
|
||||
ASSERT_NE(eventHub, nullptr);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(pattern, nullptr);
|
||||
auto gesture = host->GetOrCreateGestureEventHub();
|
||||
ASSERT_NE(gesture, nullptr);
|
||||
EXPECT_TRUE(gesture->GetTextDraggable());
|
||||
gesture->SetIsTextDraggable(true);
|
||||
pattern->InitDragDropEvent();
|
||||
EXPECT_TRUE(eventHub->HasDefaultOnDragStart());
|
||||
auto controller = pattern->GetRichEditorController();
|
||||
ASSERT_NE(controller, nullptr);
|
||||
TextStyle style;
|
||||
TextSpanOptions options;
|
||||
options.value = INIT_VALUE_1;
|
||||
options.style = style;
|
||||
auto index = controller->AddTextSpan(options);
|
||||
EXPECT_EQ(index, 0);
|
||||
ImageSpanOptions imageOptions;
|
||||
imageOptions.image = IMAGE_VALUE;
|
||||
controller->AddImageSpan(imageOptions);
|
||||
pattern->textSelector_.Update(0, 6);
|
||||
auto onDragStart = eventHub->GetDefaultOnDragStart();
|
||||
auto event = AceType::MakeRefPtr<OHOS::Ace::DragEvent>();
|
||||
auto dragDropInfo = onDragStart(event, "");
|
||||
EXPECT_EQ(dragDropInfo.extraInfo, "");
|
||||
EXPECT_EQ(pattern->textSelector_.GetTextStart(), -1);
|
||||
EXPECT_EQ(pattern->textSelector_.GetTextEnd(), -1);
|
||||
EXPECT_EQ(pattern->status_, Status::DRAGGING);
|
||||
eventHub->FireOnDragMove(event, "");
|
||||
auto onDragEnd = eventHub->GetOnDragEnd();
|
||||
onDragEnd(event);
|
||||
EXPECT_EQ(pattern->status_, Status::NONE);
|
||||
while (!ViewStackProcessor::GetInstance()->elementsStack_.empty()) {
|
||||
ViewStackProcessor::GetInstance()->elementsStack_.pop();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorDragTest002
|
||||
* @tc.desc: test the drag of RichEditor with developer's onDragStart function
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragTestNg, RichEditorDragTest002, TestSize.Level1)
|
||||
{
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
auto host = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
ASSERT_NE(host, nullptr);
|
||||
host->draggable_ = true;
|
||||
auto eventHub = host->GetEventHub<EventHub>();
|
||||
ASSERT_NE(eventHub, nullptr);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(pattern, nullptr);
|
||||
auto gesture = host->GetOrCreateGestureEventHub();
|
||||
ASSERT_NE(gesture, nullptr);
|
||||
EXPECT_TRUE(gesture->GetTextDraggable());
|
||||
gesture->SetIsTextDraggable(true);
|
||||
auto dragStart = [](const RefPtr<OHOS::Ace::DragEvent>& event, const std::string& extraParams) -> NG::DragDropInfo {
|
||||
NG::DragDropInfo info;
|
||||
info.extraInfo = INIT_VALUE_1;
|
||||
return info;
|
||||
};
|
||||
eventHub->SetOnDragStart(std::move(dragStart));
|
||||
EXPECT_TRUE(eventHub->HasOnDragStart());
|
||||
pattern->InitDragDropEvent();
|
||||
EXPECT_TRUE(eventHub->HasDefaultOnDragStart());
|
||||
auto controller = pattern->GetRichEditorController();
|
||||
ASSERT_NE(controller, nullptr);
|
||||
TextSpanOptions options;
|
||||
options.value = INIT_VALUE_1;
|
||||
controller->AddTextSpan(options);
|
||||
ImageSpanOptions imageOptions;
|
||||
imageOptions.image = IMAGE_VALUE;
|
||||
controller->AddImageSpan(imageOptions);
|
||||
pattern->textSelector_.Update(0, 6);
|
||||
auto onDragStart = eventHub->GetOnDragStart();
|
||||
auto event = AceType::MakeRefPtr<OHOS::Ace::DragEvent>();
|
||||
auto dragDropInfo = onDragStart(event, "");
|
||||
EXPECT_EQ(dragDropInfo.extraInfo, INIT_VALUE_1);
|
||||
EXPECT_EQ(pattern->textSelector_.GetTextStart(), 0);
|
||||
EXPECT_EQ(pattern->textSelector_.GetTextEnd(), 6);
|
||||
EXPECT_EQ(pattern->status_, Status::NONE);
|
||||
eventHub->FireOnDragMove(event, "");
|
||||
auto onDragEnd = eventHub->GetOnDragEnd();
|
||||
onDragEnd(event);
|
||||
EXPECT_EQ(pattern->status_, Status::NONE);
|
||||
while (!ViewStackProcessor::GetInstance()->elementsStack_.empty()) {
|
||||
ViewStackProcessor::GetInstance()->elementsStack_.pop();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorDragTest003
|
||||
* @tc.desc: test the drag of RichEditor with developer's onDragDrop function
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragTestNg, RichEditorDragTest003, TestSize.Level1)
|
||||
{
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
auto host = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
ASSERT_NE(host, nullptr);
|
||||
host->draggable_ = true;
|
||||
auto eventHub = host->GetEventHub<EventHub>();
|
||||
ASSERT_NE(eventHub, nullptr);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(pattern, nullptr);
|
||||
auto gesture = host->GetOrCreateGestureEventHub();
|
||||
ASSERT_NE(gesture, nullptr);
|
||||
EXPECT_TRUE(gesture->GetTextDraggable());
|
||||
gesture->SetIsTextDraggable(true);
|
||||
pattern->InitDragDropEvent();
|
||||
EXPECT_TRUE(eventHub->HasDefaultOnDragStart());
|
||||
EXPECT_TRUE(eventHub->HasOnDrop());
|
||||
auto controller = pattern->GetRichEditorController();
|
||||
ASSERT_NE(controller, nullptr);
|
||||
TextStyle style;
|
||||
TextSpanOptions options;
|
||||
options.value = INIT_VALUE_3;
|
||||
options.style = style;
|
||||
auto index = controller->AddTextSpan(options);
|
||||
EXPECT_EQ(index, 0);
|
||||
pattern->textSelector_.Update(0, 6);
|
||||
auto event = AceType::MakeRefPtr<OHOS::Ace::DragEvent>();
|
||||
eventHub->FireOnDrop(event, "");
|
||||
EXPECT_EQ(pattern->status_, Status::NONE);
|
||||
while (!ViewStackProcessor::GetInstance()->elementsStack_.empty()) {
|
||||
ViewStackProcessor::GetInstance()->elementsStack_.pop();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @tc.name: RichEditorDragTest004
|
||||
* @tc.desc: test the drag of RichEditor with developer's HandleOnDragDropTextOperation function
|
||||
* @tc.type: FUNC
|
||||
*/
|
||||
HWTEST_F(RichEditorDragTestNg, RichEditorDragTest004, TestSize.Level1)
|
||||
{
|
||||
RichEditorModelNG model;
|
||||
model.Create();
|
||||
auto host = ViewStackProcessor::GetInstance()->GetMainFrameNode();
|
||||
ASSERT_NE(host, nullptr);
|
||||
host->draggable_ = true;
|
||||
auto eventHub = host->GetEventHub<EventHub>();
|
||||
ASSERT_NE(eventHub, nullptr);
|
||||
auto pattern = host->GetPattern<RichEditorPattern>();
|
||||
ASSERT_NE(pattern, nullptr);
|
||||
auto gesture = host->GetOrCreateGestureEventHub();
|
||||
ASSERT_NE(gesture, nullptr);
|
||||
EXPECT_TRUE(gesture->GetTextDraggable());
|
||||
gesture->SetIsTextDraggable(true);
|
||||
pattern->InitDragDropEvent();
|
||||
EXPECT_TRUE(eventHub->HasOnDrop());
|
||||
auto controller = pattern->GetRichEditorController();
|
||||
ASSERT_NE(controller, nullptr);
|
||||
TextStyle style;
|
||||
TextSpanOptions options;
|
||||
options.value = INIT_VALUE_1 + INIT_VALUE_1;
|
||||
options.style = style;
|
||||
auto index = controller->AddTextSpan(options);
|
||||
EXPECT_EQ(index, 0);
|
||||
pattern->dragRange_.first = 0;
|
||||
pattern->caretPosition_ = options.value.length();
|
||||
pattern->HandleOnDragDropTextOperation(INIT_VALUE_1, true);
|
||||
pattern->dragRange_.first = options.value.length();
|
||||
pattern->caretPosition_ = 0;
|
||||
pattern->HandleOnDragDropTextOperation(INIT_VALUE_1, true);
|
||||
EXPECT_EQ(pattern->status_, Status::NONE);
|
||||
while (!ViewStackProcessor::GetInstance()->elementsStack_.empty()) {
|
||||
ViewStackProcessor::GetInstance()->elementsStack_.pop();
|
||||
}
|
||||
}
|
||||
} // namespace OHOS::Ace::NG
|
Loading…
Reference in New Issue
Block a user