• AdditionalCompileOptions in xcode

    3
    0 Votes
    3 Posts
    647 Views
    U
    Hi Manuel, Actually I couldn't find a clean answer.. The only way I found was to set some files into ../frameworks/settings/... Best,
  • Filename Gui how get empty folder path

    python s26
    3
    1
    0 Votes
    3 Posts
    377 Views
    chuanzhenC
    @ferdinand Thanks. I create Filename Gui in CreateLayout it work,this is code: bc = c4d.BaseContainer() bc.SetBool(c4d.FILENAME_DIRECTORY,True) self.AddCustomGui(1012, c4d.CUSTOMGUI_FILENAME,"",c4d.BFH_SCALEFIT, 50, 20, bc)
  • Display points

    python
    2
    0 Votes
    2 Posts
    567 Views
    ferdinandF
    Hello @merkvilson, thank you for reaching out to us. It would have been helpful to indicate what you would consider older and the latest version of Cinema 4D in this context, but I assume your problem is caused by you using a pre-S22 TagData plugin which implements TagData.Draw in a S22+ version. With S22, the flag TAG_IMPLEMENTS_DRAW_FUNCTION has been added to c4d.plugins.RegisterTagPlugin. You must pass it, when you want the method to be called. I would also point out that ptList = op.GetCache().GetAllPoints() is rather risky, as is assumes op to always have a cache which is a point object. Objects can have no caches and caches can contain other things than point objects. You should be a bit more defensive here, even if you intend to only use the plugin 'in this one scenario where this will work'. Cheers, Ferdinand
  • DirectSample doc

    Moved python
    12
    0 Votes
    12 Posts
    2k Views
    a_blockA
    Thanks, Ferdinand
  • 0 Votes
    6 Posts
    1k Views
    ferdinandF
    Hey @everyone, Yes, the Script Log can be quite handy, especially in cases like these where no symbols do exist. But one should also keep in mind that integer identifiers can sometimes change, and we do not publish such information then. It is therefore best to use the symbols when they exist, as doing so will avoid that problem. Cheers, Ferdinand
  • SetTime() and document updating

    python r21
    12
    0 Votes
    12 Posts
    2k Views
    ManuelM
    @brucek5 said in SetTime() and document updating: It sounds like 'op' is similar to 'this' in c# op is a pre-defined variable. Using a tag to script your python, op point to the tag itself. But using the visual selector, op will point to the object in the link and could be None. You can have a look at our manuals page where you will find Python Scripting Nodes that will give information about pre-defined variables for each node where you can use python. Cheers, Manuel
  • Voronoi Fracture Glitch

    c++ r23 sdk
    13
    2
    0 Votes
    13 Posts
    2k Views
    ferdinandF
    Dear Community, this bug has been fixed with S26.1, the glitches in the Attribute Manger should not appear anymore. Cheers, Ferdinand
  • Get port id of xpresso node

    python s24
    6
    0 Votes
    6 Posts
    1k Views
    kbarK
    Was just searching for something related and came across this post and thought I would also point out my site that also displays all the data from the resource files. https://plugins4d.com/Description/Nodes Here is the page for GVSpline: https://plugins4d.com/Description/Node?containerName=GVspline It is similar to the documentation now supplied in the official maxon docs.
  • BaseObject.SetModelingAxis(self, m) Not Working

    python sdk
    5
    1
    0 Votes
    5 Posts
    973 Views
    ManuelM
    Hi, We do not provide "on demande" script. We are here to share the knowledge and help you to find the information you need, but you must learn how to code and learn how some principales works. I provided you a thread where Ferdinand is explaining how it works to move an object to another position. We have a new example in our github repository that will help you to understand how it is done. In your case, there is no function that is doing that. You must move the object's axis at the position (0, 0, 0) and move the points at the place they were. It is a two steps operation. Cheers, Manuel
  • Right-mouse click on dialog tab

    c++
    8
    1
    0 Votes
    8 Posts
    1k Views
    ferdinandF
    Hey, You can set answer and mark as solved. If I have any follow-up questions I'll pop back in. Thanks for the reply! I was wondering about dividing by the count as well. But not sure if that would work for tabs where there are different widths? Right, I admittedly did not think of that, but what you could do is measure the width of each tab string with GeClipMap:: or GeUserArea::GetTextWidth and then normalize these values. After that you can apply that to the tab widths you want to calculate. As pseudo-code: GetItemDim(ID_MY_TABGADGET, ..., gadgetWidth) averageTabWidth = gadgetWidth / tabCount titleWidths = (clipmap.GetTextWidth(s) for s in tabTitles) maxTitleWidth = max(titleWidths) normalizedTitleWidths = (t / maxTitleWidth for t in titleWidths) absoluteTabWidths = (averageTabWidth * ntw for ntw in normalizedTitleWidths) This would not be pixel-perfect and way hackier than at least I would be comfortable with. But if you are stubborn enough, you can make everything work Cheers, Ferdinand
  • Gimbal Lock Safe Target Expression

    python
    7
    0 Votes
    7 Posts
    2k Views
    ferdinandF
    Hello @indexofrefraction, Is this correct / covers all cases to get the targets position in local space? There is no "correct" way. The way I showed you is a/the common approach to construct a frame from a vector. A vector in R³ (opposed to a tuple of rotation values which might be stored in a type called Vector) only defines two out of the three degrees of freedom of a rotation in R³. When you construct a frame manually, you can define that third degree of freedom with the up vector (or just right away construct the frame out of two meaningful vectors which are already orthogonal to each other). VectorToHPB() makes this decision for you, as it, quote, '[will always set] the bank [...] to 0.0' because a vector does not store three angles but two. I personally would never go over the Euler angles, as this seems unnecessarily complicated, but this is a question of personal preference and not right or wrong. Is this correct / covers all cases to get the targets position in local space? (~(op.GetUpMg() * op.GetFrozenMln())) * target.GetMg().off [- op->GetRelPos();] What @s_bach did there was specific to that example which operates on Euler angles. I cannot explain all the math here, but in general, the position of an object B relative to an object A, i.e, the local offset of B within the coordinate system of A is just the delta of both offsets transformed by the coordinate system of A. A: c4d.BaseObject B: c4d.BaseObject mgA: c4d.Matrix = A.GetMg() mgB: c4d.Matrix = B.GetMg() # This is the location of B in relation to A in world coordinates. delta: c4d.Vector = mgB.off - mgA.off # The same point but in the coordinate system of A. If B were parented to A, it would have # this offset. offBLocalToA: c4d.Vector = mgA * delta I again would have personally done some things differently in the loot-at example, but the solution is just as good as others. what is m = utils.MatrixMove(op.GetAbsPos()) * utils.HPBToMatrix(op.GetAbsRot()) * utils.MatrixScale(op.GetAbsScale()) in this context? (ps. GetAbsScale misses the brackets in the docs) Please read the docs, I cannot explain here transforms from scratch again. Thanks for the hint for the missing parenthesis, I will fix that in an upcoming release. As a tip: Do not fixate too much on frozen transforms in our API, you can ignore them more or less, the relevant methods are GetMg and GetMl. and... is this the real code of the Target Tag ? I am not quite sure how you mean that? You mean if the LookAtCamera::Execute example is identical to what the ::Execute of Ttargetexpression does internally? No really, the expression ~(op.GetUpMg() * op.GetFrozenMln()) pops up there, but Ttargetexpression also constructs the frame manually with the cross product, but there are more steps involved than in my simple example. But again, there is no real right or wrong here, you can do things differently if you want to. And before the question comes up, no, we unfortunately cannot share the code of the target expression. I would also point out again our Forum Rules, especially regarding the scope of support and the rules of conduct. We cannot teach you the math and you must implement your things yourself. Cheers, Ferdinand PS: If you want to explore what the frozen transform means (it is mostly smoke and mirrors for the API perspective, unless you want to specifically deconstruct a transform), I would recommend adding a Python tag to objects, adding this code, and then play around with the freeze transform feature. import c4d op: c4d.BaseTag def main() -> None: """ """ def PrettyMatrixString(m: c4d.Matrix): """_summary_ """ s: str = f"{m.__class__.__name__}(" l: int = len(s) for i, v in enumerate((m.off, m.v1, m.v2, m.v3)): s += f"{' ' * (l if i != 0 else 0)}({round(v.x, 3):>8}, {round(v.y, 3):>8}, {round(v.z, 3):>8}\n" return s[:-1] + ")" node: c4d.BaseObject = op.GetMain() if not isinstance(node, c4d.BaseObject): # Should technically never happen return for line in ( f"GetMg():\n{PrettyMatrixString(node.GetMg())}", f"GetMl():\n{PrettyMatrixString(node.GetMl())}", f"GetFrozenMln():\n{PrettyMatrixString(node.GetFrozenMln())}"): print (line) [image: 1657105682679-09c7c8b7-63d3-4020-8ef3-2881ff262003-image-resized.png]
  • "Cubic Bias" interpolation...

    5
    0 Votes
    5 Posts
    995 Views
    N
    Thanks Ferdinand!
  • Discover when a tag has been disabled

    c++
    4
    1
    0 Votes
    4 Posts
    792 Views
    ferdinandF
    Hello @user168462, Thank you for reaching out to us. You said, "I guess there is no way to observe a tag if you are not implementing it." It depends a bit on how you mean that and how you mean your question in general. @C4DS gave you already a very nice answer (thanks for that). There are basically two scenarios (which effectively will become one): There is a specific BaseTag instance tag where you did not implement the tag type yourself and you want to track changes for that specific tag instance for a specific parameter. There is a BaseTag type t where you did not implement the tag type yourself and you want to track changes of a parameter for all tags of that type in a scene. One might be tempted to solve option 1 by simply storing a pointer to that BaseTag and then periodically look up the tag to track changes. But this will not work due to node reallocation. This problem can be solved by either using the Baselink type or by manually traversing a document tree/graph and identifying nodes by their unique id stored under MAXON_CREATOR_ID. This second approach (traversing the whole document tree) is also what is the solution to option 2. To carry out the periodical checking, the most straight forward option is to the core message EVMSG_CHANGE. You can do this in a MessageData plugin or GeDialog derived GUIs. An alternative approach is to implement a SceneHookData plugin and do the traversing in its Execute() method. TLDR: While the Cinema 4D classic API does not have a dependency graph or a very granular event system, scene changes can be tracked with EVMSG_CHANGE. It is only that it is up to the user to find out if the change that occurred is of relevance as Cinema 4D does not give any context for the cause of EVMSG_CHANGE. Cheers, Ferdinand
  • How to just open a certain window instead of toggling

    python
    3
    0 Votes
    3 Posts
    440 Views
    K
    Hi @ferdinand, I deleted my original post because I realized the question contained my misunderstanding. And now your answer has completely solved the problem I had. Thank you very much for your detailed response!
  • Change FBX Exporter Settings

    python
    3
    0 Votes
    3 Posts
    946 Views
    C
    @m_adam - Now I'm sorry for my late reply! I appreciate you writing this up for me and I think it's a really good reference. This question has been answered then! Another quick question which sort of relates (I can create a new thread if admins want) - Do you have any recommendation for up-to-date C4D Python API training? I'm coming from writing Python in Houdini and Maya, but Cinema 4D seems to have a more unique setup with how to interface with their API. Any training recommendations would be appreciated. Teach a man to fish and... something something fish. Thank you, Clayton
  • Get the preview images from c4d files

    c++ s26
    5
    0 Votes
    5 Posts
    970 Views
    H
    thanks that works.
  • Osubdivisionsurface ?

    python
    4
    0 Votes
    4 Posts
    753 Views
    ferdinandF
    Hey @indexofrefraction, Well, that is because Mograph is one of the areas where the type symbols have not been exposed. So, to be clear: There is no cloner object symbol. But now that you brought this up again, I just realized that we (the SDK Team) never talked about fixing this and I do not see (fully) why. I have a suspicion why this might have been postponed or refuted in the past, but I will bring it up again. In the end we just must add a few defines to ge_prepass.h and then users do not have to jump through these hoops anymore. It will be difficult to catch all the missing symbols, but we could at least start with the ones we know. I will update the thread with the outcome of our discussion. Edit: So, we talked about this, and came to the obvious conclusion, that we should do what we should have done a long time ago, and fix this. I cannot give an ETA, but I will try to give it priority as I think this is a problem which impacts many users. Cheers, Ferdinand
  • Questions about messages (original: 关于消息的问题)

    2
    0 Votes
    2 Posts
    404 Views
    ferdinandF
    Hello @未凡fh, Thank you for reaching out to us. Support on this forum is only being provided in the English language, as this serves our community best, and because we also simply do not speak all languages of the world. I think the language you posted in is Simplified Chinese, please excuse me when I wrong, but that is what Google said. No-one on the SDK Team speaks that language. And even if we would, we would refuse to answer in this language as it would lock out large parts of the community. As we do for requests which come in German, French, or Spanish (languages we do speak). Running your request through Google Translate, I got this: Let me ask: How do I detect an object moving and send a message when an object moves? Please confirm that this is your request and that we can communicate in English. Thank you for your understanding, Ferdinand
  • How can I change the path of a Redshift shader with Python?

    r21 python
    3
    0 Votes
    3 Posts
    783 Views
    ferdinandF
    Hello @conductor, Thank you for reaching out to us. I am glad that you could solve your problem yourself. Please do not hesitate to ask further questions you might have. Cheers, Ferdinand
  • SaveWorldPreferences() in Python

    5
    0 Votes
    5 Posts
    882 Views
    a_blockA
    Hi Ferdinand, thanks a lot! No ETA needed, I'm grateful it will be added eventually. Cheers, Andreas