[Solved] Error notifier when loading another new song...

I’m having some problems with certain notifiers, after loading another song, in my tool that runs with autostar.

I explain what happens:

  1. Charge a new song, song 1. The whole tool works correctly.
  2. Without closing the tool, charge another new song, song 2. The whole tool works correctly.Some notifier gives me a error like this:

error 1)

*** std::logic_error: 'trying to access a nil object of type 'class RenoiseSong'. the object is not or no longer available.'
*** stack traceback:
*** [C]: ?
*** [C]: in function '__index'
*** [string "do..."]:37: in function <[string "do..."]:35>
***.\tools/tool_04.lua:216: in function <.\tools/tool_04.lua:214>

This error is caused by this double function (WMP_CTRL_VEL is the id of a valuebox):

function 1, with error)

--Keyboard velocity
function wmp_velocity( song )
  song = renoise.song()
  local function notifier()
  --if ( song.transport.keyboard_velocity_enabled == true ) then
    vb.views['WMP_CTRL_VEL'].value = song.transport.keyboard_velocity
  --end
  end
  notifier()
  --song.transport.keyboard_velocity_enabled_observable:add_notifier( notifier )
  song.transport.keyboard_velocity_observable:add_notifier( notifier )
end
renoise.tool().app_new_document_observable:add_notifier( wmp_velocity )
---
function wmp_keyboard_velocity( song )
  song = renoise.song()
  song.transport.keyboard_velocity = vb.views['WMP_CTRL_VEL'].value
end

Line 216 is :vb.views[‘WMP_CTRL_VEL’].value = song.transport.keyboard_velocity

But this other double function is exactly the same and works correctly (WMP_CTRL_OCT is the id of a valuebox):

function 2, ok!)

--Keyboard octave
function wmp_octave( song )
  song = renoise.song()
  local function notifier()
    vb.views['WMP_CTRL_OCT'].value = song.transport.octave
  end
  notifier()
  song.transport.octave_observable:add_notifier( notifier )
end
renoise.tool().app_new_document_observable:add_notifier( wmp_octave )
---
function wmp_keyboard_octave( song )
  song = renoise.song()
  song.transport.octave = vb.views['WMP_CTRL_OCT'].value
end

What is missing here to solve the error?

It’s definitely caused by a notifier which is still firing in the context of the old song.
Generally speaking, it’s a good practice to remove notifiers once they have been attached, before attaching new ones.

Why it happens with one of your examples, and not the other, I can’t really tell. But in the case of a new song/document, this is kind of a special case…when a new document arrives, the old song/document is already gone…so you can’t remove the notifiers because their context is gone. I have often been caught in this trap myself.

The optimal approach is to attach to ‘app_release_document_observable’ and perform cleanup there, before the song/document is gone.
Alternatively, a more simple and brute-force approach would be to remove the notifiers as the new document arrives, but in a protected call:

local success,err = pcall(function() 
 -- here you are able to call non-existing methods and objects 
 -- if the code fails, you can handle the error yourself
end)

When using ‘remove_notifier’ you will need to pass a reference to the handling method. In your case, ‘wmp_velocity’ or ‘wmp_octave’
You can’t specify arguments for those methods, they are called anonymously. But then again, I’m not really sure why you have a ‘song’ argument for those methods, as it’s never actually being used?

Ooops!!

I think I understand what is happening here.For the first song I have defined " song = renoise.song()".When reading a new song XRNS, then song disappears.It is necessary to userenoise.song()

For example:

local function notifier()
  vb.views['WMP_CTRL_OCT'].value = renoise.song().transport.octave
end

All new songs are defined with renoise.song().Then, for any _observable and _notifier , always userenoise.song(), not “song” or “rns” or similar…

Ok! Solved!

Thanks Danoise!!! :slight_smile: