Welcome to mirror list, hosted at ThFree Co, Russian Federation.

BKE_lib_override.h « blenkernel « blender « source - git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: 8542c02fab54420a8a0c4bbecdf6041300b0e7ff (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
/* SPDX-License-Identifier: GPL-2.0-or-later
 * Copyright 2016 Blender Foundation. All rights reserved. */

#pragma once

/** \file
 * \ingroup bke
 *
 * API to manage data-blocks inside of Blender's Main data-base, or as independent runtime-only
 * data.
 *
 * \note `BKE_lib_` files are for operations over data-blocks themselves, although they might
 * alter Main as well (when creating/renaming/deleting an ID e.g.).
 *
 * \section Function Names
 *
 * \warning Descriptions below is ideal goal, current status of naming does not yet fully follow it
 * (this is WIP).
 *
 *  - `BKE_lib_override_library_` should be used for function affecting a single ID.
 *  - `BKE_lib_override_library_main_` should be used for function affecting the whole collection
 *    of IDs in a given Main data-base.
 */

#ifdef __cplusplus
extern "C" {
#endif

struct BlendFileReadReport;
struct Collection;
struct ID;
struct IDOverrideLibrary;
struct IDOverrideLibraryProperty;
struct IDOverrideLibraryPropertyOperation;
struct Library;
struct Main;
struct Object;
struct PointerRNA;
struct PropertyRNA;
struct ReportList;
struct Scene;
struct ViewLayer;

/**
 * Initialize empty overriding of \a reference_id by \a local_id.
 */
struct IDOverrideLibrary *BKE_lib_override_library_init(struct ID *local_id,
                                                        struct ID *reference_id);
/**
 * Shallow or deep copy of a whole override from \a src_id to \a dst_id.
 */
void BKE_lib_override_library_copy(struct ID *dst_id, const struct ID *src_id, bool do_full_copy);
/**
 * Clear any overriding data from given \a override.
 */
void BKE_lib_override_library_clear(struct IDOverrideLibrary *override, bool do_id_user);
/**
 * Free given \a override.
 */
void BKE_lib_override_library_free(struct IDOverrideLibrary **override, bool do_id_user);

/**
 * Return the actual #IDOverrideLibrary data 'controlling' the given `id`, and the actual ID owning
 * it.
 *
 * \note This is especially useful when `id` is a non-real override (e.g. embedded ID like a master
 * collection or root node tree, or a shape key).
 *
 * \param owner_id_hint: If not NULL, a potential owner for the given override-embedded `id`.
 * \param r_owner_id: If given, will be set with the actual ID owning the return liboverride data.
 */
IDOverrideLibrary *BKE_lib_override_library_get(struct Main *bmain,
                                                struct ID *id,
                                                struct ID *owner_id_hint,
                                                struct ID **r_owner_id);

/**
 * Check if given ID has some override rules that actually indicate the user edited it.
 */
bool BKE_lib_override_library_is_user_edited(const struct ID *id);

/**
 * Check if given ID is a system override.
 */
bool BKE_lib_override_library_is_system_defined(const struct Main *bmain, const struct ID *id);

/**
 * Check if given Override Property for given ID is animated (through a F-Curve in an Action, or
 * from a driver).
 *
 * \param override_rna_prop: if not NULL, the RNA property matching the given path in the
 * `override_prop`.
 * \param rnaprop_index: Array in the RNA property, 0 if unknown or irrelevant.
 */
bool BKE_lib_override_library_property_is_animated(const ID *id,
                                                   const IDOverrideLibraryProperty *override_prop,
                                                   const struct PropertyRNA *override_rna_prop,
                                                   const int rnaprop_index);

/**
 * Check if given ID is a leaf in its liboverride hierarchy (i.e. if it does not use any other
 * override ID).
 *
 * NOTE: Embedded IDs of override IDs are not considered as leaves.
 */
bool BKE_lib_override_library_is_hierarchy_leaf(struct Main *bmain, struct ID *id);

/**
 * Create an overridden local copy of linked reference.
 *
 * \note This function is very basic, low-level. It does not consider any hierarchical dependency,
 * and also prevents any automatic re-sync of this local override.
 */
struct ID *BKE_lib_override_library_create_from_id(struct Main *bmain,
                                                   struct ID *reference_id,
                                                   bool do_tagged_remap);
/**
 * Create overridden local copies of all tagged data-blocks in given Main.
 *
 * \note Set `id->newid` of overridden libs with newly created overrides,
 * caller is responsible to clean those pointers before/after usage as needed.
 *
 * \note By default, it will only remap newly created local overriding data-blocks between
 * themselves, to avoid 'enforcing' those overrides into all other usages of the linked data in
 * main. You can add more local IDs to be remapped to use new overriding ones by setting their
 * LIB_TAG_DOIT tag.
 *
 * \param owner_library: the library in which the overrides should be created. Besides versioning
 * and resync code path, this should always be NULL (i.e. the local .blend file).
 *
 * \param id_root_reference: the linked ID that is considered as the root of the overridden
 * hierarchy.
 *
 * \param id_hierarchy_root: the override ID that is the root of the hierarchy. May be NULL, in
 * which case it is assumed that the given `id_root_reference` is tagged for override, and its
 * newly created override will be used as hierarchy root. Must be NULL if
 * `id_hierarchy_root_reference` is not NULL.
 *
 * \param id_hierarchy_root_reference: the linked ID that is the root of the hierarchy. Must be
 * tagged for override. May be NULL, in which case it is assumed that the given `id_root_reference`
 * is tagged for override, and its newly created override will be used as hierarchy root. Must be
 * NULL if `id_hierarchy_root` is not NULL.
 *
 * \param do_no_main: Create the new override data outside of Main database.
 * Used for resyncing of linked overrides.
 *
 * \param do_fully_editable: if true, tag all created overrides as user-editable by default.
 *
 * \return \a true on success, \a false otherwise.
 */
bool BKE_lib_override_library_create_from_tag(struct Main *bmain,
                                              struct Library *owner_library,
                                              const struct ID *id_root_reference,
                                              struct ID *id_hierarchy_root,
                                              const struct ID *id_hierarchy_root_reference,
                                              bool do_no_main,
                                              const bool do_fully_editable);
/**
 * Advanced 'smart' function to create fully functional overrides.
 *
 * \note Currently it only does special things if given \a id_root is an object or collection, more
 * specific behaviors may be added in the future for other ID types.
 *
 * \note It will override all IDs tagged with \a LIB_TAG_DOIT, and it does not clear that tag at
 * its beginning, so caller code can add extra data-blocks to be overridden as well.
 *
 * \param view_layer: the active view layer to search instantiated collections in, can be NULL (in
 *                    which case \a scene's master collection children hierarchy is used instead).
 *
 * \param owner_library: the library in which the overrides should be created. Besides versioning
 * and resync code path, this should always be NULL (i.e. the local .blend file).
 *
 * \param id_root_reference: The linked root ID to create an override from. May be a sub-root of
 * the overall hierarchy, in which case calling code is expected to have already tagged required
 * 'path' of IDs leading from the given `id_hierarchy_root` to the given `id_root`.
 *
 * \param id_hierarchy_root_reference: The ID to be used a hierarchy root of the overrides to be
 * created. Can be either the linked root ID of the whole override hierarchy, (typically the same
 * as `id_root`, unless a sub-part only of the hierarchy is overridden), or the already existing
 * override hierarchy root if part of the hierarchy is already overridden.
 *
 * \param id_instance_hint: Some ID used as hint/reference to do some post-processing after
 * overrides have been created, may be NULL. Typically, the Empty object instantiating the linked
 * collection we override, currently.
 *
 * \param r_id_root_override: if not NULL, the override generated for the given \a id_root.
 *
 * \param do_fully_editable: if true, tag all created overrides as user-editable by default.
 *
 * \return true if override was successfully created.
 */
bool BKE_lib_override_library_create(struct Main *bmain,
                                     struct Scene *scene,
                                     struct ViewLayer *view_layer,
                                     struct Library *owner_library,
                                     struct ID *id_root_reference,
                                     struct ID *id_hierarchy_root_reference,
                                     struct ID *id_instance_hint,
                                     struct ID **r_id_root_override,
                                     const bool do_fully_editable);
/**
 * Create a library override template.
 */
bool BKE_lib_override_library_template_create(struct ID *id);
/**
 * Convert a given proxy object into a library override.
 *
 * \note This is a thin wrapper around \a BKE_lib_override_library_create, only extra work is to
 * actually convert the proxy itself into an override first.
 *
 * \param view_layer: the active view layer to search instantiated collections in, can be NULL (in
 *                    which case \a scene's master collection children hierarchy is used instead).
 * \return true if override was successfully created.
 */
bool BKE_lib_override_library_proxy_convert(struct Main *bmain,
                                            struct Scene *scene,
                                            struct ViewLayer *view_layer,
                                            struct Object *ob_proxy);
/**
 * Convert all proxy objects into library overrides.
 *
 * \note Only affects local proxies, linked ones are not affected.
 */
void BKE_lib_override_library_main_proxy_convert(struct Main *bmain,
                                                 struct BlendFileReadReport *reports);

/**
 * Find and set the 'hierarchy root' ID pointer of all library overrides in given `bmain`.
 *
 * NOTE: Cannot be called from `do_versions_after_linking` as this code needs a single complete
 * Main database, not a split-by-libraries one.
 */
void BKE_lib_override_library_main_hierarchy_root_ensure(struct Main *bmain);

/**
 * Advanced 'smart' function to resync, re-create fully functional overrides up-to-date with linked
 * data, from an existing override hierarchy.
 *
 * \param view_layer: the active view layer to search instantiated collections in, can be NULL (in
 *                    which case \a scene's master collection children hierarchy is used instead).
 * \param id_root: The root liboverride ID to resync from.
 * \return true if override was successfully resynced.
 */
bool BKE_lib_override_library_resync(struct Main *bmain,
                                     struct Scene *scene,
                                     struct ViewLayer *view_layer,
                                     struct ID *id_root,
                                     struct Collection *override_resync_residual_storage,
                                     bool do_hierarchy_enforce,
                                     struct BlendFileReadReport *reports);
/**
 * Detect and handle required resync of overrides data, when relations between reference linked IDs
 * have changed.
 *
 * This is a fairly complex and costly operation, typically it should be called after
 * #BKE_lib_override_library_main_update, which would already detect and tag a lot of cases.
 *
 * This function will first detect the remaining cases requiring a resync (namely, either when an
 * existing linked ID that did not require to be overridden before now would be, or when new IDs
 * are added to the hierarchy).
 *
 * Then it will handle the resync of necessary IDs (through calls to
 * #BKE_lib_override_library_resync).
 *
 * \param view_layer: the active view layer to search instantiated collections in, can be NULL (in
 *                    which case \a scene's master collection children hierarchy is used instead).
 */
void BKE_lib_override_library_main_resync(struct Main *bmain,
                                          struct Scene *scene,
                                          struct ViewLayer *view_layer,
                                          struct BlendFileReadReport *reports);

/**
 * Advanced 'smart' function to delete library overrides (including their existing override
 * hierarchy) and remap their usages to their linked reference IDs.
 *
 * \note All IDs tagged with #LIB_TAG_DOIT will be deleted.
 *
 * \param id_root: The root liboverride ID to delete.
 */
void BKE_lib_override_library_delete(struct Main *bmain, struct ID *id_root);

/**
 * Make given ID fully local.
 *
 * \note Only differs from lower-level #BKE_lib_override_library_free in infamous embedded ID
 * cases.
 */
void BKE_lib_override_library_make_local(struct ID *id);

/**
 * Find override property from given RNA path, if it exists.
 */
struct IDOverrideLibraryProperty *BKE_lib_override_library_property_find(
    struct IDOverrideLibrary *override, const char *rna_path);
/**
 * Find override property from given RNA path, or create it if it does not exist.
 */
struct IDOverrideLibraryProperty *BKE_lib_override_library_property_get(
    struct IDOverrideLibrary *override, const char *rna_path, bool *r_created);
/**
 * Remove and free given \a override_property from given ID \a override.
 */
void BKE_lib_override_library_property_delete(struct IDOverrideLibrary *override,
                                              struct IDOverrideLibraryProperty *override_property);
/**
 * Get the RNA-property matching the \a library_prop override property. Used for UI to query
 * additional data about the overridden property (e.g. UI name).
 *
 * \param idpoin: Pointer to the override ID.
 * \param library_prop: The library override property to find the matching RNA property for.
 * \param r_index: The RNA array flat index (i.e. flattened index in case of multi-dimensional
 * array properties). See #RNA_path_resolve_full family of functions for details.
 */
bool BKE_lib_override_rna_property_find(struct PointerRNA *idpoin,
                                        const struct IDOverrideLibraryProperty *library_prop,
                                        struct PointerRNA *r_override_poin,
                                        struct PropertyRNA **r_override_prop,
                                        int *r_index);

/**
 * Find override property operation from given sub-item(s), if it exists.
 */
struct IDOverrideLibraryPropertyOperation *BKE_lib_override_library_property_operation_find(
    struct IDOverrideLibraryProperty *override_property,
    const char *subitem_refname,
    const char *subitem_locname,
    int subitem_refindex,
    int subitem_locindex,
    bool strict,
    bool *r_strict);
/**
 * Find override property operation from given sub-item(s), or create it if it does not exist.
 */
struct IDOverrideLibraryPropertyOperation *BKE_lib_override_library_property_operation_get(
    struct IDOverrideLibraryProperty *override_property,
    short operation,
    const char *subitem_refname,
    const char *subitem_locname,
    int subitem_refindex,
    int subitem_locindex,
    bool strict,
    bool *r_strict,
    bool *r_created);
/**
 * Remove and free given \a override_property_operation from given ID \a override_property.
 */
void BKE_lib_override_library_property_operation_delete(
    struct IDOverrideLibraryProperty *override_property,
    struct IDOverrideLibraryPropertyOperation *override_property_operation);

/**
 * Validate that required data for a given operation are available.
 */
bool BKE_lib_override_library_property_operation_operands_validate(
    struct IDOverrideLibraryPropertyOperation *override_property_operation,
    struct PointerRNA *ptr_dst,
    struct PointerRNA *ptr_src,
    struct PointerRNA *ptr_storage,
    struct PropertyRNA *prop_dst,
    struct PropertyRNA *prop_src,
    struct PropertyRNA *prop_storage);

/**
 * Check against potential \a bmain.
 */
void BKE_lib_override_library_validate(struct Main *bmain,
                                       struct ID *id,
                                       struct ReportList *reports);
/**
 * Check against potential \a bmain.
 */
void BKE_lib_override_library_main_validate(struct Main *bmain, struct ReportList *reports);

/**
 * Check that status of local data-block is still valid against current reference one.
 *
 * It means that all overridable, but not overridden, properties' local values must be equal to
 * reference ones. Clears #LIB_TAG_OVERRIDE_OK if they do not.
 *
 * This is typically used to detect whether some property has been changed in local and a new
 * #IDOverrideProperty (of #IDOverridePropertyOperation) has to be added.
 *
 * \return true if status is OK, false otherwise.
 */
bool BKE_lib_override_library_status_check_local(struct Main *bmain, struct ID *local);
/**
 * Check that status of reference data-block is still valid against current local one.
 *
 * It means that all non-overridden properties' local values must be equal to reference ones.
 * Clears LIB_TAG_OVERRIDE_OK if they do not.
 *
 * This is typically used to detect whether some reference has changed and local
 * needs to be updated against it.
 *
 * \return true if status is OK, false otherwise.
 */
bool BKE_lib_override_library_status_check_reference(struct Main *bmain, struct ID *local);

/**
 * Compare local and reference data-blocks and create new override operations as needed,
 * or reset to reference values if overriding is not allowed.
 *
 * \note Defining override operations is only mandatory before saving a `.blend` file on disk
 * (not for undo!).
 * Knowing that info at runtime is only useful for UI/UX feedback.
 *
 * \note This is by far the biggest operation (the more time-consuming) of the three so far,
 * since it has to go over all properties in depth (all overridable ones at least).
 * Generating differential values and applying overrides are much cheaper.
 *
 * \return true if any library operation was created.
 */
bool BKE_lib_override_library_operations_create(struct Main *bmain, struct ID *local);
/**
 * Check all overrides from given \a bmain and create/update overriding operations as needed.
 */
bool BKE_lib_override_library_main_operations_create(struct Main *bmain, bool force_auto);

/**
 * Reset all overrides in given \a id_root, while preserving ID relations.
 *
 * \param do_reset_system_override: If \a true, reset the given ID as a system override one (i.e.
 * non-editable).
 */
void BKE_lib_override_library_id_reset(struct Main *bmain,
                                       struct ID *id_root,
                                       bool do_reset_system_override);
/**
 * Reset all overrides in given \a id_root and its dependencies, while preserving ID relations.
 *
 * \param do_reset_system_override: If \a true, reset the given ID and all of its descendants in
 * the override hierarchy as system override ones (i.e. non-editable).
 */
void BKE_lib_override_library_id_hierarchy_reset(struct Main *bmain,
                                                 struct ID *id_root,
                                                 bool do_reset_system_override);

/**
 * Set or clear given tag in all operations in that override property data.
 */
void BKE_lib_override_library_operations_tag(struct IDOverrideLibraryProperty *override_property,
                                             short tag,
                                             bool do_set);
/**
 * Set or clear given tag in all properties and operations in that override data.
 */
void BKE_lib_override_library_properties_tag(struct IDOverrideLibrary *override,
                                             short tag,
                                             bool do_set);
/**
 * Set or clear given tag in all properties and operations in that Main's ID override data.
 */
void BKE_lib_override_library_main_tag(struct Main *bmain, short tag, bool do_set);

/**
 * Remove all tagged-as-unused properties and operations from that ID override data.
 */
void BKE_lib_override_library_id_unused_cleanup(struct ID *local);
/**
 * Remove all tagged-as-unused properties and operations from that Main's ID override data.
 */
void BKE_lib_override_library_main_unused_cleanup(struct Main *bmain);

/**
 * Update given override from its reference (re-applying overridden properties).
 */
void BKE_lib_override_library_update(struct Main *bmain, struct ID *local);
/**
 * Update all overrides from given \a bmain.
 */
void BKE_lib_override_library_main_update(struct Main *bmain);

/**
 * In case an ID is used by another liboverride ID, user may not be allowed to delete it.
 */
bool BKE_lib_override_library_id_is_user_deletable(struct Main *bmain, struct ID *id);

/* Storage (.blend file writing) part. */

/* For now, we just use a temp main list. */
typedef struct Main OverrideLibraryStorage;

/**
 * Initialize an override storage.
 */
OverrideLibraryStorage *BKE_lib_override_library_operations_store_init(void);
/**
 * Generate suitable 'write' data (this only affects differential override operations).
 *
 * Note that \a local ID is no more modified by this call,
 * all extra data are stored in its temp \a storage_id copy.
 */
struct ID *BKE_lib_override_library_operations_store_start(
    struct Main *bmain, OverrideLibraryStorage *override_storage, struct ID *local);
/**
 * Restore given ID modified by #BKE_lib_override_library_operations_store_start, to its
 * original state.
 */
void BKE_lib_override_library_operations_store_end(OverrideLibraryStorage *override_storage,
                                                   struct ID *local);
void BKE_lib_override_library_operations_store_finalize(OverrideLibraryStorage *override_storage);

#ifdef __cplusplus
}
#endif