0
$\begingroup$

I realize similar questions have been asked, but I'm having a lot of trouble and would like to understand.

How can I UV unwrap (smart project) the originally selected object and scale all UVs (scale double) while in Object Mode?

I have a script that adds some array modifiers. It also adds some empties to manipulate the arrays. When I attempt to unwrap it I can't get past the 'failed, context is incorrect'

I read a little about override, but I'm not sure how to use it.

I've included the code for setting up the empties and arrays. I gets input from the user as to how many are needed. I greatly appreciate any help!

    #define selected object
    obj = bpy.context.active_object

    #store current object to select again?
    object1 = obj 


    # code so that I can move the origin of each empty
    # store the location of current 3d cursor
    #saved_location = bpy.context.scene.cursor_location.copy()  

    # give 3dcursor new coordinates
    #bpy.context.scene.cursor_location = (1.0,0.0,0.0)

    # set the origin on the current object to the 3dcursor location
    #bpy.ops.object.origin_set(type='ORIGIN_CURSOR')

    #CREATE EMPTIES TO MANIPULATE ARRAYS
    #for i in range(int(context.scene.arry_amnt)):
    #    i_amnt = i
    #    e_mount = ("E" + str(i_amnt))
    #    bpy.ops.object.text_add()
    #    obt = bpy.context.object
    #    obt.name = e_mount
    #    obt.data.body = e_mount
    #    obt.data.offset_y = i_amnt
    #    obt.show_x_ray = True
    #    obt.show_texture_space = True
    #    obt.hide_render = True

    #    if context.scene.rnd_rotation == 1:
    #        obt.rotation_euler[2] = random.randint(0,2)

    #    if context.scene.rnd_location == 1:
    #        obt.location[2] = random.randint(0,2)

        #ADD ARRAYS
    #    p = obj.modifiers.new(name= "BLIX01", type='ARRAY')
    #    p.use_relative_offset=False
    #    p.use_object_offset=True
    #    p.offset_object = bpy.data.objects[e_mount]
    #    p.count = context.scene.arry_cnt

    #how can i select the original object and unwarp / scale uv
    bpy.ops.mesh.select_all(action='DESELECT')

    bpy.ops.object.select_all(action='TOGGLE')

    object1.select = True
    bpy.ops.object.editmode_toggle()

    bpy.ops.mesh.select_all(action='DESELECT')
    bpy.ops.mesh.select_mode(type='EDGE')
    bpy.ops.mesh.mark_seam(clear=False)
    bpy.ops.mesh.select_all(action='SELECT')
    bpy.ops.object.editmode_toggle()
    bpy.ops.uv.smart_project(angle_limit=30, island_margin=0.02, user_area_weight=0.03)
$\endgroup$

1 Answer 1

3
$\begingroup$

Look for python code in bl_operators

Some default blender operators have their python code available in 2.79/scripts/startup/bl_operators in this case uvcalc_smart_project.py .A quick peruse of the code and you will see that most of it can be done in object mode, by passing operator properties to the main(...) method. . Except "aspect correction"

print("Smart Projection time: %.2f" % (time.time() - time1))
# Window.DrawProgressBar(0.9, "Smart Projections done, time: %.2f sec" % (time.time() - time1))

# aspect correction is only done in edit mode - and only smart unwrap supports currently

Quick test in console, in object mode (defaut scene camera view) (Please also note that even though blender uses radians as its rotation unitprojection_limit appears to use degrees going from 1 to 89. So pass it 30 rather than radians(30)

>>> from bl_operators.uvcalc_smart_project import main
>>> main(
main(context, island_margin, projection_limit, user_area_weight, use_aspect, stretch_to_bounds, )
>>> main(C, .02, 30, 0.03, True, True) # not radians?
Smart Projection time: 0.10

producing

enter image description here

Scaling UV is pretty trivial see python templates > Operator UV simple Script below doubles the size of object mode context object UV.

import bpy
import bmesh


def main(context):
    obj = context.active_object
    me = obj.data
    bm = bmesh.new()
    bm = bmesh.from_mesh(me)

    uv_layer = bm.loops.layers.uv.verify()
    bm.faces.layers.tex.verify()  # currently blender needs both layers.

    # scale UVs x2
    for f in bm.faces:
        for l in f.loops:
            l[uv_layer].uv *= 2

    bm.to_mesh(me)

Note:

bm.faces.layers.tex.verify()

is no longer supported in 2.80 and will need to be removed.

$\endgroup$
3
  • $\begingroup$ Thank you batFINGER!!!!! :D Is there a way I can buy you a coffee or something? I had been grappling with this for weeks. $\endgroup$
    – admbro
    Commented Jun 22, 2018 at 13:45
  • $\begingroup$ Where can I access Python templates > Operator UV simple ? $\endgroup$
    – RDK
    Commented Apr 24, 2019 at 22:32
  • $\begingroup$ text editor, templates menu. $\endgroup$
    – batFINGER
    Commented Apr 25, 2019 at 1:27

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .