1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2013 Blender Foundation.
17  * All rights reserved.
18  */
19 
20 /** \file
21  * \ingroup depsgraph
22  *
23  * Datatypes for internal use in the Depsgraph
24  *
25  * All of these datatypes are only really used within the "core" depsgraph.
26  * In particular, node types declared here form the structure of operations
27  * in the graph.
28  */
29 
30 #pragma once
31 
32 #include <functional>
33 
34 /* TODO(sergey): Ideally we'll just use char* and statically allocated strings
35  * to avoid any possible overhead caused by string (re)allocation/formatting. */
36 #include <algorithm>
37 #include <deque>
38 #include <map>
39 #include <set>
40 #include <string>
41 #include <vector>
42 
43 #include "BLI_map.hh"
44 #include "BLI_set.hh"
45 #include "BLI_string_ref.hh"
46 #include "BLI_vector.hh"
47 #include "BLI_vector_set.hh"
48 
49 struct Depsgraph;
50 
51 struct CustomData_MeshMasks;
52 
53 namespace blender {
54 namespace deg {
55 
56 /* Commonly used types. */
57 using std::deque;
58 using std::optional;
59 using std::pair;
60 using std::string;
61 using std::unique_ptr;
62 
63 /* Commonly used functions. */
64 using std::make_pair;
65 using std::max;
66 using std::to_string;
67 
68 /* Function bindings. */
69 using std::function;
70 using namespace std::placeholders;
71 #define function_bind std::bind
72 
73 /* Source of the dependency graph node update tag.
74  *
75  * NOTE: This is a bit mask, so accumulation of sources is possible.
76  *
77  * TODO(sergey): Find a better place for this. */
78 enum eUpdateSource {
79   /* Update is caused by a time change. */
80   DEG_UPDATE_SOURCE_TIME = (1 << 0),
81   /* Update caused by user directly or indirectly influencing the node. */
82   DEG_UPDATE_SOURCE_USER_EDIT = (1 << 1),
83   /* Update is happening as a special response for the relations update. */
84   DEG_UPDATE_SOURCE_RELATIONS = (1 << 2),
85   /* Update is happening due to visibility change. */
86   DEG_UPDATE_SOURCE_VISIBILITY = (1 << 3),
87 };
88 
89 /* C++ wrapper around DNA's CustomData_MeshMasks struct. */
90 struct DEGCustomDataMeshMasks {
91   uint64_t vert_mask;
92   uint64_t edge_mask;
93   uint64_t face_mask;
94   uint64_t loop_mask;
95   uint64_t poly_mask;
96 
DEGCustomDataMeshMasksDEGCustomDataMeshMasks97   DEGCustomDataMeshMasks() : vert_mask(0), edge_mask(0), face_mask(0), loop_mask(0), poly_mask(0)
98   {
99   }
100 
101   explicit DEGCustomDataMeshMasks(const CustomData_MeshMasks *other);
102 
103   DEGCustomDataMeshMasks &operator|=(const DEGCustomDataMeshMasks &other)
104   {
105     this->vert_mask |= other.vert_mask;
106     this->edge_mask |= other.edge_mask;
107     this->face_mask |= other.face_mask;
108     this->loop_mask |= other.loop_mask;
109     this->poly_mask |= other.poly_mask;
110     return *this;
111   }
112 
113   DEGCustomDataMeshMasks operator|(const DEGCustomDataMeshMasks &other) const
114   {
115     DEGCustomDataMeshMasks result;
116     result.vert_mask = this->vert_mask | other.vert_mask;
117     result.edge_mask = this->edge_mask | other.edge_mask;
118     result.face_mask = this->face_mask | other.face_mask;
119     result.loop_mask = this->loop_mask | other.loop_mask;
120     result.poly_mask = this->poly_mask | other.poly_mask;
121     return result;
122   }
123 
124   bool operator==(const DEGCustomDataMeshMasks &other) const
125   {
126     return (this->vert_mask == other.vert_mask && this->edge_mask == other.edge_mask &&
127             this->face_mask == other.face_mask && this->loop_mask == other.loop_mask &&
128             this->poly_mask == other.poly_mask);
129   }
130 
131   bool operator!=(const DEGCustomDataMeshMasks &other) const
132   {
133     return !(*this == other);
134   }
135 
MaskVertDEGCustomDataMeshMasks136   static DEGCustomDataMeshMasks MaskVert(const uint64_t vert_mask)
137   {
138     DEGCustomDataMeshMasks result;
139     result.vert_mask = vert_mask;
140     return result;
141   }
142 
MaskEdgeDEGCustomDataMeshMasks143   static DEGCustomDataMeshMasks MaskEdge(const uint64_t edge_mask)
144   {
145     DEGCustomDataMeshMasks result;
146     result.edge_mask = edge_mask;
147     return result;
148   }
149 
MaskFaceDEGCustomDataMeshMasks150   static DEGCustomDataMeshMasks MaskFace(const uint64_t face_mask)
151   {
152     DEGCustomDataMeshMasks result;
153     result.face_mask = face_mask;
154     return result;
155   }
156 
MaskLoopDEGCustomDataMeshMasks157   static DEGCustomDataMeshMasks MaskLoop(const uint64_t loop_mask)
158   {
159     DEGCustomDataMeshMasks result;
160     result.loop_mask = loop_mask;
161     return result;
162   }
163 
MaskPolyDEGCustomDataMeshMasks164   static DEGCustomDataMeshMasks MaskPoly(const uint64_t poly_mask)
165   {
166     DEGCustomDataMeshMasks result;
167     result.poly_mask = poly_mask;
168     return result;
169   }
170 };
171 
172 }  // namespace deg
173 }  // namespace blender
174