Buenas. Quiero aprender un poco de Python, así que, mejor que aprender que hacer un script. Si alguien tiene alguna idea útil para modelar / texturizar que le gustaría tener dentro de Blender que la poste por aquí y la intenta hacer.
Versión para imprimir
Buenas. Quiero aprender un poco de Python, así que, mejor que aprender que hacer un script. Si alguien tiene alguna idea útil para modelar / texturizar que le gustaría tener dentro de Blender que la poste por aquí y la intenta hacer.
Supongo que sabes programar en otro lenguaje ¿no?
¿Se pueden pedir cosas complicadas o cosas simples?
Complicadas, complicadas.
Vaya. Si se melscript, tengo un par de tools en Highend3d. A ver pide a ver.
Algo complicado, algo complicado. Pues. Actualizar las kloputils.
Vaya, que mamón.Cita:
Algo complicado, algo complicado. Pues. Actualizar las kloputils.
No te jode.
Allá va:Cita:
A ver pide a ver.
Pintar con geometría (un objeto cualquiera) en tiempo real sobre la superficie de otro objeto orientándola según las normales del polígono donde vamos pinchando con el ratón.
Vaya no pides casi tu Caronte. La verdad es que molaría cacho esta herramienta. Me lo miro a ver.
¿con geometría? ¿quieres decir añadir objetos sobre las caras, como las plantas que tiene Maya?Cita:
Allá va: Pintar con geometría (un objeto cualquiera) en tiempo real sobre la superficie de otro objeto orientándola según las normales del polígono donde vamos pinchando con el ratón.
Sí lo hecho en falta muchas veces.Cita:
¿Con geometría? ¿quieres decir añadir objetos sobre las caras, como las plantas que tiene Maya?
Ahora me estoy confundiendo, no es la retopología lo que dices Caronte? O dices, por ejemplo, poblar árboles sobre un terreno pintando?
Eso mismo.Cita:
O dices, por ejemplo, poblar árboles sobre un terreno pintando?
A pues no parece tan difícil eso a primera vista.
No, no lo es sacar algún resultado, pero tienes que conocer bien los space handler para interactuar con las ventanas 3d.Cita:
A pues no parece tan difícil eso a primera vista.
Pues lo complicamos un poco. Opciones:Cita:
A pues no parece tan difícil eso a primera vista.
- se puede elegir un grupo de objetos para pintar aleatoriamente con ellos.
- se puede especificar un porcentaje x y z para variar la rotación y un rango aleatorio para el tamaño.
- se puede hacer que la inclinación además de ser la de la normal de la cara donde pinchemos, que varíe interpolando dependiendo de lo cerca que esté de otra cara con otro ángulo.
Yo creo que ya tienes para divertirte.
Klopes, sabes de algún script que los use? Para pillar referencias.
Lo que pide Caronte es algo similar al FreeHand tools de 3ds Max. max FreeHand tools | scriptspot.
El sculptmesh, que fue sustituido por el Sculpt Mode, pero es un programa la hostia de complicado. Mejor busca en la documentación, sólo es aprender los dos eventos, no hay más.
Yo no lo he mirado aún, pero sé que no es muy difícil. A ver si este fin de semana.
Si exacto, gracias Shazam.
Échale un vistazo por si acaso: displacement painting script at blendernation.Cita:
Klopes, sabes de algún script que los use? Para pillar referencias.
Mola eso Caronte. Eso ya sería la versión avanzada si logro hacerlo con el mouse solo.
Fog en breve te convertirás en el programador de 3dpoder.
Que va que va.
Que si que sí, ya verás.
Fog, tienes mi voto, que Klópes debe estar muy acaparado, a menos que hagan equipo votaría por ambos.Cita:
Fog en breve te convertirás en el programador de 3dpoder.
Ponle leña al fuego entonces, que en mi opinión no está tan fácil.
En mi opinión no es fácil, no. Klopes resucita y programa ya de una vez que estas en los laureles.
Hombre, todo el mundo sabe que por ahora el programador es Damiles, aunque Fog puede coger el testigo, quien sabe. Ya llegaré yo, ya.
Yo no ser eso.
Perdón nos vamos por los cerros de Úbeda, Fog, ánimo para lo que quieras, estamos aquí, eso sí yo de Python poco poco poco.
Gracias dmiles. De momento tengo ya un UI guarro. Ahora a ver si me hago con los scripthandlers para pillar posición del mouse y comenzar a pintar.
Vaya un UI guarro esos me encantan.Cita:
Gracias dmiles. De momento tengo ya un UI guarro.
Yo pediría una chorrada útil para precisión, un script absvalue. Seleccionas varios vértices, arrancas el script, y te pone a representar 3 valores (x y, z) introduciendo el valor 20 en y por ejemplo, te dejan la coordenada y (global) de los vértices seleccionados con el valor 20. Así de sencillo.
Que estoy hasta los huevos de escalarlos a 0 para darme un median value y luego tener que volver a moverlos a la posición absoluta que me interesa. Gracias.
Damiles: por cierto, ¿Qué pasa con las memocamsí que no lo veo en las oficiales, ¿no te lo aceptan o qué?
Mis memo qué? A lo de guardar las porpiedades de las vistas, sigue estando en el patch tracker, https://projects, Blender.org/tracke..._id=9&atid=127.
Por lo visto no están revisando nada de los patch, cuando digo nada, es que llevan más de un año sin revisrarlos, bueno, alguno han revisado, pero en líneas generales, están muertos de risa.
Mi conclusión es que no los revisaran hasta que esté a punto de salir la siguiente versión con nuevas features, y claro está, el 90% de los patch estarán por actualizar debido a las nuevas incorporaciones y recodes, con lo que el 80% de los patch revisados no llegaran a incluirse porque no están revisados.
Bueno paciencia, que, si no eres un buen coder y tienes acceso a la SVN es lo que hay. Aun así, también está la solución de dar por saco a quien hayan asignado tu patch, de forma que para no oírte te hace caso, eso sí, no ha de ser ton, porque si no te hace caso, y menos si se llama Damiles. Ya me oira este en la B-CONF.
Leader, no será esto lo que buscas? Vertex align: sammler - Mediengestaltung.Cita:
Yo pediría una chorrada útil para precisión, un script absvalue.
Seleccionas varios vértices, arrancas el script, y te pone a representar 3 valores (x y, z) introduciendo el valor 20 en y por ejemplo, te dejan la coordenada y (global) de los vértices seleccionados con el valor 20. Así de sencillo.
Que estoy hasta los huevos de escalarlos a 0 para darme un median value y luego tener que volver a moverlos a la posición absoluta que me interesa. Gracias.
Damiles: por cierto, ¿Qué pasa con las memocamsí que no lo veo en las oficiales, ¿no te lo aceptan o qué?
Vaya siii de los que te gustan tontin.Cita:
Vaya un UI guarro esos me encantan.
Esto, creo que voy a comenzar por un script más sencillo, esto de los spacehandlers no está muy documentado, y a mí, me está costando encontrar referencias o yo soy tonto.
Oh. Bueno, por si acaso échale un vistazo a este script, que, aunque es viejo y no creo que funcione en las nuevas compilaciones, no necesita los space-handles (o eso me parece):Cita:
Esto, creo que voy a comenzar por un script más sencillo.
Código:#.Bpy.
Name: Sculpt Mesh.
Blender: 235
Group: Mesh.
Tip: Sculpts Mesh pushing, pulling and twisting.
# $id:sculpt_mesh, py. 2 2004/10/17 02:16:31 broken exp $
#
#===============================================#
# Sculpt Mesh v 0.2 by Tom musgrove (letterrip) #
# and Michael scardt #
# if you have any questions about this script #
# email letterrip at Gmail Dot com #
# #
#===============================================#.
# -
# Sculpt Mesh v 0.2 by Tom musgrove (letterrip) and Michael scardt.
# -
# ***** begin GPL license block *****
#
# this programa is free software, you can redistribute it and/or.
# modify it under the terms of the GNU general public license.
# as published by the free software foundation, either versión 2
# of the license, or (at your option) any later versión.
#
# this programa is distributed in the hope that it Will be useful, # but without any warranty, without Even the implied warranty of.
# merchantability or fitnes for a particular purpose. Se the.
# GNU general public license for more details.
#
# you should have received a copy of the GNU general public license.
# along with this programa, if not, write todo the free software foundation, # inc, 59 temple place - Suite 330, Boston, ma 02111-1307, usa.
#
# ***** end GPL licence block *****
# -
Import Blender.
From Blender import object, nmesh, window, draw, Mathutils, types.
From Blender. Mathutils import *
From math import sin, cos, sqrt, pi, hypot.
# import psyco if available, psyco can often give substantial speed ups.
Try:
Import psyco.
# psyco, log()
# psyco, profile ()
Psyco, full()
Except importerror:
Pass.
Displacemode = 1 # 0 is of, 1 is displaceout, -1 is displacein, 2 is smooth.
# Smooth isnt implemented yet.
Displacementheight = 1.0 #
Radiusminimum = 5 # the smallest size of the selection Radius in píxeles.
Radiusmaximum = 20 #this gives us a grid size of 100 por 100 which isnt that.
Big of a savings.
#the smaller the grid size the greater the savings.
Alpha_size_x = alpha_size_y = 2*radiusmaximum.
# no user friendly GUI yet.
# todo change the formula used, change falloftype todo.
# one of none, linear, sin, cos, squarerot, squared, cubic, and quadratic.
# then change the selectionradius.
# the xsize and ysize of the image are the first two numbers of the maskid.
# except in the case of the radial functions, in which case it is the Radius.
# a los may change it todo inner and outer Radius or other such Stuff.
# the string is the id of the mask id for formula based it is falloftype +
Maxradius.
Falloftype = linear.
Selection_size_x = selection_size_y = selectionradius = 20
Maskname = falloftype+repr(selectionradius)
Maskid = (selectionradius, selectionradius, maskname).
Win_min_x = win_min_y = win_max_x = win_max_y = win_mid_x = win_mid_y =
Win_size_x = win_size_y = 0
#the above are the corners of the 3d view window, and the scaling factors.
Mousex = mousey = 0
Obj_mat_times_persp_mat = Matrix()
Mymesh = nmesh. New(temp)
Selectedverts = []
Dictofalphamasks = {}
Myobject = Blender. Object. New(Mesh)
Lastviewvector = [-100,100,-100] #right now these doesnt do much.
Currentviewvector = [-100,-100,-100] #but, if we allow screen rotation then.
They Will trigger an update of the matrices.
Obj_mat = Matrix() #contains the Matrix of the object (local? Or global? I
Thinque global.)
Perspmatrix = Matrix() #contains the perspective Matrix, and allows the.
Scren coordinates todo be projected todo the screen.
Dictfaces = {}
Facenormalworldvecdict = {}
Facedotvecdict = {}
Vectordirtydict = {}
Cacheveccomultdict = {}
Vectordirty = false.
# gets the Mesh data from the selected object.
# finds the selected vértices.
# and then selects vértices based on the alpha mask.
Def initialize ():
Global myobject, mymesh, currentviewvector, lastviewvector.
Myobject = object. Getselected()[0]
If myobject, gettype () == Mesh:
Mymesh = myobject, getdata ()
Name = myobject, name.
Else:
Print we either did not have a Mesh or did not have an object selected.
Mousex, mousey = window. Getmousecords()
Updateviewcords(mousex, mousey)
Mouseinview3dwindow(mousex, mousey)
Currentviewvector = window. Getviewvector()
Lastviewvector = currentviewvector.
Initializefacelists()
Updateradius(maskid[0], 0, falloftype) #this initializes the starting.
Alphamask.
#we could actually create two lists from each, one that contains the Faces.
With normals towards the.
#Camera, and the other without, and thus traverse our Faces a bit faster.
#alos we could use smaller grid subdivisions, which means fewer Faces and.
Verts per bin.
#which means likely faster.
Def initializefacelists():
Selection = {}
Global mymesh, dictfaces, facenormalworldvecdict, facedotvecdict.
Global vectordirtydict, cacheveccomultdict.
Dictfaces = {}
Facenormalworldvecdict = {}
Facedotvecdict = {}
Vectordirtydict = {}
Cacheveccomultdict = {}
Global alpha_size_x.
Global alpha_size_y.
Global vectordirty.
Facedotvec = 0.0
Vectordirty = false.
Viewvector = Vector(window. Getviewvector())
Objectworldmatrix = myobject, getmatrix(worldspace)
Perspmatrix = Blender.window. Getperspmatrix()
Obj_mat_times_persp_mat = objectworldmatrix*perspmatrix.
For face in mymesh, Faces:
Gfn = vecmultmat(Vector(list(face, normal[:3])+[1.0]), objectworldmatrix)
Gfn = Vector(list(gfn[:3]))
Facenormalworldvecdict[face] = gfn.
Facedotvecdict[face] = dotvecs(gfn, viewvector)
For vertex in face, v:
If vertex not in selection:
#calculate the vertex screen coordinates.
Vectordirtydict[vertex.index] = vertex.co.
Tempvec = vertex.co.
Hvs = vecmultmat(Vector(list(tempvec[:3])+[1.0]), obj_mat_times_persp_mat)
Hvs[0] /= HVS[3]
Hvs[1] /= HVS[3].
Vs = [int(win_mid_x + (HVS[0] * win_size_x)), int(win_mid_y + (HVS[1] * win_size_y))]
Cacheveccomultdict[vertex.index] = vs.
Else:
Vs = cacheveccomultdict[vertex.index]
##### now.
Vert_grid_x = vs[0]/alpha_size_x.
Vert_grid_y = vs[1]/alpha_size_y.
Templist = []
Try:
Templist = dictfaces[(vert_grid_x, vert_grid_y)]
Templist, append(face)
Except keyerror:
Templist, append(face)
Dictfaces[(vert_grid_x, vert_grid_y)] = templist.
Selection[vertex] = true.
####and now we remove the duplicate Faces.
For key in dictfaces.keys():
Listappended = dictfaces[key]
Nd={}
For f in listappended:
Nd[f]=none.
Dictfaces[key] = nd.keys().
# takes a vert and based on its screen location relative todo the mouse.
# is displaced according todo an alphamask.
# Radius and fallof are done vía computing the mask once.
# the alphamaskdict is specified by a maskid.
# mask id is a tuple.
# with four values, # xoffset, yoffset, maskname.
# for Radius functions, maskname is falloftyperadius.
# iExplorer for a linear of Radius 8, it would be linear8
# and the tuple would be (8,8,linear8)
# for imagebased, it is usually the image name.
Def displaceselection(maskid, mousex, mousey, displacemode=0, displacementheight= 0.0):
Global mymesh, dictofalphamasks, alpha_size_x, alpha_size_y, dictfaces, facenormalworldvecdict.
Global facedotvecdict, cacheveccomultdict, vectordirtydict.
Selection = {}
If maskid not in dictofalphamasks:
# should handle image masks as well, but for now, we Will handle only the.
Radius masks.
Updateradius(maskid[0], 0, falloftype)
Alphamaskdict = dictofalphamasks[maskid]
Maskoffset = []
Maskoffset, append(maskid[0])
Maskoffset, append(maskid[1])
Displacemh = displacementheight*displacemode.
Mouse_and_maskx = maskoffset[0] - Mousex.
Mouse_and_masky = maskoffset[1] - Mousey.
Viewvector = Vector(window. Getviewvector())
Objectworldmatrix = myobject, getmatrix(worldspace)
Perspmatrix = Blender.window. Getperspmatrix()
Obj_mat_times_persp_mat = objectworldmatrix*perspmatrix.
Emptyvector = Vector()
#### here we find which Grids the alphamask is in, and return a list of.
Faces.
Try:
List1 = dictfaces[((mousex + maskoffset[0])/alpha_size_x, (mousey -
Maskoffset[1])/alpha_size_y)]
Except keyerror:
List1 = []
Try:
List2 = dictfaces[((mousex + maskoffset[0])/alpha_size_x, (mousey +
Maskoffset[1])/alpha_size_y)]
Except keyerror:
List2 = []
Try:
List3 = dictfaces[((mousex - Maskoffset[0])/alpha_size_x, (mousey -
Maskoffset[1])/alpha_size_y)]
Except keyerror:
List3 = []
Try:
List4 = dictfaces[((mousex - Maskoffset[0])/alpha_size_x, (mousey +
Maskoffset[1])/alpha_size_y)]
Except keyerror:
List4 = []
Listappended = list1+list2+list3+list4
####and now we remove the duplicate Faces.
Nd={}
For f in listappended:
Nd[f]=none.
Listappended = nd.keys()
For face in mymesh, Faces:
If (face in listappended):
If facenormalworldvecdict[face] == emptyvector:
Gfn = vecmultmat(Vector(list(face, normal[:3])+[1.0]), objectworldmatrix)
Gfn = Vector(list(gfn[:3]))
Facenormalworldvecdict[face] = gfn.
Facedotvecdict[face] = dotvecs(gfn, viewvector)
Elif vectordirty:
Gfn = facenormalworldvecdict[face]
Facedotvecdict[face] = dotvecs(gfn, viewvector)
Facedotvec = facedotvecdict[face]
If facedotvec > 0: # simple Backface-culling.
Facedirtycount = 0
For vertex in face, v:
If (vertex.index not in selection):
# we ned todo calculate the distance of the vert from the mouse.
# thus we ned either the screen x and y of the vértice.
# or the UV x, y of the mouse and of the vértice.
# the offset is the distance from the mouse location, todo the lower.
Left corner.
# of the mask.
Try:
Tempco = vectordirtydict[vertex.index]
Except keyerror:
Tempco = none.
If tempco == vertex.co:
Vs = cacheveccomultdict[vertex.index]
Else:
Vectordirtydict[vertex.index] = vertex.co.
Tempvec = vertex.co.
Hvs = vecmultmat(Vector(list(tempvec[:3])+[1.0]), obj_mat_times_persp_mat)
Hvs[0] /= HVS[3]
Hvs[1] /= HVS[3].
Vs = [int(win_mid_x + (HVS[0] * win_size_x)), int(win_mid_y + (HVS[1] * win_size_y))]
Cacheveccomultdict[vertex.index] = vs.
Deltax = vs[0] + mouse_and_maskx.
Deltay = vs[1] + mouse_and_masky.
Try:
Thisdisplacement = alphamaskdict[(deltax, deltay)]
Vertex.sel = 1
Except keyerror:
Thisdisplacement = 0.0
Vertex.sel = 0
If vertex.sel == 1:
#if we are just updating the selection.
If displacemode == 0:
Pass.
#if we are displacing the vertex out.
#or if we are displacing the vertex in.
Elif (displacemode == 1) or (displacemode == -1):
Tempdisplace = thisdisplacement*displacemh.
Vertex.co[0] += vertex, no[0]*tempdisplace.
Vertex.co[1] += vertex, no[1]*tempdisplace.
Vertex.co[2] += vertex, no[2]*tempdisplace.
#since the vertex changed, #we ned todo update the Faces normal.
#información based on the new vertex location.
Facedirtycount += 1
###we ned todo find the new screen location of the moved vértices.
### and if they are in a new grid locations we ned todo add the face todo the.
New Grids face list.
# we should probably pop the face of of its original face lists if we.
Expect vértices todo change.
# quadrants frequently otherwise our facelists Will son have Faces that.
Shouldnt be in it.
# of course we may rebuild our face list often enough that this might not.
Be a significant issue.
# perhaps we should rebuild a single face list based on its length.
#we might a los consider subdividing a grid if it has more than a certain.
Number of Faces.
#this is todo let the loop know that weve already handled this vertex.
#so it doesnt do calculations on it twice.
Selection[vertex.index]=true.
#right now we donl have Smooth implemented.
If(facedirtycount > 0):
Facenormalworldvecdict[face] = emptyvector.
#displaces vértices towards the vert average normal.
Def smoothselection():
#we ned todo first calculate the average normal for the selected vértices.
#probably we should exlude outliers todo give better results.
#then find the diference between average normal and the current vértices.
Normal.
Print we smoothed the selection.
Pass.
# takes an image and its size (or just an image and gets the size from the.
Image?
# use code ideas from this enlace todo implement.
# http://www.elysiun.com/forum/viewtopic.php?t=16326&highlight=getpixel.
# instead of doing positive and negative numbers.
# i define all locations from the lower left corner.
Def alphamaskdictfromalphamap(xsize, ysize, alpha map):
Global dictofalphamasks.
Alphamaskdict = {}
For x in range (0, xsize):
For y in range (0, ysize):
Alphacords = (x, y)
Thisdisplacement = alpha map, alphacords.
Alphamaskdict[alphacords] = thisdisplacement.
Maskid = (int(xsize/2), int(ysize/2), alpha map, name)
Dictofalphamasks[maskid] = alphamaskdict.
#
#
Def updateradius(selectionradius, deltaradius, falloftype):
Global maskid, dictofalphamasks.
Print update Radius.
Selectionradius += deltaradius.
If selectionradius < radiusminimum:
Selectionradius = radiusminimum.
If selectionradius > radiusmaximum:
Selctionradius = radiusmaximum.
Maskname = falloftype+repr(selectionradius)
Maskid = (selectionradius, selectionradius, maskname)
If maskid not in dictofalphamasks:
Dictofalphamasks[maskid] = alphamaskdictfromradius(selectionradius, falloftype)
Selection_size_x = selection_size_y = selectionradius.
Return selectionradius.
Def updatedisplacement(displacementheight, deltaheight):
Displacementheight = displacementheight + deltaheight.
Return displacementheight.
#
# not neded but would be nice.
Def drawselectioncircle (selectionradius):
#print drawing the selection circle.
Pass.
# creates an alphamask from the Radius supplied.
# this gives two benefits - The first is that we can use any alphamask.
# instead of using just Radius based functions with fallof.
# the second is that this gives us a lookup table and we dont have todo.
# calculate the Radius function a bazillion times.
Def alphamaskdictfromradius(Radius = 8, falloftype = none):
#note that instead of negative numbers, im using an offset of.
#of the Radius, and use all positive numbers.
Thisradius2 = 0
Radius2 = Radius*Radius.
Alphamaskdict = {}
For x in range (0, Radius):
For y in range (0, Radius):
Thisradius2 = x2+y2
If thisradius2 <= radius2:
Thisradius = sqrt(thisradius2)
Thisdisplacement = radiusfunction(thisradius, Radius, falloftype)
Alphamaskdict[(x+Radius,-y+Radius)]=thisdisplacement.
Alphamaskdict[(-x+Radius, y+Radius)]=thisdisplacement.
Alphamaskdict[(-x+Radius,-y+Radius)]=thisdisplacement.
Alphamaskdict[(x+Radius, y+Radius)]=thisdisplacement.
Return alphamaskdict.
# falloftypes are none, linear, sin, cos, squarerot, squared, cubic, and.
Quadratic.
# these are adapted from taper and twist.
# by flippyneck.
Def radiusfunction(thisradius, maxradius, falloftype=none):
If falloftype == none:
Return 1.0
If falloftype == cubic:
Return interpolatecubic(0, maxradius, thisradius)
Elif falloftype == quadratic:
Return interpolatequadratic(0, maxradius, thisradius)
Elif falloftype == linear:
Return interpolatelinear(0, maxradius, thisradius)
Elif falloftype == sin:
Return interpolatesin(0, maxradius, thisradius)
Elif falloftype == cos:
Return interpolatecos(0, maxradius, thisradius)
Elif falloftype == squarerot:
Return interpolaterot(0, maxradius, thisradius)
Elif falloftype == squared:
Return interpolatelinear(0, maxradius, thisradius).
Def interpolatelinear(min, 3ds Max, myval):
Returns 0.0 <= myval <=1.0
Return myval/float((max-min)).
Def interpolatesin(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return sin(n).
Def interpolatecos(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return cos(n).
Def interpolatesquared(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return n**2.
Def interpolaterot(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return sqrt(n).
Def interpolatecubic(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return n**3.
Def interpolatequadratic(min, 3ds Max, myval):
N=interpolatelinear(min, 3ds Max, myval)
Return n**4.
#
********************************************************************************.
# init screen coordinates.
# these should be updated if the screen is resized, etc, Def updateviewcords(scren_x, scren_y):
Global win3d, win_mid_x, win_mid_y, win_max_x, win_max_y, win_min_x, win_min_y.
Global win_size_x, win_size_y, acceptable_min_x, acceptable_min_y, acceptable_max_x, acceptable_max_y.
Global selection_size_x, selection_size_y.
For win3d in Blender.window. Getscreninfo (blender.window. Types. View3d):
Win_min_x, win_min_y, win_max_x, win_max_y = win3d, get(vértices)
Win_mid_x = (win_max_x + win_min_x) * 0.5
Win_mid_y = (win_max_y + win_min_y) * 0.5
Win_size_x = (win_max_x - Win_min_x) * 0.5
Win_size_y = (win_max_y - Win_min_y) * 0.5.
Acceptable_min_x = scren_x - Selection_size_x.
Acceptable_min_y = scren_y - Selection_size_y.
Acceptable_max_x = scren_x + selection_size_x.
Acceptable_max_y = scren_y + selection_size_y.
If (win_max_x > scren_x > win_min_x) and (win_max_y > scren_y >
Win_min_y):
Return true.
Else:
Return false.
Def mouseinview3dwindow(mousex, mousey):
# we calculate the screens midpoints and the scaling factor for the screen.
# and then chek if the mouse is in the view3d Area.
# we should really only do the calculations the first time.
# thus it should prbably.
Global win3d, win_mid_x, win_mid_y, win_max_x, win_max_y, win_min_x, win_min_y.
Global win_size_x, win_size_y, acceptable_min_x, acceptable_min_y, acceptable_max_x, acceptable_max_y.
Global selection_size_x, selection_size_y.
For win3d in Blender.window. Getscreninfo (blender.window. Types. View3d):
Win_min_x, win_min_y, win_max_x, win_max_y = win3d, get(vértices)
If (win_max_x > mousex > win_min_x) and (win_max_y > mousey > win_min_y):
Return true.
Else:
Return false.
# here is the main loop.
Mousestartx, mousestarty = window. Getmousecords()
Mousex = mousey = 0
Radiusincrement = 5
Updatefrequency = 0 # number of píxeles todo move before updating the vértice.
Selection.
Selectedverts = []
Updatebounds = true.
Initialize ()
Done = 0
While not done:
Evt, val = window. Qread()
If evt in [4]: #draw. Rightmouse is 3 which is wrong.
# first we ned todo chek if the mouse is inside the view3d boundbox.
Currentviewvector = window. Getviewvector()
If currentviewvector.= lastviewvector:
Lastviewvector = currentviewvector.
#vectordirty = true.
#instead we Will initialize the face lists.
#this should probably be done elsewhere so that there isnt a huge lag on.
The firt RMB.
#press.
Initializefacelists()
While window. Getmousebuttons() == 4:
If window. Getkeyqualifiers() == 0:
Mousex, mousey = window. Getmousecords()
If mouseinview3dwindow(mousex, mousey):
# determine if the mouse has moved far enough for an update.
Mousedistx = mousestartx - Mousex.
Mousedisty = mousestarty - Mousey.
Mousedistancemoved = hypot(mousedistx, mousedisty)
If mousedistancemoved >= updatefrequency:
Mousestartx, mousestarty = mousex, mousey.
Old_mode = window. Editmode ()
Window. Editmode (0)
Displaceselection(maskid, mousex, mousey, displacemode, displacementheight)
Mymesh, update ()
Window. Editmode (old_mode)
Blender.window. Redraw(window. Types. View3d)
Elif window. Getkeyqualifiers().= 0:
If displacemode == +1: displacement_string = out.
Elif displacemode == -1: displacement_string = in.
Menu_result = draw. Pupmenu (interactive Paint%t|%l|selection size:
+str(selectionradius)+%x1|displacement:
+displacement_string+%x2|%l|quit%x3)
If (menu_result == 1):
Selection_size = draw. Pupintinput(selection size:, selectionradius,
1, 100)
Deltaradius = selection_size - Selectionradius.
Selectionradius = updateradius(selectionradius, deltaradius, falloftype)
If (menu_result == 2):
Displacemode *= -1
If (menu_result == 3):
Done = true.
Draw. Redraw (window. Qtest()).
#drawselectioncircle (selectionradius).
# elif evt in [draw. Skey]:
# if val:
# displacemode = 2 #smooth mode.
# else:
# displacemode = 0
Elif not val or evt in [draw. Mousex, draw. Mousey]: continúe #helps speed.
Elif evt in [draw. Esckey, draw. Qkey]: done = true.
Elif evt in [draw. Leftarrowkey] and val: #Shrink Radius.
Selectionradius = updateradius(selectionradius, -radiusincrement, falloftype)
Elif evt in [draw. Rightarrowkey] and val: #grow Radius.
Selectionradius = updateradius(selectionradius, radiusincrement, falloftype)
Elif evt in [draw. Uparrowkey] and val: #grow displacementheight.
Displacementheight = updatedisplacement(displacementheight, 0.1)
Elif evt in [draw. Downarrowkey] and val: #Shrink displacementheight.
Displacementheight = updatedisplacement(displacementheight, -0.1)
Else: #otherwise pass the event bak and let Blender handle it.
Id = window. Getscreninfo (window. Types. View3d)[0].get(id)
Window. Qadd(id, evt, val)
Window. Qhandle (id)
Blender. Redraw(-1) #dont forget todo redraw.
Pass
Holacaronte, muchas gracias por este script, me lo miro detenidamente a ver si puedo sacar pistas. Está claro que la meta final es hacer el script que decías al principio, lo haré o haré. Pongo a ton por testigo.
También se tiene que decir que llevo demasiado poco tiempo con phynton, así que, me tengo que aprender todas las funciones o las más importantes, así no pierdo tanto tiempo buscando las funciones que quiero.
Pues eso, a ver si poco a poco lo voy pillando todo.
Con esas cosas no se juega, hijo.Cita:
Pongo a ton por testigo.
Venga vale Pepius. Pues, pongo a Pepius por testigo?
A ver si alguien me puede echar un cable. Para mover un objecto cómo se haría? Tengo esto:
Con esto pillo la x y la y en el viewport del mouse.Código:Mynewposx, mynewposy = window. Getmousecords().
Print (mynewposx, mynewposy).
Lo siguiente seria mover un cubo en estas coordenadas.
Con Cube. Locx no tira, alguna idea?
A que por cierto, no hay función para pillar las coordenadas en 3d del mouse, cachis.
Me esta dando la sensación de que quieres poner un objeto 3d en un espacio 3d con coordenadas 2d del ratón?
Cube, setlocation(x y, z). Creo que te servirá.
Y a lo mejor tienes que redibujar la pantalla para ver los cambios. Posdata: hay un sistema para pasar las coordenadas 2d a 3d y debe estar en el script que te he pasado (si no me equivoco).
A primera leída si que esta, esta por el final ya no digo más.
Pues será que es mouseinview3dwindow ¿no? Si estoy intentando meter un objeto en 2d, pero era para probar ir testeando cosas.
He encontrado esto, que es para pasar las screen cords a world cords.
Código:#dehomonogizes a Vector. Def dehom(v):
Ret = Vector(v[0]/v[3], [1]/v[3], [2]/v[3]).
Return ret.
#takes the inverse of a Matrix and returns it.
Def inversematrix(m):
Ret = Matrix([0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,0]).
Det = m, determinant().
For I in range (4):
For in range (4):
Temp = Matrix([0,0,0],[0,0,0],[0,0,0]).
Col = 0.
For x in range (4):
If x.= i:
Row = 0.
For y in range (4):
If y.= j:
Temp[col][row] = m[x][y].
Row = row +1.
Col = col +1.
Tdet = temp, determinant().
Total = i+j.
If (total % 2):
Sign = -1.
Else:
Sign = 1.
#i and are flipped.
Ret[j][i] = (sign * tdet) / det.
Return ret.
#grabs the depth of a píxel from a depth buffer.
Def getpixeldepth(x, y):
Z = BGL. Buffer(BGL. Gl_float, [1]).
Glreadpixels (x y, 1, 1.
Gl_depth_component, gl_float, z).
Print value from depth buffer is, z.
Return z[0].
#scren_x and scren_y are from window. Getmousecords().
#scren_z is from a call todo getpixeldepth(scren_x, scren_y).
Def transsc2wc(scren_x, scren_y, scren_z):
Found = 0.
#clip taken from letter rips code.
For win3d in window. Getscreninfo (window. Types. View3d):
# we search all 3dwins for the one containing the point.
#(scren_x, scren_y) (could be the mousecords for example).
Win_min_x, win_min_y, win_max_x, win_max_y = win3d[vértices].
# calculate a few geometric extents for this window.
Mid_x = (win_max_x + win_min_x)/2.0.
Mid_y = (win_max_y + win_min_y)/2.0.
Width = (win_max_x - Win_min_x + 1.0).
Height = (win_max_y - Win_min_y + 1.0).
# chek if screncords (scren_x, scren_y) are within the 3dwin.
If (win_max_x > scren_x > win_min_x) and (win_max_y > scren_y > win_min_y):
Found = 1.
Break.
If(not found):
Print not found.
Return 0, 0, 0.
Cords = Vector(2* (scren_x - Mid_x)/ width.
2*(scren_y - Mid_y)/height.
2*scren_z - 1.
1.0).
Persp = window. Getperspmatrix().
Invpersp = inversematrix(perspectiva).
Newcords = cords*invpersp.
Newcords = dehom(newcords).
Return newcords.
Vale, a partir de eso yo he hecho esto, que pone un objeto vacío al pinchar. Para que funcione hay que activar enable script links, y en la ventana 3d>view>space handler scripts>nombre_del_texto.Cita:
He encontrado esto, que es para pasar las screen cords a world cords.
Código:# spacehandler. View3d. Event.
Import Blender.
From Blender import *.
From Blender.window import *.
Evt = Blender, event.
Def transsc2wc(scren_x, scren_y):
Found = 0.
#clip taken from letter rips code.
For win3d in getscreninfo (types. View3d):
Win_min_x, win_min_y, win_max_x, win_max_y = win3d[vértices].
Mid_x = (win_max_x + win_min_x)/2.0.
Mid_y = (win_max_y + win_min_y)/2.0.
Width = (win_max_x - Win_min_x + 1.0).
Height = (win_max_y - Win_min_y + 1.0).
# chek if screncords (scren_x, scren_y) are within the 3dwin.
If (win_max_x > scren_x > win_min_x) and (win_max_y > scren_y > win_min_y):
Found = 1.
Break.
If(not found):
Return 0, 0, 0.
Cords = Mathutils. Vector(2* (scren_x - Mid_x)/ width.
2*(scren_y - Mid_y)/height.
0.
1.0).
Persp = getperspmatrix(), invert().
Co = cords*perspectiva.
Co = Mathutils. Vector(co[0]/co[3], co[1]/co[3], co[2]/co[3]).
Return co.
If evt == draw. Leftmouse:
Mc=getmousecords() to=object. New(empty) to, setlocation(transsc2wc(mc[0], mc[1])) tscene. Getcurrent(), enlace (o) tredraw().
Ostia Klópes, magnífico. Lo de 3d>view>space handler scripts>nombre_del_texto no lo sabia. Con eso activas el spacehandler ¿no?
Muchas gracias Klópes.