Hey @ferdinand ,
Sorry I forgot click Submit button 
well, that is the info I need, I use same tech to get icons for CMD, and now waiting for svg part in the future.
Cheers~
DunHou
Hey @ferdinand ,
Sorry I forgot click Submit button 
well, that is the info I need, I use same tech to get icons for CMD, and now waiting for svg part in the future.
Cheers~
DunHou
Ha, If only in terms of usage, I hope to export capsule icons that can be dragged to OM, save to disk, which I can read through regular code, not just limited to C4D.
For example, my custom menu plugin has a settings dialog that is not based on C4D SDK, but I want to UI/UX it closer to C4D, so I want to obtain icon data for drawing.
I hope this makes sense for my purpose.
Cheers~
DunHou
Hey @ferdinand ,
This is also related to SVG to some extent. My ultimate goal is to export the required commands and corresponding icons for use in my menu plugin. As it is not a traditional C4D API, it needs to be saved as a local image/svg. I am not sure if this is feasible.
Cheers~
DunHou
Hey community,
I want to get icon of assets like Redshift Nodes or OM capsule(Axis Center). but I can't export or download them, at least that's what @ferdinand said before. Do we have some way to get those icons?
I want to match icons and asset ids, so I can use them in pipeline, but a bit outside the c4d system.
Cheers~
DunHou
import c4d
import maxon
import shutil
def GetAssetDescription(mid: maxon.Id = maxon.Id("net.maxon.pattern.node.twod.blur")) -> maxon.AssetDescription:
repository = maxon.AssetInterface.GetUserPrefsRepository()
assetDescription = repository.FindLatestAsset(
maxon.AssetTypes.File(), mid, maxon.Id(), maxon.ASSET_FIND_MODE.LATEST)
if assetDescription is None:
raise RuntimeError("Could not find the asset.")
return assetDescription
def IterateAssetMetadata():
assetDescription = GetAssetDescription()
icon = maxon.AssetUtilitiesInterface.GetAssetIcon(assetDescription)
print(icon.GetUrl())
if __name__ == "__main__":
IterateAssetMetadata()
Well, that's exactly what I'm worried about. I try my best to avoid introducing third-party libraries, but currently it seems that I can only use resvg or pillow.
Cheers~
DunHou.
Hey community,
I want to display capsule assets with icon with maxon.AssetUtilitiesInterface.GetAssetIcon , but some of the icon is in svg format, can we draw this into a bitmap like command palate did?
import c4d
import maxon
doc: c4d.documents.BaseDocument # The currently active document.
op: c4d.BaseObject | None # The primary selected object in `doc`. Can be `None`.
def main() -> None:
"""Called by Cinema 4D when the script is being executed.
"""
repo = maxon.AssetInterface.GetUserPrefsRepository()
uid = maxon.Id("file_bc73b379cb5e509e")
# this is the ivy capsule id, it has a svg icon
# uid = maxon.Id("com.rocketlasso.neutron.asset.generator.ivy")
asset_description = repo.FindLatestAsset(
maxon.AssetTypes.File(), uid, maxon.Id(), maxon.ASSET_FIND_MODE.LATEST)
preview_url = maxon.AssetUtilitiesInterface.GetAssetIcon(asset_description)
bmp = c4d.bitmaps.BaseBitmap()
result, _ = bmp.InitWith(preview_url)
if result != c4d.IMAGERESULT_OK:
return None
c4d.bitmaps.ShowBitmap(bmp)
if __name__ == '__main__':
main()
Cheers~
DunHou
Sorry for my stupid question @ferdinand , I should use c4d.DRAW_ALPHA_NORMAL but not c4d.DRAW_ALPHA_FROM_IMAGE.
Shame on me 
Cheers~
DunHou
It works! Thanks!
@ferdinand said in How to add tabs to tool plugins.:
Unlike for node description resources, custom GUIs are not indicated as SOME_DATA_TYPE { CUSTOMGUI SOME_CUSTOM_GUI; ... } in dialog resources but always as their own data type (don't ask me why).
Hahaha, this is really strange. The first thing I tried was CUTOMGUI SOME_CUSTOM_GUI. This is what I got with Agent Ransack...
One more thing, I couldn't find the idd_uv_map.res file in the image in the local resources. Is it already embedded without displaying the source code.
Cheers~
DunHou
Hey,
I want to draw images with alpha in viewport, but what I got is a image with black bg, I already test DrawTexture flag DRAW_ALPHA_NORMAL_FROM_IMAGE and DRAW_ALPHA_FROM_IMAGE, they will not work.
Can I draw bitmaps with alpha in viewport, like the little icon under the mouse?
Cheers~
DunHou
Thanks for your detailed answer @ferdinand
I do know quicktab, but I didn't find its symbol in res file, seems I can only make it works in python codes.
I also agree it is bit strange to use sculpt plugins.
Cheers~
DunHou
I want to use groups UI in ToolData plugins is resource file( or in codes maybe ), but I didn't figure out witch us the right flag.
Still, I can not upload images, but please see selection tool, it has option / axis / soft selection groups.
How can I do this?
Cheers~
DunHou
Thanks for your detailed answers @ferdinand !
At night, I suddenly had a flash of inspiration and found a simpler solution, use html tags:
IDS_PLUGIN_HELP "description about......<br><b>Ctrl: </b> do something...<br><b>Alt: </b> do something...
Cheers~
DunHou
Thanks for your tips!
@ferdinand said in How to start a new line in plugin help with localization?:
I am personally also not sure it is a good idea to allow users putting control characters into strings, primarily due to whitespace
I want to add some shortcut description to plugin like:
Plugin Name
description about.....
Alt : do something...
Shift : do something...
do you have suggestions about this case?
Cheers~
DunHou
Hey community,
I want to add plugin help (or tooltips), I can use embed string for \n, it works fine. but when I use c4d resource files (c4d_strings.str), it not worked, how can I fix this?
I can not paste imgs, (Something went wrong while parsing server response)
SeeMove Toolin c4d, it has 3 lines.
Cheers~
DunHou
Hi SDK team,
I notice that webview in python only have few api but without functions such as ExecuteJavascript or SetWebMessageCallback and the SetURLCallback is diffrent form C++, at least that's what the document says.
Do we have plans to add corresponding functions in Python APIs?
Or, on the existing basis, how do you suggest implementing data processing from C4D ->web ->C4D?e.g. Read the selected object, click the button in the webview, and rename the selected object.
Cheers~
DunHou
Timer should return None:
def Timer(self, msg: BaseContainer) -> None:
"""
If you subscribe to timer events using :meth:`SetTimer` (x), this function is called every x'th millisecond.
:type msg: BaseContainer
:param msg: The raw timer message.
"""
pass
@ferdinand Thanks for your great examples! Very helpful!
Thanks for @ferdinand awesome answer!
I found DescLevel and DescId always confused to me, but them do can access more than simple set item, time to dive deeper to the DescLevel part 
Cheers~
DunHou
Hey community,
This my first dive into graphview node, sorry if this is a stupid basic question.
I want to set condition node input port (GvPort) value, but it seems I can not do this via __settitem__ / SetParameter, is this is a limit or I do it in wrong way?
Cheers~
DunHou

import c4d
def iterateNodes(node):
while node:
description = node.GetDescription(c4d.DESCFLAGS_DESC_0)
data: c4d.BaseContainer
pid: c4d.DescID
for data, pid, _ in description:
value: any | None = None
try:
value = node[pid]
except:
value = "Inaccessible in Python"
if str(data[c4d.DESC_NAME]).startswith("Input"):
print(f"\tInput '{data[c4d.DESC_NAME]}'(c4d.{data[c4d.DESC_IDENT]}) = {value} type: {type(value)}")
node[2000, 1001] = 2 # TypeError: __setitem__ got unexpected type 'int'.
node.SetParameter([2000, 1002],2,0) # no error but not worrk.
print(node[2000, 1001].GetDataInstance()) # AttributeError: parameter access failed
if node.IsGroupNode():
iterateNodes(node.GetDown())
node = node.GetNext()
def main():
# Checks if selected object is valid
if op is None:
raise ValueError("op is none, please select one object.")
# Retrieves the xpresso Tag
xpressoTag = op.GetTag(c4d.Texpresso)
if xpressoTag is None:
raise ValueError("Make sure the selected object get an Xpresso Tag.")
# Retrieves the node master
gvNodeMaster = xpressoTag.GetNodeMaster()
if gvNodeMaster is None:
raise RuntimeError("Failed to retrieve the Node Master.")
# Retrieves the Root node (the Main XGroup) that holds all others nodes
gvRoot = gvNodeMaster.GetRoot()
if gvRoot is None:
raise RuntimeError("Failed to retrieve the Root Node.")
# Iterates overs all nodes of this root node.
iterateNodes(gvRoot)
if __name__ == '__main__':
main()
I think you need to override RenderEngineCheck to false, the document said:
Bool MyRenderer::RenderEngineCheck(const BaseVideoPost* node, Int32 id) const
{
switch (id)
{
case RENDERSETTING_STATICTAB_MULTIPASS:
case RENDERSETTING_STATICTAB_ANTIALIASING:
case RENDERSETTING_STATICTAB_OPTIONS:
case RENDERSETTING_STATICTAB_STEREO:
return false;
}
return true;
}
Cheers~
DunHou