Skip to content

Commit

Permalink
Add files via upload
Browse files Browse the repository at this point in the history
  • Loading branch information
sttng authored Jul 1, 2020
1 parent c4d29aa commit 9e3746b
Show file tree
Hide file tree
Showing 3 changed files with 96 additions and 50 deletions.
79 changes: 53 additions & 26 deletions LegoToR.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,17 @@
#!/usr/bin/env python

#
# LegoToR Version 0.5.0.8 - Copyright (c) 2020 by m2m
# LegoToR Version 0.5.1 - Copyright (c) 2020 by m2m
# based on pyldd2obj Version 0.4.8 - Copyright (c) 2019 by jonnysp
# LegoToR parses LXF files and command line parameters to create a renderman compliant rib file.
#
# Usage: ./LegoToR.py /Users/username/Documents/LEGO\ Creations/Models/mylxffile.lxf -v -np
#
# Updates:
#
# 0.5.0.8 Improved custom2DField handling, adjusted logoonstuds height to accomodate new custom bricks better
# 0.5.1 Added reading correct focus distance from lxf file camera, allowing for correct depth-of-field rendering.
# 0.5.0.9 Fixed decorations bug, improved material assignments handling
# 0.5.0.8 Improved custom2DField handling, adjusted logoonstuds height to better accommodate new custom bricks, fixed decorations bug, improved material assignments handling
# 0.5.0.7 DB folder support for modifications (such as custom bricks) in addition to db.lif support
# 0.5.0.6 Seperated chrome and metallic materials. Fixed textures on chrome, metallic, transparent materials
# 0.5.0.5 Added color linearization (Thanks to earlywill !). Corrected metal (chrome) materials. Corrected transparency with added maxspeculardepth.
Expand Down Expand Up @@ -41,8 +43,9 @@
import ParseCommandLine as cl
import random

__version__ = "0.5.0.8"
__version__ = '0.5.1'
compression = zipfile.ZIP_DEFLATED
PRMANPATH = '/Applications/Pixar/RenderManProServer-23.3/'

class Materials:
def __init__(self, data):
Expand Down Expand Up @@ -567,18 +570,18 @@ def LoadDBFolder(self, dbfolderlocation):
self.allMaterials = Materials(data=self.database.filelist[os.path.join(dbfolderlocation,'Materials.xml')].read());
self.allMaterials.setLOC(loc=LOCReader(data=self.database.filelist[MATERIALNAMESPATH + 'EN/localizedStrings.loc'].read()))

def LoadDatabase(self,databaselocation):
def LoadDatabase(self, databaselocation):
self.database = LIFReader(file=databaselocation)

if self.database.initok and self.database.fileexist('/Materials.xml') and self.database.fileexist(MATERIALNAMESPATH + 'EN/localizedStrings.loc'):
self.allMaterials = Materials(data=self.database.filelist['/Materials.xml'].read());
self.allMaterials.setLOC(loc=LOCReader(data=self.database.filelist[MATERIALNAMESPATH + 'EN/localizedStrings.loc'].read()))

def LoadScene(self,filename):
def LoadScene(self, filename):
if self.database.initok:
self.scene = Scene(file=filename)

def Export(self,filename):
def Export(self, filename):
invert = Matrix3D()
#invert.n33 = -1 #uncomment to invert the Z-Axis

Expand All @@ -602,9 +605,13 @@ def Export(self,filename):
useplane = cl.useplane
usenormal = cl.usenormal
uselogoonstuds = cl.uselogoonstuds
fstop = cl.args.fstop
fov = cl.args.fov

