Avoid: IsActive()
-
Hi there,
I'm wondering, is it possible to avoid
IsActive()inMessageto support older C4D-Versions.In another thread: https://developers.maxon.net/forum/topic/11462/understanding-setcommanddragid/4 we've talked about the ability to drag BitmapButtons into the layout via
SetCommandDragId.def CreateLayout(self): bc = c4d.BaseContainer() bc.SetBool(c4d.BITMAPBUTTON_BUTTON, True) bc.SetInt32(c4d.BITMAPBUTTON_ICONID1, c4d.Ocube) bc.SetInt32(c4d.BITMAPBUTTON_FORCE_SIZE, 32) button = self.AddCustomGui(10003, c4d.CUSTOMGUI_BITMAPBUTTON, "but", c4d.BFH_SCALEFIT | c4d.BFV_SCALEFIT, 40, 40, bc) button.SetCommandDragId(c4d.Ocube) return True def Message(self, msg, result): if msg.GetId() == c4d.BFM_INTERACTEND: if self.IsActive(10003): print 'Icon clicked in the GeDialog.'Is it simply not possible to support older C4D-Versions AND have a draggable BitmapButton...?
Thanks,
Lasse -
Hi @lasselauch, I will take a look, but only in few days since R18 is the minimal version working for IsActive and it's more than 3years old, while we provide support only for 2 previous release.
But maybe there is another way to catch this kind of stuff that would work in older version so that's why I said I will take a look.
Cheers,
Maxime. -
Thanks @m_adam,
for now I've added a workaround for older versions so it's not possible to drag the buttons to the layout.
Works for me, but would be nice to know anyway.
Thanks,
Lasse -
Hi Maxime,
I still have some problems using
IsActive(). I'm having somec4d.plugins.CommandDatautilizing thec4d.gui.ShowPopupDialog. Sadly sometimes the Popup will be called even after pressing the button. Happens escpially in the end of the following *.gif. (After clicking on the button, I constantly click on the Menubar, and sometimes the popup will be displayed again...)
My
Message(self, msg, result)looks like the following:def Message(self, msg, result): if c4d.GetC4DVersion() >= 18000: #Handle CommandDragID if msg.GetId() == c4d.BFM_INTERACTEND: if self.IsActive(ids.IDC_BUTTON1): c4d.CallCommand(ids.PLUGIN_ID_EXPORT) elif self.IsActive(ids.IDC_BUTTON2): c4d.CallCommand(ids.PLUGIN_ID_OMCLEANER) elif self.IsActive(ids.IDC_BUTTON3): c4d.CallCommand(ids.PLUGIN_ID_PYSCRIPTS) elif self.IsActive(ids.IDC_BUTTON4): c4d.CallCommand(ids.PLUGIN_ID_RECENTFILES) elif self.IsActive(ids.IDC_BUTTON5): c4d.CallCommand(ids.PLUGIN_ID_CHATLOG) return c4d.gui.GeDialog.Message(self, msg, result)Any ideas how to avoid or counter-act this!?
Thanks,
Lasse -
May I ask in what range you enumerated your Dialog controls?
If I recall correctly, there was this kind of behavior if the control IDs were below a certain number. -
The
idsare starting from20001.IDD_DIALOG = 20001 IDC_BUTTONFLUSHGROUP = 20002 IDC_BUTTON1 = 20003 IDC_BUTTON2 = 20004 IDC_BUTTON3 = 20005 IDC_BUTTON4 = 20006 IDC_BUTTON5 = 20007Then of course the Commands like
ids.PLUGIN_ID_EXPORTare generated PluginIDs. -
After looking at your GIF again, it seems like the following happens:
When checking forBFM_INTERACTENDand poking yround inyour dialog, the focus switches back to the last active Gadget. Thus your commands are fired since you are checking if the gadgets do have the focus. -
Yeah, I guess that makes sense.
What would be the best way to work around that behaviour?Shall I return
return c4d.gui.GeDialog.Message(self, msg, result)after eachc4d.CallCommand()?A simple else statement didn't work.
Cheers,
Lasse -
This does not solve your initial issue since it requires the use of GetItemDim and it was introduced in R18 but here is how to avoid your second issue:
import c4d class Dialog(c4d.gui.GeDialog): def CreateLayout(self): bc = c4d.BaseContainer() bc.SetBool(c4d.BITMAPBUTTON_BUTTON, True) bc.SetInt32(c4d.BITMAPBUTTON_ICONID1, c4d.Ocube) bc.SetInt32(c4d.BITMAPBUTTON_FORCE_SIZE, 32) button = self.AddCustomGui(10003, c4d.CUSTOMGUI_BITMAPBUTTON, "but", c4d.BFH_SCALEFIT | c4d.BFV_SCALEFIT, 40, 40, bc) button.SetCommandDragId(c4d.Ocube) self.AddStaticText(10001, 0, 0, name="test") return True def IsPositionOnGadget(self, gadgetId, x, y): # Be sure that the windows is opened, # in our case since we call it in BFM_INTERACTSTART it's ok buttonData = self.GetItemDim(gadgetId) if not buttonData["x"] < x < buttonData["x"] + buttonData["w"]: return False if not buttonData["y"] < y < buttonData["y"] + buttonData["h"]: return False return True def Message(self, msg, result): # Main thread if msg.GetId() == c4d.BFM_INTERACTSTART: c4d.StopAllThreads() # Check the mouse is clicked state = c4d.BaseContainer() self.GetInputState(c4d.BFM_INPUT_MOUSE, c4d.BFM_INPUT_MOUSERIGHT, state) if state.GetInt32(c4d.BFM_INPUT_CHANNEL) != 0: # Get coordinates x = state.GetInt32(c4d.BFM_INPUT_X) y = state.GetInt32(c4d.BFM_INPUT_Y) g2l = self.Global2Local() x += g2l['x'] y += g2l['y'] # Checks the coordinate is within the range of the BitmapButton if self.IsPositionOnGadget(10003, x, y): print 'Icon clicked in the GeDialog.' # Stop others event to be processed self.KillEvents() return True return c4d.gui.GeDialog.Message(self, msg, result) # Main function def main(): global dlg dlg = Dialog() dlg.Open(c4d.DLG_TYPE_ASYNC) # Execute main() if __name__=='__main__': main()Note that there is a very similar problem Disable default Right-Click Menu that you may found interesting about how to handle popup in your dialog.
And adding this constraint in mind, I'm afraid I don't see any solution to make it work before R18.
Cheers,
Maxime. -