Resize dialog after LayoutFlushGroup(id)
On 30/03/2014 at 07:38, xxxxxxxx wrote:
I have this commandplugin with a "dynamic" dialog.
I use LayoutFlushGroup(id) and GeDialog.LayoutChanged(id) to create and remove groups in the dialog.
That is working as expected.
However, I would like to resize the dialog, so that it fits all fields.
Now when removing a field, there is an empty space.
I know I can rebuild the whole dialog, but I would think that flushing only one field and then resize should be enough?
I have seen the post "Topic: Controlling the window size of a gui" covering this question, but I cannot get it to work.**
import c4d from c4d import gui, plugins, bitmaps import os PLUGIN_ID = 1031945 # Plugin ID class ALDIDialog(gui.GeDialog) : def __init__(self, host, width) : self.host = host self.width = width def CreateLayout(self) : self.AddEditNumber(1000, c4d.BFH_SCALEFIT) self.GroupBegin(1001, c4d.BFH_LEFT) self.AddButton(1002, c4d.BFH_SCALEFIT, name = 'Reopen') self.AddButton(1003, c4d.BFH_SCALEFIT, name = 'Close') self.GroupEnd() return True def InitValues(self) : self.SetLong(1000, self.width, 0, step=1) return True def Command(self, id, msg) : if id == 1002: self.host.ReOpen(self.GetLong(1000)) if id == 1003: self.Close() return True class MyMenuPlugin(plugins.CommandData) : def Execute(self, doc) : # create the dialogs self.dialoog = ALDIDialog(self, 200) return self.dialoog.Open(dlgtype=c4d.DLG_TYPE_ASYNC, xpos = 150, ypos = 150, defaultw = 200) def ReOpen(self, width) : if self.dialoog.Close() : self.dialoog = ALDIDialog(self, width) return self.dialoog.Open(dlgtype=c4d.DLG_TYPE_ASYNC, xpos = 150, ypos = 150, defaultw = width) if __name__ == "__main__": bmp = bitmaps.BaseBitmap() dir, file = os.path.split(__file__) fn = os.path.join(dir, "res", "aldi.png") bmp.InitWith(fn) okyn = plugins.RegisterCommandPlugin(PLUGIN_ID, "re-open",0, bmp, "re-open", MyMenuPlugin()) if (okyn) : print "re-open initialized." else: print "Error initializing re-open"
I also noticed that when you manually resize a dialog, that is being stored by cinema.
The next time you startup the dialog, the last stored size is used.
How is that done?
Edit: Added link to topic
On 01/04/2014 at 01:48, xxxxxxxx wrote:
I am afraid this is not possible.
On 01/04/2014 at 02:11, xxxxxxxx wrote:
Sorry, what is not possible?
In this topic "Topic: Controlling the window size of a gui**" there is a script doing the same.
Is it not possible in a plugin?
On 01/04/2014 at 08:13, xxxxxxxx wrote:
All that code example does is change the position of the window when it opens.
It does not change the size of the window. Because like I said in that thread. It's not possible to change the size of a window with the SDK...period...end of story..game over.
This rather annoying limitation is one reason why I posted a C++ example on my site using the Windows OS to control the windows in C4D. It really is a very big SDK limitation.
But you know me. Whenever the developers hard code things like this. I can usually find a way to hack around it. I'm the king of the hacks.
I discovered that we can force the window to shrink after dynamically removing gizmos by doing a quick layout swap.
It seems that the developers are caching the window sizes in the layout (or something related).
So what you can do is use this kind of code in that code example you posted that will switch to another layout. Then switch back to the layout you were originally in.
Then the window will shrink down to fit your current gizmo layout.
def Command(self, id, msg) : if id == 1002: path = "\\Program Files\\MAXON\\YOUR C4D VERSION\\library\\layout\\Animation.l4d" c4d.documents.LoadFile(path) c4d.EventAdd() path = "\\Program Files\\MAXON\\YOUR C4D VERSION\\library\\layout\\Standard.l4d" c4d.documents.LoadFile(path) c4d.EventAdd() self.callReOpen.ReOpen(self.GetLong(1000)) if id == 1003: self.Close() return True
I know it's a terrible hack. But these are the kinds of sneaky tricks we have to do when the developer hard code things and don't give us proper access.
But it happens very fast and you never see the layouts change. So it's not really that bad.
* The one thing I don't know how to do though, is how to get the current layout you're in. So that you can jump back to where you came from.
If anyone knows how to get the current layout. Then you're golden.
On 03/04/2014 at 08:42, xxxxxxxx wrote:
You are indeed " the king of the hacks".
You also triggered me with "It's not possible to change the size of a window with the SDK".
The example I mentioned, see https://plugincafe.maxon.net/topic/7287/8465_controlling-the-window-size-of-a-gui&PID=35001#35001, uses a DLG_TYPE_ASYNC_POPUPEDIT and not a DLG_TYPE_ASYNC.
Thus not a window, but a pop-up.
Then the example also works as a plugin.
On 03/04/2014 at 10:49, xxxxxxxx wrote:
I'd still love to know how to get the current layout if anyone knows how to do that?
Right now all I can do is send the user to the Standard layout to re-size the plugin's window. And that's not good.
It would be very nice to be able to put the user back in the layout they were in.
On 03/04/2014 at 13:12, xxxxxxxx wrote:
Can't you use c4d.CallCommand(12673) # Save Layout as...
Then change to another layout.
Then reload the previous layout that was just saved.
Only thing is how to handle the Save As dialog?
But of course the information is stored somewhere.
It is kept when you close cinema.
It is also shown Windows >> Customization >> Layouts.
The current layout is here indicated.
On 03/04/2014 at 14:10, xxxxxxxx wrote:
That's a good idea. And it might work.
But I'd still really like to know how to get the current active layout.
I'm also wondering where the Startup layout is stored?
Because I can't find it where the other layouts are stored. Or anywhere else either.
It turns out that we can't save layouts with code. And that's a problem because we can neither get the current layout, or save to a temporary one to use this trick more elegantly.
The best we can do is hard code the layouts to jump back and forth to. Or maybe give your dialog plugin a textbox gizmo where the user can physically type in their current layout. And make the code use that path for jumping back to that layout after you quickly swap to the Animation layout.
Clumsy...But better than nothing. And easier than using C++ and OS code to shrink your windows.