out.write('''# Camera Minus One
TransformBegin
Projection "PxrCamera" "float fov" [25] "float fStop" [9.99999968e+37] "float focalLength" [1.3] "float focalDistance" [5.0]
Translate 0 -2 80
Rotate -25 1 0 0
Rotate 45 0 1 0
Expand All @@ -631,6 +638,8 @@ def Export(self,filename):

out.write('''# Camera {0}
TransformBegin
Projection "PxrCamera" "float fov" [{19}] "float fStop" [{20}] "float focalLength" [1.3] "float focalDistance" [{18}]
ConcatTransform [{1} {2} {3} {4} {5} {6} {7} {8} {9} {10} {11} {12} {13} {14} {15} {16}]
Camera "Cam-{0}"
"float shutterOpenTime" [0]
Expand All @@ -642,7 +651,12 @@ def Export(self,filename):
"float dofaspect" [1]
"float nearClip" [0.1]
"float farClip" [10000]
TransformEnd\n'''.format(cam.refID, undoTransformMatrix.n11, undoTransformMatrix.n21, -1 * undoTransformMatrix.n31, undoTransformMatrix.n41, undoTransformMatrix.n12, undoTransformMatrix.n22, -1 * undoTransformMatrix.n32, undoTransformMatrix.n42, -1 * undoTransformMatrix.n13, -1 * undoTransformMatrix.n23, undoTransformMatrix.n33, undoTransformMatrix.n43, undoTransformMatrix.n14, undoTransformMatrix.n24, -1 * undoTransformMatrix.n34, undoTransformMatrix.n44))
#"float fov" [{17}]
TransformEnd\n'''.format(cam.refID, undoTransformMatrix.n11, undoTransformMatrix.n21, -1 * undoTransformMatrix.n31,
undoTransformMatrix.n41, undoTransformMatrix.n12, undoTransformMatrix.n22, -1 * undoTransformMatrix.n32,
undoTransformMatrix.n42, -1 * undoTransformMatrix.n13, -1 * undoTransformMatrix.n23, undoTransformMatrix.n33,
undoTransformMatrix.n43, undoTransformMatrix.n14, undoTransformMatrix.n24, -1 * undoTransformMatrix.n34, undoTransformMatrix.n44,
cam.fieldOfView, cam.distance, fov, fstop))

