The Stack Overflow podcast is back! Listen to an interview with our new CEO.

New answers tagged

0

Try what was answered in this thread: https://blenderartists.org/t/can-a-modal-operator-use-snapping/1175190


2

You can surround your code with something like: current_frame = bpy.context.scene.frame_current obj = bpy.data.objects['Cube'] obj.keyframe_insert(data_path='location', frame=0) obj.location.z += 5 obj.keyframe_insert(data_path='location', frame=100) s.frame_set(current_frame) So that the current (or the frame you want) is restored once the key frames ...


-1

i just search in the api and it seems that there is multiples solution possible. in this case the best code i found is grid_flow (thanks merlin for confirming) https://docs.blender.org/api/current/bpy.types.UILayout.html?highlight=grid_flow#bpy.types.UILayout.grid_flow it also seems that ui_units_x and y are good contestors but i didn't try them yet. ...


1

This should work: def draw(self, context): grid = self.layout.grid_flow() for icon in custom_icons: grid.template_icon(icon_value=icons.icon_id,scale=self.item_size)


0

The following script prints the global point coordinates for every grease pencil object in the scene. The coordinates seem to be accurate, judging from basic tests. import bpy for obj in bpy.data.objects: if obj.type == "GPENCIL": print(f"\n{obj.name}") for layer in obj.data.layers: for frame in layer.frames: ...


0

bpy.data.materials['Material'].node_tree.nodes['Cracks_Mapping'].rotation[2] = some value That's how you do it. input[0] is the only input of the node, the Vector. The 0 is the index. For example rotation has 3 index, 0, 1, and 2 for X, Y, and Z. Knowing that, if you assign a value to .rotation[2] like in my code example you'll modify Z rotation value of ...


1

Already gave you a answer to this here https://blenderartists.org/t/how-to-access-and-draw-the-node-group-input-slider-in-layout-panel/1185331/12 You had a material named "TestMat" and a group named "Group". It draws the group properties if there is a material and group with those names.


1

if the quality desired is not important this technique may work (icons) this script will display all the .jpg file of the directory folder in the n panel import os import bpy import bpy.utils.previews directory = os.path.join(bpy.utils.user_resource('SCRIPTS'), "presets", "scatter_presets_custom\\") list_raw = [] from os import listdir from os.path ...


0

That error was driving me crazy. To solve on Visual Studio Code. Click with mouse right button, and select Command Palette on your code, and after that select de command 'Convert Indentation to Tabs'


4

Easy Way Have you looked at template_preview tex = bpy.data.textures['.hidden'] col = layout.box().column() col.template_preview(tex) Hard Way So this works, but it requires a lot of finesse to make it usable. Not figured out yet how to create a layout of a fixed size to append to the panel layout for rendering over the top of. This code will render ...


0

Basically, you have to take care of two things: first selecting the relevant bones you want to smooth and second to switch to the graph editor context. For some reason, selecting and deselecting the respective curves did not effect the operator. I rather locked the respective curves I did not want to smooth. import bpy # types = {'VIEW_3D', 'TIMELINE', '...


1

The file needs to have the proper file extension. Files without the proper file extension gets filtered out in the dialog. Or you need to turn off the file filter. This can be done up right in the filter settings. The better way is to name the scripts proper though, with its correct file extension. Python scripts ends with *.py


0

The operator still works in 2.80, but you need two parameters: A custom context that tells the operator what area should be used for the new window The correct execution context The custom context can be created by modifying a copy of the current one. The area object for the 3D view can be found by iterating through bpy.context.screen.areas and checking ...


1

This is a bug as acknowledged by the developers here: https://developer.blender.org/T70768 But basically it works if you set bl_region_type = 'PREVIEW'


1

I think I can safely say these are reliable, for a couple reasons: They are reliable for modal operator classes, and there is little difference between a modal operator class and a non-modal operator class, except for a specific function being defined and returning certain values from specific functions. It makes sense that the constructor/destructor can be ...


0

with a handler it may work import bpy, os ao = None def h(s): # just for testing, normally i won't use global global ao o = bpy.context.active_object if(ao != o): ao = o print(ao) if ao.name == "Cam Small": return None bpy.app.handlers.depsgraph_update_post.append(h) but that doesn't really respond to the goal ...


6

Blender 2.80 already protects against enabling incompatible add-ons. If the Blender version in the bl_info is too low, it will display a warning in the preferences. Blender will not run the register() function on these add-ons. However it does allow to tick the checkbox and the user may get the impression that it's properly enabled. If you want to avoid ...


