Thank you @ferdinand for looking into this, as well as bumping the request to the RS developers.
Any update on this would be appreciated!
Thanks.
Posts
-
RE: c4d.RSCAMERAOBJECT_COLOR_CONTROLS_CURVE_RGB
-
c4d.RSCAMERAOBJECT_COLOR_CONTROLS_CURVE_RGB
Hi there,
is it possible to get access to the Color Correction curves within a Redshift Camera or within the RS Post Effects through python? Any magical ints that I'm missing?
Thanks,
Lasse
-
Object-level "Show Help" (CMD+F1) for ObjectData plugins?
I'm using
RegisterPluginHelpCallbackto provide context-sensitive help for myObjectDataplugins. It works when CMD+F1 is triggered on parameters in the Attribute Manager.However, I'd like to also handle help requests on the object itself β for example:
- Right-click β "Show Help" on the object icon/header in the Attribute Manager
- CMD+F1 on the object in the Object Manager
Does the help callback fire in this case (perhaps with empty group/property)? Or is there a separate mechanism β like a
message inObjectData.Message()β that I should be handling?
Current implementation (works for parameters):
def my_help_callback(opType, baseType, group, property): if opType in MY_HELP_MAP: open_help_page(MY_HELP_MAP[opType]) return True return False c4d.plugins.RegisterPluginHelpCallback(PLUGIN_ID, my_help_callback)I've checked
ObjectData.Message()for help-related messages (like MSG_DESCRIPTION_GETHELP) but haven't found a reliable trigger for object-level help.Any guidance appreciated!
Thanks & Cheers,
Lasse -
RE: ColorField/ColorDialog and GeUserArea β Color Space Questions
Thank you, Ferdinand. (Again!)

That was exactly what I needed. It's working great now!
Thanks for taking the time to answer this so thoroughly and quickly!Cheers,
Lasse -
ColorField/ColorDialog and GeUserArea β Color Space Questions
Hi SDK Team,
we're currently developing a plugin that uses
GeUserAreato display color swatches that users can sample with the ColorField's eyedropper. We've encountered some color space behaviors we'd like clarification on.
Issue 1: GetColorField returns LINEAR, DrawSetPen expects sRGB
When using a
ColorFieldwith aGeUserArea:# Get color from ColorField - returns LINEAR field_data = self.GetColorField(self.ID_COLOR_FIELD) linear_color = field_data['color'] # Draw in GeUserArea - expects sRGB self.DrawSetPen(linear_color) # WRONG - appears too dark! # Correct approach: srgb_color = c4d.utils.TransformColor(linear_color, c4d.COLORSPACETRANSFORMATION_LINEAR_TO_SRGB) self.DrawSetPen(srgb_color) # Correct!
Question 1:
Is this the intended behavior? Should we always convert LINEARβsRGB when drawing colors from ColorField/ColorDialog in a GeUserArea?
Issue 2: Eyedropper Roundtrip Doesn't Preserve Saturated Colors
We've noticed a more significant issue when using the ColorField's eyedropper to sample colors from our GeUserArea:
Test Case
- Draw a pure red square in GeUserArea using
DrawSetPen(Vector(1.0, 0, 0))(sRGB) - Use ColorField's eyedropper to sample that red pixel
GetColorField()returns a LINEAR value- Convert back with
linear_to_srgb()and draw the result
Expected Result
The sampled color should match the original: sRGB
(1.0, 0, 0)Actual Result
- Purple (less saturated): Works correctly - roundtrip preserves the color
- Pure Red/Green/Blue (saturated): Fails - the result appears darker/desaturated
The LINEAR value returned seems incorrect for highly saturated colors, causing the sRGB conversion to not match the original. That's why the user need to be advised to sample colors in "Raw" mode?! But then again, it's not working in all cases.
Reproducible Demo
We've attached a demo script (
color_space_demo.py) that demonstrates this. It shows:- Test color squares (RED, GREEN, BLUE, PURPLE) drawn with known sRGB values
- A ColorField to sample those colors
- The result after LINEARβsRGB conversion
- The actual LINEAR and sRGB values for comparison
Question 2:
Is there a known issue with the ColorDialog eyedropper and color space conversion for saturated colors? Or are we missing something in our approach? Clearly I'm a little lost at this point.

Environment
- Cinema 4D 2025+
- macOS and Windows
Attached Files
color_space_demo.py- Runnable demo in Script Manager showing both issues
Thanks for any clarification!
- Draw a pure red square in GeUserArea using
-
RE: Educational Licenses
Thanks for all the info, Ferdinand!