out.write('''
Display "{0}{1}{2}.beauty.001.exr" "openexr" "Ci,a,mse,albedo,albedo_var,diffuse,diffuse_mse,specular,specular_mse,zfiltered,zfiltered_var,normal,normal_var,forward,backward" "int asrgba" 1
Expand Down Expand Up @@ -785,13 +799,28 @@ def Export(self,filename):
#transform with inverted values (to undo the transformation)
#geo.Parts[part].outnormals[k].transformW(undoTransformMatrix)

lddmatri = self.allMaterials.getMaterialRibyId(pa.materials[part])
matname = pa.materials[part]
#try catch here for possible problems in materials assignment of various g, g1, g2, .. files in lxf file
try:
materialCurrentPart = pa.materials[part]
except IndexError:
print('WARNING: {0}.g{1} has NO material assignment in lxf. Replaced with color 9. Fix {0}.xml faces values.'.format(pa.designID, part))
materialCurrentPart = '9'

lddmatri = self.allMaterials.getMaterialRibyId(materialCurrentPart)
matname = materialCurrentPart

deco = '0'
if hasattr(pa, 'decoration') and len(geo.Parts[part].textures) > 0:
if decoCount <= len(pa.decoration):
deco = pa.decoration[decoCount]
#if decoCount < len(pa.decoration):
try:
deco = pa.decoration[decoCount]
#print 'Good DecoCount' + str(decoCount)
#print 'Good len' + str(len(pa.decoration))
except IndexError:
print('Error here')
print(decoCount)
print(pa.decoration)
decoCount += 1

extfile = ''
Expand All @@ -809,7 +838,7 @@ def Export(self,filename):
os.system(txmake_cmd)
os.remove(extfile)
else:
print('RMANTREE environment variable not set correctly. Set with: \nexport RMANTREE=/Applications/Pixar/RenderManProServer-23.2/\nexport PATH="$PATH:$RMANTREE/bin"')
print('RMANTREE environment variable not set correctly. Set with: \nexport RMANTREE={0}\nexport PATH="$PATH:$RMANTREE/bin"'.format(PRMANPATH))

if not matname in usedmaterials:
usedmaterials.append(matname)
Expand Down Expand Up @@ -999,22 +1028,22 @@ def Export(self,filename):
zfmat.close()
out.write('WorldEnd')
sys.stdout.write('%s\r' % (' '))
print("--- %s seconds ---" % (time.time() - start_time))
print('--- %s seconds ---' % (time.time() - start_time))

def FindRmtree():
if os.name =='posix':
rmtree = os.getenv('RMANTREE')
if rmtree is not None:
return str(rmtree)
else:
print('RMANTREE environment variable not set correctly. Set with: \n\nexport RMANTREE=/Applications/Pixar/RenderManProServer-23.2/\nexport PATH="$PATH:$RMANTREE/bin"\n')
print('RMANTREE environment variable not set correctly. Set with: \n\nexport RMANTREE={0}\nexport PATH="$PATH:$RMANTREE/bin"\n'.format(PRMANPATH))
exit()
else:
rmtree = os.getenv('RMANTREE')
if rmtree is not None:
return str(rmtree)
else:
print('RMANTREE environment variable not set correctly. Set with: setx RMANTREE "C:\Program Files\Pixar\RenderManProServer-23.2\" /M')
print('RMANTREE environment variable not set correctly. Set with: setx RMANTREE "C:\Program Files\Pixar\RenderManProServer-23.3\" /M')
exit()


Expand Down Expand Up @@ -1068,8 +1097,7 @@ def generate_rib_header(infile, srate, pixelvar, width, height, fov, fstop, sear
DisplayChannel "vector forward" "string source" "vector motionFore"
DisplayChannel "vector backward" "string source" "vector motionBack"
Projection "PxrCamera" "float fov" [{11}] "float fStop" [{12}] "float focalLength" [0.8] "float focalDistance" [5] "point focus1" [0.0 0.0 -1] "point focus2" [1 0.0 -1] "point focus3" [1 1 -1]
'''.format(__version__, datetime.datetime.now(), str(searcharchive) + os.sep, FindRmtree(), str(searchtexture) + os.sep, pixelvar, width, height, '.' + os.sep + str(infile), integrator, srate, fov, fstop)
'''.format(__version__, datetime.datetime.now(), str(searcharchive) + os.sep, FindRmtree(), str(searchtexture) + os.sep, pixelvar, width, height, '.' + os.sep + str(infile), integrator, srate)

with open('rib_header.rib', 'w') as file_writer:
file_writer.write(rib_header)
Expand All @@ -1089,9 +1117,9 @@ def main():
os.remove(obj_filename + "_Bricks_Archive.zip")

converter = Converter()
print("LegoToR Version " + __version__)
print('LegoToR Version ' + __version__)
if os.path.isdir(FindDBFolder()):
print "Found DB folder. Will use DB folder instead of db.lif!"
print('Found DB folder. Will use DB folder instead of db.lif file!')
global PRIMITIVEPATH
global GEOMETRIEPATH
global DECORATIONPATH
Expand All @@ -1102,28 +1130,27 @@ def main():
DECORATIONPATH = FindDBFolder() + '/Decorations/'
MATERIALNAMESPATH = FindDBFolder() + '/MaterialNames/'
converter.LoadDBFolder(dbfolderlocation = FindDBFolder())
converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

elif os.path.exists(FindDatabase()):
converter.LoadDatabase(databaselocation = FindDatabase())
converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

else:
print("No LDD database found. Please install LEGO Digital-Designer.")
print('No LDD database found. Please install LEGO Digital-Designer.')
os._exit()

converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

with open(obj_filename + '_Scene.rib','wb') as wfd:
for f in ['rib_header.rib', obj_filename + '.rib']:
with open(f,'rb') as fd:
shutil.copyfileobj(fd, wfd, 1024*1024*10)
os.remove(obj_filename + '.rib')
os.remove('rib_header.rib')

print "\nNow start Renderman with (for preview):\n./prman -d it -t:-2 {0}{1}_Scene.rib".format(cl.args.searcharchive, os.sep + obj_filename)
print "Or start Renderman with (for final mode without preview):\n./prman -t:-2 -checkpoint 1m {0}{1}_Scene.rib".format(cl.args.searcharchive, os.sep + obj_filename)
print "\nFinally denoise the final output with:./denoise {0}{1}.beauty.001.exr\n".format(cl.args.searcharchive, os.sep + obj_filename)
print('\nNow start Renderman with (for preview):\n prman -d it -t:-2 {0}{1}_Scene.rib'.format(cl.args.searcharchive, os.sep + obj_filename))
print('Or start Renderman with (for final mode without preview):\n prman -t:-2 -checkpoint 1m {0}{1}_Scene.rib'.format(cl.args.searcharchive, os.sep + obj_filename))
print('\nFinally denoise the final output with: denoise {0}{1}.beauty.001.exr\n'.format(cl.args.searcharchive, os.sep + obj_filename))


if __name__ == "__main__":
Expand Down
52 changes: 31 additions & 21 deletions LegoToRHD.py
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
#!/usr/bin/env python

#
# LegoToRHD Version 0.5.0.3 - Copyright (c) 2020 by m2m
# LegoToRHD Version 0.5.1 - Copyright (c) 2020 by m2m
# based on pyldd2obj Version 0.4.8 - Copyright (c) 2019 by jonnysp
# LegoToRHD parses LXF files and command line parameters to create USDA compliant files.
#
# Usage: ./LegoToRHD.py /Users/username/Documents/LEGO\ Creations/Models/mylxffile.lxf -np
#
# Updates:
# 0.5.0.3 improved custom2DField handling, adjusted logoonstuds height to accomodate new custom bricks better
# 0.5.1 added reading correct focus distance from lxf file camera
# 0.5.0.3 improved custom2DField handling, adjusted logoonstuds height to better accommodate new custom bricks, fixed decorations bug, improved material assignments handling
# 0.5.0.2 db folder support for modifications (such as custom bricks) in addition to db.lif support
# 0.5.0.1 more logo on studs supported
# 0.5 initial logo on studs support
Expand Down Expand Up @@ -38,7 +39,7 @@
import ParseCommandLine as cl
import random

__version__ = "0.5.0.3"
__version__ = "0.5.1"

compression = zipfile.ZIP_STORED #uncompressed archive for USDZ, otherwise would use ZIP_DEFLATED, the usual zip compression

Expand Down Expand Up @@ -246,7 +247,7 @@ def Export(self,filename):
os.mkdir(assetsDir)
#print("Directory " , assetsDir , " Created ")
else:
print("Directory " , assetsDir , " already exists")
print('Directory {0} already exists'.format(assetsDir))

total = len(self.scene.Bricks)
current = 0
Expand All @@ -258,6 +259,8 @@ def Export(self,filename):
useplane = cl.useplane
usenormal = cl.usenormal
uselogoonstuds = cl.uselogoonstuds
fstop = cl.args.fstop
fov = cl.args.fov

out.write('''
{
Expand Down Expand Up @@ -286,9 +289,9 @@ def Camera "Cam_{0}"
{{
float4[] clippingPlanes = []
float2 clippingRange = (0.15815565, 6045.622)
float focalLength = 50
float focusDistance = 5
float fStop = 5.6
float focalLength = 80
float focusDistance = {18}
float fStop = {20}
float horizontalAperture = 41.4214
float horizontalApertureOffset = 0
float verticalAperture = 23.299536
Expand All @@ -297,7 +300,7 @@ def Camera "Cam_{0}"
matrix4d xformOp:transform = ( ({1}, {2}, {3}, {4}), ({5}, {6}, {7}, {8}), ({9}, {10}, {11}, {12}), ({13}, {14}, {15}, {16}) )
uniform token[] xformOpOrder = ["xformOp:transform"]
}}\n'''.format(cam.refID, cam.matrix.n11, cam.matrix.n12, cam.matrix.n13, cam.matrix.n14, cam.matrix.n21, cam.matrix.n22, cam.matrix.n23, cam.matrix.n24, cam.matrix.n31, cam.matrix.n32, cam.matrix.n33, cam.matrix.n34, cam.matrix.n41, cam.matrix.n42, cam.matrix.n43, cam.matrix.n44))
}}\n'''.format(cam.refID, cam.matrix.n11, cam.matrix.n12, cam.matrix.n13, cam.matrix.n14, cam.matrix.n21, cam.matrix.n22, cam.matrix.n23, cam.matrix.n24, cam.matrix.n31, cam.matrix.n32, cam.matrix.n33, cam.matrix.n34, cam.matrix.n41, cam.matrix.n42, cam.matrix.n43, cam.matrix.n44, cam.fieldOfView, cam.distance, fov, fstop))

for bri in self.scene.Bricks:
current += 1
Expand Down Expand Up @@ -460,12 +463,20 @@ def Mesh "mesh{0}"
gop.write('\t\t\tinterpolation = "vertex"\n')
gop.write('\t\t)\n')

lddmatri = self.allMaterials.getMaterialRibyId(pa.materials[part])
matname = pa.materials[part]
#try catch here for possible problems in materials assignment of various g, g1, g2, .. files in lxf file
try:
materialCurrentPart = pa.materials[part]
except IndexError:
print('WARNING: {0}.g{1} has NO material assignment in lxf. Replaced with color 9. Fix {0}.xml faces values.'.format(pa.designID, part))
materialCurrentPart = '9'

lddmatri = self.allMaterials.getMaterialRibyId(materialCurrentPart)
matname = materialCurrentPart

deco = '0'
if hasattr(pa, 'decoration') and len(geo.Parts[part].textures) > 0:
if decoCount <= len(pa.decoration):
#if decoCount <= len(pa.decoration):
if decoCount < len(pa.decoration):
deco = pa.decoration[decoCount]
decoCount += 1

Expand Down Expand Up @@ -661,9 +672,9 @@ def main():
generate_rib_header(cl.args.infile, cl.args.srate, cl.args.pixelvar, cl.args.width, cl.args.height, cl.args.fov, cl.args.fstop, cl.args.searcharchive, cl.args.searchtexture, cl.integrator, cl.integratorParams, cl.useplane, cl.usenormal, cl.uselogoonstuds)

converter = Converter()
print("LegoToRHD Version " + __version__)
print('LegoToRHD Version ' + __version__)
if os.path.isdir(FindDBFolder()):
print "Found DB folder. Will use DB folder instead of db.lif!"
print('Found DB folder. Will use DB folder instead of db.lif!')
global PRIMITIVEPATH
global GEOMETRIEPATH
global DECORATIONPATH
Expand All @@ -674,27 +685,26 @@ def main():
DECORATIONPATH = FindDBFolder() + '/Decorations/'
MATERIALNAMESPATH = FindDBFolder() + '/MaterialNames/'
converter.LoadDBFolder(dbfolderlocation = FindDBFolder())
converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

elif os.path.exists(FindDatabase()):
converter.LoadDatabase(databaselocation = FindDatabase())
converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

else:
print("No LDD database found. Please install LEGO Digital-Designer.")
print('No LDD database found. Please install LEGO Digital-Designer.')
os._exit()


converter.LoadScene(filename=lxf_filename)
converter.Export(filename=obj_filename)

with open(obj_filename + '_Scene.usda','wb') as wfd:
for f in ['rib_header.rib', obj_filename + '.usda']:
with open(f,'rb') as fd:
shutil.copyfileobj(fd, wfd, 1024*1024*10)
os.remove(obj_filename + '.usda')
os.remove('rib_header.rib')

print "\nNow start usdcat to convert from usda to usdc with :\n./usdcat -f -o {0}{1}_Scene.usdc {0}{1}_Scene.usda".format(cl.args.searcharchive, os.sep + obj_filename)
print "\nFinally put the file into an usdz archive with:./usdzconvert {0}{1}_Scene.usdc\n".format(cl.args.searcharchive, os.sep + obj_filename)
print("\nNow start usdcat to convert from usda to usdc with :\n./usdcat -f -o {0}{1}_Scene.usdc {0}{1}_Scene.usda".format(cl.args.searcharchive, os.sep + obj_filename))
print("\nFinally put the file into an usdz archive with:./usdzconvert {0}{1}_Scene.usdc\n".format(cl.args.searcharchive, os.sep + obj_filename))

if __name__ == "__main__":
main()
15 changes: 12 additions & 3 deletions pylddlib.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
# based on pyldd2obj version 0.4.8 - Copyright (c) 2019 by jonnysp
#
# Updates:
# 0.4.9.1 improved custom2DField handling
# 0.4.9.1 improved custom2DField handling, fixed decorations bug, improved material assignments handling
# 0.4.9 updates to support reading extracted db.lif from db folder
#
# License: MIT License
Expand Down Expand Up @@ -760,12 +760,21 @@ def Export(self,filename):
out.write("g " + "(" + geo.designID + ") " + geo.Partname + '\n')
for part in geo.Parts:

lddmat = self.allMaterials.getMaterialbyId(pa.materials[part])

#try catch here for possible problems in materials assignment of various g, g1, g2, .. files in lxf file
try:
materialCurrentPart = pa.materials[part]
except IndexError:
print 'WARNING: {0}.g{1} has NO material assignment in lxf. Replaced with color 9. Fix {0}.xml faces values.'.format(pa.designID, part)
materialCurrentPart = '9'

lddmat = self.allMaterials.getMaterialbyId(materialCurrentPart)
matname = lddmat.name

deco = '0'
if hasattr(pa, 'decoration') and len(geo.Parts[part].textures) > 0:
if decoCount <= len(pa.decoration):
#if decoCount <= len(pa.decoration):
if decoCount < len(pa.decoration):
deco = pa.decoration[decoCount]
decoCount += 1

Expand Down

0 comments on commit 9e3746b

Please sign in to comment.