Maxon Developers Maxon Developers
    • Documentation
      • Cinema 4D Python API
      • Cinema 4D C++ API
      • Cineware API
      • ZBrush GoZ API
      • Code Examples on Github
    • Forum
    • Downloads
    • Support
      • Support Procedures
      • Registered Developer Program
      • Plugin IDs
      • Contact Us
    • Categories
      • Overview
      • News & Information
      • Cinema 4D SDK Support
      • Cineware SDK Support
      • ZBrush 4D SDK Support
      • Bugs
      • General Talk
    • Unread
    • Recent
    • Tags
    • Users
    • Login

    Dialog generates EVMSG_CHANGE messages

    Cinema 4D SDK
    2
    4
    599
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • P
      potashalum
      last edited by

      Hi,

      I am running into this problem that when create a dialog and keep its reference alive it generates an EVMSG_CHANGE message whenever I click in the viewport.

      I am using Cinema 4D R21.115 on windows.

      Here is a small test I created that does not generate any EVMSG_CHANGE messages.

      import c4d
      
      class CollectionManager(c4d.gui.GeDialog):
          def CoreMessage(self, kind, data):
              if kind == c4d.EVMSG_CHANGE:
                  print("Something changed")
              return super(CollectionManager, self).CoreMessage(kind, data)
      
      
      # Main function
      def main():
          dialog = CollectionManager()
          dialog.Open(c4d.DLG_TYPE_ASYNC, 1040130)
      
      # Execute main()
      if __name__=='__main__':
          main()
      

      Here is the same code with the only difference being that the variable dialog has been moved out of the function and into the global scope. This generates EVMSG_CHANGE messages whenever I click in the viewport/editor window.

      import c4d
      
      class CollectionManager(c4d.gui.GeDialog):
          def CoreMessage(self, kind, data):
              if kind == c4d.EVMSG_CHANGE:
                  print("Something changed")
              return super(CollectionManager, self).CoreMessage(kind, data)
      
      
      # Main function
      dialog = CollectionManager()
      def main():
          dialog.Open(c4d.DLG_TYPE_ASYNC, 1040130)
      
      # Execute main()
      if __name__=='__main__':
          main()
      

      It might be something that don't quite understand but any help would be greatly appreciated.

      Best Regards,
      Alamgir Nasir

      1 Reply Last reply Reply Quote 0
      • M
        m_adam
        last edited by m_adam

        The Script Manager doesn't have official support for DLG_TYPE_ASYNC but only for Modal (blocking) dialog since that means your variable (your dialog) must live for a longer time than the executed script.
        Which we can't grant.

        So the second script works because you moved the dialog definition outside of the main function, so the dialog variable is now a global variable.

        But in any case, it's not really a good thing, while it's working, at each execution of the Script Manager, the scope is renewed meaning all global variables are trashed. Since the internal Python Object who is responsible for the GeDialog host does not longer exist, nothing delete this GeDialog instance in memory it means you will create a lot of memory leak (ram usage will increase without a way to free it except restart Cinema 4D).

        Cheers,
        Maxime.

        MAXON SDK Specialist

        Development Blog, MAXON Registered Developer

        1 Reply Last reply Reply Quote 0
        • P
          potashalum
          last edited by

          @m_adam said in Dialog generates EVMSG_CHANGE messages:

          So the second script works because you moved the dialog definition outside of the main function, so the dialog variable is now a global variable. But in any case, it's not really a good thing, since at each execution, the scope is renewed (meaning all global variable trashed, so you will create a memory leak).

          The second script is the one that does NOT work, meaning that it produces EVMSG_CHANGE messages. I took this code out of a much larger piece of code that is run from the plugins folder when cinema starts not the script manager it also does not use global variables, this was only meant for the demonstration of the problem with the minimum amount of code. In the actual use case the dialog is being created by a command data plugin and saved as a member variable. The problem still persists.

          The command data plugin that creates the dialog:

          class CollectionManagerCommand(c4d.plugins.CommandData):
          
            dialog = CollectionManager()
          
          
            def Execute(self, doc):
              return self.dialog.Open(c4d.DLG_TYPE_ASYNC, res.COLLECTION_MANAGER_PLUGIN_ID)
          
            def RestoreLayout(self, secret):
              return self.dialog.Restore(res.COLLECTION_MANAGER_PLUGIN_ID, secret)
          
            def register(self):
              return c4d.plugins.RegisterCommandPlugin(res.COLLECTION_MANAGER_PLUGIN_ID,
                res.string('IDS_COLLECTIONMANAGER'), c4d.PLUGINFLAG_HIDEPLUGINMENU,
                res.bitmap('res/icons/manager.png'), "", self)
          
          1 Reply Last reply Reply Quote 0
          • P
            potashalum
            last edited by

            I found the problem this is not the issue.

            1 Reply Last reply Reply Quote 0
            • First post
              Last post