And thank you for the input about the booting phase, I'll definitely adjust this for the next version!Cheers,
Lasse -
RE: Educational Licenses
Hi Ferdinand,
Thanks for the answer. That all makes sense in light of my current understanding.
You can download the trial to test it on your end.
Once prompted with the license dialog you can enter:
trialbut that would already tell us that he plugin is loaded properly. So looking forward to your feedback!
Thanks & Cheers,
Lasse -
Educational Licenses
Hi there,
A customer of mine who uses my C4D2HOU Python plugin has contacted me to say that he cannot see the plugin after installation. He seems to have installed it correctly, though.
He is using an educational licence. Is there anything special for these licences? I have a version check in place before loading the plugin β could this be the issue, or are there python limitations with the educational licence?
I would be grateful for any input on this topic.
Thanks,
Lasse(
Random Screenshot he sent, if that helps.
)

Description: The C4D2HOU plugin does not load or appear in Cinema 4D 2025.3.1 (Educational license). Itβs correctly installed, but no entry shows up in Window or Extensions, and thereβs no visible error in the Console. System Setup: Windows 11 (64-bit) Cinema 4D 2025.3.1 β Educational Houdini 20.5 β Education (Non-Commercial) C4D2HOU v1.0.4 Python 3.11 (built into C4D 2025) Steps Tried: Installed plugin into: C:\Program Files\Maxon Cinema 4D 2025\plugins\c4d2hou\ (also tested under AppData\Roaming...) Verified plugin path in Edit β Preferences β Plugins. Confirmed correct structure (c4d2hou.pypv + res/). Ran C4D as Administrator and restarted multiple times. -
RE: Plugin module import freezes on startup
Hi Ferdinand,
I was essentially just forwarding this message from the developer of the licence framework. Sorry for not being clearer in the first place.
I showed him your answer, and here is his response. Please let me know if I can be of any further assistance.Hi Ferdinand! I totally understand you so I'll write my findings in this mail instead. I'm not after help with my code, I just want to report the bug I found.
The pyz file is part of python and allows you to package modules in a zip file for easier distribution, it has nothing to do with obfuscation in our case, it's just easier for the end user to copy one file instead of multiple folders and files.
My finding with the 10mb file freeze comes from my trial and error. If I compile our licensing framework to work with Python 3.7-3.9 the resulting size is below 10mb, same if I compile for 3.9-3.11, same for 3.10-3.13 or what ever combo I do that ends up in less than 10mb pyz file the C4D plugin will read it but if I compile any combo where the pyz file ends up being more than 10mb the freeze happens.
Let's say I compile for C4D 2026 it will work if I compile for 3.9-3.11 and it will work for 3.11-3.13 but it won't work for 3.9-3.13, exactly after 10mb. That ends me up thinking something is going on on C4D side.Lasselauch sadly seemt o have packaged the project a bit weird, thus Demo_Script.py is pointing wrongly. With "it doesn't happen when running a script" I mean when you run a script from Extensions -> User Scripts.
Here is another zip with all different file combos for you to try out with yourself: https://www.swisstransfer.com/d/1f1d457f-89fe-4fef-80fd-2185c0ebe34c
As you can see, using 3.9-3.13 freezes C4D but 3.9-3.11 and 3.11-3.13 does not. The internal code is exactly the same except that they package different PyArmor frameworks. I have double-checked the code and there is no execution-difference between the different pyz files.And the whole thing about obfuscation, honestly I'm just a dev that aescripts hired to add their licensing system to python and they want to protect the code so in that area I'm just doing what I'm told.
//Jacob Danell
-
-
Plugin module import freezes on startup
Hi Maxon/Cinema4D devs!
I'm currently working with aescripts on developing their licensing system for python and for C4D. The license script is packaged in a pyz file for easy of distribution and the plugin script simply imports the pyz file to get access to the licensing system.
One problem we're facing is that for C4D plugins C4D gets stuck on startup when showing
Initializing Plugins 100%. After a lot of trial and error I found out that this happens ONLY when the pyz file is bigger than ~10mb.This doesn't happen if you run a script that imports the pyz. Only for plugins that gets loaded on startup.
Here's a link to a demo repo for you to try it out and hopefully can figure out what's causing this:
Any ideas on why that is and how to best prevent the freeze are welcome!
Thanks & Cheers,
Lasse -
RE: Importing pythonapi from ctypes freezes C4D
Hi Ferdinand, thanks for the reply and I totally understand the out of scope of support part!
Thanks!
Regarding the freeze, my system specs are:
15", Apple M2 2023
macOS 13.5.2 (22G91)
C4D 2024.4.0
Just trying to import ctypes freezes C4D instantly.
Regarding the SpecialEventAdd() case:
I essentially want to act after a threaded operation is finished. So the last line of my threaded function calls:
c4d.SpecialEventAdd(ids.PLUGIN_ID_EXPORT)To distinguish between different types of export I thought I could use the p1 (x) e.g.:
c4d.SpecialEventAdd(ids.PLUGIN_ID_EXPORT, x)However when using this inside my dialog, I'm not sure how to receive the different p1 or p2 integers inside the CoreMessage():
def CoreMessage(self, id, msg): if id == ids.PLUGIN_ID_EXPORT: logger.info("PLUGIN_ID_EXPORT Message") if msg == x: logger.info("Finished thread Message") do_some_logic_here() return True return FalseSo what I'm asking is: I think different
intare sufficient enough for my case, but I'm not sure how to receive those correctly within the CoreMessage or Message of a commanddata plugin.Thanks again,
Lasse -
RE: Importing pythonapi from ctypes freezes C4D
Hi @m_adam,
yes, that is correct. However, I experience a freeze everytime I do:
from ctypes import pythonapi
which I need either way. -
Importing pythonapi from ctypes freezes C4D
Hi there,
I've just noticed something slightly odd.. While doing the following:from ctypes import pythonapi, c_void_p, py_objecteither in a script or plugin, Cinema4D freezes instantly.
I came across this issue, because I wanted to implement a way to react to my SpecialEventAdd() messages. I stumbled upon this example:
Is this still the way to go in 2024 to receive the SpecialEventAdd() p1 or p2 messages? And why is this instantly freezing C4D on my MacBook Air M2?

