mirror of
https://github.com/thorvg/thorvg.git
synced 2025-06-13 19:44:28 +00:00
lottie: revise the effect parsing logic
Unify the common parts of the parsing logic by applying a strategy pattern, allowing the behavior to vary based on the effect type. This helps to reduce the size and improved the parsing safety.
This commit is contained in:
parent
8f7103e109
commit
09ebf10432
3 changed files with 74 additions and 129 deletions
|
@ -1261,7 +1261,7 @@ void LottieParser::parseMasks(LottieLayer* layer)
|
|||
}
|
||||
|
||||
|
||||
void LottieParser::parseTint(LottieFxTint* effect)
|
||||
void LottieParser::parseEffect(LottieEffect* effect, void(LottieParser::*func)(LottieEffect*, int))
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
|
@ -1269,144 +1269,88 @@ void LottieParser::parseTint(LottieFxTint* effect)
|
|||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 0) parsePropertyInternal(effect->black);
|
||||
else if (idx == 1) parsePropertyInternal(effect->white);
|
||||
else if (idx == 2) parsePropertyInternal(effect->intensity);
|
||||
if (peekType() == kObjectType) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) (this->*func)(effect, idx);
|
||||
else skip(key);
|
||||
} else skip(key);
|
||||
}
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
++idx;
|
||||
} else skip();
|
||||
} else skip();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseTritone(LottieFxTritone* effect)
|
||||
void LottieParser::parseTint(LottieEffect* effect, int idx)
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
while (nextArrayValue()) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 0) parsePropertyInternal(effect->bright);
|
||||
else if (idx == 1) parsePropertyInternal(effect->midtone);
|
||||
else if (idx == 2) parsePropertyInternal(effect->dark);
|
||||
else skip(key);
|
||||
} else skip(key);
|
||||
}
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
}
|
||||
auto tint = static_cast<LottieFxTint*>(effect);
|
||||
|
||||
if (idx == 0) parsePropertyInternal(tint->black);
|
||||
else if (idx == 1) parsePropertyInternal(tint->white);
|
||||
else if (idx == 2) parsePropertyInternal(tint->intensity);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseFill(LottieFxFill* effect)
|
||||
void LottieParser::parseTritone(LottieEffect* effect, int idx)
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
while (nextArrayValue()) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 2) parsePropertyInternal(effect->color);
|
||||
else if (idx == 6) parsePropertyInternal(effect->opacity);
|
||||
else skip(key);
|
||||
} else skip(key);
|
||||
}
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
}
|
||||
auto tritone = static_cast<LottieFxTritone*>(effect);
|
||||
|
||||
if (idx == 0) parsePropertyInternal(tritone->bright);
|
||||
else if (idx == 1) parsePropertyInternal(tritone->midtone);
|
||||
else if (idx == 2) parsePropertyInternal(tritone->dark);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseGaussianBlur(LottieFxGaussianBlur* effect)
|
||||
void LottieParser::parseFill(LottieEffect* effect, int idx)
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
while (nextArrayValue()) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 0) parsePropertyInternal(effect->blurness);
|
||||
else if (idx == 1) parsePropertyInternal(effect->direction);
|
||||
else if (idx == 2) parsePropertyInternal(effect->wrap);
|
||||
else skip(key);
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
} else skip(key);
|
||||
}
|
||||
}
|
||||
auto fill = static_cast<LottieFxFill*>(effect);
|
||||
|
||||
if (idx == 2) parsePropertyInternal(fill->color);
|
||||
else if (idx == 6) parsePropertyInternal(fill->opacity);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseDropShadow(LottieFxDropShadow* effect)
|
||||
void LottieParser::parseGaussianBlur(LottieEffect* effect, int idx)
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
while (nextArrayValue()) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 0) parsePropertyInternal(effect->color);
|
||||
else if (idx == 1) parsePropertyInternal(effect->opacity);
|
||||
else if (idx == 2) parsePropertyInternal(effect->angle);
|
||||
else if (idx == 3) parsePropertyInternal(effect->distance);
|
||||
else if (idx == 4) parsePropertyInternal(effect->blurness);
|
||||
else skip(key);
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
} else skip(key);
|
||||
}
|
||||
}
|
||||
auto blur = static_cast<LottieFxGaussianBlur*>(effect);
|
||||
|
||||
if (idx == 0) parsePropertyInternal(blur->blurness);
|
||||
else if (idx == 1) parsePropertyInternal(blur->direction);
|
||||
else if (idx == 2) parsePropertyInternal(blur->wrap);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseStroke(LottieFxStroke* effect)
|
||||
void LottieParser::parseDropShadow(LottieEffect* effect, int idx)
|
||||
{
|
||||
int idx = 0;
|
||||
enterArray();
|
||||
while (nextArrayValue()) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("v")) {
|
||||
enterObject();
|
||||
while (auto key = nextObjectKey()) {
|
||||
if (KEY_AS("k")) {
|
||||
if (idx == 0) parsePropertyInternal(effect->mask);
|
||||
else if (idx == 1) parsePropertyInternal(effect->allMask);
|
||||
else if (idx == 3) parsePropertyInternal(effect->color);
|
||||
else if (idx == 4) parsePropertyInternal(effect->size);
|
||||
else if (idx == 6) parsePropertyInternal(effect->opacity);
|
||||
else if (idx == 7) parsePropertyInternal(effect->begin);
|
||||
else if (idx == 8) parsePropertyInternal(effect->end);
|
||||
else skip(key);
|
||||
++idx;
|
||||
} else skip(key);
|
||||
}
|
||||
} else skip(key);
|
||||
}
|
||||
}
|
||||
auto shadow = static_cast<LottieFxDropShadow*>(effect);
|
||||
|
||||
if (idx == 0) parsePropertyInternal(shadow->color);
|
||||
else if (idx == 1) parsePropertyInternal(shadow->opacity);
|
||||
else if (idx == 2) parsePropertyInternal(shadow->angle);
|
||||
else if (idx == 3) parsePropertyInternal(shadow->distance);
|
||||
else if (idx == 4) parsePropertyInternal(shadow->blurness);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
void LottieParser::parseStroke(LottieEffect* effect, int idx)
|
||||
{
|
||||
auto stroke = static_cast<LottieFxStroke*>(effect);
|
||||
|
||||
if (idx == 0) parsePropertyInternal(stroke->mask);
|
||||
else if (idx == 1) parsePropertyInternal(stroke->allMask);
|
||||
else if (idx == 3) parsePropertyInternal(stroke->color);
|
||||
else if (idx == 4) parsePropertyInternal(stroke->size);
|
||||
else if (idx == 6) parsePropertyInternal(stroke->opacity);
|
||||
else if (idx == 7) parsePropertyInternal(stroke->begin);
|
||||
else if (idx == 8) parsePropertyInternal(stroke->end);
|
||||
else skip();
|
||||
}
|
||||
|
||||
|
||||
|
@ -1414,27 +1358,27 @@ void LottieParser::parseEffect(LottieEffect* effect)
|
|||
{
|
||||
switch (effect->type) {
|
||||
case LottieEffect::Tint: {
|
||||
parseTint(static_cast<LottieFxTint*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseTint);
|
||||
break;
|
||||
}
|
||||
case LottieEffect::Fill: {
|
||||
parseFill(static_cast<LottieFxFill*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseFill);
|
||||
break;
|
||||
}
|
||||
case LottieEffect::Stroke: {
|
||||
parseStroke(static_cast<LottieFxStroke*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseStroke);
|
||||
break;
|
||||
}
|
||||
case LottieEffect::Tritone: {
|
||||
parseTritone(static_cast<LottieFxTritone*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseTritone);
|
||||
break;
|
||||
}
|
||||
case LottieEffect::DropShadow: {
|
||||
parseDropShadow(static_cast<LottieFxDropShadow*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseDropShadow);
|
||||
break;
|
||||
}
|
||||
case LottieEffect::GaussianBlur: {
|
||||
parseGaussianBlur(static_cast<LottieFxGaussianBlur*>(effect));
|
||||
parseEffect(effect, &LottieParser::parseGaussianBlur);
|
||||
break;
|
||||
}
|
||||
default: break;
|
||||
|
|
|
@ -98,12 +98,13 @@ private:
|
|||
LottieFont* parseFont();
|
||||
LottieMarker* parseMarker();
|
||||
|
||||
void parseStroke(LottieFxStroke* effect);
|
||||
void parseTritone(LottieFxTritone* effect);
|
||||
void parseTint(LottieFxTint* effect);
|
||||
void parseFill(LottieFxFill* effect);
|
||||
void parseGaussianBlur(LottieFxGaussianBlur* effect);
|
||||
void parseDropShadow(LottieFxDropShadow* effect);
|
||||
void parseEffect(LottieEffect* effect, void(LottieParser::*func)(LottieEffect*, int));
|
||||
void parseStroke(LottieEffect* effect, int idx);
|
||||
void parseTritone(LottieEffect* effect, int idx);
|
||||
void parseTint(LottieEffect* effect, int idx);
|
||||
void parseFill(LottieEffect* effect, int idx);
|
||||
void parseGaussianBlur(LottieEffect* effect, int idx);
|
||||
void parseDropShadow(LottieEffect* effect, int idx);
|
||||
|
||||
bool parseDirection(LottieShape* shape, const char* key);
|
||||
bool parseCommon(LottieObject* obj, const char* key);
|
||||
|
|
|
@ -192,7 +192,7 @@ struct LookaheadParserHandler
|
|||
void getNull();
|
||||
bool parseNext();
|
||||
const char* nextObjectKey();
|
||||
void skip(const char* key);
|
||||
void skip(const char* key = nullptr);
|
||||
void skipOut(int depth);
|
||||
int peekType();
|
||||
char* getPos();
|
||||
|
|
Loading…
Add table
Reference in a new issue