0

In Blender 2.80, I've had some success with something simpler that previous @johnzero7's solution : collection = bpy.data.collections.new('My Collection') bpy.context.scene.collection.children.link(collection) # NOTE the use of 'collection.name' to account for potential automatic renaming layer_collection = bpy.context.view_layer.layer_collection.children[...


1

This can be solved by checking whether the timer has been set before. Unfortunately the example has a little confusing mistake. self._timer = wm.event_timer_add(0.1, window=context.window) does not assign a value to the class attribute _timer as declared at the beginning of the class. Instead it creates an instance attribute named _timer. You can see this by ...


1

The following example shows how to create multiple operators each with their specific function. It only shows three buttons, but the concept remains the same for an arbitrary number of buttons and their underlying operators. The panel is created in the sidebar of the 3D View which can be opened with N. I hope I haven't misunderstood what you're trying to ...


0

Found the solution! After completing the rendering of the scene you should free the bake of the objects by using: bpy.ops.ptcache.free_bake_all() Hope that help to other ones as well.


1

You need to indent your call to bpy.ops.wm.modal_test_operator() so it will only be executed when the code as run as a script, which is the case when __name__ == "__main__". Otherwise you're trying to access blend data when the add-on isn't registered, which results in the exception you're seeing. For more information about this topic take a look at this ...


2

The good answer stays for hatinacat2000. Though, the implementation could be optimized from the code given in the question, and stay in $O(n^3)$, but does not need to allocate combinations (and that can spare a lot of memory if there are many points). It considers parallel planes as we progressively check best plane containing first point, then second ...


0

You can load the default startup file using bpy.ops.wm.read_homefile(). This operator also allows you to load application templates if you use the optional app_template argument. Be aware that the current .blend project file will not be saved automatically, meaning all unsaved state will be lost. The problem with loading the default startup file or any ...


3

New shortcuts can be added in the preferences Edit > Preferences > Keymap. With the keymap tab open, navigate to the Window category of shortcuts. Click the Add New button to create a new shortcut. The operator for reloading scripts is bpy.ops.script.reload() therefore the identifier for the shortcut is script.reload. Click on the shortcut field and press ...


0

A little later, I reported to the developers and they fixed this error. T70714 This question has ceased to be relevant.


0

not the best answer yet, but you could try with these commands, from the script-editor or console-window: import bpy bpy.ops.preferences.addon_refresh() # # OR: # (replace module name !) - first disable ... bpy.ops.preferences.addon_disable(module="space_view3d_align_tools") # ... then re-enable bpy.ops.preferences.addon_enable( module="...


0

import bpy for obj in bpy.data.objects.keys(): bpy.context.view_layer.objects.active = bpy.data.objects[obj] activeobj = bpy.context.active_object try: if "." in activeobj.active_material.name: mat = bpy.context.object.active_material.name[:-4] activeobj.data.materials[0] = bpy.data.materials[mat] ...


3

obj.name gives you the object name. obj.data.name gives you mesh name. And yes, AFAIK there can be only one mesh per object. However there can be multiple objects sharing the same mesh data block.


0

The difference between a copied object and an instance is that the copied object is a separate entity that can have its properties, materials, modifiers etc. adjusted without affecting the object it was copied from. Instances of an object are practically identical except for their location, scale and rotation. Changes to the object affect all instances of it....


0

Another way you could do it is: def render_scene(self, file_name): bpy.data.scenes[0].render.filepath = os.path.join(self.output_path, file_name) bpy.ops.ptcache.bake_all() bpy.ops.render.render(animation=True)


0

Found the solution! since using third party (Blender) import sys sys.path.insert(0, <path_to_repo>) is needed to set the environmental variables


0

An example that should work with Blender 2.80: The directory: folder | -> main.py | -> scripts -> __init__.py -> hello.py scripts/__init__.py: from scripts.hello import * scripts/hello.py: def hello(): print('Hi') main.py import bpy import sys if __name__ == '__main__': sys.path.append('') import scripts scripts....


3

There is no "simple" way to do anything in numerical analysis. However, the tasks can be laid out straightforwardly. EDIT: This idea is a brain-fart because it doesn't distinguish parallel planes. The Internet must never forget though. Pile on, people. How about this: generate an array of normalized normal vectors (not vectors in the dynamic array sense; ...


0

