114 lines
3.4 KiB
Python
114 lines
3.4 KiB
Python
#!/user/bin/env python3
|
|
# invokes shadercross
|
|
# and builds shaders for samples
|
|
|
|
import os
|
|
import subprocess
|
|
|
|
from sys import platform
|
|
|
|
origDir = os.path.abspath(os.path.dirname(__file__))
|
|
repoRoot = os.path.abspath(os.path.join(origDir, "../../"))
|
|
engineRoot = os.path.abspath(os.path.join(repoRoot, 'engine'))
|
|
libRoot = os.path.abspath(os.path.join(repoRoot, 'lib'))
|
|
|
|
# a little explanation on how we find the content dir
|
|
# 1. check the path we ran this from, if there is a folder called content/ use that.
|
|
# 2. if not, walk up the dir from the current dir until we encounter
|
|
# contentDir.txt
|
|
# then use the relative path from that
|
|
|
|
contentDir = os.path.abspath(os.path.join('.', 'content/'))
|
|
|
|
lastPath = None
|
|
if not os.path.isdir(contentDir):
|
|
newPath = os.path.abspath('.')
|
|
while newPath != lastPath:
|
|
dirTxtPath = os.path.join(newPath, 'content.txt')
|
|
if os.path.exists(dirTxtPath):
|
|
print(dirTxtPath)
|
|
with open(dirTxtPath) as f:
|
|
relPath = f.read().strip()
|
|
contentDir = os.path.abspath(os.path.join(newPath, relPath))
|
|
break
|
|
newPath = os.path.abspath(os.path.join('../'))
|
|
lastPath = newPath
|
|
|
|
print("content target dir: ", contentDir)
|
|
|
|
shadercrossDir = os.path.join(libRoot, 'sdl3/shadercross/bin')
|
|
|
|
if platform == "linux" or platform == "linux2":
|
|
shadercrossDir = os.path.join(shadercrossDir, 'linux')
|
|
elif platform == "darwin":
|
|
shadercrossDir = os.path.join(shadercrossDir, 'osx')
|
|
elif platform == "win32":
|
|
shadercrossDir = os.path.join(shadercrossDir, 'win64')
|
|
|
|
shadercross = os.path.join(shadercrossDir, 'shadercross')
|
|
|
|
def discoverShaders():
|
|
rv = []
|
|
itemlist = os.listdir(engineRoot)
|
|
for x in itemlist:
|
|
modRoot = os.path.abspath(os.path.join(engineRoot, x))
|
|
if os.path.isdir(modRoot):
|
|
shaderRoot = os.path.abspath(os.path.join(modRoot, 'shaders/'))
|
|
if os.path.isdir(os.path.join(modRoot, 'shaders/')):
|
|
for x in os.listdir(shaderRoot):
|
|
if x.endswith(".hlsl"):
|
|
rv.append(os.path.abspath(os.path.join(shaderRoot, x)))
|
|
|
|
return rv
|
|
|
|
def cookList(inputFiles):
|
|
# general cooking flow I think for shaders is
|
|
# they will go under
|
|
cookedRoot = os.path.join(contentDir, '_shaders')
|
|
|
|
# we cook into 3 formats
|
|
# spirv
|
|
# msl
|
|
# dxil
|
|
|
|
outputFormats = [
|
|
('dxil', []),
|
|
('spv', []),
|
|
('msl', []),
|
|
]
|
|
|
|
spvs = []
|
|
|
|
for fmt in outputFormats:
|
|
outdir = os.path.join(cookedRoot, fmt[0])
|
|
for f in inputFiles:
|
|
basefile = f[:-5]
|
|
|
|
outfile = os.path.abspath(os.path.join(outdir, os.path.basename(basefile) + '.' + fmt[0] ))
|
|
os.makedirs(os.path.dirname(outfile), exist_ok=True)
|
|
cmd = [shadercross, f] + fmt[1] + [ '-o', outfile ]
|
|
|
|
if 'spv' == fmt[0]:
|
|
spvs.append((outfile, os.path.dirname(f)))
|
|
|
|
print(cmd)
|
|
subprocess.run(cmd)
|
|
|
|
# run spirv-cross and generate .json files
|
|
for f in spvs:
|
|
basefile = f[0][:-4]
|
|
outfile = os.path.join(f[1], os.path.basename(basefile) + '.json' )
|
|
os.makedirs(os.path.dirname(outfile), exist_ok=True)
|
|
|
|
assert os.path.getsize(f[0]) > 1
|
|
|
|
cmd = ['spirv-cross', f[0], '--reflect', '--output', outfile ]
|
|
print(cmd)
|
|
subprocess.run(cmd)
|
|
|
|
if __name__ == '__main__':
|
|
inputFiles = discoverShaders()
|
|
print(inputFiles)
|
|
cookList(inputFiles)
|
|
|