Pass EvaluationContext argument everywhere
[blender.git] / source / blender / modifiers / intern / MOD_meshsequencecache.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * Contributor(s): Campbell Barton
19  *
20  * ***** END GPL LICENSE BLOCK *****
21  */
22
23 /** \file blender/modifiers/intern/MOD_meshsequencecache.c
24  *  \ingroup modifiers
25  */
26
27 #include "DNA_cachefile_types.h"
28 #include "DNA_modifier_types.h"
29 #include "DNA_object_types.h"
30 #include "DNA_scene_types.h"
31
32 #include "BKE_cachefile.h"
33 #include "BKE_DerivedMesh.h"
34 #include "BKE_global.h"
35 #include "BKE_library.h"
36 #include "BKE_library_query.h"
37 #include "BKE_scene.h"
38
39 #include "DEG_depsgraph_build.h"
40
41 #include "MOD_modifiertypes.h"
42
43 #ifdef WITH_ALEMBIC
44 #       include "ABC_alembic.h"
45 #endif
46
47 static void initData(ModifierData *md)
48 {
49         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *)md;
50
51         mcmd->cache_file = NULL;
52         mcmd->object_path[0] = '\0';
53         mcmd->read_flag = MOD_MESHSEQ_READ_ALL;
54 }
55
56 static void copyData(ModifierData *md, ModifierData *target)
57 {
58 #if 0
59         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *)md;
60 #endif
61         MeshSeqCacheModifierData *tmcmd = (MeshSeqCacheModifierData *)target;
62
63         modifier_copyData_generic(md, target);
64
65         if (tmcmd->cache_file) {
66                 id_us_plus(&tmcmd->cache_file->id);
67                 tmcmd->reader = NULL;
68         }
69 }
70
71 static void freeData(ModifierData *md)
72 {
73         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *) md;
74
75         if (mcmd->cache_file) {
76                 id_us_min(&mcmd->cache_file->id);
77         }
78
79         if (mcmd->reader) {
80 #ifdef WITH_ALEMBIC
81                 CacheReader_free(mcmd->reader);
82 #endif
83                 mcmd->reader = NULL;
84         }
85 }
86
87 static bool isDisabled(ModifierData *md, int UNUSED(useRenderParams))
88 {
89         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *) md;
90
91         /* leave it up to the modifier to check the file is valid on calculation */
92         return (mcmd->cache_file == NULL) || (mcmd->object_path[0] == '\0');
93 }
94
95 static DerivedMesh *applyModifier(ModifierData *md, struct EvaluationContext *UNUSED(eval_ctx),
96                                   Object *ob, DerivedMesh *dm,
97                                   ModifierApplyFlag flag)
98 {
99 #ifdef WITH_ALEMBIC
100         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *) md;
101
102         Scene *scene = md->scene;
103         const float frame = BKE_scene_frame_get(scene);
104         const float time = BKE_cachefile_time_offset(mcmd->cache_file, frame, FPS);
105
106         const char *err_str = NULL;
107
108         CacheFile *cache_file = mcmd->cache_file;
109
110         BKE_cachefile_ensure_handle(G.main, cache_file);
111
112         if (!mcmd->reader) {
113                 mcmd->reader = CacheReader_open_alembic_object(cache_file->handle,
114                                                                NULL,
115                                                                ob,
116                                                                mcmd->object_path);
117                 if (!mcmd->reader) {
118                         modifier_setError(md, "Could not create Alembic reader for file %s", cache_file->filepath);
119                         return dm;
120                 }
121         }
122
123         DerivedMesh *result = ABC_read_mesh(mcmd->reader,
124                                             ob,
125                                             dm,
126                                             time,
127                                             &err_str,
128                                             mcmd->read_flag);
129
130         if (err_str) {
131                 modifier_setError(md, "%s", err_str);
132         }
133
134         return result ? result : dm;
135         UNUSED_VARS(flag);
136 #else
137         return dm;
138         UNUSED_VARS(md, ob, flag);
139 #endif
140 }
141
142 static bool dependsOnTime(ModifierData *md)
143 {
144         UNUSED_VARS(md);
145         return true;
146 }
147
148 static void foreachIDLink(ModifierData *md, Object *ob,
149                           IDWalkFunc walk, void *userData)
150 {
151         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *) md;
152
153         walk(userData, ob, (ID **)&mcmd->cache_file, IDWALK_CB_USER);
154 }
155
156
157 static void updateDepsgraph(ModifierData *md,
158                             struct Main *bmain,
159                             struct Scene *scene,
160                             Object *ob,
161                             struct DepsNodeHandle *node)
162 {
163         MeshSeqCacheModifierData *mcmd = (MeshSeqCacheModifierData *) md;
164
165         if (mcmd->cache_file != NULL) {
166                 DEG_add_object_cache_relation(node, mcmd->cache_file, DEG_OB_COMP_CACHE, "Mesh Cache File");
167         }
168
169         UNUSED_VARS(bmain, scene, ob);
170 }
171
172 ModifierTypeInfo modifierType_MeshSequenceCache = {
173     /* name */              "Mesh Sequence Cache",
174     /* structName */        "MeshSeqCacheModifierData",
175     /* structSize */        sizeof(MeshSeqCacheModifierData),
176     /* type */              eModifierTypeType_Constructive,
177     /* flags */             eModifierTypeFlag_AcceptsMesh |
178                             eModifierTypeFlag_AcceptsCVs,
179     /* copyData */          copyData,
180     /* deformVerts */       NULL,
181     /* deformMatrices */    NULL,
182     /* deformVertsEM */     NULL,
183     /* deformMatricesEM */  NULL,
184     /* applyModifier */     applyModifier,
185     /* applyModifierEM */   NULL,
186     /* initData */          initData,
187     /* requiredDataMask */  NULL,
188     /* freeData */          freeData,
189     /* isDisabled */        isDisabled,
190     /* updateDepsgraph */   updateDepsgraph,
191     /* dependsOnTime */     dependsOnTime,
192     /* dependsOnNormals */  NULL,
193     /* foreachObjectLink */ NULL,
194     /* foreachIDLink */     foreachIDLink,
195     /* foreachTexLink */    NULL,
196 };