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

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSergey Sharybin <sergey.vfx@gmail.com>2019-06-11 11:55:13 +0300
committerSergey Sharybin <sergey.vfx@gmail.com>2019-06-11 16:11:07 +0300
commit0767f95a63959e156c302520db7fbf480159abe0 (patch)
treee4f416474ae320156e9e35b1d25d2b8300ad628e /source/blender/blenkernel/intern
parent3a6f6c87e051edd3e98c92428980a52bafd7abf0 (diff)
Sound: Fix queries of sound info
A lot of areas were querying sound information directly using audio handle which does not exist on an original sound IDs. This change basically makes it so it's possible to query information about given sound ID, without worrying about whether it's loaded or not: if it is needed to load it first it happens automatically (no automatically-opened handles are left behind though). While this seems a bit extreme to open files on such queries it is still better than the old situation when all sound handles were opened on file load, no matter if it's needed or not. Besides, none of the changed code paths are performance critical, just handful of tools. Fixes T65696: Sequencer fails to create a new sound sequence strip via Python Fixes T65656: Audio strip - SHIFT K crashes Blender Reviewers: brecht Reviewed By: brecht Subscribers: ISS Maniphest Tasks: T65696, T65656 Differential Revision: https://developer.blender.org/D5061
Diffstat (limited to 'source/blender/blenkernel/intern')
-rw-r--r--source/blender/blenkernel/intern/nla.c14
-rw-r--r--source/blender/blenkernel/intern/scene.c2
-rw-r--r--source/blender/blenkernel/intern/sequencer.c30
-rw-r--r--source/blender/blenkernel/intern/sound.c120
4 files changed, 98 insertions, 68 deletions
diff --git a/source/blender/blenkernel/intern/nla.c b/source/blender/blenkernel/intern/nla.c
index 15e53e12ece..d7546e5db0c 100644
--- a/source/blender/blenkernel/intern/nla.c
+++ b/source/blender/blenkernel/intern/nla.c
@@ -51,10 +51,7 @@
#include "BKE_library.h"
#include "BKE_main.h"
#include "BKE_nla.h"
-
-#ifdef WITH_AUDASPACE
-# include <AUD_Special.h>
-#endif
+#include "BKE_sound.h"
#include "RNA_access.h"
#include "nla_private.h"
@@ -392,7 +389,7 @@ NlaStrip *BKE_nlastack_add_strip(AnimData *adt, bAction *act)
}
/* Add a NLA Strip referencing the given speaker's sound */
-NlaStrip *BKE_nla_add_soundstrip(Scene *scene, Speaker *speaker)
+NlaStrip *BKE_nla_add_soundstrip(Main *bmain, Scene *scene, Speaker *speaker)
{
NlaStrip *strip = MEM_callocN(sizeof(NlaStrip), "NlaSoundStrip");
@@ -401,9 +398,10 @@ NlaStrip *BKE_nla_add_soundstrip(Scene *scene, Speaker *speaker)
*/
#ifdef WITH_AUDASPACE
if (speaker->sound) {
- AUD_SoundInfo info = AUD_getInfo(speaker->sound->playback_handle);
-
- strip->end = (float)ceil((double)info.length * FPS);
+ SoundInfo info;
+ if (BKE_sound_info_get(bmain, speaker->sound, &info)) {
+ strip->end = (float)ceil((double)info.length * FPS);
+ }
}
else
#endif
diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c
index ef33cd7d137..7fb9b2f2281 100644
--- a/source/blender/blenkernel/intern/scene.c
+++ b/source/blender/blenkernel/intern/scene.c
@@ -1515,7 +1515,7 @@ static void scene_update_sound(Depsgraph *depsgraph, Main *bmain)
BKE_sound_seek_scene(bmain, scene);
}
if (recalc & ID_RECALC_AUDIO_FPS) {
- BKE_sound_update_fps(scene);
+ BKE_sound_update_fps(bmain, scene);
}
if (recalc & ID_RECALC_AUDIO_VOLUME) {
BKE_sound_set_scene_volume(scene, scene->audio.volume);
diff --git a/source/blender/blenkernel/intern/sequencer.c b/source/blender/blenkernel/intern/sequencer.c
index ac242e35b03..215f651811c 100644
--- a/source/blender/blenkernel/intern/sequencer.c
+++ b/source/blender/blenkernel/intern/sequencer.c
@@ -909,7 +909,7 @@ static void seq_multiview_name(Scene *scene,
}
/* note: caller should run BKE_sequence_calc(scene, seq) after */
-void BKE_sequence_reload_new_file(Scene *scene, Sequence *seq, const bool lock_range)
+void BKE_sequence_reload_new_file(Main *bmain, Scene *scene, Sequence *seq, const bool lock_range)
{
char path[FILE_MAX];
int prev_startdisp = 0, prev_enddisp = 0;
@@ -1050,7 +1050,7 @@ void BKE_sequence_reload_new_file(Scene *scene, Sequence *seq, const bool lock_r
if (!seq->sound) {
return;
}
- seq->len = ceil((double)AUD_getInfo(seq->sound->playback_handle).length * FPS);
+ seq->len = ceil((double)BKE_sound_get_length(bmain, seq->sound) * FPS);
seq->len -= seq->anim_startofs;
seq->len -= seq->anim_endofs;
if (seq->len < 0) {
@@ -4923,24 +4923,24 @@ bool BKE_sequence_base_shuffle_time(ListBase *seqbasep, Scene *evil_scene)
/* Unlike _update_sound_ funcs, these ones take info from audaspace to update sequence length! */
#ifdef WITH_AUDASPACE
-static bool sequencer_refresh_sound_length_recursive(Scene *scene, ListBase *seqbase)
+static bool sequencer_refresh_sound_length_recursive(Main *bmain, Scene *scene, ListBase *seqbase)
{
Sequence *seq;
bool changed = false;
for (seq = seqbase->first; seq; seq = seq->next) {
if (seq->type == SEQ_TYPE_META) {
- if (sequencer_refresh_sound_length_recursive(scene, &seq->seqbase)) {
+ if (sequencer_refresh_sound_length_recursive(bmain, scene, &seq->seqbase)) {
BKE_sequence_calc(scene, seq);
changed = true;
}
}
else if (seq->type == SEQ_TYPE_SOUND_RAM) {
- AUD_SoundInfo info = AUD_getInfo(seq->sound->playback_handle);
+ const float length = BKE_sound_get_length(bmain, seq->sound);
int old = seq->len;
float fac;
- seq->len = (int)ceil((double)info.length * FPS);
+ seq->len = (int)ceil((double)length * FPS);
fac = (float)seq->len / (float)old;
old = seq->startofs;
seq->startofs *= fac;
@@ -4955,11 +4955,11 @@ static bool sequencer_refresh_sound_length_recursive(Scene *scene, ListBase *seq
}
#endif
-void BKE_sequencer_refresh_sound_length(Scene *scene)
+void BKE_sequencer_refresh_sound_length(Main *bmain, Scene *scene)
{
#ifdef WITH_AUDASPACE
if (scene->ed) {
- sequencer_refresh_sound_length_recursive(scene, &scene->ed->seqbase);
+ sequencer_refresh_sound_length_recursive(bmain, scene, &scene->ed->seqbase);
}
#else
(void)scene;
@@ -5562,17 +5562,13 @@ Sequence *BKE_sequencer_add_sound_strip(bContext *C, ListBase *seqbasep, SeqLoad
sound = BKE_sound_new_file(bmain, seq_load->path); /* handles relative paths */
- /* Load the original sound, so we can access number of channels and length information.
- * We free the sound handle on the original bSound datablock before existing this function, it is
- * to be allocated on an evaluated version after this. */
- BKE_sound_load_audio(bmain, sound);
- AUD_SoundInfo info = AUD_getInfo(sound->playback_handle);
- if (sound->playback_handle == NULL) {
+ SoundInfo info;
+ if (!BKE_sound_info_get(bmain, sound, &info)) {
BKE_id_free(bmain, sound);
return NULL;
}
- if (info.specs.channels == AUD_CHANNELS_INVALID) {
+ if (info.specs.channels == SOUND_CHANNELS_INVALID) {
BKE_id_free(bmain, sound);
return NULL;
}
@@ -5602,9 +5598,7 @@ Sequence *BKE_sequencer_add_sound_strip(bContext *C, ListBase *seqbasep, SeqLoad
seq_load_apply(bmain, scene, seq, seq_load);
- BKE_sound_free_audio(sound);
-
- /* TODO(sergey): Shall we tag here or in the oeprator? */
+ /* TODO(sergey): Shall we tag here or in the operator? */
DEG_relations_tag_update(bmain);
return seq;
diff --git a/source/blender/blenkernel/intern/sound.c b/source/blender/blenkernel/intern/sound.c
index 029fea5c300..927a45accca 100644
--- a/source/blender/blenkernel/intern/sound.c
+++ b/source/blender/blenkernel/intern/sound.c
@@ -145,6 +145,24 @@ bSound *BKE_sound_new_file_exists(Main *bmain, const char *filepath)
return BKE_sound_new_file_exists_ex(bmain, filepath, NULL);
}
+static void sound_free_audio(bSound *sound)
+{
+#ifdef WITH_AUDASPACE
+ if (sound->handle) {
+ AUD_Sound_free(sound->handle);
+ sound->handle = NULL;
+ sound->playback_handle = NULL;
+ }
+
+ if (sound->cache) {
+ AUD_Sound_free(sound->cache);
+ sound->cache = NULL;
+ }
+#else
+ UNUSED_VARS(sound);
+#endif /* WITH_AUDASPACE */
+}
+
/** Free (or release) any data used by this sound (does not free the sound itself). */
void BKE_sound_free(bSound *sound)
{
@@ -155,7 +173,7 @@ void BKE_sound_free(bSound *sound)
sound->packedfile = NULL;
}
- BKE_sound_free_audio(sound);
+ sound_free_audio(sound);
BKE_sound_free_waveform(sound);
if (sound->spinlock) {
@@ -165,24 +183,6 @@ void BKE_sound_free(bSound *sound)
}
}
-void BKE_sound_free_audio(bSound *sound)
-{
-#ifdef WITH_AUDASPACE
- if (sound->handle) {
- AUD_Sound_free(sound->handle);
- sound->handle = NULL;
- sound->playback_handle = NULL;
- }
-
- if (sound->cache) {
- AUD_Sound_free(sound->cache);
- sound->cache = NULL;
- }
-#else
- UNUSED_VARS(sound);
-#endif /* WITH_AUDASPACE */
-}
-
/**
* Only copy internal data of Sound ID from source
* to already allocated/initialized destination.
@@ -412,13 +412,7 @@ void BKE_sound_delete_cache(bSound *sound)
}
}
-void BKE_sound_load(Main *bmain, bSound *sound)
-{
- sound_verify_evaluated_id(&sound->id);
- BKE_sound_load_audio(bmain, sound);
-}
-
-void BKE_sound_load_audio(Main *bmain, bSound *sound)
+static void sound_load_audio(Main *bmain, bSound *sound)
{
if (sound->cache) {
@@ -492,6 +486,12 @@ void BKE_sound_load_audio(Main *bmain, bSound *sound)
}
}
+void BKE_sound_load(Main *bmain, bSound *sound)
+{
+ sound_verify_evaluated_id(&sound->id);
+ sound_load_audio(bmain, sound);
+}
+
AUD_Device *BKE_sound_mixdown(Scene *scene, AUD_DeviceSpecs specs, int start, float volume)
{
sound_verify_evaluated_id(&scene->id);
@@ -560,7 +560,7 @@ void BKE_sound_mute_scene(Scene *scene, int muted)
}
}
-void BKE_sound_update_fps(Scene *scene)
+void BKE_sound_update_fps(Main *bmain, Scene *scene)
{
sound_verify_evaluated_id(&scene->id);
@@ -568,7 +568,7 @@ void BKE_sound_update_fps(Scene *scene)
AUD_Sequence_setFPS(scene->sound_scene, FPS);
}
- BKE_sequencer_refresh_sound_length(scene);
+ BKE_sequencer_refresh_sound_length(bmain, scene);
}
void BKE_sound_update_scene_listener(Scene *scene)
@@ -895,11 +895,15 @@ void BKE_sound_free_waveform(bSound *sound)
sound->tags &= ~SOUND_TAGS_WAVEFORM_NO_RELOAD;
}
-/* TODO(sergey): Consider mamakinging this function fully autonomous, as in, not require having
- * an existing playback handle. That would make it easy to read waveforms, which doesn't seem to
- * be affected by evaluated scene (waveworm comes from file). */
-void BKE_sound_read_waveform(bSound *sound, short *stop)
+void BKE_sound_read_waveform(Main *bmain, bSound *sound, short *stop)
{
+ bool need_close_audio_handles = false;
+ if (sound->playback_handle == NULL) {
+ /* TOOD(sergey): Make it fully independent audio handle. */
+ sound_load_audio(bmain, sound);
+ need_close_audio_handles = true;
+ }
+
AUD_SoundInfo info = AUD_getInfo(sound->playback_handle);
SoundWaveform *waveform = MEM_mallocN(sizeof(SoundWaveform), "SoundWaveform");
@@ -936,6 +940,10 @@ void BKE_sound_read_waveform(bSound *sound, short *stop)
sound->waveform = waveform;
sound->tags &= ~SOUND_TAGS_WAVEFORM_LOADING;
BLI_spin_unlock(sound->spinlock);
+
+ if (need_close_audio_handles) {
+ sound_free_audio(sound);
+ }
}
static void sound_update_base(Scene *scene, Object *object, void *new_set)
@@ -1047,12 +1055,16 @@ void *BKE_sound_get_factory(void *sound)
return ((bSound *)sound)->playback_handle;
}
-/* stupid wrapper because AUD_C-API.h includes Python.h which makesrna doesn't like */
-float BKE_sound_get_length(bSound *sound)
+float BKE_sound_get_length(Main *bmain, bSound *sound)
{
- sound_verify_evaluated_id(&sound->id);
- AUD_SoundInfo info = AUD_getInfo(sound->playback_handle);
-
+ if (sound->playback_handle != NULL) {
+ AUD_SoundInfo info = AUD_getInfo(sound->playback_handle);
+ return info.length;
+ }
+ SoundInfo info;
+ if (!BKE_sound_info_get(bmain, sound, &info)) {
+ return 0.0f;
+ }
return info.length;
}
@@ -1065,6 +1077,29 @@ char **BKE_sound_get_device_names(void)
return audio_device_names;
}
+static bool sound_info_from_playback_handle(void *playback_handle, SoundInfo *sound_info)
+{
+ if (playback_handle == NULL) {
+ return false;
+ }
+ AUD_SoundInfo info = AUD_getInfo(playback_handle);
+ sound_info->specs.channels = (eSoundChannels)info.specs.channels;
+ sound_info->length = info.length;
+ return true;
+}
+
+bool BKE_sound_info_get(struct Main *main, struct bSound *sound, SoundInfo *sound_info)
+{
+ if (sound->playback_handle != NULL) {
+ return sound_info_from_playback_handle(sound->playback_handle, sound_info);
+ }
+ /* TOOD(sergey): Make it fully independent audio handle. */
+ sound_load_audio(main, sound);
+ const bool result = sound_info_from_playback_handle(sound->playback_handle, sound_info);
+ sound_free_audio(sound);
+ return result;
+}
+
#else /* WITH_AUDASPACE */
# include "BLI_utildefines.h"
@@ -1162,7 +1197,7 @@ int BKE_sound_scene_playing(Scene *UNUSED(scene))
{
return -1;
}
-void BKE_sound_read_waveform(bSound *sound, short *stop)
+void BKE_sound_read_waveform(Main *bmain, bSound *sound, short *stop)
{
UNUSED_VARS(sound, stop);
}
@@ -1184,7 +1219,7 @@ void BKE_sound_update_scene_sound(void *UNUSED(handle), bSound *UNUSED(sound))
void BKE_sound_update_scene_listener(Scene *UNUSED(scene))
{
}
-void BKE_sound_update_fps(Scene *UNUSED(scene))
+void BKE_sound_update_fps(Main *UNUSED(bmain), Scene *UNUSED(scene))
{
}
void BKE_sound_set_scene_sound_volume(void *UNUSED(handle),
@@ -1203,7 +1238,7 @@ void BKE_sound_set_scene_sound_pitch(void *UNUSED(handle),
char UNUSED(animated))
{
}
-float BKE_sound_get_length(bSound *UNUSED(sound))
+float BKE_sound_get_length(struct Main *UNUSED(bmain), bSound *UNUSED(sound))
{
return 0;
}
@@ -1217,8 +1252,11 @@ void BKE_sound_free_waveform(bSound *UNUSED(sound))
{
}
-void BKE_sound_load_audio(Main *UNUSED(bmain), bSound *UNUSED(sound))
+bool BKE_sound_info_get(struct Main *UNUSED(main),
+ struct bSound *UNUSED(sound),
+ SoundInfo *UNUSED(sound_info))
{
+ return false;
}
#endif /* WITH_AUDASPACE */