Merge branch 'master' into blender2.8

This commit is contained in:
Campbell Barton
2018-07-03 06:58:34 +02:00
56 changed files with 757 additions and 622 deletions
-1
View File
@@ -33,7 +33,6 @@ from modules.test_utils import (with_tempdir,
)
class AbcPropError(Exception):
"""Raised when AbstractAlembicTest.abcprop() finds an error."""
-1
View File
@@ -109,7 +109,6 @@ class SimpleImportTest(AbstractAlembicTest):
self.assertAlmostEqual(0, y)
self.assertAlmostEqual(2, z)
def test_select_after_import(self):
# Add a sphere, so that there is something in the scene, selected, and active,
# before we do the Alembic import.
+5 -4
View File
@@ -33,7 +33,7 @@ import imp
BLACKLIST_DIRS = (
os.path.join(bpy.utils.resource_path('USER'), "scripts"),
) + tuple(addon_utils.paths()[1:])
) + tuple(addon_utils.paths()[1:])
BLACKLIST_ADDONS = set()
@@ -54,9 +54,10 @@ def _init_addon_blacklist():
def addon_modules_sorted():
modules = addon_utils.modules({})
modules[:] = [
mod for mod in modules
if not (mod.__file__.startswith(BLACKLIST_DIRS))
if not (mod.__name__ in BLACKLIST_ADDONS)]
mod for mod in modules
if not (mod.__file__.startswith(BLACKLIST_DIRS))
if not (mod.__name__ in BLACKLIST_ADDONS)
]
modules.sort(key=lambda mod: mod.__name__)
return modules
+6 -5
View File
@@ -39,20 +39,20 @@ BLACKLIST = {
# The unpacked wheel is only loaded when actually used, not directly on import:
os.path.join("io_blend_utils", "blender_bam-unpacked.whl"),
}
}
# Some modules need to add to the `sys.path`.
MODULE_SYS_PATHS = {
# Runs in a Python subprocess, so its expected its basedir can be imported.
"io_blend_utils.blendfile_pack": ".",
}
}
if not bpy.app.build_options.freestyle:
BLACKLIST.add("render_freestyle_svg")
BLACKLIST_DIRS = (
os.path.join(bpy.utils.resource_path('USER'), "scripts"),
) + tuple(addon_utils.paths()[1:])
) + tuple(addon_utils.paths()[1:])
def module_names_recursive(mod_dir, *, parent=None):
@@ -168,7 +168,7 @@ def load_modules():
os.sep + "presets" + os.sep,
os.sep + "templates" + os.sep,
] + ([(os.sep + f + os.sep) for f in BLACKLIST] +
[(os.sep + f + ".py") for f in BLACKLIST])
[(os.sep + f + ".py") for f in BLACKLIST])
#
# now submodules
@@ -185,7 +185,7 @@ def load_modules():
sys.path.extend([
os.path.normpath(os.path.join(mod_dir, f))
for f in MODULE_SYS_PATHS.get(mod_name_full, ())
])
])
try:
__import__(mod_name_full)
@@ -248,6 +248,7 @@ def main():
load_addons()
load_modules()
if __name__ == "__main__":
# So a python error exits(1)
try:
+86 -61
View File
@@ -61,11 +61,11 @@ def render_gl(context, filepath, shade):
ctx_shading_type(context, shade)
#~ # stop to inspect!
#~ if filepath == "test_cube_shell_solidify_subsurf_wp_wire":
#~ assert(0)
#~ else:
#~ return
# stop to inspect!
# if filepath == "test_cube_shell_solidify_subsurf_wp_wire":
# assert(0)
# else:
# return
bpy.ops.render.opengl(write_still=True,
view_context=True)
@@ -219,6 +219,7 @@ def mesh_bmesh_poly_elems(poly, elems):
vert_total = poly.loop_total
return elems[vert_start:vert_start + vert_total]
def mesh_bmesh_poly_vertices(poly):
return [loop.vertex_index
for loop in mesh_bmesh_poly_elems(poly, poly.id_data.loops)]
@@ -505,7 +506,7 @@ cube_like_vertices = (
(-1, 1, 3),
(0, 1, 3),
(0, 0, 3),
)
)
cube_like_faces = (
@@ -547,7 +548,7 @@ cube_like_faces = (
(31, 30, 36, 33),
(32, 31, 33, 34),
(35, 34, 33, 36),
)
)
# useful since its a shell for solidify and it can be mirrored
@@ -564,7 +565,7 @@ cube_shell_vertices = (
(0, -1, 0),
(0, 0, -1),
(0, 1, -1),
)
)
cube_shell_face = (
@@ -577,7 +578,7 @@ cube_shell_face = (
(6, 5, 11),
(7, 4, 9, 8),
(10, 7, 6, 11),
)
)
def make_cube(scene):
@@ -678,59 +679,77 @@ def make_monkey_extra(scene):
global_tests = []
global_tests.append(("none",
(),
))
global_tests.append(
("none",
(),
)
)
# single
global_tests.append(("subsurf_single",
((modifier_subsurf_add, dict(levels=2)), ),
))
global_tests.append(
("subsurf_single",
((modifier_subsurf_add, dict(levels=2)), ),
)
)
global_tests.append(
("armature_single",
((modifier_armature_add, dict()), ),
)
)
global_tests.append(("armature_single",
((modifier_armature_add, dict()), ),
))
global_tests.append(
("mirror_single",
((modifier_mirror_add, dict()), ),
)
)
global_tests.append(
("hook_single",
((modifier_hook_add, dict()), ),
)
)
global_tests.append(("mirror_single",
((modifier_mirror_add, dict()), ),
))
global_tests.append(
("decimate_single",
((modifier_decimate_add, dict()), ),
)
)
global_tests.append(("hook_single",
((modifier_hook_add, dict()), ),
))
global_tests.append(
("build_single",
((modifier_build_add, dict()), ),
)
)
global_tests.append(("decimate_single",
((modifier_decimate_add, dict()), ),
))
global_tests.append(("build_single",
((modifier_build_add, dict()), ),
))
global_tests.append(("mask_single",
((modifier_mask_add, dict()), ),
))
global_tests.append(
("mask_single",
((modifier_mask_add, dict()), ),
)
)
# combinations
global_tests.append(("mirror_subsurf",
((modifier_mirror_add, dict()),
(modifier_subsurf_add, dict(levels=2))),
))
global_tests.append(
("mirror_subsurf",
((modifier_mirror_add, dict()),
(modifier_subsurf_add, dict(levels=2))),
)
)
global_tests.append(("solidify_subsurf",
((modifier_solidify_add, dict()),
(modifier_subsurf_add, dict(levels=2))),
))
global_tests.append(
("solidify_subsurf",
((modifier_solidify_add, dict()),
(modifier_subsurf_add, dict(levels=2))),
)
)
def apply_test(test, scene, obj,
render_func=None,
render_args=None,
render_kwargs=None,
):
def apply_test(
test, scene, obj,
render_func=None,
render_args=None,
render_kwargs=None,
):
test_name, test_funcs = test
@@ -756,10 +775,12 @@ def test_cube(context, test):
obj = make_cube_extra(scene)
ctx_camera_setup(context, location=(3, 3, 3))
apply_test(test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami()))
apply_test(
test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami())
)
def test_cube_like(context, test):
@@ -767,10 +788,12 @@ def test_cube_like(context, test):
obj = make_cube_like_extra(scene)
ctx_camera_setup(context, location=(5, 5, 5))
apply_test(test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami()))
apply_test(
test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami())
)
def test_cube_shell(context, test):
@@ -778,10 +801,12 @@ def test_cube_shell(context, test):
obj = make_cube_shell_extra(scene)
ctx_camera_setup(context, location=(4, 4, 4))
apply_test(test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami()))
apply_test(
test, scene, obj,
render_func=render_gl_all_modes,
render_args=(context, obj),
render_kwargs=dict(filepath=whoami())
)
# -----------------------------------------------------------------------------
+23 -23
View File
@@ -45,20 +45,20 @@ MESHES = {
( # Edges
),
( # Loops
0, 1, 4, 3,
3, 4, 6,
1, 2, 5, 4,
3, 4, 6,
4, 7, 6,
4, 5, 9, 4, 8, 7,
0, 1, 4, 3,
3, 4, 6,
1, 2, 5, 4,
3, 4, 6,
4, 7, 6,
4, 5, 9, 4, 8, 7,
),
( # Polygons
(0, 4),
(4, 3),
(7, 4),
(11, 3),
(14, 3),
(16, 6),
(0, 4),
(4, 3),
(7, 4),
(11, 3),
(14, 3),
(16, 6),
),
),
),
@@ -66,17 +66,17 @@ MESHES = {
BUILTINS = (
"primitive_plane_add",
"primitive_cube_add",
"primitive_circle_add",
"primitive_uv_sphere_add",
"primitive_ico_sphere_add",
"primitive_cylinder_add",
"primitive_cone_add",
"primitive_grid_add",
"primitive_monkey_add",
"primitive_torus_add",
)
"primitive_plane_add",
"primitive_cube_add",
"primitive_circle_add",
"primitive_uv_sphere_add",
"primitive_ico_sphere_add",
"primitive_cylinder_add",
"primitive_cone_add",
"primitive_grid_add",
"primitive_monkey_add",
"primitive_torus_add",
)
BUILTINS_NBR = 4
BUILTINS_NBRCHANGES = 5
+22 -17
View File
@@ -5,25 +5,26 @@ import unittest
from bpy.utils import units
class UnitsTesting(unittest.TestCase):
# From user typing to 'internal' Blender value.
INPUT_TESTS = (
# system, type, ref, input, value
##### LENGTH
# LENGTH
('IMPERIAL', 'LENGTH', "", "1ft", 0.3048),
('IMPERIAL', 'LENGTH', "", "(1+1)ft", 0.3048 * 2),
('IMPERIAL', 'LENGTH', "", "1mi4\"", 1609.344 + 0.0254 * 4),
('METRIC', 'LENGTH', "", "0.005µm", 0.000001 * 0.005),
('METRIC', 'LENGTH', "", "1e6km", 1000.0 * 1e6),
('METRIC', 'LENGTH', "", "0.005µm", 0.000001 * 0.005),
('METRIC', 'LENGTH', "", "1e6km", 1000.0 * 1e6),
('IMPERIAL', 'LENGTH', "", "1ft5cm", 0.3048 + 0.01 * 5),
('METRIC', 'LENGTH', "", "1ft5cm", 0.3048 + 0.01 * 5),
('METRIC', 'LENGTH', "", "1ft5cm", 0.3048 + 0.01 * 5),
# Using reference string to find a unit when none is given.
('IMPERIAL', 'LENGTH', "33.3ft", "1", 0.3048),
('METRIC', 'LENGTH', "33.3dm", "1", 0.1),
('METRIC', 'LENGTH', "33.3dm", "1", 0.1),
('IMPERIAL', 'LENGTH', "33.3cm", "1", 0.3048), # ref unit is not in IMPERIAL system, default to feet...
('IMPERIAL', 'LENGTH', "33.3ft", "1\"", 0.0254), # unused ref unit, since one is given already!
('IMPERIAL', 'LENGTH', "", "1+1ft", 0.3048 * 2), # default unit taken from current string (feet).
('METRIC', 'LENGTH', "", "1+1ft", 1.3048), # no metric units, we default to meters.
('METRIC', 'LENGTH', "", "1+1ft", 1.3048), # no metric units, we default to meters.
('IMPERIAL', 'LENGTH', "", "3+1in+1ft", 0.3048 * 4 + 0.0254), # bigger unit becomes default one!
('IMPERIAL', 'LENGTH', "", "(3+1)in+1ft", 0.3048 + 0.0254 * 4),
)
@@ -31,18 +32,18 @@ class UnitsTesting(unittest.TestCase):
# From 'internal' Blender value to user-friendly printing
OUTPUT_TESTS = (
# system, type, prec, sep, compat, value, output
##### LENGTH
# LENGTH
# Note: precision handling is a bit complicated when using multi-units...
('IMPERIAL', 'LENGTH', 3, False, False, 0.3048, "1'"),
('IMPERIAL', 'LENGTH', 3, False, True, 0.3048, "1ft"),
('IMPERIAL', 'LENGTH', 4, True, False, 0.3048 * 2 + 0.0254 * 5.5, "2' 5.5\""),
('IMPERIAL', 'LENGTH', 3, False, True, 0.3048, "1ft"),
('IMPERIAL', 'LENGTH', 4, True, False, 0.3048 * 2 + 0.0254 * 5.5, "2' 5.5\""),
('IMPERIAL', 'LENGTH', 3, False, False, 1609.344 * 1e6, "1000000mi"),
('IMPERIAL', 'LENGTH', 6, False, False, 1609.344 * 1e6, "1000000mi"),
('METRIC', 'LENGTH', 3, True, False, 1000 * 2 + 0.001 * 15, "2km 2cm"),
('METRIC', 'LENGTH', 5, True, False, 1234.56789, "1km 234.6m"),
('METRIC', 'LENGTH', 6, True, False, 1234.56789, "1km 234.57m"),
('METRIC', 'LENGTH', 9, False, False, 1234.56789, "1.234568km"),
('METRIC', 'LENGTH', 9, True, False, 1000.000123456789, "1km 0.123mm"),
('METRIC', 'LENGTH', 3, True, False, 1000 * 2 + 0.001 * 15, "2km 2cm"),
('METRIC', 'LENGTH', 5, True, False, 1234.56789, "1km 234.6m"),
('METRIC', 'LENGTH', 6, True, False, 1234.56789, "1km 234.57m"),
('METRIC', 'LENGTH', 9, False, False, 1234.56789, "1.234568km"),
('METRIC', 'LENGTH', 9, True, False, 1000.000123456789, "1km 0.123mm"),
)
def test_units_inputs(self):
@@ -63,9 +64,13 @@ class UnitsTesting(unittest.TestCase):
def test_units_outputs(self):
for usys, utype, prec, sep, compat, val, output in self.OUTPUT_TESTS:
opt_str = units.to_string(usys, utype, val, prec, sep, compat)
self.assertEqual(opt_str, output,
msg="%s, %s: %f (precision: %d, separate units: %d, compat units: %d) => "
"\"%s\", expected \"%s\"" % (usys, utype, val, prec, sep, compat, opt_str, output))
self.assertEqual(
opt_str, output,
msg=(
"%s, %s: %f (precision: %d, separate units: %d, compat units: %d) => "
"\"%s\", expected \"%s\""
) % (usys, utype, val, prec, sep, compat, opt_str, output)
)
if __name__ == '__main__':
+1
View File
@@ -198,6 +198,7 @@ class TestBufferProtocol(TestHelper, unittest.TestCase):
self.assertEqual(list(view1), list(view2))
self.assertEqual(view1.tobytes(), view2.tobytes())
if __name__ == '__main__':
import sys
sys.argv = [__file__] + (sys.argv[sys.argv.index("--") + 1:] if "--" in sys.argv else [])
+5 -2
View File
@@ -61,8 +61,10 @@ class TestClass(bpy.types.PropertyGroup):
def get_scene(lib_name, sce_name):
for s in bpy.data.scenes:
if s.name == sce_name:
if (s.library and s.library.name == lib_name) or \
(lib_name == None and s.library == None):
if (
(s.library and s.library.name == lib_name) or
(lib_name is None and s.library is None)
):
return s
@@ -309,6 +311,7 @@ def test_restrictions2():
class TestUIList(UIList):
test = bpy.props.PointerProperty(type=bpy.types.Object)
def draw_item(self, context, layout, data, item, icon, active_data, active_propname, index):
layout.prop(item, "name", text="", emboss=False, icon_value=icon)
+13 -14
View File
@@ -21,22 +21,22 @@ vector_data = (
(-0.854645, 0.518036, 0.033936),
(0.42514, -0.437866, -0.792114),
(-0.358948, 0.597046, 0.717377),
(-0.985413,0.144714, 0.089294),
)
(-0.985413, 0.144714, 0.089294),
)
# get data at different scales
vector_data = sum(
(tuple(tuple(a * scale for a in v) for v in vector_data)
for scale in (s * sign for s in (0.0001, 0.1, 1.0, 10.0, 1000.0, 100000.0)
for sign in (1.0, -1.0))), ()) + ((0.0, 0.0, 0.0),)
for scale in (s * sign for s in (0.0001, 0.1, 1.0, 10.0, 1000.0, 100000.0)
for sign in (1.0, -1.0))), ()) + ((0.0, 0.0, 0.0),)
class MatrixTesting(unittest.TestCase):
def test_matrix_column_access(self):
#mat =
#[ 1 2 3 4 ]
#[ 1 2 3 4 ]
#[ 1 2 3 4 ]
# mat =
# [ 1 2 3 4 ]
# [ 1 2 3 4 ]
# [ 1 2 3 4 ]
mat = Matrix(((1, 11, 111),
(2, 22, 222),
(3, 33, 333),
@@ -81,11 +81,11 @@ class MatrixTesting(unittest.TestCase):
self.assertIn(item, indices)
def test_matrix_to_3x3(self):
#mat =
#[ 1 2 3 4 ]
#[ 2 4 6 8 ]
#[ 3 6 9 12 ]
#[ 4 8 12 16 ]
# mat =
# [ 1 2 3 4 ]
# [ 2 4 6 8 ]
# [ 3 6 9 12 ]
# [ 4 8 12 16 ]
mat = Matrix(tuple((i, 2 * i, 3 * i, 4 * i) for i in range(1, 5)))
mat_correct = Matrix(((1, 2, 3), (2, 4, 6), (3, 6, 9)))
self.assertEqual(mat.to_3x3(), mat_correct)
@@ -372,7 +372,6 @@ class KDTreeTesting(unittest.TestCase):
ret_filter = k_all.find(co, lambda i: (i % 2) == 0)
self.assertAlmostEqualVector(ret_regular, ret_filter)
# filter out all values (search odd tree for even values and the reverse)
co = (0,) * 3
ret_filter = k_odd.find(co, lambda i: (i % 2) == 0)
+2 -1
View File
@@ -8,7 +8,7 @@ DUMMY_NAME = "Untitled"
DUMMY_PATH = __file__
GLOBALS = {
"error_num": 0,
}
}
def as_float_32(f):
@@ -142,5 +142,6 @@ def main():
print("Error (total): %d" % GLOBALS["error_num"])
if __name__ == "__main__":
main()
+1
View File
@@ -155,5 +155,6 @@ def main():
test_language_coverage()
test_urls()
if __name__ == "__main__":
main()
+8 -6
View File
@@ -36,7 +36,7 @@ RANDOM_MULTIPLY = 10
STATE = {
"counter": 0,
}
}
op_blacklist = (
@@ -91,7 +91,7 @@ op_blacklist = (
"wm.keymap_restore", # another annoying one
"wm.addon_*", # harmless, but dont change state
"console.*", # just annoying - but harmless
)
)
def blend_list(mainpath):
@@ -114,6 +114,7 @@ def blend_list(mainpath):
return list(sorted(file_list(mainpath, is_blend)))
if USE_FILES:
USE_FILES_LS = blend_list(USE_FILES)
# print(USE_FILES_LS)
@@ -176,7 +177,7 @@ if USE_ATTRSET:
CLS_BLACKLIST = (
bpy.types.BrushTextureSlot,
bpy.types.Brush,
)
)
property_typemap = build_property_typemap(CLS_BLACKLIST)
bpy_struct_type = bpy.types.Struct.__base__
@@ -228,7 +229,7 @@ if USE_ATTRSET:
{0: "", 1: "hello", 2: "test"}, {"": 0, "hello": 1, "test": 2},
set(), {"", "test", "."}, {None, ..., type},
range(10), (" " * i for i in range(10)),
)
)
def attrset_data():
for attr in dir(bpy.data):
@@ -480,8 +481,9 @@ def main():
print("Finished %r" % __file__)
if __name__ == "__main__":
#~ for i in range(200):
#~ RANDOM_SEED[0] += 1
# ~ for i in range(200):
# ~ RANDOM_SEED[0] += 1
#~ main()
main()
@@ -31,6 +31,7 @@ import difflib
import pathlib
from pathlib import Path
def with_tempdir(wrapped):
"""Creates a temporary directory for the function, cleaning up after it returns normally.
@@ -56,8 +57,10 @@ def with_tempdir(wrapped):
return decorator
LINE = "+----------------------------------------------------------------"
class AbstractColladaTest(unittest.TestCase):
@classmethod
@@ -71,33 +74,33 @@ class AbstractColladaTest(unittest.TestCase):
ref = open(reference)
exp = open(export)
diff=difflib.unified_diff(ref.readlines(), exp.readlines(), lineterm='', n=0)
diff = difflib.unified_diff(ref.readlines(), exp.readlines(), lineterm='', n=0)
ref.close()
exp.close()
diff_count = 0;
diff_count = 0
for line in diff:
error = True
for prefix in ('---', '+++', '@@'):
# Ignore diff metadata
if line.startswith(prefix):
error=False
error = False
break
else:
# Ignore time stamps
for ignore in ('<created>', '<modified>', '<authoring_tool>'):
if line[1:].strip().startswith(ignore):
error=False
error = False
break
if error:
diff_count +=1
diff_count += 1
pline = line.strip()
if diff_count == 1:
print("\n%s" % LINE)
print("|Test has errors:")
print(LINE)
pre = "reference" if pline[0] == "-" else "generated"
print ("| %s:%s"% (pre, pline[1:]))
print("| %s:%s" % (pre, pline[1:]))
if diff_count > 0:
print(LINE)
@@ -107,14 +110,16 @@ class AbstractColladaTest(unittest.TestCase):
return diff_count == 0
class MeshExportTest4(AbstractColladaTest):
@with_tempdir
def test_export_animation_suzannes_sample_matrix(self, tempdir: pathlib.Path):
test = "suzannes_parent_inverse_sample_10_matrix"
reference_dae = self.testdir / Path("%s.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
bpy.ops.wm.collada_export(filepath="%s" % str(outfile),
bpy.ops.wm.collada_export(
filepath="%s" % str(outfile),
check_existing=True,
filemode=8,
display_type='DEFAULT',
@@ -142,20 +147,23 @@ class MeshExportTest4(AbstractColladaTest):
export_texture_type_selection='mat',
open_sim=False,
limit_precision=True,
keep_bind_info=False)
keep_bind_info=False,
)
# Now check the resulting Collada file.
if not self.checkdae(reference_dae, outfile):
self.fail()
class MeshExportTest3(AbstractColladaTest):
@with_tempdir
def test_export_animation_suzannes_sample_locrotscale(self, tempdir: pathlib.Path):
test = "suzannes_parent_inverse_sample_10_channels"
reference_dae = self.testdir / Path("%s.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
bpy.ops.wm.collada_export(filepath="%s" % str(outfile),
bpy.ops.wm.collada_export(
filepath="%s" % str(outfile),
check_existing=True,
filemode=8,
display_type='DEFAULT',
@@ -183,20 +191,23 @@ class MeshExportTest3(AbstractColladaTest):
export_texture_type_selection='mat',
open_sim=False,
limit_precision=True,
keep_bind_info=False)
keep_bind_info=False,
)
# Now check the resulting Collada file.
if not self.checkdae(reference_dae, outfile):
self.fail()
class MeshExportTest2(AbstractColladaTest):
@with_tempdir
def test_export_animation_suzannes_keyframe_matrix(self, tempdir: pathlib.Path):
test = "suzannes_parent_inverse_keyframes_matrix"
reference_dae = self.testdir / Path("%s.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
bpy.ops.wm.collada_export(filepath="%s" % str(outfile),
bpy.ops.wm.collada_export(
filepath="%s" % str(outfile),
check_existing=True,
filemode=8,
display_type='DEFAULT',
@@ -224,20 +235,23 @@ class MeshExportTest2(AbstractColladaTest):
export_texture_type_selection='mat',
open_sim=False,
limit_precision=True,
keep_bind_info=False)
keep_bind_info=False,
)
# Now check the resulting Collada file.
if not self.checkdae(reference_dae, outfile):
self.fail()
class MeshExportTest1(AbstractColladaTest):
@with_tempdir
def test_export_animation_suzannes_keyframe_locrotscale(self, tempdir: pathlib.Path):
test = "suzannes_parent_inverse_keyframes_channels"
reference_dae = self.testdir / Path("%s.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
bpy.ops.wm.collada_export(filepath="%s" % str(outfile),
bpy.ops.wm.collada_export(
filepath="%s" % str(outfile),
check_existing=True,
filemode=8,
display_type='DEFAULT',
@@ -265,7 +279,8 @@ class MeshExportTest1(AbstractColladaTest):
export_texture_type_selection='mat',
open_sim=False,
limit_precision=True,
keep_bind_info=False)
keep_bind_info=False,
)
# Now check the resulting Collada file.
if not self.checkdae(reference_dae, outfile):
@@ -277,4 +292,4 @@ if __name__ == '__main__':
parser = argparse.ArgumentParser()
parser.add_argument('--testdir', required=True)
args, remaining = parser.parse_known_args()
unittest.main(argv=sys.argv[0:1]+remaining)
unittest.main(argv=sys.argv[0:1] + remaining)
+17 -10
View File
@@ -31,6 +31,7 @@ import difflib
import pathlib
from pathlib import Path
def with_tempdir(wrapped):
"""Creates a temporary directory for the function, cleaning up after it returns normally.
@@ -56,8 +57,10 @@ def with_tempdir(wrapped):
return decorator
LINE = "+----------------------------------------------------------------"
class AbstractColladaTest(unittest.TestCase):
@classmethod
@@ -71,33 +74,33 @@ class AbstractColladaTest(unittest.TestCase):
ref = open(reference)
exp = open(export)
diff=difflib.unified_diff(ref.readlines(), exp.readlines(), lineterm='', n=0)
diff = difflib.unified_diff(ref.readlines(), exp.readlines(), lineterm='', n=0)
ref.close()
exp.close()
diff_count = 0;
diff_count = 0
for line in diff:
error = True
for prefix in ('---', '+++', '@@'):
# Ignore diff metadata
if line.startswith(prefix):
error=False
error = False
break
else:
# Ignore time stamps
for ignore in ('<created>', '<modified>', '<authoring_tool>'):
if line[1:].strip().startswith(ignore):
error=False
error = False
break
if error:
diff_count +=1
diff_count += 1
pline = line.strip()
if diff_count == 1:
print("\n%s" % LINE)
print("|Test has errors:")
print(LINE)
pre = "reference" if pline[0] == "-" else "generated"
print ("| %s:%s"% (pre, pline[1:]))
print("| %s:%s" % (pre, pline[1:]))
if diff_count > 0:
print(LINE)
@@ -107,14 +110,16 @@ class AbstractColladaTest(unittest.TestCase):
return diff_count == 0
class MeshExportTest(AbstractColladaTest):
@with_tempdir
def test_export_single_mesh(self, tempdir: pathlib.Path):
test = "mesh_simple_001"
reference_dae = self.testdir / Path("%s.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
outfile = tempdir / Path("%s_out.dae" % test)
bpy.ops.wm.collada_export(filepath="%s" % str(outfile),
bpy.ops.wm.collada_export(
filepath="%s" % str(outfile),
check_existing=True,
filemode=8,
display_type="DEFAULT",
@@ -140,15 +145,17 @@ class MeshExportTest(AbstractColladaTest):
export_texture_type_selection="mat",
open_sim=False,
limit_precision=False,
keep_bind_info=False)
keep_bind_info=False,
)
# Now check the resulting Collada file.
if not self.checkdae(reference_dae, outfile):
self.fail()
if __name__ == '__main__':
sys.argv = [__file__] + (sys.argv[sys.argv.index("--") + 1:] if "--" in sys.argv else [])
parser = argparse.ArgumentParser()
parser.add_argument('--testdir', required=True)
args, remaining = parser.parse_known_args()
unittest.main(argv=sys.argv[0:1]+remaining)
unittest.main(argv=sys.argv[0:1] + remaining)
+10 -10
View File
@@ -23,6 +23,7 @@ class COLORS_DUMMY:
GREEN = ''
ENDC = ''
COLORS = COLORS_DUMMY
@@ -55,10 +56,12 @@ def blend_list(dirpath):
filepath = os.path.join(dirpath, filename)
yield filepath
def test_get_name(filepath):
filename = os.path.basename(filepath)
return os.path.splitext(filename)[0]
def test_get_images(output_dir, filepath, reference_dir):
testname = test_get_name(filepath)
dirpath = os.path.dirname(filepath)
@@ -99,7 +102,7 @@ class Report:
'passed_tests',
'compare_tests',
'compare_engines'
)
)
def __init__(self, title, output_dir, idiff):
self.title = title
@@ -158,7 +161,7 @@ class Report:
filepath = os.path.join(outdir, "compare.data")
pathlib.Path(filepath).write_text(self.compare_tests)
def _write_html(self, comparison = False):
def _write_html(self, comparison=False):
# Gather intermediate data for all tests.
if comparison:
failed_data = []
@@ -307,7 +310,6 @@ class Report:
self.compare_tests += test_html
def _diff_output(self, filepath, tmp_filepath):
old_img, ref_img, new_img, diff_img = test_get_images(self.output_dir, filepath, self.reference_dir)
@@ -330,7 +332,7 @@ class Report:
"-failpercent", "1",
ref_img,
tmp_filepath,
)
)
try:
subprocess.check_output(command)
failed = False
@@ -357,7 +359,7 @@ class Report:
"-abs", "-scale", "16",
ref_img,
tmp_filepath
)
)
try:
subprocess.check_output(command)
@@ -367,7 +369,6 @@ class Report:
return not failed
def _run_test(self, filepath, render_cb):
testname = test_get_name(filepath)
print_message(testname, 'SUCCESS', 'RUN')
@@ -394,7 +395,7 @@ class Report:
return error
elif error == "NO_START":
print_message('Can not perform tests because blender fails to start.',
'Make sure INSTALL target was run.')
'Make sure INSTALL target was run.')
return error
elif error == 'VERIFY':
print_message("Rendered result is different from reference image")
@@ -404,7 +405,6 @@ class Report:
'FAILURE', 'FAILED')
return error
def _run_all_tests(self, dirname, dirpath, render_cb):
passed_tests = []
failed_tests = []
@@ -437,8 +437,8 @@ class Report:
'SUCCESS', 'PASSED')
if failed_tests:
print_message("{} tests, listed below:" .
format(len(failed_tests)),
'FAILURE', 'FAILED')
format(len(failed_tests)),
'FAILURE', 'FAILED')
failed_tests.sort()
for test in failed_tests:
print_message("{}" . format(test), 'FAILURE', "FAILED")
+1 -2
View File
@@ -62,7 +62,6 @@ class AbstractBlenderRunnerTest(unittest.TestCase):
blender: pathlib.Path = None
testdir: pathlib.Path = None
def run_blender(self, filepath: str, python_script: str, timeout: int=300) -> str:
"""Runs Blender by opening a blendfile and executing a script.
@@ -92,7 +91,7 @@ class AbstractBlenderRunnerTest(unittest.TestCase):
'-E', 'CYCLES',
'--python-exit-code', '47',
'--python-expr', python_script,
]
]
)
proc = subprocess.run(command, stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
+3
View File
@@ -8,6 +8,7 @@ import shutil
import subprocess
import sys
def screenshot():
import bpy
@@ -19,6 +20,7 @@ def screenshot():
bpy.ops.wm.quit_blender()
# When run from inside Blender, take screenshot and exit.
try:
import bpy
@@ -93,5 +95,6 @@ def main():
sys.exit(not ok)
if __name__ == "__main__":
main()
+3 -4
View File
@@ -93,7 +93,7 @@ def check_files_flake8(files):
# times types are compared,
# I rather keep them specific
"E721",
)
)
for f, pep8_type in files:
@@ -129,10 +129,10 @@ def check_files_pylint(files):
"C0413," # import should be placed at the top
"W0613," # unused argument, may add this back
# but happens a lot for 'context' for eg.
"W0232," # class has no __init__, Operator/Panel/Menu etc
"W0232," # class has no __init__, Operator/Panel/Menu etc
"W0142," # Used * or ** magic
# even needed in some cases
"R0902," # Too many instance attributes
"R0902," # Too many instance attributes
"R0903," # Too many statements
"R0911," # Too many return statements
"R0912," # Too many branches
@@ -204,6 +204,5 @@ def main():
print("Skipping pylint checks (command not found)")
if __name__ == "__main__":
main()
+43 -33
View File
@@ -3,7 +3,7 @@
import unittest
import random
test= bpy.data.test
test = bpy.data.test
# farr - 1-dimensional array of float
# fdarr - dynamic 1-dimensional array of float
@@ -12,6 +12,7 @@ test= bpy.data.test
# same as above for other types except that the first letter is "i" for int and "b" for bool
class TestArray(unittest.TestCase):
# test that assignment works by: assign -> test value
# - rvalue = list of float
@@ -20,14 +21,14 @@ class TestArray(unittest.TestCase):
# bpy.data.test.farr[3], iarr[3], barr[...], fmarr, imarr, bmarr
def setUp(self):
test.farr= (1.0, 2.0, 3.0)
test.iarr= (7, 8, 9)
test.barr= (False, True, False)
test.farr = (1.0, 2.0, 3.0)
test.iarr = (7, 8, 9)
test.barr = (False, True, False)
# test access
# test slice access, negative indices
def test_access(self):
rvals= ([1.0, 2.0, 3.0], [7, 8, 9], [False, True, False])
rvals = ([1.0, 2.0, 3.0], [7, 8, 9], [False, True, False])
for arr, rval in zip((test.farr, test.iarr, test.barr), rvals):
self.assertEqual(prop_to_list(arr), rval)
self.assertEqual(arr[0:3], rval)
@@ -39,12 +40,12 @@ class TestArray(unittest.TestCase):
# fail when index out of bounds
def test_access_fail(self):
for arr in (test.farr, test.iarr, test.barr):
self.assertRaises(IndexError, lambda : arr[4])
self.assertRaises(IndexError, lambda: arr[4])
# test assignment of a whole array
def test_assign_array(self):
# should accept int as float
test.farr= (1, 2, 3)
test.farr = (1, 2, 3)
# fail when: unexpected no. of items, invalid item type
def test_assign_array_fail(self):
@@ -55,20 +56,20 @@ class TestArray(unittest.TestCase):
self.assertRaises(ValueError, assign_empty_list, arr)
def assign_invalid_float():
test.farr= (1.0, 2.0, "3.0")
test.farr = (1.0, 2.0, "3.0")
def assign_invalid_int():
test.iarr= ("1", 2, 3)
test.iarr = ("1", 2, 3)
def assign_invalid_bool():
test.barr= (True, 0.123, False)
test.barr = (True, 0.123, False)
for func in [assign_invalid_float, assign_invalid_int, assign_invalid_bool]:
self.assertRaises(TypeError, func)
# shouldn't accept float as int
def assign_float_as_int():
test.iarr= (1, 2, 3.0)
test.iarr = (1, 2, 3.0)
self.assertRaises(TypeError, assign_float_as_int)
# non-dynamic arrays cannot change size
@@ -81,14 +82,14 @@ class TestArray(unittest.TestCase):
def test_assign_item(self):
for arr, rand_func in zip((test.farr, test.iarr, test.barr), (rand_float, rand_int, rand_bool)):
for i in range(len(arr)):
val= rand_func()
val = rand_func()
arr[i] = val
self.assertEqual(arr[i], val)
# float prop should accept also int
for i in range(len(test.farr)):
val= rand_int()
val = rand_int()
test.farr[i] = val
self.assertEqual(test.farr[i], float(val))
@@ -112,7 +113,7 @@ class TestArray(unittest.TestCase):
# test various lengths here
for arr, rand_func in zip(("fdarr", "idarr", "bdarr"), (rand_float, rand_int, rand_bool)):
for length in range(1, 64):
rval= make_random_array(length, rand_func)
rval = make_random_array(length, rand_func)
setattr(test, arr, rval)
self.assertEqual(prop_to_list(getattr(test, arr)), rval)
@@ -136,7 +137,7 @@ class TestMArray(unittest.TestCase):
def test_assign_array(self):
for arr, func in zip(("fmarr", "imarr", "bmarr"), (rand_float, rand_int, rand_bool)):
# assignment of [3][4][5]
rval= make_random_3d_array((3, 4, 5), func)
rval = make_random_3d_array((3, 4, 5), func)
setattr(test, arr, rval)
self.assertEqual(prop_to_list(getattr(test, arr)), rval)
@@ -144,7 +145,7 @@ class TestMArray(unittest.TestCase):
def test_assign_array_fail(self):
def assign_empty_array():
test.fmarr= ()
test.fmarr = ()
self.assertRaises(ValueError, assign_empty_array)
def assign_invalid_size(arr, rval):
@@ -152,19 +153,19 @@ class TestMArray(unittest.TestCase):
# assignment of 3,4,4 or 3,3,5 should raise ex
for arr, func in zip(("fmarr", "imarr", "bmarr"), (rand_float, rand_int, rand_bool)):
rval= make_random_3d_array((3, 4, 4), func)
rval = make_random_3d_array((3, 4, 4), func)
self.assertRaises(ValueError, assign_invalid_size, arr, rval)
rval= make_random_3d_array((3, 3, 5), func)
rval = make_random_3d_array((3, 3, 5), func)
self.assertRaises(ValueError, assign_invalid_size, arr, rval)
rval= make_random_3d_array((3, 3, 3), func)
rval = make_random_3d_array((3, 3, 3), func)
self.assertRaises(ValueError, assign_invalid_size, arr, rval)
def test_assign_item(self):
# arr[i] = x
for arr, func in zip(("fmarr", "imarr", "bmarr", "fdmarr", "idmarr", "bdmarr"), (rand_float, rand_int, rand_bool) * 2):
rval= make_random_2d_array((4, 5), func)
rval = make_random_2d_array((4, 5), func)
for i in range(3):
getattr(test, arr)[i] = rval
@@ -173,23 +174,22 @@ class TestMArray(unittest.TestCase):
# arr[i][j] = x
for arr, func in zip(("fmarr", "imarr", "bmarr", "fdmarr", "idmarr", "bdmarr"), (rand_float, rand_int, rand_bool) * 2):
arr= getattr(test, arr)
rval= make_random_array(5, func)
arr = getattr(test, arr)
rval = make_random_array(5, func)
for i in range(3):
for j in range(4):
arr[i][j] = rval
self.assertEqual(prop_to_list(arr[i][j]), rval)
def test_assign_item_fail(self):
def assign_wrong_size(arr, i, rval):
getattr(test, arr)[i] = rval
# assign wrong size at level 2
for arr, func in zip(("fmarr", "imarr", "bmarr"), (rand_float, rand_int, rand_bool)):
rval1= make_random_2d_array((3, 5), func)
rval2= make_random_2d_array((4, 3), func)
rval1 = make_random_2d_array((3, 5), func)
rval2 = make_random_2d_array((4, 3), func)
for i in range(3):
self.assertRaises(ValueError, assign_wrong_size, arr, i, rval1)
@@ -198,22 +198,22 @@ class TestMArray(unittest.TestCase):
def test_dynamic_assign_array(self):
for arr, func in zip(("fdmarr", "idmarr", "bdmarr"), (rand_float, rand_int, rand_bool)):
# assignment of [3][4][5]
rval= make_random_3d_array((3, 4, 5), func)
rval = make_random_3d_array((3, 4, 5), func)
setattr(test, arr, rval)
self.assertEqual(prop_to_list(getattr(test, arr)), rval)
# [2][4][5]
rval= make_random_3d_array((2, 4, 5), func)
rval = make_random_3d_array((2, 4, 5), func)
setattr(test, arr, rval)
self.assertEqual(prop_to_list(getattr(test, arr)), rval)
# [1][4][5]
rval= make_random_3d_array((1, 4, 5), func)
rval = make_random_3d_array((1, 4, 5), func)
setattr(test, arr, rval)
self.assertEqual(prop_to_list(getattr(test, arr)), rval)
# test access
def test_access(self):
pass
@@ -221,26 +221,32 @@ class TestMArray(unittest.TestCase):
def test_access_fail(self):
pass
random.seed()
def rand_int():
return random.randint(-1000, 1000)
def rand_float():
return float(rand_int())
def rand_bool():
return bool(random.randint(0, 1))
def make_random_array(len, rand_func):
arr= []
arr = []
for i in range(len):
arr.append(rand_func())
return arr
def make_random_2d_array(dimsize, rand_func):
marr= []
marr = []
for i in range(dimsize[0]):
marr.append([])
@@ -249,8 +255,9 @@ def make_random_2d_array(dimsize, rand_func):
return marr
def make_random_3d_array(dimsize, rand_func):
marr= []
marr = []
for i in range(dimsize[0]):
marr.append([])
@@ -262,8 +269,9 @@ def make_random_3d_array(dimsize, rand_func):
return marr
def prop_to_list(prop):
ret= []
ret = []
for x in prop:
if type(x) not in {bool, int, float}:
@@ -273,8 +281,10 @@ def prop_to_list(prop):
return ret
def suite():
return unittest.TestSuite([unittest.TestLoader().loadTestsFromTestCase(TestArray), unittest.TestLoader().loadTestsFromTestCase(TestMArray)])
if __name__ == "__main__":
unittest.TextTestRunner(verbosity=2).run(suite())