2 * ***** BEGIN GPL LICENSE BLOCK *****
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.
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.
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.
18 * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
19 * All rights reserved.
21 * The Original Code is: all of this file.
23 * Contributor(s): none yet.
25 * ***** END GPL LICENSE BLOCK *****
28 /** \file blender/blenkernel/intern/scene.c
37 #include "MEM_guardedalloc.h"
39 #include "DNA_anim_types.h"
40 #include "DNA_group_types.h"
41 #include "DNA_linestyle_types.h"
42 #include "DNA_mesh_types.h"
43 #include "DNA_node_types.h"
44 #include "DNA_object_types.h"
45 #include "DNA_rigidbody_types.h"
46 #include "DNA_scene_types.h"
47 #include "DNA_screen_types.h"
48 #include "DNA_sequence_types.h"
49 #include "DNA_space_types.h"
50 #include "DNA_view3d_types.h"
51 #include "DNA_windowmanager_types.h"
52 #include "DNA_gpencil_types.h"
55 #include "BLI_blenlib.h"
56 #include "BLI_utildefines.h"
57 #include "BLI_callbacks.h"
58 #include "BLI_string.h"
59 #include "BLI_string_utils.h"
60 #include "BLI_threads.h"
63 #include "BLT_translation.h"
66 #include "BKE_animsys.h"
67 #include "BKE_action.h"
68 #include "BKE_armature.h"
69 #include "BKE_cachefile.h"
70 #include "BKE_collection.h"
71 #include "BKE_colortools.h"
72 #include "BKE_editmesh.h"
73 #include "BKE_fcurve.h"
74 #include "BKE_freestyle.h"
75 #include "BKE_global.h"
76 #include "BKE_gpencil.h"
77 #include "BKE_group.h"
78 #include "BKE_icons.h"
79 #include "BKE_idprop.h"
80 #include "BKE_image.h"
81 #include "BKE_layer.h"
82 #include "BKE_library.h"
83 #include "BKE_library_remap.h"
84 #include "BKE_linestyle.h"
88 #include "BKE_object.h"
89 #include "BKE_paint.h"
90 #include "BKE_rigidbody.h"
91 #include "BKE_scene.h"
92 #include "BKE_screen.h"
93 #include "BKE_sequencer.h"
94 #include "BKE_sound.h"
96 #include "BKE_world.h"
98 #include "DEG_depsgraph.h"
99 #include "DEG_depsgraph_build.h"
100 #include "DEG_depsgraph_query.h"
102 #include "RE_engine.h"
104 #include "PIL_time.h"
106 #include "IMB_colormanagement.h"
107 #include "IMB_imbuf.h"
111 const char *RE_engine_id_BLENDER_RENDER = "BLENDER_RENDER";
112 const char *RE_engine_id_BLENDER_GAME = "BLENDER_GAME";
113 const char *RE_engine_id_BLENDER_CLAY = "BLENDER_CLAY";
114 const char *RE_engine_id_BLENDER_EEVEE = "BLENDER_EEVEE";
115 const char *RE_engine_id_CYCLES = "CYCLES";
117 void free_avicodecdata(AviCodecData *acd)
121 MEM_freeN(acd->lpFormat);
122 acd->lpFormat = NULL;
126 MEM_freeN(acd->lpParms);
133 void free_qtcodecdata(QuicktimeCodecData *qcd)
137 MEM_freeN(qcd->cdParms);
144 static void remove_sequencer_fcurves(Scene *sce)
146 AnimData *adt = BKE_animdata_from_id(&sce->id);
148 if (adt && adt->action) {
149 FCurve *fcu, *nextfcu;
151 for (fcu = adt->action->curves.first; fcu; fcu = nextfcu) {
154 if ((fcu->rna_path) && strstr(fcu->rna_path, "sequences_all")) {
155 action_groups_remove_channel(adt->action, fcu);
162 /* copy SceneCollection tree but keep pointing to the same objects */
163 static void scene_collection_copy(SceneCollection *scn, SceneCollection *sc)
165 BLI_duplicatelist(&scn->objects, &sc->objects);
166 for (LinkData *link = scn->objects.first; link; link = link->next) {
167 id_us_plus(link->data);
170 BLI_duplicatelist(&scn->filter_objects, &sc->filter_objects);
171 for (LinkData *link = scn->filter_objects.first; link; link = link->next) {
172 id_us_plus(link->data);
175 BLI_duplicatelist(&scn->scene_collections, &sc->scene_collections);
176 SceneCollection *nscn = scn->scene_collections.first; /* nested SceneCollection new */
177 for (SceneCollection *nsc = sc->scene_collections.first; nsc; nsc = nsc->next) {
178 scene_collection_copy(nscn, nsc);
183 /* Find the equivalent SceneCollection in the new tree */
184 static SceneCollection *scene_collection_from_new_tree(SceneCollection *sc_reference, SceneCollection *scn, SceneCollection *sc)
186 if (sc == sc_reference) {
190 SceneCollection *nscn = scn->scene_collections.first; /* nested master collection new */
191 for (SceneCollection *nsc = sc->scene_collections.first; nsc; nsc = nsc->next) {
193 SceneCollection *found = scene_collection_from_new_tree(sc_reference, nscn, nsc);
202 /* recreate the LayerCollection tree */
203 static void layer_collections_recreate(SceneLayer *sl, ListBase *lb, SceneCollection *mcn, SceneCollection *mc)
205 for (LayerCollection *lc = lb->first; lc; lc = lc->next) {
207 SceneCollection *sc = scene_collection_from_new_tree(lc->scene_collection, mcn, mc);
210 /* instead of syncronizing both trees we simply re-create it */
211 BKE_collection_link(sl, sc);
215 Scene *BKE_scene_copy(Main *bmain, Scene *sce, int type)
218 SceneRenderLayer *srl, *new_srl;
219 FreestyleLineSet *lineset;
221 BaseLegacy *legacy_base, *olegacy_base;
223 if (type == SCE_COPY_EMPTY) {
225 scen = BKE_scene_add(bmain, sce->id.name + 2);
229 curvemapping_free_data(&scen->r.mblur_shutter_curve);
234 scen->unit = sce->unit;
235 scen->physics_settings = sce->physics_settings;
237 scen->audio = sce->audio;
239 if (sce->id.properties)
240 scen->id.properties = IDP_CopyProperty(sce->id.properties);
242 MEM_freeN(scen->toolsettings);
243 BKE_sound_destroy_scene(scen);
246 scen = BKE_libblock_copy(bmain, &sce->id);
247 BLI_duplicatelist(&(scen->base), &(sce->base));
249 id_us_plus((ID *)scen->world);
250 id_us_plus((ID *)scen->set);
251 /* id_us_plus((ID *)scen->gm.dome.warptext); */ /* XXX Not refcounted? see readfile.c */
255 scen->depsgraph = NULL;
258 scen->fps_info = NULL;
260 if (sce->rigidbody_world)
261 scen->rigidbody_world = BKE_rigidbody_world_copy(sce->rigidbody_world);
263 BLI_duplicatelist(&(scen->markers), &(sce->markers));
264 BLI_duplicatelist(&(scen->transform_spaces), &(sce->transform_spaces));
265 BLI_duplicatelist(&(scen->r.layers), &(sce->r.layers));
266 BLI_duplicatelist(&(scen->r.views), &(sce->r.views));
267 BKE_keyingsets_copy(&(scen->keyingsets), &(sce->keyingsets));
270 /* ID's are managed on both copy and switch */
271 scen->nodetree = ntreeCopyTree(bmain, sce->nodetree);
272 BKE_libblock_relink_ex(bmain, scen->nodetree, &sce->id, &scen->id, false);
275 olegacy_base = sce->base.first;
276 legacy_base = scen->base.first;
277 while (legacy_base) {
278 id_us_plus(&legacy_base->object->id);
279 if (olegacy_base == sce->basact) scen->basact = legacy_base;
281 olegacy_base = olegacy_base->next;
282 legacy_base = legacy_base->next;
285 /* copy action and remove animation used by sequencer */
286 BKE_animdata_copy_id_action(&scen->id, false);
288 if (type != SCE_COPY_FULL)
289 remove_sequencer_fcurves(scen);
291 /* copy Freestyle settings */
292 new_srl = scen->r.layers.first;
293 for (srl = sce->r.layers.first; srl; srl = srl->next) {
294 if (new_srl->prop != NULL) {
295 new_srl->prop = IDP_CopyProperty(new_srl->prop);
297 BKE_freestyle_config_copy(&new_srl->freestyleConfig, &srl->freestyleConfig);
298 if (type == SCE_COPY_FULL) {
299 for (lineset = new_srl->freestyleConfig.linesets.first; lineset; lineset = lineset->next) {
300 if (lineset->linestyle) {
301 id_us_plus((ID *)lineset->linestyle);
302 lineset->linestyle = BKE_linestyle_copy(bmain, lineset->linestyle);
306 new_srl = new_srl->next;
309 /* layers and collections */
310 scen->collection = MEM_dupallocN(sce->collection);
311 SceneCollection *mcn = BKE_collection_master(scen);
312 SceneCollection *mc = BKE_collection_master(sce);
314 /* recursively creates a new SceneCollection tree */
315 scene_collection_copy(mcn, mc);
317 BLI_duplicatelist(&scen->render_layers, &sce->render_layers);
318 SceneLayer *new_sl = scen->render_layers.first;
319 for (SceneLayer *sl = sce->render_layers.first; sl; sl = sl->next) {
321 /* we start fresh with no overrides and no visibility flags set
322 * instead of syncing both trees we simply unlink and relink the scene collection */
323 BLI_listbase_clear(&new_sl->layer_collections);
324 BLI_listbase_clear(&new_sl->object_bases);
325 layer_collections_recreate(new_sl, &sl->layer_collections, mcn, mc);
328 Object *active_ob = sl->basact->object;
329 for (Base *base = new_sl->object_bases.first; base; base = base->next) {
330 if (base->object == active_ob) {
331 new_sl->basact = base;
336 new_sl = new_sl->next;
339 IDPropertyTemplate val = {0};
340 scen->collection_properties = IDP_New(IDP_GROUP, &val, ROOT_PROP);
343 /* copy color management settings */
344 BKE_color_managed_display_settings_copy(&scen->display_settings, &sce->display_settings);
345 BKE_color_managed_view_settings_copy(&scen->view_settings, &sce->view_settings);
346 BKE_color_managed_colorspace_settings_copy(&scen->sequencer_colorspace_settings, &sce->sequencer_colorspace_settings);
348 BKE_color_managed_display_settings_copy(&scen->r.im_format.display_settings, &sce->r.im_format.display_settings);
349 BKE_color_managed_view_settings_copy(&scen->r.im_format.view_settings, &sce->r.im_format.view_settings);
351 BKE_color_managed_display_settings_copy(&scen->r.bake.im_format.display_settings, &sce->r.bake.im_format.display_settings);
352 BKE_color_managed_view_settings_copy(&scen->r.bake.im_format.view_settings, &sce->r.bake.im_format.view_settings);
354 curvemapping_copy_data(&scen->r.mblur_shutter_curve, &sce->r.mblur_shutter_curve);
357 scen->toolsettings = MEM_dupallocN(sce->toolsettings);
359 ts = scen->toolsettings;
362 ts->vpaint = MEM_dupallocN(ts->vpaint);
363 ts->vpaint->paintcursor = NULL;
364 ts->vpaint->vpaint_prev = NULL;
365 ts->vpaint->wpaint_prev = NULL;
366 BKE_paint_copy(&ts->vpaint->paint, &ts->vpaint->paint);
369 ts->wpaint = MEM_dupallocN(ts->wpaint);
370 ts->wpaint->paintcursor = NULL;
371 ts->wpaint->vpaint_prev = NULL;
372 ts->wpaint->wpaint_prev = NULL;
373 BKE_paint_copy(&ts->wpaint->paint, &ts->wpaint->paint);
376 ts->sculpt = MEM_dupallocN(ts->sculpt);
377 BKE_paint_copy(&ts->sculpt->paint, &ts->sculpt->paint);
380 BKE_paint_copy(&ts->imapaint.paint, &ts->imapaint.paint);
381 ts->imapaint.paintcursor = NULL;
382 id_us_plus((ID *)ts->imapaint.stencil);
383 ts->particle.paintcursor = NULL;
385 /* duplicate Grease Pencil Drawing Brushes */
386 BLI_listbase_clear(&ts->gp_brushes);
387 for (bGPDbrush *brush = sce->toolsettings->gp_brushes.first; brush; brush = brush->next) {
388 bGPDbrush *newbrush = BKE_gpencil_brush_duplicate(brush);
389 BLI_addtail(&ts->gp_brushes, newbrush);
392 /* duplicate Grease Pencil interpolation curve */
393 ts->gp_interpolate.custom_ipo = curvemapping_copy(ts->gp_interpolate.custom_ipo);
396 /* make a private copy of the avicodecdata */
397 if (sce->r.avicodecdata) {
398 scen->r.avicodecdata = MEM_dupallocN(sce->r.avicodecdata);
399 scen->r.avicodecdata->lpFormat = MEM_dupallocN(scen->r.avicodecdata->lpFormat);
400 scen->r.avicodecdata->lpParms = MEM_dupallocN(scen->r.avicodecdata->lpParms);
403 /* make a private copy of the qtcodecdata */
404 if (sce->r.qtcodecdata) {
405 scen->r.qtcodecdata = MEM_dupallocN(sce->r.qtcodecdata);
406 scen->r.qtcodecdata->cdParms = MEM_dupallocN(scen->r.qtcodecdata->cdParms);
409 if (sce->r.ffcodecdata.properties) { /* intentionally check scen not sce. */
410 scen->r.ffcodecdata.properties = IDP_CopyProperty(sce->r.ffcodecdata.properties);
413 /* NOTE: part of SCE_COPY_LINK_DATA and SCE_COPY_FULL operations
414 * are done outside of blenkernel with ED_objects_single_users! */
417 if (type == SCE_COPY_LINK_DATA || type == SCE_COPY_FULL) {
418 ID_NEW_REMAP(scen->camera);
421 /* before scene copy */
422 BKE_sound_create_scene(scen);
425 if (type == SCE_COPY_FULL) {
427 id_us_plus((ID *)scen->world);
428 scen->world = BKE_world_copy(bmain, scen->world);
429 BKE_animdata_copy_id_action((ID *)scen->world, false);
433 scen->ed = MEM_callocN(sizeof(Editing), "addseq");
434 scen->ed->seqbasep = &scen->ed->seqbase;
435 BKE_sequence_base_dupli_recursive(sce, scen, &scen->ed->seqbase, &sce->ed->seqbase, SEQ_DUPE_ALL);
441 if (type == SCE_COPY_FULL) {
442 scen->gpd = BKE_gpencil_data_duplicate(bmain, scen->gpd, false);
444 else if (type == SCE_COPY_EMPTY) {
448 id_us_plus((ID *)scen->gpd);
452 BKE_previewimg_id_copy(&scen->id, &sce->id);
454 if (type != SCE_COPY_NEW) {
455 if (sce->collection_properties) {
456 IDP_MergeGroup(scen->collection_properties, sce->collection_properties, true);
463 void BKE_scene_groups_relink(Scene *sce)
465 if (sce->rigidbody_world)
466 BKE_rigidbody_world_groups_relink(sce->rigidbody_world);
469 void BKE_scene_make_local(Main *bmain, Scene *sce, const bool lib_local)
471 /* For now should work, may need more work though to support all possible corner cases
472 * (also scene_copy probably needs some love). */
473 BKE_id_make_local_generic(bmain, &sce->id, true, lib_local);
476 /** Free (or release) any data used by this scene (does not free the scene itself). */
477 void BKE_scene_free(Scene *sce)
479 SceneRenderLayer *srl;
481 BKE_animdata_free((ID *)sce, false);
483 /* check all sequences */
484 BKE_sequencer_clear_scene_in_allseqs(G.main, sce);
487 BLI_freelistN(&sce->base);
488 BKE_sequencer_editing_free(sce);
490 BKE_keyingsets_free(&sce->keyingsets);
492 /* is no lib link block, but scene extension */
494 ntreeFreeTree(sce->nodetree);
495 MEM_freeN(sce->nodetree);
496 sce->nodetree = NULL;
499 if (sce->rigidbody_world) {
500 BKE_rigidbody_free_world(sce->rigidbody_world);
501 sce->rigidbody_world = NULL;
504 if (sce->r.avicodecdata) {
505 free_avicodecdata(sce->r.avicodecdata);
506 MEM_freeN(sce->r.avicodecdata);
507 sce->r.avicodecdata = NULL;
509 if (sce->r.qtcodecdata) {
510 free_qtcodecdata(sce->r.qtcodecdata);
511 MEM_freeN(sce->r.qtcodecdata);
512 sce->r.qtcodecdata = NULL;
514 if (sce->r.ffcodecdata.properties) {
515 IDP_FreeProperty(sce->r.ffcodecdata.properties);
516 MEM_freeN(sce->r.ffcodecdata.properties);
517 sce->r.ffcodecdata.properties = NULL;
520 for (srl = sce->r.layers.first; srl; srl = srl->next) {
521 if (srl->prop != NULL) {
522 IDP_FreeProperty(srl->prop);
523 MEM_freeN(srl->prop);
525 BKE_freestyle_config_free(&srl->freestyleConfig);
528 BLI_freelistN(&sce->markers);
529 BLI_freelistN(&sce->transform_spaces);
530 BLI_freelistN(&sce->r.layers);
531 BLI_freelistN(&sce->r.views);
533 if (sce->toolsettings) {
534 if (sce->toolsettings->vpaint) {
535 BKE_paint_free(&sce->toolsettings->vpaint->paint);
536 MEM_freeN(sce->toolsettings->vpaint);
538 if (sce->toolsettings->wpaint) {
539 BKE_paint_free(&sce->toolsettings->wpaint->paint);
540 MEM_freeN(sce->toolsettings->wpaint);
542 if (sce->toolsettings->sculpt) {
543 BKE_paint_free(&sce->toolsettings->sculpt->paint);
544 MEM_freeN(sce->toolsettings->sculpt);
546 if (sce->toolsettings->uvsculpt) {
547 BKE_paint_free(&sce->toolsettings->uvsculpt->paint);
548 MEM_freeN(sce->toolsettings->uvsculpt);
550 BKE_paint_free(&sce->toolsettings->imapaint.paint);
552 /* free Grease Pencil Drawing Brushes */
553 BKE_gpencil_free_brushes(&sce->toolsettings->gp_brushes);
554 BLI_freelistN(&sce->toolsettings->gp_brushes);
556 /* free Grease Pencil interpolation curve */
557 if (sce->toolsettings->gp_interpolate.custom_ipo) {
558 curvemapping_free(sce->toolsettings->gp_interpolate.custom_ipo);
561 MEM_freeN(sce->toolsettings);
562 sce->toolsettings = NULL;
565 DEG_scene_graph_free(sce);
567 DEG_graph_free(sce->depsgraph);
569 MEM_SAFE_FREE(sce->stats);
570 MEM_SAFE_FREE(sce->fps_info);
572 BKE_sound_destroy_scene(sce);
574 BKE_color_managed_view_settings_free(&sce->view_settings);
576 BKE_previewimg_free(&sce->preview);
577 curvemapping_free_data(&sce->r.mblur_shutter_curve);
579 for (SceneLayer *sl = sce->render_layers.first; sl; sl = sl->next) {
580 BKE_scene_layer_free(sl);
582 BLI_freelistN(&sce->render_layers);
584 /* Master Collection */
585 BKE_collection_master_free(sce);
586 MEM_freeN(sce->collection);
587 sce->collection = NULL;
589 /* Runtime Engine Data */
590 if (sce->collection_properties) {
591 IDP_FreeProperty(sce->collection_properties);
592 MEM_freeN(sce->collection_properties);
593 sce->collection_properties = NULL;
597 void BKE_scene_init(Scene *sce)
599 ParticleEditSettings *pset;
601 const char *colorspace_name;
602 SceneRenderView *srv;
603 CurveMapping *mblur_shutter_curve;
605 BLI_assert(MEMCMP_STRUCT_OFS_IS_ZERO(sce, id));
607 sce->lay = sce->layact = 1;
609 sce->r.mode = R_GAMMA | R_OSA | R_SHADOW | R_SSS | R_ENVMAP | R_RAYTRACE;
613 sce->r.frame_step = 1;
620 sce->r.mblur_samples = 1;
621 sce->r.filtertype = R_FILTER_MITCH;
624 sce->r.im_format.planes = R_IMF_PLANES_RGBA;
625 sce->r.im_format.imtype = R_IMF_IMTYPE_PNG;
626 sce->r.im_format.depth = R_IMF_CHAN_DEPTH_8;
627 sce->r.im_format.quality = 90;
628 sce->r.im_format.compress = 15;
630 sce->r.displaymode = R_OUTPUT_AREA;
631 sce->r.framapto = 100;
633 sce->r.framelen = 1.0;
634 sce->r.blurfac = 0.5;
636 sce->r.frs_sec_base = 1;
640 /* OCIO_TODO: for forwards compatibility only, so if no tonecurve are used,
641 * images would look in the same way as in current blender
643 * perhaps at some point should be completely deprecated?
645 sce->r.color_mgt_flag |= R_COLOR_MANAGEMENT;
649 /* deprecated but keep for upwards compat */
650 sce->r.postgamma = 1.0;
651 sce->r.posthue = 0.0;
652 sce->r.postsat = 1.0;
654 sce->r.bake_mode = 1; /* prevent to include render stuff here */
655 sce->r.bake_filter = 16;
657 sce->r.bake_flag = R_BAKE_CLEAR;
658 sce->r.bake_normal_space = R_BAKE_SPACE_TANGENT;
659 sce->r.bake_samples = 256;
660 sce->r.bake_biasdist = 0.001;
662 sce->r.bake.flag = R_BAKE_CLEAR;
663 sce->r.bake.pass_filter = R_BAKE_PASS_FILTER_ALL;
664 sce->r.bake.width = 512;
665 sce->r.bake.height = 512;
666 sce->r.bake.margin = 16;
667 sce->r.bake.normal_space = R_BAKE_SPACE_TANGENT;
668 sce->r.bake.normal_swizzle[0] = R_BAKE_POSX;
669 sce->r.bake.normal_swizzle[1] = R_BAKE_POSY;
670 sce->r.bake.normal_swizzle[2] = R_BAKE_POSZ;
671 BLI_strncpy(sce->r.bake.filepath, U.renderdir, sizeof(sce->r.bake.filepath));
673 sce->r.bake.im_format.planes = R_IMF_PLANES_RGBA;
674 sce->r.bake.im_format.imtype = R_IMF_IMTYPE_PNG;
675 sce->r.bake.im_format.depth = R_IMF_CHAN_DEPTH_8;
676 sce->r.bake.im_format.quality = 90;
677 sce->r.bake.im_format.compress = 15;
679 sce->r.scemode = R_DOCOMP | R_DOSEQ | R_EXTENSION;
680 sce->r.stamp = R_STAMP_TIME | R_STAMP_FRAME | R_STAMP_DATE | R_STAMP_CAMERA | R_STAMP_SCENE | R_STAMP_FILENAME | R_STAMP_RENDERTIME | R_STAMP_MEMORY;
681 sce->r.stamp_font_id = 12;
682 sce->r.fg_stamp[0] = sce->r.fg_stamp[1] = sce->r.fg_stamp[2] = 0.8f;
683 sce->r.fg_stamp[3] = 1.0f;
684 sce->r.bg_stamp[0] = sce->r.bg_stamp[1] = sce->r.bg_stamp[2] = 0.0f;
685 sce->r.bg_stamp[3] = 0.25f;
686 sce->r.raytrace_options = R_RAYTRACE_USE_INSTANCES;
688 sce->r.seq_prev_type = OB_SOLID;
689 sce->r.seq_rend_type = OB_SOLID;
690 sce->r.seq_flag = R_SEQ_GL_PREV;
694 sce->r.simplify_subsurf = 6;
695 sce->r.simplify_particles = 1.0f;
696 sce->r.simplify_shadowsamples = 16;
697 sce->r.simplify_aosss = 1.0f;
699 sce->r.border.xmin = 0.0f;
700 sce->r.border.ymin = 0.0f;
701 sce->r.border.xmax = 1.0f;
702 sce->r.border.ymax = 1.0f;
704 sce->r.preview_start_resolution = 64;
706 sce->r.line_thickness_mode = R_LINE_THICKNESS_ABSOLUTE;
707 sce->r.unit_line_thickness = 1.0f;
709 mblur_shutter_curve = &sce->r.mblur_shutter_curve;
710 curvemapping_set_defaults(mblur_shutter_curve, 1, 0.0f, 0.0f, 1.0f, 1.0f);
711 curvemapping_initialize(mblur_shutter_curve);
712 curvemap_reset(mblur_shutter_curve->cm,
713 &mblur_shutter_curve->clipr,
715 CURVEMAP_SLOPE_POS_NEG);
717 sce->toolsettings = MEM_callocN(sizeof(struct ToolSettings), "Tool Settings Struct");
718 sce->toolsettings->doublimit = 0.001;
719 sce->toolsettings->vgroup_weight = 1.0f;
720 sce->toolsettings->uvcalc_margin = 0.001f;
721 sce->toolsettings->unwrapper = 1;
722 sce->toolsettings->select_thresh = 0.01f;
724 sce->toolsettings->selectmode = SCE_SELECT_VERTEX;
725 sce->toolsettings->uv_selectmode = UV_SELECT_VERTEX;
726 sce->toolsettings->normalsize = 0.1;
727 sce->toolsettings->autokey_mode = U.autokey_mode;
729 sce->toolsettings->snap_node_mode = SCE_SNAP_MODE_GRID;
731 sce->toolsettings->skgen_resolution = 100;
732 sce->toolsettings->skgen_threshold_internal = 0.01f;
733 sce->toolsettings->skgen_threshold_external = 0.01f;
734 sce->toolsettings->skgen_angle_limit = 45.0f;
735 sce->toolsettings->skgen_length_ratio = 1.3f;
736 sce->toolsettings->skgen_length_limit = 1.5f;
737 sce->toolsettings->skgen_correlation_limit = 0.98f;
738 sce->toolsettings->skgen_symmetry_limit = 0.1f;
739 sce->toolsettings->skgen_postpro = SKGEN_SMOOTH;
740 sce->toolsettings->skgen_postpro_passes = 1;
741 sce->toolsettings->skgen_options = SKGEN_FILTER_INTERNAL | SKGEN_FILTER_EXTERNAL | SKGEN_FILTER_SMART | SKGEN_HARMONIC | SKGEN_SUB_CORRELATION | SKGEN_STICK_TO_EMBEDDING;
742 sce->toolsettings->skgen_subdivisions[0] = SKGEN_SUB_CORRELATION;
743 sce->toolsettings->skgen_subdivisions[1] = SKGEN_SUB_LENGTH;
744 sce->toolsettings->skgen_subdivisions[2] = SKGEN_SUB_ANGLE;
746 sce->toolsettings->curve_paint_settings.curve_type = CU_BEZIER;
747 sce->toolsettings->curve_paint_settings.flag |= CURVE_PAINT_FLAG_CORNERS_DETECT;
748 sce->toolsettings->curve_paint_settings.error_threshold = 8;
749 sce->toolsettings->curve_paint_settings.radius_max = 1.0f;
750 sce->toolsettings->curve_paint_settings.corner_angle = DEG2RADF(70.0f);
752 sce->toolsettings->statvis.overhang_axis = OB_NEGZ;
753 sce->toolsettings->statvis.overhang_min = 0;
754 sce->toolsettings->statvis.overhang_max = DEG2RADF(45.0f);
755 sce->toolsettings->statvis.thickness_max = 0.1f;
756 sce->toolsettings->statvis.thickness_samples = 1;
757 sce->toolsettings->statvis.distort_min = DEG2RADF(5.0f);
758 sce->toolsettings->statvis.distort_max = DEG2RADF(45.0f);
760 sce->toolsettings->statvis.sharp_min = DEG2RADF(90.0f);
761 sce->toolsettings->statvis.sharp_max = DEG2RADF(180.0f);
763 sce->toolsettings->proportional_size = 1.0f;
765 sce->toolsettings->imapaint.paint.flags |= PAINT_SHOW_BRUSH;
766 sce->toolsettings->imapaint.normal_angle = 80;
767 sce->toolsettings->imapaint.seam_bleed = 2;
769 sce->physics_settings.gravity[0] = 0.0f;
770 sce->physics_settings.gravity[1] = 0.0f;
771 sce->physics_settings.gravity[2] = -9.81f;
772 sce->physics_settings.flag = PHYS_GLOBAL_GRAVITY;
774 sce->unit.scale_length = 1.0f;
776 pset = &sce->toolsettings->particle;
777 pset->flag = PE_KEEP_LENGTHS | PE_LOCK_FIRST | PE_DEFLECT_EMITTER | PE_AUTO_VELOCITY;
778 pset->emitterdist = 0.25f;
781 pset->brushtype = PE_BRUSH_NONE;
783 pset->fade_frames = 2;
784 pset->selectmode = SCE_SELECT_PATH;
785 for (a = 0; a < PE_TOT_BRUSH; a++) {
786 pset->brush[a].strength = 0.5f;
787 pset->brush[a].size = 50;
788 pset->brush[a].step = 10;
789 pset->brush[a].count = 10;
791 pset->brush[PE_BRUSH_CUT].strength = 1.0f;
793 sce->r.ffcodecdata.audio_mixrate = 48000;
794 sce->r.ffcodecdata.audio_volume = 1.0f;
795 sce->r.ffcodecdata.audio_bitrate = 192;
796 sce->r.ffcodecdata.audio_channels = 2;
798 BLI_strncpy(sce->r.engine, RE_engine_id_BLENDER_RENDER, sizeof(sce->r.engine));
800 sce->audio.distance_model = 2.0f;
801 sce->audio.doppler_factor = 1.0f;
802 sce->audio.speed_of_sound = 343.3f;
803 sce->audio.volume = 1.0f;
805 BLI_strncpy(sce->r.pic, U.renderdir, sizeof(sce->r.pic));
807 BLI_rctf_init(&sce->r.safety, 0.1f, 0.9f, 0.1f, 0.9f);
810 /* note; in header_info.c the scene copy happens..., if you add more to renderdata it has to be checked there */
811 BKE_scene_add_render_layer(sce, NULL);
813 /* multiview - stereo */
814 BKE_scene_add_render_view(sce, STEREO_LEFT_NAME);
815 srv = sce->r.views.first;
816 BLI_strncpy(srv->suffix, STEREO_LEFT_SUFFIX, sizeof(srv->suffix));
818 BKE_scene_add_render_view(sce, STEREO_RIGHT_NAME);
819 srv = sce->r.views.last;
820 BLI_strncpy(srv->suffix, STEREO_RIGHT_SUFFIX, sizeof(srv->suffix));
823 sce->gm.stereoflag = STEREO_NOSTEREO;
824 sce->gm.stereomode = STEREO_ANAGLYPH;
825 sce->gm.eyeseparation = 0.10;
827 sce->gm.dome.angle = 180;
828 sce->gm.dome.mode = DOME_FISHEYE;
829 sce->gm.dome.res = 4;
830 sce->gm.dome.resbuf = 1.0f;
831 sce->gm.dome.tilt = 0;
835 sce->gm.freqplay = 60;
838 sce->gm.gravity = 9.8f;
839 sce->gm.physicsEngine = WOPHY_BULLET;
840 sce->gm.mode = 32; //XXX ugly harcoding, still not sure we should drop mode. 32 == 1 << 5 == use_occlusion_culling
841 sce->gm.occlusionRes = 128;
842 sce->gm.ticrate = 60;
843 sce->gm.maxlogicstep = 5;
844 sce->gm.physubstep = 1;
845 sce->gm.maxphystep = 5;
846 sce->gm.lineardeactthreshold = 0.8f;
847 sce->gm.angulardeactthreshold = 1.0f;
848 sce->gm.deactivationtime = 0.0f;
850 sce->gm.flag = GAME_DISPLAY_LISTS;
851 sce->gm.matmode = GAME_MAT_MULTITEX;
853 sce->gm.obstacleSimulation = OBSTSIMULATION_NONE;
854 sce->gm.levelHeight = 2.f;
856 sce->gm.recastData.cellsize = 0.3f;
857 sce->gm.recastData.cellheight = 0.2f;
858 sce->gm.recastData.agentmaxslope = M_PI_4;
859 sce->gm.recastData.agentmaxclimb = 0.9f;
860 sce->gm.recastData.agentheight = 2.0f;
861 sce->gm.recastData.agentradius = 0.6f;
862 sce->gm.recastData.edgemaxlen = 12.0f;
863 sce->gm.recastData.edgemaxerror = 1.3f;
864 sce->gm.recastData.regionminsize = 8.f;
865 sce->gm.recastData.regionmergesize = 20.f;
866 sce->gm.recastData.vertsperpoly = 6;
867 sce->gm.recastData.detailsampledist = 6.0f;
868 sce->gm.recastData.detailsamplemaxerror = 1.0f;
870 sce->gm.lodflag = SCE_LOD_USE_HYST;
871 sce->gm.scehysteresis = 10;
873 sce->gm.exitkey = 218; // Blender key code for ESC
875 BKE_sound_create_scene(sce);
877 /* color management */
878 colorspace_name = IMB_colormanagement_role_colorspace_name_get(COLOR_ROLE_DEFAULT_SEQUENCER);
880 BKE_color_managed_display_settings_init(&sce->display_settings);
881 BKE_color_managed_view_settings_init(&sce->view_settings);
882 BLI_strncpy(sce->sequencer_colorspace_settings.name, colorspace_name,
883 sizeof(sce->sequencer_colorspace_settings.name));
886 copy_v2_fl2(sce->safe_areas.title, 3.5f / 100.0f, 3.5f / 100.0f);
887 copy_v2_fl2(sce->safe_areas.action, 10.0f / 100.0f, 5.0f / 100.0f);
888 copy_v2_fl2(sce->safe_areas.title_center, 17.5f / 100.0f, 5.0f / 100.0f);
889 copy_v2_fl2(sce->safe_areas.action_center, 15.0f / 100.0f, 5.0f / 100.0f);
893 /* GP Sculpt brushes */
895 GP_BrushEdit_Settings *gset = &sce->toolsettings->gp_sculpt;
896 GP_EditBrush_Data *gp_brush;
898 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_SMOOTH];
900 gp_brush->strength = 0.3f;
901 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF | GP_EDITBRUSH_FLAG_SMOOTH_PRESSURE;
903 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_THICKNESS];
905 gp_brush->strength = 0.5f;
906 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
908 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_STRENGTH];
910 gp_brush->strength = 0.5f;
911 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
913 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_GRAB];
915 gp_brush->strength = 0.3f;
916 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
918 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_PUSH];
920 gp_brush->strength = 0.3f;
921 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
923 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_TWIST];
925 gp_brush->strength = 0.3f; // XXX?
926 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
928 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_PINCH];
930 gp_brush->strength = 0.5f; // XXX?
931 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
933 gp_brush = &gset->brush[GP_EDITBRUSH_TYPE_RANDOMIZE];
935 gp_brush->strength = 0.5f;
936 gp_brush->flag = GP_EDITBRUSH_FLAG_USE_FALLOFF;
939 /* GP Stroke Placement */
940 sce->toolsettings->gpencil_v3d_align = GP_PROJECT_VIEWSPACE;
941 sce->toolsettings->gpencil_v2d_align = GP_PROJECT_VIEWSPACE;
942 sce->toolsettings->gpencil_seq_align = GP_PROJECT_VIEWSPACE;
943 sce->toolsettings->gpencil_ima_align = GP_PROJECT_VIEWSPACE;
945 /* Master Collection */
946 sce->collection = MEM_callocN(sizeof(SceneCollection), "Master Collection");
947 BLI_strncpy(sce->collection->name, "Master Collection", sizeof(sce->collection->name));
949 IDPropertyTemplate val = {0};
950 sce->collection_properties = IDP_New(IDP_GROUP, &val, ROOT_PROP);
951 BKE_layer_collection_engine_settings_create(sce->collection_properties);
953 BKE_scene_layer_add(sce, "Render Layer");
956 Scene *BKE_scene_add(Main *bmain, const char *name)
960 sce = BKE_libblock_alloc(bmain, ID_SCE, name);
962 id_us_ensure_real(&sce->id);
969 BaseLegacy *BKE_scene_base_find_by_name(struct Scene *scene, const char *name)
973 for (base = scene->base.first; base; base = base->next) {
974 if (STREQ(base->object->id.name + 2, name)) {
982 BaseLegacy *BKE_scene_base_find(Scene *scene, Object *ob)
984 return BLI_findptr(&scene->base, ob, offsetof(BaseLegacy, object));
988 * Sets the active scene, mainly used when running in background mode (``--scene`` command line argument).
989 * This is also called to set the scene directly, bypassing windowing code.
990 * Otherwise #ED_screen_set_scene is used when changing scenes by the user.
992 void BKE_scene_set_background(Main *bmain, Scene *scene)
1000 /* check for cyclic sets, for reading old files but also for definite security (py?) */
1001 BKE_scene_validate_setscene(bmain, scene);
1003 /* can happen when switching modes in other scenes */
1004 if (scene->obedit && !(scene->obedit->mode & OB_MODE_EDIT))
1005 scene->obedit = NULL;
1007 /* deselect objects (for dataselect) */
1008 for (ob = bmain->object.first; ob; ob = ob->id.next)
1009 ob->flag &= ~(SELECT | OB_FROMGROUP);
1011 /* group flags again */
1012 for (group = bmain->group.first; group; group = group->id.next) {
1013 for (go = group->gobject.first; go; go = go->next) {
1015 go->ob->flag |= OB_FROMGROUP;
1020 /* sort baselist for scene and sets */
1021 for (sce = scene; sce; sce = sce->set)
1022 DEG_scene_relations_rebuild(bmain, sce);
1024 /* copy layers and flags from bases to objects */
1025 for (base = scene->base.first; base; base = base->next) {
1027 ob->lay = base->lay;
1029 /* group patch... */
1030 BKE_scene_base_flag_sync_from_base(base);
1032 /* no full animation update, this to enable render code to work (render code calls own animation updates) */
1035 /* called from creator_args.c */
1036 Scene *BKE_scene_set_name(Main *bmain, const char *name)
1038 Scene *sce = (Scene *)BKE_libblock_find_name_ex(bmain, ID_SCE, name);
1040 BKE_scene_set_background(bmain, sce);
1041 printf("Scene switch for render: '%s' in file: '%s'\n", name, bmain->name);
1045 printf("Can't find scene: '%s' in file: '%s'\n", name, bmain->name);
1049 /* Used by metaballs, return *all* objects (including duplis) existing in the scene (including scene's sets) */
1050 int BKE_scene_base_iter_next(EvaluationContext *eval_ctx, SceneBaseIter *iter,
1051 Scene **scene, int val, BaseLegacy **base, Object **ob)
1053 bool run_again = true;
1057 iter->phase = F_START;
1059 iter->duplilist = NULL;
1060 iter->dupli_refob = NULL;
1063 /* run_again is set when a duplilist has been ended */
1067 /* the first base */
1068 if (iter->phase == F_START) {
1069 *base = (*scene)->base.first;
1071 *ob = (*base)->object;
1072 iter->phase = F_SCENE;
1075 /* exception: empty scene */
1076 while ((*scene)->set) {
1077 (*scene) = (*scene)->set;
1078 if ((*scene)->base.first) {
1079 *base = (*scene)->base.first;
1080 *ob = (*base)->object;
1081 iter->phase = F_SCENE;
1088 if (*base && iter->phase != F_DUPLI) {
1089 *base = (*base)->next;
1091 *ob = (*base)->object;
1094 if (iter->phase == F_SCENE) {
1095 /* (*scene) is finished, now do the set */
1096 while ((*scene)->set) {
1097 (*scene) = (*scene)->set;
1098 if ((*scene)->base.first) {
1099 *base = (*scene)->base.first;
1100 *ob = (*base)->object;
1109 if (*base == NULL) {
1110 iter->phase = F_START;
1113 if (iter->phase != F_DUPLI) {
1114 if ( (*base)->object->transflag & OB_DUPLI) {
1115 /* groups cannot be duplicated for mballs yet,
1116 * this enters eternal loop because of
1117 * makeDispListMBall getting called inside of group_duplilist */
1118 if ((*base)->object->dup_group == NULL) {
1119 iter->duplilist = object_duplilist_ex(eval_ctx, (*scene), (*base)->object, false);
1121 iter->dupob = iter->duplilist->first;
1124 free_object_duplilist(iter->duplilist);
1125 iter->duplilist = NULL;
1127 iter->dupli_refob = NULL;
1131 /* handle dupli's */
1133 (*base)->flag_legacy |= OB_FROMDUPLI;
1134 *ob = iter->dupob->ob;
1135 iter->phase = F_DUPLI;
1137 if (iter->dupli_refob != *ob) {
1138 if (iter->dupli_refob) {
1139 /* Restore previous object's real matrix. */
1140 copy_m4_m4(iter->dupli_refob->obmat, iter->omat);
1142 /* Backup new object's real matrix. */
1143 iter->dupli_refob = *ob;
1144 copy_m4_m4(iter->omat, iter->dupli_refob->obmat);
1146 copy_m4_m4((*ob)->obmat, iter->dupob->mat);
1148 iter->dupob = iter->dupob->next;
1150 else if (iter->phase == F_DUPLI) {
1151 iter->phase = F_SCENE;
1152 (*base)->flag_legacy &= ~OB_FROMDUPLI;
1154 if (iter->dupli_refob) {
1155 /* Restore last object's real matrix. */
1156 copy_m4_m4(iter->dupli_refob->obmat, iter->omat);
1157 iter->dupli_refob = NULL;
1160 free_object_duplilist(iter->duplilist);
1161 iter->duplilist = NULL;
1170 printf("Scene: '%s', '%s'\n", (*scene)->id.name + 2, (*ob)->id.name + 2);
1177 Scene *BKE_scene_find_from_collection(const Main *bmain, const SceneCollection *scene_collection)
1179 for (Scene *scene = bmain->scene.first; scene; scene = scene->id.next) {
1180 for (SceneLayer *layer = scene->render_layers.first; layer; layer = layer->next) {
1181 if (BKE_scene_layer_has_collection(layer, scene_collection)) {
1190 Object *BKE_scene_camera_find(Scene *sc)
1194 for (base = sc->base.first; base; base = base->next)
1195 if (base->object->type == OB_CAMERA)
1196 return base->object;
1201 #ifdef DURIAN_CAMERA_SWITCH
1202 Object *BKE_scene_camera_switch_find(Scene *scene)
1205 int cfra = scene->r.cfra;
1206 int frame = -(MAXFRAME + 1);
1207 int min_frame = MAXFRAME + 1;
1208 Object *camera = NULL;
1209 Object *first_camera = NULL;
1211 for (m = scene->markers.first; m; m = m->next) {
1212 if (m->camera && (m->camera->restrictflag & OB_RESTRICT_RENDER) == 0) {
1213 if ((m->frame <= cfra) && (m->frame > frame)) {
1221 if (m->frame < min_frame) {
1222 first_camera = m->camera;
1223 min_frame = m->frame;
1228 if (camera == NULL) {
1229 /* If there's no marker to the left of current frame,
1230 * use camera from left-most marker to solve all sort
1231 * of Schrodinger uncertainties.
1233 return first_camera;
1240 int BKE_scene_camera_switch_update(Scene *scene)
1242 #ifdef DURIAN_CAMERA_SWITCH
1243 Object *camera = BKE_scene_camera_switch_find(scene);
1245 scene->camera = camera;
1254 char *BKE_scene_find_marker_name(Scene *scene, int frame)
1256 ListBase *markers = &scene->markers;
1257 TimeMarker *m1, *m2;
1259 /* search through markers for match */
1260 for (m1 = markers->first, m2 = markers->last; m1 && m2; m1 = m1->next, m2 = m2->prev) {
1261 if (m1->frame == frame)
1267 if (m2->frame == frame)
1274 /* return the current marker for this frame,
1275 * we can have more than 1 marker per frame, this just returns the first :/ */
1276 char *BKE_scene_find_last_marker_name(Scene *scene, int frame)
1278 TimeMarker *marker, *best_marker = NULL;
1279 int best_frame = -MAXFRAME * 2;
1280 for (marker = scene->markers.first; marker; marker = marker->next) {
1281 if (marker->frame == frame) {
1282 return marker->name;
1285 if (marker->frame > best_frame && marker->frame < frame) {
1286 best_marker = marker;
1287 best_frame = marker->frame;
1291 return best_marker ? best_marker->name : NULL;
1294 void BKE_scene_remove_rigidbody_object(Scene *scene, Object *ob)
1296 /* remove rigid body constraint from world before removing object */
1297 if (ob->rigidbody_constraint)
1298 BKE_rigidbody_remove_constraint(scene, ob);
1299 /* remove rigid body object from world before removing object */
1300 if (ob->rigidbody_object)
1301 BKE_rigidbody_remove_object(scene, ob);
1304 BaseLegacy *BKE_scene_base_add(Scene *sce, Object *ob)
1306 BaseLegacy *b = MEM_callocN(sizeof(*b), __func__);
1307 BLI_addhead(&sce->base, b);
1310 b->flag_legacy = ob->flag;
1316 void BKE_scene_base_unlink(Scene *sce, BaseLegacy *base)
1318 BKE_scene_remove_rigidbody_object(sce, base->object);
1320 BLI_remlink(&sce->base, base);
1321 if (sce->basact == base)
1325 /* deprecated, use BKE_scene_layer_base_deselect_all */
1326 void BKE_scene_base_deselect_all(Scene *sce)
1330 for (b = sce->base.first; b; b = b->next) {
1331 b->flag_legacy &= ~SELECT;
1332 int flag = b->object->flag & (OB_FROMGROUP);
1333 b->object->flag = b->flag_legacy;
1334 b->object->flag |= flag;
1338 void BKE_scene_base_select(Scene *sce, BaseLegacy *selbase)
1340 selbase->flag_legacy |= SELECT;
1341 selbase->object->flag = selbase->flag_legacy;
1343 sce->basact = selbase;
1346 /* checks for cycle, returns 1 if it's all OK */
1347 bool BKE_scene_validate_setscene(Main *bmain, Scene *sce)
1352 if (sce->set == NULL) return true;
1353 totscene = BLI_listbase_count(&bmain->scene);
1355 for (a = 0, sce_iter = sce; sce_iter->set; sce_iter = sce_iter->set, a++) {
1356 /* more iterations than scenes means we have a cycle */
1358 /* the tested scene gets zero'ed, that's typically current scene */
1367 /* This function is needed to cope with fractional frames - including two Blender rendering features
1368 * mblur (motion blur that renders 'subframes' and blurs them together), and fields rendering.
1370 float BKE_scene_frame_get(const Scene *scene)
1372 return BKE_scene_frame_get_from_ctime(scene, scene->r.cfra);
1375 /* This function is used to obtain arbitrary fractional frames */
1376 float BKE_scene_frame_get_from_ctime(const Scene *scene, const float frame)
1378 float ctime = frame;
1379 ctime += scene->r.subframe;
1380 ctime *= scene->r.framelen;
1386 * Sets the frame int/float components.
1388 void BKE_scene_frame_set(struct Scene *scene, double cfra)
1391 scene->r.subframe = modf(cfra, &intpart);
1392 scene->r.cfra = (int)intpart;
1395 /* That's like really a bummer, because currently animation data for armatures
1396 * might want to use pose, and pose might be missing on the object.
1397 * This happens when changing visible layers, which leads to situations when
1398 * pose is missing or marked for recalc, animation will change it and then
1399 * object update will restore the pose.
1401 * This could be solved by the new dependency graph, but for until then we'll
1402 * do an extra pass on the objects to ensure it's all fine.
1404 #define POSE_ANIMATION_WORKAROUND
1406 #ifdef POSE_ANIMATION_WORKAROUND
1407 static void scene_armature_depsgraph_workaround(Main *bmain)
1410 if (BLI_listbase_is_empty(&bmain->armature) || !DEG_id_type_tagged(bmain, ID_OB)) {
1413 for (ob = bmain->object.first; ob; ob = ob->id.next) {
1414 if (ob->type == OB_ARMATURE && ob->adt && ob->adt->recalc & ADT_RECALC_ANIM) {
1415 if (ob->pose == NULL || (ob->pose->flag & POSE_RECALC)) {
1416 BKE_pose_rebuild(ob, ob->data);
1423 static bool check_rendered_viewport_visible(Main *bmain)
1425 wmWindowManager *wm = bmain->wm.first;
1427 for (window = wm->windows.first; window != NULL; window = window->next) {
1428 bScreen *screen = window->screen;
1429 Scene *scene = screen->scene;
1431 RenderEngineType *type = RE_engines_find(scene->r.engine);
1432 if ((type->draw_engine != NULL) || (type->render_to_view == NULL)) {
1435 const bool use_legacy = (type->flag & RE_USE_LEGACY_PIPELINE) != 0;
1436 for (area = screen->areabase.first; area != NULL; area = area->next) {
1437 View3D *v3d = area->spacedata.first;
1438 if (area->spacetype != SPACE_VIEW3D) {
1441 if (v3d->drawtype == OB_RENDER || !use_legacy) {
1449 static void prepare_mesh_for_viewport_render(Main *bmain, Scene *scene)
1451 /* This is needed to prepare mesh to be used by the render
1452 * engine from the viewport rendering. We do loading here
1453 * so all the objects which shares the same mesh datablock
1454 * are nicely tagged for update and updated.
1456 * This makes it so viewport render engine doesn't need to
1457 * call loading of the edit data for the mesh objects.
1460 Object *obedit = scene->obedit;
1462 Mesh *mesh = obedit->data;
1463 if ((obedit->type == OB_MESH) &&
1464 ((obedit->id.tag & LIB_TAG_ID_RECALC_ALL) ||
1465 (mesh->id.tag & LIB_TAG_ID_RECALC_ALL)))
1467 if (check_rendered_viewport_visible(bmain)) {
1468 BMesh *bm = mesh->edit_btmesh->bm;
1469 BM_mesh_bm_to_me(bm, mesh, (&(struct BMeshToMeshParams){0}));
1470 DEG_id_tag_update(&mesh->id, 0);
1476 void BKE_scene_update_tagged(EvaluationContext *eval_ctx, Main *bmain, Scene *scene)
1480 /* keep this first */
1481 BLI_callback_exec(bmain, &scene->id, BLI_CB_EVT_SCENE_UPDATE_PRE);
1483 /* (re-)build dependency graph if needed */
1484 for (sce_iter = scene; sce_iter; sce_iter = sce_iter->set) {
1485 DEG_scene_relations_update(bmain, sce_iter);
1486 /* Uncomment this to check if graph was properly tagged for update. */
1488 DEG_scene_relations_validate(bmain, sce_iter);
1492 /* flush editing data if needed */
1493 prepare_mesh_for_viewport_render(bmain, scene);
1495 /* flush recalc flags to dependencies */
1496 DEG_ids_flush_tagged(bmain);
1498 /* removed calls to quick_cache, see pointcache.c */
1500 /* clear "LIB_TAG_DOIT" flag from all materials, to prevent infinite recursion problems later
1501 * when trying to find materials with drivers that need evaluating [#32017]
1503 BKE_main_id_tag_idcode(bmain, ID_MA, LIB_TAG_DOIT, false);
1504 BKE_main_id_tag_idcode(bmain, ID_LA, LIB_TAG_DOIT, false);
1506 /* update all objects: drivers, matrices, displists, etc. flags set
1507 * by depgraph or manual, no layer check here, gets correct flushed
1509 * in the future this should handle updates for all datablocks, not
1510 * only objects and scenes. - brecht */
1511 DEG_evaluate_on_refresh(eval_ctx, scene->depsgraph, scene);
1512 /* TODO(sergey): This is to beocme a node in new depsgraph. */
1513 BKE_mask_update_scene(bmain, scene);
1515 /* update sound system animation (TODO, move to depsgraph) */
1516 BKE_sound_update_scene(bmain, scene);
1518 /* extra call here to recalc scene animation (for sequencer) */
1520 AnimData *adt = BKE_animdata_from_id(&scene->id);
1521 float ctime = BKE_scene_frame_get(scene);
1523 if (adt && (adt->recalc & ADT_RECALC_ANIM))
1524 BKE_animsys_evaluate_animdata(scene, &scene->id, adt, ctime, 0);
1527 /* notify editors and python about recalc */
1528 BLI_callback_exec(bmain, &scene->id, BLI_CB_EVT_SCENE_UPDATE_POST);
1530 /* Inform editors about possible changes. */
1531 DEG_ids_check_recalc(bmain, scene, false);
1533 /* clear recalc flags */
1534 DEG_ids_clear_recalc(bmain);
1537 /* applies changes right away, does all sets too */
1538 void BKE_scene_update_for_newframe(EvaluationContext *eval_ctx, Main *bmain, Scene *sce)
1540 float ctime = BKE_scene_frame_get(sce);
1543 DEG_editors_update_pre(bmain, sce, true);
1545 /* keep this first */
1546 BLI_callback_exec(bmain, &sce->id, BLI_CB_EVT_FRAME_CHANGE_PRE);
1547 BLI_callback_exec(bmain, &sce->id, BLI_CB_EVT_SCENE_UPDATE_PRE);
1549 /* update animated image textures for particles, modifiers, gpu, etc,
1550 * call this at the start so modifiers with textures don't lag 1 frame */
1551 BKE_image_update_frame(bmain, sce->r.cfra);
1553 BKE_sound_set_cfra(sce->r.cfra);
1555 /* clear animation overrides */
1558 for (sce_iter = sce; sce_iter; sce_iter = sce_iter->set)
1559 DEG_scene_relations_update(bmain, sce_iter);
1561 BKE_mask_evaluate_all_masks(bmain, ctime, true);
1563 /* Update animated cache files for modifiers. */
1564 BKE_cachefile_update_frame(bmain, sce, ctime, (((double)sce->r.frs_sec) / (double)sce->r.frs_sec_base));
1566 #ifdef POSE_ANIMATION_WORKAROUND
1567 scene_armature_depsgraph_workaround(bmain);
1570 /* clear "LIB_TAG_DOIT" flag from all materials, to prevent infinite recursion problems later
1571 * when trying to find materials with drivers that need evaluating [#32017]
1573 BKE_main_id_tag_idcode(bmain, ID_MA, LIB_TAG_DOIT, false);
1574 BKE_main_id_tag_idcode(bmain, ID_LA, LIB_TAG_DOIT, false);
1576 /* BKE_object_handle_update() on all objects, groups and sets */
1577 DEG_evaluate_on_framechange(eval_ctx, bmain, sce->depsgraph, ctime);
1579 /* update sound system animation (TODO, move to depsgraph) */
1580 BKE_sound_update_scene(bmain, sce);
1582 /* notify editors and python about recalc */
1583 BLI_callback_exec(bmain, &sce->id, BLI_CB_EVT_SCENE_UPDATE_POST);
1584 BLI_callback_exec(bmain, &sce->id, BLI_CB_EVT_FRAME_CHANGE_POST);
1586 /* Inform editors about possible changes. */
1587 DEG_ids_check_recalc(bmain, sce, true);
1589 /* clear recalc flags */
1590 DEG_ids_clear_recalc(bmain);
1593 /* return default layer, also used to patch old files */
1594 SceneRenderLayer *BKE_scene_add_render_layer(Scene *sce, const char *name)
1596 SceneRenderLayer *srl;
1599 name = DATA_("RenderLayer");
1601 srl = MEM_callocN(sizeof(SceneRenderLayer), "new render layer");
1602 BLI_strncpy(srl->name, name, sizeof(srl->name));
1603 BLI_uniquename(&sce->r.layers, srl, DATA_("RenderLayer"), '.', offsetof(SceneRenderLayer, name), sizeof(srl->name));
1604 BLI_addtail(&sce->r.layers, srl);
1606 /* note, this is also in render, pipeline.c, to make layer when scenedata doesnt have it */
1607 srl->lay = (1 << 20) - 1;
1608 srl->layflag = 0x7FFF; /* solid ztra halo edge strand */
1609 srl->passflag = SCE_PASS_COMBINED | SCE_PASS_Z;
1610 srl->pass_alpha_threshold = 0.5f;
1611 BKE_freestyle_config_init(&srl->freestyleConfig);
1616 bool BKE_scene_remove_render_layer(Main *bmain, Scene *scene, SceneRenderLayer *srl)
1618 const int act = BLI_findindex(&scene->r.layers, srl);
1624 else if ( (scene->r.layers.first == scene->r.layers.last) &&
1625 (scene->r.layers.first == srl))
1627 /* ensure 1 layer is kept */
1631 BKE_freestyle_config_free(&srl->freestyleConfig);
1634 IDP_FreeProperty(srl->prop);
1635 MEM_freeN(srl->prop);
1638 BLI_remlink(&scene->r.layers, srl);
1641 scene->r.actlay = 0;
1643 for (sce = bmain->scene.first; sce; sce = sce->id.next) {
1644 if (sce->nodetree) {
1645 BKE_nodetree_remove_layer_n(sce->nodetree, scene, act);
1652 /* return default view */
1653 SceneRenderView *BKE_scene_add_render_view(Scene *sce, const char *name)
1655 SceneRenderView *srv;
1658 name = DATA_("RenderView");
1660 srv = MEM_callocN(sizeof(SceneRenderView), "new render view");
1661 BLI_strncpy(srv->name, name, sizeof(srv->name));
1662 BLI_uniquename(&sce->r.views, srv, DATA_("RenderView"), '.', offsetof(SceneRenderView, name), sizeof(srv->name));
1663 BLI_addtail(&sce->r.views, srv);
1668 bool BKE_scene_remove_render_view(Scene *scene, SceneRenderView *srv)
1670 const int act = BLI_findindex(&scene->r.views, srv);
1675 else if (scene->r.views.first == scene->r.views.last) {
1676 /* ensure 1 view is kept */
1680 BLI_remlink(&scene->r.views, srv);
1683 scene->r.actview = 0;
1688 /* render simplification */
1690 int get_render_subsurf_level(const RenderData *r, int lvl, bool for_render)
1692 if (r->mode & R_SIMPLIFY) {
1694 return min_ii(r->simplify_subsurf_render, lvl);
1696 return min_ii(r->simplify_subsurf, lvl);
1703 int get_render_child_particle_number(const RenderData *r, int num, bool for_render)
1705 if (r->mode & R_SIMPLIFY) {
1707 return (int)(r->simplify_particles_render * num);
1709 return (int)(r->simplify_particles * num);
1716 int get_render_shadow_samples(const RenderData *r, int samples)
1718 if ((r->mode & R_SIMPLIFY) && samples > 0)
1719 return min_ii(r->simplify_shadowsamples, samples);
1724 float get_render_aosss_error(const RenderData *r, float error)
1726 if (r->mode & R_SIMPLIFY)
1727 return ((1.0f - r->simplify_aosss) * 10.0f + 1.0f) * error;
1733 * Helper function for the SETLOOPER macro
1735 * It iterates over the bases of the active layer and then the bases
1736 * of the active layer of the background (set) scenes recursively.
1738 Base *_setlooper_base_step(Scene **sce_iter, Base *base)
1740 if (base && base->next) {
1741 /* common case, step to the next */
1744 else if (base == NULL) {
1745 /* first time looping, return the scenes first base */
1747 /* for the first loop we should get the layer from context */
1748 SceneLayer *sl = BKE_scene_layer_context_active((*sce_iter));
1750 if (sl->object_bases.first) {
1751 return (Base *)sl->object_bases.first;
1753 /* no base on this scene layer */
1758 /* reached the end, get the next base in the set */
1759 while ((*sce_iter = (*sce_iter)->set)) {
1760 SceneLayer *sl = BKE_scene_layer_render_active((*sce_iter));
1761 base = (Base *)sl->object_bases.first;
1772 bool BKE_scene_use_new_shading_nodes(const Scene *scene)
1774 const RenderEngineType *type = RE_engines_find(scene->r.engine);
1775 return (type && type->flag & RE_USE_SHADING_NODES);
1778 bool BKE_scene_use_shading_nodes_custom(Scene *scene)
1780 RenderEngineType *type = RE_engines_find(scene->r.engine);
1781 return (type && type->flag & RE_USE_SHADING_NODES_CUSTOM);
1784 bool BKE_scene_use_world_space_shading(Scene *scene)
1786 const RenderEngineType *type = RE_engines_find(scene->r.engine);
1787 return ((scene->r.mode & R_USE_WS_SHADING) ||
1788 (type && (type->flag & RE_USE_SHADING_NODES)));
1791 bool BKE_scene_use_spherical_stereo(Scene *scene)
1793 RenderEngineType *type = RE_engines_find(scene->r.engine);
1794 return (type && type->flag & RE_USE_SPHERICAL_STEREO);
1797 bool BKE_scene_uses_blender_internal(const Scene *scene)
1799 return STREQ(scene->r.engine, RE_engine_id_BLENDER_RENDER);
1802 bool BKE_scene_uses_blender_game(const Scene *scene)
1804 return STREQ(scene->r.engine, RE_engine_id_BLENDER_GAME);
1807 bool BKE_scene_uses_blender_eevee(const Scene *scene)
1809 return STREQ(scene->r.engine, RE_engine_id_BLENDER_EEVEE);
1812 void BKE_scene_base_flag_to_objects(SceneLayer *sl)
1814 Base *base = sl->object_bases.first;
1817 BKE_scene_object_base_flag_sync_from_base(base);
1822 void BKE_scene_base_flag_sync_from_base(BaseLegacy *base)
1824 BKE_scene_object_base_flag_sync_from_base(base);
1827 void BKE_scene_base_flag_sync_from_object(BaseLegacy *base)
1829 BKE_scene_object_base_flag_sync_from_object(base);
1832 void BKE_scene_object_base_flag_sync_from_base(Base *base)
1834 Object *ob = base->object;
1836 /* keep the object only flags untouched */
1837 int flag = ob->flag & OB_FROMGROUP;
1839 ob->flag = base->flag;
1842 if ((base->flag & BASE_SELECTED) != 0) {
1846 ob->flag &= ~SELECT;
1850 void BKE_scene_object_base_flag_sync_from_object(Base *base)
1852 Object *ob = base->object;
1853 base->flag = ob->flag;
1855 if ((ob->flag & SELECT) != 0) {
1856 base->flag |= BASE_SELECTED;
1857 BLI_assert((base->flag & BASE_SELECTABLED) != 0);
1860 base->flag &= ~BASE_SELECTED;
1864 void BKE_scene_disable_color_management(Scene *scene)
1866 ColorManagedDisplaySettings *display_settings = &scene->display_settings;
1867 ColorManagedViewSettings *view_settings = &scene->view_settings;
1869 const char *none_display_name;
1871 none_display_name = IMB_colormanagement_display_get_none_name();
1873 BLI_strncpy(display_settings->display_device, none_display_name, sizeof(display_settings->display_device));
1875 view = IMB_colormanagement_view_get_default_name(display_settings->display_device);
1878 BLI_strncpy(view_settings->view_transform, view, sizeof(view_settings->view_transform));
1882 bool BKE_scene_check_color_management_enabled(const Scene *scene)
1884 return !STREQ(scene->display_settings.display_device, "None");
1887 bool BKE_scene_check_rigidbody_active(const Scene *scene)
1889 return scene && scene->rigidbody_world && scene->rigidbody_world->group && !(scene->rigidbody_world->flag & RBW_FLAG_MUTED);
1892 int BKE_render_num_threads(const RenderData *rd)
1896 /* override set from command line? */
1897 threads = BLI_system_num_threads_override_get();
1902 /* fixed number of threads specified in scene? */
1903 if (rd->mode & R_FIXED_THREADS)
1904 threads = rd->threads;
1906 threads = BLI_system_thread_count();
1908 return max_ii(threads, 1);
1911 int BKE_scene_num_threads(const Scene *scene)
1913 return BKE_render_num_threads(&scene->r);
1916 /* Apply the needed correction factor to value, based on unit_type (only length-related are affected currently)
1917 * and unit->scale_length.
1919 double BKE_scene_unit_scale(const UnitSettings *unit, const int unit_type, double value)
1921 if (unit->system == USER_UNIT_NONE) {
1922 /* Never apply scale_length when not using a unit setting! */
1926 switch (unit_type) {
1928 return value * (double)unit->scale_length;
1930 return value * pow(unit->scale_length, 2);
1932 return value * pow(unit->scale_length, 3);
1934 return value * pow(unit->scale_length, 3);
1935 case B_UNIT_CAMERA: /* *Do not* use scene's unit scale for camera focal lens! See T42026. */
1941 /******************** multiview *************************/
1943 int BKE_scene_multiview_num_views_get(const RenderData *rd)
1945 SceneRenderView *srv;
1948 if ((rd->scemode & R_MULTIVIEW) == 0)
1951 if (rd->views_format == SCE_VIEWS_FORMAT_STEREO_3D) {
1952 srv = BLI_findstring(&rd->views, STEREO_LEFT_NAME, offsetof(SceneRenderView, name));
1953 if ((srv && srv->viewflag & SCE_VIEW_DISABLE) == 0) {
1957 srv = BLI_findstring(&rd->views, STEREO_RIGHT_NAME, offsetof(SceneRenderView, name));
1958 if ((srv && srv->viewflag & SCE_VIEW_DISABLE) == 0) {
1963 for (srv = rd->views.first; srv; srv = srv->next) {
1964 if ((srv->viewflag & SCE_VIEW_DISABLE) == 0) {
1972 bool BKE_scene_multiview_is_stereo3d(const RenderData *rd)
1974 SceneRenderView *srv[2];
1976 if ((rd->scemode & R_MULTIVIEW) == 0)
1979 srv[0] = (SceneRenderView *)BLI_findstring(&rd->views, STEREO_LEFT_NAME, offsetof(SceneRenderView, name));
1980 srv[1] = (SceneRenderView *)BLI_findstring(&rd->views, STEREO_RIGHT_NAME, offsetof(SceneRenderView, name));
1982 return (srv[0] && ((srv[0]->viewflag & SCE_VIEW_DISABLE) == 0) &&
1983 srv[1] && ((srv[1]->viewflag & SCE_VIEW_DISABLE) == 0));
1986 /* return whether to render this SceneRenderView */
1987 bool BKE_scene_multiview_is_render_view_active(const RenderData *rd, const SceneRenderView *srv)
1992 if ((rd->scemode & R_MULTIVIEW) == 0)
1995 if ((srv->viewflag & SCE_VIEW_DISABLE))
1998 if (rd->views_format == SCE_VIEWS_FORMAT_MULTIVIEW)
2001 /* SCE_VIEWS_SETUP_BASIC */
2002 if (STREQ(srv->name, STEREO_LEFT_NAME) ||
2003 STREQ(srv->name, STEREO_RIGHT_NAME))
2011 /* return true if viewname is the first or if the name is NULL or not found */
2012 bool BKE_scene_multiview_is_render_view_first(const RenderData *rd, const char *viewname)
2014 SceneRenderView *srv;
2016 if ((rd->scemode & R_MULTIVIEW) == 0)
2019 if ((!viewname) || (!viewname[0]))
2022 for (srv = rd->views.first; srv; srv = srv->next) {
2023 if (BKE_scene_multiview_is_render_view_active(rd, srv)) {
2024 return STREQ(viewname, srv->name);
2031 /* return true if viewname is the last or if the name is NULL or not found */
2032 bool BKE_scene_multiview_is_render_view_last(const RenderData *rd, const char *viewname)
2034 SceneRenderView *srv;
2036 if ((rd->scemode & R_MULTIVIEW) == 0)
2039 if ((!viewname) || (!viewname[0]))
2042 for (srv = rd->views.last; srv; srv = srv->prev) {
2043 if (BKE_scene_multiview_is_render_view_active(rd, srv)) {
2044 return STREQ(viewname, srv->name);
2051 SceneRenderView *BKE_scene_multiview_render_view_findindex(const RenderData *rd, const int view_id)
2053 SceneRenderView *srv;
2056 if ((rd->scemode & R_MULTIVIEW) == 0)
2059 for (srv = rd->views.first, nr = 0; srv; srv = srv->next) {
2060 if (BKE_scene_multiview_is_render_view_active(rd, srv)) {
2061 if (nr++ == view_id)
2068 const char *BKE_scene_multiview_render_view_name_get(const RenderData *rd, const int view_id)
2070 SceneRenderView *srv = BKE_scene_multiview_render_view_findindex(rd, view_id);
2078 int BKE_scene_multiview_view_id_get(const RenderData *rd, const char *viewname)
2080 SceneRenderView *srv;
2083 if ((!rd) || ((rd->scemode & R_MULTIVIEW) == 0))
2086 if ((!viewname) || (!viewname[0]))
2089 for (srv = rd->views.first, nr = 0; srv; srv = srv->next) {
2090 if (BKE_scene_multiview_is_render_view_active(rd, srv)) {
2091 if (STREQ(viewname, srv->name)) {
2103 void BKE_scene_multiview_filepath_get(
2104 SceneRenderView *srv, const char *filepath,
2107 BLI_strncpy(r_filepath, filepath, FILE_MAX);
2108 BLI_path_suffix(r_filepath, FILE_MAX, srv->suffix, "");
2112 * When multiview is not used the filepath is as usual (e.g., ``Image.jpg``).
2113 * When multiview is on, even if only one view is enabled the view is incorporated
2114 * into the file name (e.g., ``Image_L.jpg``). That allows for the user to re-render
2117 void BKE_scene_multiview_view_filepath_get(
2118 const RenderData *rd, const char *filepath, const char *viewname,
2121 SceneRenderView *srv;
2122 char suffix[FILE_MAX];
2124 srv = BLI_findstring(&rd->views, viewname, offsetof(SceneRenderView, name));
2126 BLI_strncpy(suffix, srv->suffix, sizeof(suffix));
2128 BLI_strncpy(suffix, viewname, sizeof(suffix));
2130 BLI_strncpy(r_filepath, filepath, FILE_MAX);
2131 BLI_path_suffix(r_filepath, FILE_MAX, suffix, "");
2134 const char *BKE_scene_multiview_view_suffix_get(const RenderData *rd, const char *viewname)
2136 SceneRenderView *srv;
2138 if ((viewname == NULL) || (viewname[0] == '\0'))
2141 srv = BLI_findstring(&rd->views, viewname, offsetof(SceneRenderView, name));
2148 const char *BKE_scene_multiview_view_id_suffix_get(const RenderData *rd, const int view_id)
2150 if ((rd->scemode & R_MULTIVIEW) == 0) {
2154 const char *viewname = BKE_scene_multiview_render_view_name_get(rd, view_id);
2155 return BKE_scene_multiview_view_suffix_get(rd, viewname);
2159 void BKE_scene_multiview_view_prefix_get(Scene *scene, const char *name, char *rprefix, const char **rext)
2161 SceneRenderView *srv;
2163 const char *suf_act;
2164 const char delims[] = {'.', '\0'};
2168 /* begin of extension */
2169 index_act = BLI_str_rpartition(name, delims, rext, &suf_act);
2172 BLI_assert(index_act > 0);
2173 UNUSED_VARS_NDEBUG(index_act);
2175 for (srv = scene->r.views.first; srv; srv = srv->next) {
2176 if (BKE_scene_multiview_is_render_view_active(&scene->r, srv)) {
2177 size_t len = strlen(srv->suffix);
2178 if (strlen(*rext) >= len && STREQLEN(*rext - len, srv->suffix, len)) {
2179 BLI_strncpy(rprefix, name, strlen(name) - strlen(*rext) - len + 1);
2186 void BKE_scene_multiview_videos_dimensions_get(
2187 const RenderData *rd, const size_t width, const size_t height,
2188 size_t *r_width, size_t *r_height)
2190 if ((rd->scemode & R_MULTIVIEW) &&
2191 rd->im_format.views_format == R_IMF_VIEWS_STEREO_3D)
2193 IMB_stereo3d_write_dimensions(
2194 rd->im_format.stereo3d_format.display_mode,
2195 (rd->im_format.stereo3d_format.flag & S3D_SQUEEZED_FRAME) != 0,
2205 int BKE_scene_multiview_num_videos_get(const RenderData *rd)
2207 if (BKE_imtype_is_movie(rd->im_format.imtype) == false)
2210 if ((rd->scemode & R_MULTIVIEW) == 0)
2213 if (rd->im_format.views_format == R_IMF_VIEWS_STEREO_3D) {
2217 /* R_IMF_VIEWS_INDIVIDUAL */
2218 return BKE_scene_multiview_num_views_get(rd);