• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2016 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SKSL_TERNARYEXPRESSION
9 #define SKSL_TERNARYEXPRESSION
10 
11 #include "src/sksl/ir/SkSLExpression.h"
12 
13 namespace SkSL {
14 
15 /**
16  * A ternary expression (test ? ifTrue : ifFalse).
17  */
18 class TernaryExpression final : public Expression {
19 public:
20     inline static constexpr Kind kExpressionKind = Kind::kTernary;
21 
TernaryExpression(int line,std::unique_ptr<Expression> test,std::unique_ptr<Expression> ifTrue,std::unique_ptr<Expression> ifFalse)22     TernaryExpression(int line, std::unique_ptr<Expression> test,
23                       std::unique_ptr<Expression> ifTrue, std::unique_ptr<Expression> ifFalse)
24         : INHERITED(line, kExpressionKind, &ifTrue->type())
25         , fTest(std::move(test))
26         , fIfTrue(std::move(ifTrue))
27         , fIfFalse(std::move(ifFalse)) {
28         SkASSERT(this->ifTrue()->type() == this->ifFalse()->type());
29     }
30 
31     // Creates a potentially-simplified form of the ternary. Typechecks and coerces input
32     // expressions; reports errors via ErrorReporter.
33     static std::unique_ptr<Expression> Convert(const Context& context,
34                                             std::unique_ptr<Expression> test,
35                                             std::unique_ptr<Expression> ifTrue,
36                                             std::unique_ptr<Expression> ifFalse);
37 
38     // Creates a potentially-simplified form of the ternary; reports errors via ASSERT.
39     static std::unique_ptr<Expression> Make(const Context& context,
40                                             std::unique_ptr<Expression> test,
41                                             std::unique_ptr<Expression> ifTrue,
42                                             std::unique_ptr<Expression> ifFalse);
43 
test()44     std::unique_ptr<Expression>& test() {
45         return fTest;
46     }
47 
test()48     const std::unique_ptr<Expression>& test() const {
49         return fTest;
50     }
51 
ifTrue()52     std::unique_ptr<Expression>& ifTrue() {
53         return fIfTrue;
54     }
55 
ifTrue()56     const std::unique_ptr<Expression>& ifTrue() const {
57         return fIfTrue;
58     }
59 
ifFalse()60     std::unique_ptr<Expression>& ifFalse() {
61         return fIfFalse;
62     }
63 
ifFalse()64     const std::unique_ptr<Expression>& ifFalse() const {
65         return fIfFalse;
66     }
67 
hasProperty(Property property)68     bool hasProperty(Property property) const override {
69         return this->test()->hasProperty(property) || this->ifTrue()->hasProperty(property) ||
70                this->ifFalse()->hasProperty(property);
71     }
72 
isConstantOrUniform()73     bool isConstantOrUniform() const override {
74         return this->test()->isConstantOrUniform() && this->ifTrue()->isConstantOrUniform() &&
75                this->ifFalse()->isConstantOrUniform();
76     }
77 
clone()78     std::unique_ptr<Expression> clone() const override {
79         return std::make_unique<TernaryExpression>(fLine, this->test()->clone(),
80                                                    this->ifTrue()->clone(),
81                                                    this->ifFalse()->clone());
82     }
83 
description()84     String description() const override {
85         return "(" + this->test()->description() + " ? " + this->ifTrue()->description() + " : " +
86                this->ifFalse()->description() + ")";
87     }
88 
89 private:
90     std::unique_ptr<Expression> fTest;
91     std::unique_ptr<Expression> fIfTrue;
92     std::unique_ptr<Expression> fIfFalse;
93 
94     using INHERITED = Expression;
95 };
96 
97 }  // namespace SkSL
98 
99 #endif
100