xref: /aosp_15_r20/external/skia/src/sksl/ir/SkSLTernaryExpression.h (revision c8dee2aa9b3f27cf6c858bd81872bdeb2c07ed17)
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 "include/core/SkTypes.h"
12 #include "src/sksl/SkSLPosition.h"
13 #include "src/sksl/ir/SkSLExpression.h"
14 #include "src/sksl/ir/SkSLIRNode.h"
15 #include "src/sksl/ir/SkSLType.h"
16 
17 #include <cstdint>
18 #include <memory>
19 #include <string>
20 #include <utility>
21 
22 namespace SkSL {
23 
24 class Context;
25 enum class OperatorPrecedence : uint8_t;
26 
27 /**
28  * A ternary expression (test ? ifTrue : ifFalse).
29  */
30 class TernaryExpression final : public Expression {
31 public:
32     inline static constexpr Kind kIRNodeKind = Kind::kTernary;
33 
TernaryExpression(Position pos,std::unique_ptr<Expression> test,std::unique_ptr<Expression> ifTrue,std::unique_ptr<Expression> ifFalse)34     TernaryExpression(Position pos, std::unique_ptr<Expression> test,
35             std::unique_ptr<Expression> ifTrue, std::unique_ptr<Expression> ifFalse)
36         : INHERITED(pos, kIRNodeKind, &ifTrue->type())
37         , fTest(std::move(test))
38         , fIfTrue(std::move(ifTrue))
39         , fIfFalse(std::move(ifFalse)) {
40         SkASSERT(this->ifTrue()->type().matches(this->ifFalse()->type()));
41     }
42 
43     // Creates a potentially-simplified form of the ternary. Typechecks and coerces input
44     // expressions; reports errors via ErrorReporter.
45     static std::unique_ptr<Expression> Convert(const Context& context,
46                                                Position pos,
47                                                std::unique_ptr<Expression> test,
48                                                std::unique_ptr<Expression> ifTrue,
49                                                std::unique_ptr<Expression> ifFalse);
50 
51     // Creates a potentially-simplified form of the ternary; reports errors via ASSERT.
52     static std::unique_ptr<Expression> Make(const Context& context,
53                                             Position pos,
54                                             std::unique_ptr<Expression> test,
55                                             std::unique_ptr<Expression> ifTrue,
56                                             std::unique_ptr<Expression> ifFalse);
57 
test()58     std::unique_ptr<Expression>& test() {
59         return fTest;
60     }
61 
test()62     const std::unique_ptr<Expression>& test() const {
63         return fTest;
64     }
65 
ifTrue()66     std::unique_ptr<Expression>& ifTrue() {
67         return fIfTrue;
68     }
69 
ifTrue()70     const std::unique_ptr<Expression>& ifTrue() const {
71         return fIfTrue;
72     }
73 
ifFalse()74     std::unique_ptr<Expression>& ifFalse() {
75         return fIfFalse;
76     }
77 
ifFalse()78     const std::unique_ptr<Expression>& ifFalse() const {
79         return fIfFalse;
80     }
81 
clone(Position pos)82     std::unique_ptr<Expression> clone(Position pos) const override {
83         return std::make_unique<TernaryExpression>(pos, this->test()->clone(),
84                                                    this->ifTrue()->clone(),
85                                                    this->ifFalse()->clone());
86     }
87 
88     std::string description(OperatorPrecedence parentPrecedence) const override;
89 
90 private:
91     std::unique_ptr<Expression> fTest;
92     std::unique_ptr<Expression> fIfTrue;
93     std::unique_ptr<Expression> fIfFalse;
94 
95     using INHERITED = Expression;
96 };
97 
98 }  // namespace SkSL
99 
100 #endif
101