blender/release/scripts/flt_palettemanager.py
2008-08-09 10:12:59 +00:00

505 lines
13 KiB
Python

#!BPY
"""
Name: 'FLT Palette Manager'
Blender: 240
Group: 'Misc'
Tooltip: 'Manage FLT colors'
"""
__author__ = "Geoffrey Bantle"
__version__ = "1.0 11/21/2007"
__email__ = ('scripts', 'Author, ')
__url__ = ('blender', 'blenderartists.org')
__bpydoc__ ="""\
This script manages colors in OpenFlight databases. OpenFlight is a
registered trademark of MultiGen-Paradigm, Inc.
Todo:
-Figure out whats causing the PC speaker to beep when initializing...
Feature overview and more availible at:
http://wiki.blender.org/index.php/Scripts/Manual/FLTools
"""
# --------------------------------------------------------------------------
# flt_palettemanager.py version 1.0 2005/04/08
# --------------------------------------------------------------------------
# ***** BEGIN GPL LICENSE BLOCK *****
#
# Copyright (C) 2007: Blender Foundation
#
# This program 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 version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software Foundation,
# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#
# ***** END GPL LICENCE BLOCK *****
# --------------------------------------------------------------------------
import Blender.Draw as Draw
from Blender.BGL import *
import Blender
import flt_properties
import flt_defaultp as defaultp
from flt_properties import *
def RGBtoHSV( r, g, b):
minc = min( r, g, b )
maxc = max( r, g, b )
v = maxc
delta = maxc - minc
if( max != 0 ):
s = delta / maxc
else:
s = 0
h = -1
return (h,s,v)
if( r == maxc ):
h = ( g - b ) / delta
elif( g == maxc ):
h = 2 + ( b - r ) / delta
else:
h = 4 + ( r - g ) / delta
h *= 60
if( h < 0 ):
h += 360
return(h,s,v)
def HSVtoRGB(h,s,v):
if( s == 0 ):
return (v,v,v)
h /= 60
i = math.floor( h)
f = h - i
p = v * ( 1 - s )
q = v * ( 1 - s * f )
t = v * ( 1 - s * ( 1 - f ) )
if i == 0:
r = v
g = t
b = p
elif i == 1:
r = q
g = v
b = p
elif i== 2:
r = p
g = v
b = t
elif i==3:
r = p
g = q
b = v
elif i==4:
r = t
g = p
b = v
else:
r = v
g = p
b = q
return(r,g,b)
palette_size = 12
palette_x = 0
palette_y = 0
colors = list()
curint = 1.0
curswatch = 0
#make a default palette, not very useful.
cinc = 1.0 / 1024.0
cstep = 0.0
picker = None
ptt = ""
ts1=None
ts2=None
ts3=None
ts4=None
ts5=None
for i in xrange(1024):
colors.append([cstep,cstep,cstep])
cstep = cstep + cinc
def update_state():
state = dict()
state["activeScene"] = Blender.Scene.getCurrent()
state["activeObject"] = state["activeScene"].getActiveObject()
state["activeMesh"] = None
if state["activeObject"] and state["activeObject"].type == 'Mesh':
state["activeMesh"] = state["activeObject"].getData(mesh=True)
state["activeFace"] = None
if state["activeMesh"]:
if state["activeMesh"].faceUV and state["activeMesh"].activeFace != None:
state["activeFace"] = state["activeMesh"].faces[state["activeMesh"].activeFace]
return state
def pack_face_index(index, intensity):
return ((127*intensity)+(128*index))
def unpack_face_index(face_index):
index = face_index / 128
intensity = float(face_index - 128.0 * index) / 127.0
return(index,intensity)
def event(evt,val):
global palette_size
global palette_x
global palette_y
global colors
global curint
global curswatch
areas = Blender.Window.GetScreenInfo()
curarea = Blender.Window.GetAreaID()
curRect = None
editmode = 0
for area in areas:
if area['id'] == curarea:
curRect = area['vertices']
break
if evt == Draw.LEFTMOUSE:
mval = Blender.Window.GetMouseCoords()
rastx = mval[0] - curRect[0]
rasty = mval[1] - curRect[1]
swatchx = (rastx -palette_x) / palette_size #+state["palette_x"]
swatchy = (rasty -palette_y) / palette_size #+state["palette_y"]
if rastx > palette_x and rastx < (palette_x + palette_size * 32) and rasty > palette_y and rasty < (palette_y+ palette_size* 32):
if swatchx < 32 and swatchy < 32:
curswatch = (swatchx * 32) + swatchy
Draw.Redraw(1)
elif swatchy < 34 and swatchx < 32:
curint = 1.0 - (float(rastx-palette_x)/(palette_size*32.0))
Draw.Redraw(1)
#copy current color and intensity to selected faces.
elif evt == Draw.VKEY:
if Blender.Window.EditMode():
Blender.Window.EditMode(0)
editmode = 1
state = update_state()
#retrieve color from palette
color = struct.unpack('>BBBB',struct.pack('>i',colors[curswatch]))
actmesh = state["activeMesh"]
if actmesh:
if(Blender.Window.GetKeyQualifiers() != Blender.Window.Qual["CTRL"]):
selfaces = list()
for face in actmesh.faces:
if face.sel:
selfaces.append(face)
if not "FLT_COL" in actmesh.faces.properties:
actmesh.faces.addPropertyLayer("FLT_COL",Blender.Mesh.PropertyTypes["INT"])
for face in actmesh.faces:
face.setProperty("FLT_COL",127) #default
try:
actmesh.activeColorLayer = "FLT_Fcol"
except:
actmesh.addColorLayer("FLT_Fcol")
actmesh.activeColorLayer = "FLT_Fcol"
for face in selfaces:
#First append packed index + color and store in face property
face.setProperty("FLT_COL",int(pack_face_index(curswatch,curint)))
#Save baked color to face vertex colors
for col in face.col:
col.r = int(color[0] * curint)
col.g = int(color[1] * curint)
col.b = int(color[2] * curint)
col.a = int(color[3] * curint)
else:
if Blender.Mesh.Mode() == Blender.Mesh.SelectModes['VERTEX']:
if not 'FLT_VCOL' in actmesh.verts.properties:
actmesh.verts.addPropertyLayer("FLT_VCOL",Blender.Mesh.PropertyTypes["INT"])
for vert in actmesh.verts:
vert.setProperty("FLT_VCOL",127)
else:
for vert in actmesh.verts:
if vert.sel:
vert.setProperty("FLT_VCOL",int(pack_face_index(curswatch,curint)))
if editmode:
Blender.Window.EditMode(1)
Blender.Window.RedrawAll()
#grab color and intensity from active face
elif evt == Draw.CKEY:
if Blender.Window.EditMode():
Blender.Window.EditMode(0)
editmode = 1
state = update_state()
actmesh = state["activeMesh"]
activeFace = state["activeFace"]
if activeFace:
if not "FLT_COL" in actmesh.faces.properties:
actmesh.faces.addPropertyLayer("FLT_COL",Blender.Mesh.PropertyTypes["INT"])
for face in actmesh.faces:
face.setProperty("FLT_COL",127) #default
try:
actmesh.activeColorLayer = "FLT_Fcol"
except:
actmesh.addColorLayer("FLT_Fcol")
actmesh.activeColorLayer = "FLT_Fcol"
tcol = activeFace.getProperty("FLT_COL")
(index,intensity) = unpack_face_index(tcol)
curswatch = index
curint = intensity
if editmode:
Blender.Window.EditMode(1)
Blender.Window.RedrawAll()
elif evt == Draw.GKEY:
if Blender.Window.EditMode():
Blender.Window.EditMode(0)
editmode =1
state = update_state()
actmesh = state["activeMesh"]
activeFace = state["activeFace"]
if activeFace and "FLT_COL" in actmesh.faces.properties:
(index,intensity) = unpack_face_index(activeFace.getProperty("FLT_COL"))
for face in actmesh.faces:
(index2, intensity2) = unpack_face_index(face.getProperty("FLT_COL"))
if index == index2:
face.sel = 1
elif evt == Draw.ESCKEY:
Draw.Exit()
if editmode:
Blender.Window.EditMode(1)
def update_all():
global colors
state = update_state()
#update the baked FLT colors for all meshes.
for object in state["activeScene"].objects:
if object.type == "Mesh":
mesh = object.getData(mesh=True)
if 'FLT_COL' in mesh.faces.properties and "FLT_Fcol" in mesh.getColorLayerNames():
mesh.activeColorLayer = "FLT_Fcol"
for face in mesh.faces:
(index,intensity) = unpack_face_index(face.getProperty('FLT_COL'))
color = struct.unpack('>BBBB',struct.pack('>i',colors[index]))
#update the vertex colors for this face
for col in face.col:
col.r = int(color[0] * intensity)
col.g = int(color[1] * intensity)
col.b = int(color[2] * intensity)
col.a = 255
def but_event(evt):
global palette_size
global palette_x
global palette_y
global colors
global curint
global curswatch
global picker
state = update_state()
if evt == 1:
if picker.val:
rval = (int(picker.val[0]*255),int(picker.val[1]*255),int(picker.val[2]*255),255)
rval = struct.pack('>BBBB',rval[0],rval[1],rval[2],rval[3])
rval = struct.unpack('>i',rval)
colors[curswatch] = rval[0]
#go cd through all meshes and update their FLT colors
update_all()
Draw.Redraw(1)
def init_pal():
global palette_size
global palette_x
global palette_y
global colors
global curint
global curswatch
state = update_state()
if not state["activeScene"].properties.has_key('FLT'):
state["activeScene"].properties['FLT'] = dict()
try:
colors = state["activeScene"].properties['FLT']['Color Palette']
except:
state["activeScene"].properties['FLT']['Color Palette'] = defaultp.pal
colors = state["activeScene"].properties['FLT']['Color Palette']
def draw_palette():
global palette_size
global palette_x
global palette_y
global colors
global curint
global curswatch
global picker
global ts1
global ts2
global ts3
global ts4
global ts5
state = update_state()
init_pal()
ssize = palette_size
xpos = palette_x
cid = 0
highlight = [(palette_x,palette_y),(palette_x+palette_size,palette_y),(palette_x+palette_size,palette_y+palette_size),(palette_x,palette_y+palette_size)]
for x in xrange(32):
ypos = palette_y
for y in xrange(32):
color = struct.unpack('>BBBB',struct.pack('>i',colors[cid]))
glColor3f(color[0]/255.0,color[1]/255.0,color[2]/255.0)
glBegin(GL_POLYGON)
glVertex2i(xpos,ypos)
glVertex2i(xpos+ssize,ypos)
glVertex2i(xpos+ssize,ypos+ssize)
glVertex2i(xpos,ypos+ssize)
glEnd()
if curswatch == cid:
highlight[0] = (xpos,ypos)
highlight[1] = (xpos+ssize,ypos)
highlight[2] = (xpos+ssize,ypos+ssize)
highlight[3] = (xpos,ypos+ssize)
glColor3f(0.0,0.0,0.0)
glBegin(GL_LINE_LOOP)
glVertex2i(xpos,ypos)
glVertex2i(xpos+ssize,ypos)
glVertex2i(xpos+ssize,ypos+ssize)
glVertex2i(xpos,ypos+ssize)
glVertex2i(xpos,ypos)
glEnd()
cid = cid + 1
ypos = ypos + ssize
xpos = xpos + ssize
#draw intensity gradient
color = struct.unpack('>BBBB',struct.pack('>i',colors[curswatch]))
color = [color[0]/255.0,color[1]/255.0,color[2]/255.0]
colsteps = [color[0]/255.0,color[1]/255.0,color[2]/255.0]
stripwidth = (palette_size * 32.0) / 256
strippad = palette_size / 2.0
xpos = palette_x
grady = (palette_y + (palette_size * 32.0)) + strippad
for x in xrange(256):
color[0] = color[0] - colsteps[0]
color[1] = color[1] - colsteps[1]
color[2] = color[2] - colsteps[2]
glColor3f(color[0], color[1] ,color[2])
glBegin(GL_POLYGON)
glVertex2f(xpos,grady)
glVertex2f(xpos+stripwidth,grady)
glVertex2f(xpos+stripwidth,grady+palette_size)
glVertex2f(xpos,grady+palette_size)
glEnd()
xpos = xpos + stripwidth
#draw intensity slider bar
#xposition == 512 - ((curint) * 512)
xpos = ((palette_size*32) * (1.0 - curint)) + palette_x
glColor3f(1.0,1.0,1.0)
glBegin(GL_LINE_LOOP)
glVertex2i(int(xpos-6),int(grady-1))
glVertex2i(int(xpos+6),int(grady-1))
glVertex2i(int(xpos+6),int(grady+palette_size+1))
glVertex2i(int(xpos-6),int(grady+palette_size+1))
#glVertex2i(xpos-6,grady+7)
glEnd()
#draw color picker
color = struct.unpack('>BBBB',struct.pack('>i',colors[curswatch]))
pickcol = (color[0]/255.0,color[1]/255.0,color[2]/255.0)
picker = Blender.Draw.ColorPicker(1,highlight[0][0]+1,highlight[0][1]+1,ssize-2,ssize-2,pickcol,ptt)
#draw highlight swatch
glColor3f(1.0,1.0,1.0)
glBegin(GL_LINE_LOOP)
glVertex2i(highlight[0][0],highlight[0][1])
glVertex2i(highlight[1][0],highlight[1][1])
glVertex2i(highlight[2][0],highlight[2][1])
glVertex2i(highlight[3][0],highlight[3][1])
glVertex2i(highlight[0][0],highlight[0][1])
glEnd()
#draw text string explanations
xpos = palette_size*32+20
ypos = palette_size*32+10
glRasterPos2d(xpos,ypos)
ts1 = Blender.Draw.Text("FLT Palette Manager V 1.0")
ypos = ypos - 20
glRasterPos2d(xpos,ypos)
ts3 = Blender.Draw.Text("CKEY - Copy Active Face Color*")
ypos = ypos - 20
glRasterPos2d(xpos,ypos)
ts2 = Blender.Draw.Text("VKEY - Paste Color to Selected Faces")
ypos = ypos - 20
glRasterPos2d(xpos,ypos)
ts4 = Blender.Draw.Text("GKEY - Select Faces With Same Color")
ypos = ypos - 15
glRasterPos2d(xpos,ypos)
ts5 = Blender.Draw.Text("(*Requires mesh with UV coordinates)", 'small')
def gui():
glClearColor(0.5,0.5,0.5,1.0)
glClear(GL_COLOR_BUFFER_BIT)
draw_palette()
init_pal()
Draw.Register(gui,event,but_event)