Think you need to flush your selection. This code works, slightly different from yours as it uses bmesh.from_edit_mesh, but if it gets the job done then maybe okay: import bpy import bmesh context = bpy.context obj = context.edit_object me = obj.data bm = bmesh.from_edit_mesh(me) bm.select_mode = {'VERT'} for v in bm.verts: v.select = ( v.co.x > 0 )...


0

You can find the Collada presets in [your install dir]\2.80\scripts\presets\operator\wm.collada_export There are two files sl_plus_open_sim_rigged.py and sl_plus_open_sim_static.py


0

I'm just doing my duty here. Quick answer that works in 2.8: objectToSelect = bpy.data.objects["objectName"] objectToSelect.select_set(True) bpy.context.view_layer.objects.active = objectToSelect You need that last line. Without it I couldn't switch into edit mode. I got the answer here. I wanted to post it here, which is actually the question that ...


2

Add-ons can do per-file initialisation, if the add-on has some kind of panel in the UI somewhere. You may notice various panels in Blender's UI have checkboxes next to the panel title. This is can be because they don't want to be active unless specifically turned on, but it can also be because they want to do some setup before being used: This can be ...


2

There are multiple issues with your script: The indentation is incorrect. Code that belongs into your T_M function isn't indented by four spaces, which results in the code being executed even though the functions wasn't called. Similarly the functions that should be part of the class aren't indented, e.g. the execute function for Test_MaterialOP. The ...


1

You could do it like this: obj = bpy.context.object # Select the active object. mat = bpy.data.materials.new(name='Material') # Create a material. # Settings for the material go here. obj.data.materials.append(mat) # Assign the new material.


-1

If you don't want curved surfaces then points are on a plane when one of their (x,y,z) coords is the same e.g z (a horizontal plane). When a linear function f(x)=ax+b is involved the plane is rotated/sheared.


1

The error message is trying to inform you that the property lookup <screen>.overlay was unsuccessful, because that's not where that property is located (the tooltip is misleading..) . It's something you might want to iterate through screen area.spaces to locate and set. It's a little awkward, but acceptable. import bpy AREA = 'VIEW_3D' for window in ...


2

The way you could do this is by trying for almost all combinations of three points, choose the plane which contains the most points. It will run in $O(n^4)$ for $n$ points.


1

Yes, of course this can be done. If you have an add-on with its folder and __init__.py inside it, if you have other files like file.py in the same folder you just import stuff from it like this: from .file import Some_stuff Just open [Blender's installation folder]\[version]\scripts\addons\ and see how it's done with any of the add-ons in the folders there....


1

There are two things necessary to set the fullscreen mode successfully: Wait for the workspace to be switched Create a custom context for the operator The first part can be accomplished by adding an application handler that is triggered after the dependency graph is updated. The second part is necessary to set the correct area to fullscreen. This can be ...


0

You shouldn't access or change properties before the add-on is properly loaded. The unit settings can be changed for example in an operator as can be seen below: bl_info = { "name": "Make Imperial", "author": "Robert Guetzkow", "version": (1, 0), "blender": (2, 80, 0), "location": "Dummy panel in View3D", "description": "Changes the ...


0

Ok, the following script does a bit more. See comments - disable "renameUVMaps" if you don't plan to join the meshes. Useful to rename the UV of identical textures so that mapping data is kept active. import bpy # Options renameUVMaps = 1 # 1. Get the "active texture name" activeObject = bpy.context.object activeUVMap = activeObject.data.uv_layers[0] ...


3

mathutils now uses the PEP 465 binary operator for multiplying matrices. matrix_final = obj.matrix_world * pose_bone.matrix becomes matrix_final = obj.matrix_world @ pose_bone.matrix Since 2.8 object are now stored in Collections, so : context.scene.objects.link(obj_empty) becomes bpy.data.collections['Collection'].objects.link(obj_empty) Here is the ...


1

import bpy for obj in bpy.data.collections["Collection"].objects.keys(): bpy.ops.object.duplicate(linked=True) light = bpy.context.active_object.name bpy.data.objects[light].location = bpy.data.objects[obj].location This should do the trick, make sure you create a light first (this will control all the other light) and have it selected. Also ...


1

You can add a wiki URL ("wiki_url") to the bl_info of your add-on. This will result in a link to the documentation in the add-on preferences. Alternatively you can use bpy.ops.wm.url_open(url="") in your code to open the browser.


Top 50 recent answers are included