Cheers,
Lasse -
RE: How to find the CallCommand id for Redshift 'Convert and Replace with Nodes'
AFK currently, but I think you can open the "Script Log..." from the Extensions Menu to check the ID's right!?
-
RE: Detect Menu/Manager while hovering...
Thanks, for the clarification. @ferdinand
-
Detect Menu/Manager while hovering...
With "Customize Commands..." we are able to "restrict" certain commands to certain "managers" or "menus". I'm wondering if it's possible to detect these managers within a cmd-data-plugin while the mouse is hovering over a certain area.
Imagine a popup filled with different content based on the currently hovered manager i.e. object-manager, material-manager, take-manager...!

Is there a way to detect the underlying context of the mouse via python..?
Cheers,
Lasse -
RE: Arranging Objects by order of Object Manager
I could make a recursive iteration to go through all of the document's objects but that would slow it down significantly...
Yeah, but that's basically the way to go... Not sure if the following yields faster results:
def get_next_element(op): if not op: return if op.GetDown(): return op.GetDown() while (not op.GetNext()) and op.GetUp(): op = op.GetUp() return op.GetNext() def main(): obj = doc.GetFirstObject() while obj: # act on obj print(obj.GetName()) obj = get_next_element(obj)Always wondered what approach would yield faster results...
Feel free to do some testing, would love to hear your results.

-
RE: Arranging Objects by order of Object Manager
My guess is that iterating over with enumerate BaseDocument.GetObjects(self) would be efficient enough..?
For example:
all_objs = doc.GetObjects() for i, obj in enumerate(all_objs): # Distance can be whatever float or integer your_dist = i * 27 pos = c4d.Vector(your_dist, 0, 0)Β obj.SetAbsPos(pos) -
Japanese Language Interface β Problems
Hi there,
I'm currently having a japanese customer for my AEC4D-PRO plugin that complains, that the plugin isn't behaving correctly in R23. In older C4D-Versions the plugin seems to behave correctly.
At first, I thought the problem lies within string encoding. However at further testing, it works for the customer if he changes his "Interface Language" to English. So it's not the typical string encoding when transferring Objects between the two programs.
I'm actually a bit lost, how this language setup is intertwined with the plugin itself. Sadly, I don't have the time to test the Japanese Language myself, so I thought if anyone has experienced these kind of issues before he or she might jump in and help.
If you want to test it yourself, feel free to download the 14-day trial here:
https://aescripts.com/aec4d/Thanks so much.
Cheers,
Lasse -
RE: Detect closing of Document
I guess I found a workaround... I cannot show the whole code involved but something along those lines:
I have a
Treeviewthat stores an absolute pathabs_pathof different documents... Now, I just check if one of these filepaths is in my open documents paths via:get_all_docs_paths()def get_all_docs_paths(): all_docs_paths = [] first = c4d.documents.GetFirstDocument() while first: folder = first.GetDocumentPath() abs_path = os.path.join(folder, first.GetDocumentName()) all_docs_paths.append(abs_path) first = first.GetNext() return all_docs_pathsIf yes, the document is open, if not it is closed.
Cheers,
Lasse