| @@ -342,6 +342,7 @@ OBJECTS := \ | |||||
| $(OBJDIR)/juce_PropertiesFile_8faca026.o \ | $(OBJDIR)/juce_PropertiesFile_8faca026.o \ | ||||
| $(OBJDIR)/juce_RecentlyOpenedFilesList_f791257.o \ | $(OBJDIR)/juce_RecentlyOpenedFilesList_f791257.o \ | ||||
| $(OBJDIR)/juce_UndoManager_33b197fc.o \ | $(OBJDIR)/juce_UndoManager_33b197fc.o \ | ||||
| $(OBJDIR)/juce_UnitTest_4a02c10d.o \ | |||||
| .PHONY: clean | .PHONY: clean | ||||
| @@ -1873,4 +1874,9 @@ $(OBJDIR)/juce_UndoManager_33b197fc.o: ../../src/utilities/juce_UndoManager.cpp | |||||
| @echo "Compiling juce_UndoManager.cpp" | @echo "Compiling juce_UndoManager.cpp" | ||||
| @$(CXX) $(CXXFLAGS) -o "$@" -c "$<" | @$(CXX) $(CXXFLAGS) -o "$@" -c "$<" | ||||
| $(OBJDIR)/juce_UnitTest_4a02c10d.o: ../../src/utilities/juce_UnitTest.cpp | |||||
| -@mkdir -p $(OBJDIR) | |||||
| @echo "Compiling juce_UnitTest.cpp" | |||||
| @$(CXX) $(CXXFLAGS) -o "$@" -c "$<" | |||||
| -include $(OBJECTS:%.o=%.d) | -include $(OBJECTS:%.o=%.d) | ||||
| @@ -337,6 +337,7 @@ | |||||
| 0DE731ED3EC994B9227C2741 = { isa = PBXBuildFile; fileRef = 4BE2727CCD2CD7603402C8FE; }; | 0DE731ED3EC994B9227C2741 = { isa = PBXBuildFile; fileRef = 4BE2727CCD2CD7603402C8FE; }; | ||||
| A124FE5709D9324B5BAFFE53 = { isa = PBXBuildFile; fileRef = A618FC3255ECE14EC9259E6B; }; | A124FE5709D9324B5BAFFE53 = { isa = PBXBuildFile; fileRef = A618FC3255ECE14EC9259E6B; }; | ||||
| A84A5CA4654AE87192A6A096 = { isa = PBXBuildFile; fileRef = A59A5DCFCCAAEA79D03C2B27; }; | A84A5CA4654AE87192A6A096 = { isa = PBXBuildFile; fileRef = A59A5DCFCCAAEA79D03C2B27; }; | ||||
| 55EDB4D9B702B469DB4655C3 = { isa = PBXBuildFile; fileRef = ADE5F12AA5AD969E2C7002B3; }; | |||||
| 389351359BA78C682E1931A6 = { isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libjucedebug.a; sourceTree = BUILT_PRODUCTS_DIR; }; | 389351359BA78C682E1931A6 = { isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libjucedebug.a; sourceTree = BUILT_PRODUCTS_DIR; }; | ||||
| 144F56FCF3DF9EC922765901 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_Application.cpp; path = ../../src/application/juce_Application.cpp; sourceTree = SOURCE_ROOT; }; | 144F56FCF3DF9EC922765901 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_Application.cpp; path = ../../src/application/juce_Application.cpp; sourceTree = SOURCE_ROOT; }; | ||||
| F6A490BA93AC3558E9A6FBB0 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Application.h; path = ../../src/application/juce_Application.h; sourceTree = SOURCE_ROOT; }; | F6A490BA93AC3558E9A6FBB0 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Application.h; path = ../../src/application/juce_Application.h; sourceTree = SOURCE_ROOT; }; | ||||
| @@ -1021,6 +1022,8 @@ | |||||
| EECE464606AE845BFC4B941B = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoableAction.h; path = ../../src/utilities/juce_UndoableAction.h; sourceTree = SOURCE_ROOT; }; | EECE464606AE845BFC4B941B = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoableAction.h; path = ../../src/utilities/juce_UndoableAction.h; sourceTree = SOURCE_ROOT; }; | ||||
| A59A5DCFCCAAEA79D03C2B27 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UndoManager.cpp; path = ../../src/utilities/juce_UndoManager.cpp; sourceTree = SOURCE_ROOT; }; | A59A5DCFCCAAEA79D03C2B27 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UndoManager.cpp; path = ../../src/utilities/juce_UndoManager.cpp; sourceTree = SOURCE_ROOT; }; | ||||
| 3C9E6597968358B57374502C = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoManager.h; path = ../../src/utilities/juce_UndoManager.h; sourceTree = SOURCE_ROOT; }; | 3C9E6597968358B57374502C = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoManager.h; path = ../../src/utilities/juce_UndoManager.h; sourceTree = SOURCE_ROOT; }; | ||||
| ADE5F12AA5AD969E2C7002B3 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UnitTest.cpp; path = ../../src/utilities/juce_UnitTest.cpp; sourceTree = SOURCE_ROOT; }; | |||||
| 75700D13513346310CEAC30D = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UnitTest.h; path = ../../src/utilities/juce_UnitTest.h; sourceTree = SOURCE_ROOT; }; | |||||
| 2FD5C998952BE08F8ED3F262 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce.h; path = ../../juce.h; sourceTree = SOURCE_ROOT; }; | 2FD5C998952BE08F8ED3F262 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce.h; path = ../../juce.h; sourceTree = SOURCE_ROOT; }; | ||||
| 01778F26212AECCBF2452804 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Config.h; path = ../../juce_Config.h; sourceTree = SOURCE_ROOT; }; | 01778F26212AECCBF2452804 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Config.h; path = ../../juce_Config.h; sourceTree = SOURCE_ROOT; }; | ||||
| D443FD24B52106986FC8A531 = { isa = PBXGroup; children = ( | D443FD24B52106986FC8A531 = { isa = PBXGroup; children = ( | ||||
| @@ -1803,7 +1806,9 @@ | |||||
| FA833EFA9E93C7DBE6624676, | FA833EFA9E93C7DBE6624676, | ||||
| EECE464606AE845BFC4B941B, | EECE464606AE845BFC4B941B, | ||||
| A59A5DCFCCAAEA79D03C2B27, | A59A5DCFCCAAEA79D03C2B27, | ||||
| 3C9E6597968358B57374502C ); name = utilities; sourceTree = "<group>"; }; | |||||
| 3C9E6597968358B57374502C, | |||||
| ADE5F12AA5AD969E2C7002B3, | |||||
| 75700D13513346310CEAC30D ); name = utilities; sourceTree = "<group>"; }; | |||||
| 9AA3D660772E3D4C64EC7859 = { isa = PBXGroup; children = ( | 9AA3D660772E3D4C64EC7859 = { isa = PBXGroup; children = ( | ||||
| D443FD24B52106986FC8A531, | D443FD24B52106986FC8A531, | ||||
| F2B0E44A08E127FD31184241, | F2B0E44A08E127FD31184241, | ||||
| @@ -2231,7 +2236,8 @@ | |||||
| D8B9941A1375579D6CE7C1C4, | D8B9941A1375579D6CE7C1C4, | ||||
| 0DE731ED3EC994B9227C2741, | 0DE731ED3EC994B9227C2741, | ||||
| A124FE5709D9324B5BAFFE53, | A124FE5709D9324B5BAFFE53, | ||||
| A84A5CA4654AE87192A6A096 ); runOnlyForDeploymentPostprocessing = 0; }; | |||||
| A84A5CA4654AE87192A6A096, | |||||
| 55EDB4D9B702B469DB4655C3 ); runOnlyForDeploymentPostprocessing = 0; }; | |||||
| 01555BA382FAED280FF5F58A = { isa = PBXNativeTarget; buildConfigurationList = D14EC3F0DC5861E37D35E15A; buildPhases = ( | 01555BA382FAED280FF5F58A = { isa = PBXNativeTarget; buildConfigurationList = D14EC3F0DC5861E37D35E15A; buildPhases = ( | ||||
| 8914D147048B9EE245989ACB ); buildRules = ( ); dependencies = ( ); name = Juce; productName = Juce; productReference = 389351359BA78C682E1931A6; productType = "com.apple.product-type.library.static"; }; | 8914D147048B9EE245989ACB ); buildRules = ( ); dependencies = ( ); name = Juce; productName = Juce; productReference = 389351359BA78C682E1931A6; productType = "com.apple.product-type.library.static"; }; | ||||
| FCFFEDFC83101B196BFA2AE2 = { isa = PBXProject; buildConfigurationList = 3A1CB6B5ECF4A79CDE35CC66; compatibilityVersion = "Xcode 3.0"; hasScannedForEncodings = 0; mainGroup = 992526B83B6AA618A4FAECEB; projectDirPath = ""; projectRoot = ""; targets = ( 01555BA382FAED280FF5F58A ); }; | FCFFEDFC83101B196BFA2AE2 = { isa = PBXProject; buildConfigurationList = 3A1CB6B5ECF4A79CDE35CC66; compatibilityVersion = "Xcode 3.0"; hasScannedForEncodings = 0; mainGroup = 992526B83B6AA618A4FAECEB; projectDirPath = ""; projectRoot = ""; targets = ( 01555BA382FAED280FF5F58A ); }; | ||||
| @@ -964,6 +964,8 @@ | |||||
| <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.cpp"/> | |||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.h"/> | |||||
| </Filter> | </Filter> | ||||
| <File RelativePath="..\..\juce.h"/> | <File RelativePath="..\..\juce.h"/> | ||||
| <File RelativePath="..\..\juce_Config.h"/> | <File RelativePath="..\..\juce_Config.h"/> | ||||
| @@ -964,6 +964,8 @@ | |||||
| <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.cpp"/> | |||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.h"/> | |||||
| </Filter> | </Filter> | ||||
| <File RelativePath="..\..\juce.h"/> | <File RelativePath="..\..\juce.h"/> | ||||
| <File RelativePath="..\..\juce_Config.h"/> | <File RelativePath="..\..\juce_Config.h"/> | ||||
| @@ -966,6 +966,8 @@ | |||||
| <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoableAction.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.cpp"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | <File RelativePath="..\..\src\utilities\juce_UndoManager.h"/> | ||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.cpp"/> | |||||
| <File RelativePath="..\..\src\utilities\juce_UnitTest.h"/> | |||||
| </Filter> | </Filter> | ||||
| <File RelativePath="..\..\juce.h"/> | <File RelativePath="..\..\juce.h"/> | ||||
| <File RelativePath="..\..\juce_Config.h"/> | <File RelativePath="..\..\juce_Config.h"/> | ||||
| @@ -425,6 +425,7 @@ | |||||
| <ClCompile Include="..\..\src\utilities\juce_PropertiesFile.cpp"/> | <ClCompile Include="..\..\src\utilities\juce_PropertiesFile.cpp"/> | ||||
| <ClCompile Include="..\..\src\utilities\juce_RecentlyOpenedFilesList.cpp"/> | <ClCompile Include="..\..\src\utilities\juce_RecentlyOpenedFilesList.cpp"/> | ||||
| <ClCompile Include="..\..\src\utilities\juce_UndoManager.cpp"/> | <ClCompile Include="..\..\src\utilities\juce_UndoManager.cpp"/> | ||||
| <ClCompile Include="..\..\src\utilities\juce_UnitTest.cpp"/> | |||||
| </ItemGroup> | </ItemGroup> | ||||
| <ItemGroup> | <ItemGroup> | ||||
| <ClInclude Include="..\..\src\application\juce_Application.h"/> | <ClInclude Include="..\..\src\application\juce_Application.h"/> | ||||
| @@ -768,6 +769,7 @@ | |||||
| <ClInclude Include="..\..\src\utilities\juce_SystemClipboard.h"/> | <ClInclude Include="..\..\src\utilities\juce_SystemClipboard.h"/> | ||||
| <ClInclude Include="..\..\src\utilities\juce_UndoableAction.h"/> | <ClInclude Include="..\..\src\utilities\juce_UndoableAction.h"/> | ||||
| <ClInclude Include="..\..\src\utilities\juce_UndoManager.h"/> | <ClInclude Include="..\..\src\utilities\juce_UndoManager.h"/> | ||||
| <ClInclude Include="..\..\src\utilities\juce_UnitTest.h"/> | |||||
| <ClInclude Include="..\..\juce.h"/> | <ClInclude Include="..\..\juce.h"/> | ||||
| <ClInclude Include="..\..\juce_Config.h"/> | <ClInclude Include="..\..\juce_Config.h"/> | ||||
| </ItemGroup> | </ItemGroup> | ||||
| @@ -1201,6 +1201,9 @@ | |||||
| <ClCompile Include="..\..\src\utilities\juce_UndoManager.cpp"> | <ClCompile Include="..\..\src\utilities\juce_UndoManager.cpp"> | ||||
| <Filter>Juce\Source\utilities</Filter> | <Filter>Juce\Source\utilities</Filter> | ||||
| </ClCompile> | </ClCompile> | ||||
| <ClCompile Include="..\..\src\utilities\juce_UnitTest.cpp"> | |||||
| <Filter>Juce\Source\utilities</Filter> | |||||
| </ClCompile> | |||||
| </ItemGroup> | </ItemGroup> | ||||
| <ItemGroup> | <ItemGroup> | ||||
| <ClInclude Include="..\..\src\application\juce_Application.h"> | <ClInclude Include="..\..\src\application\juce_Application.h"> | ||||
| @@ -2226,6 +2229,9 @@ | |||||
| <ClInclude Include="..\..\src\utilities\juce_UndoManager.h"> | <ClInclude Include="..\..\src\utilities\juce_UndoManager.h"> | ||||
| <Filter>Juce\Source\utilities</Filter> | <Filter>Juce\Source\utilities</Filter> | ||||
| </ClInclude> | </ClInclude> | ||||
| <ClInclude Include="..\..\src\utilities\juce_UnitTest.h"> | |||||
| <Filter>Juce\Source\utilities</Filter> | |||||
| </ClInclude> | |||||
| <ClInclude Include="..\..\juce.h"> | <ClInclude Include="..\..\juce.h"> | ||||
| <Filter>Juce\Source</Filter> | <Filter>Juce\Source</Filter> | ||||
| </ClInclude> | </ClInclude> | ||||
| @@ -337,6 +337,7 @@ | |||||
| 0DE731ED3EC994B9227C2741 = { isa = PBXBuildFile; fileRef = 4BE2727CCD2CD7603402C8FE; }; | 0DE731ED3EC994B9227C2741 = { isa = PBXBuildFile; fileRef = 4BE2727CCD2CD7603402C8FE; }; | ||||
| A124FE5709D9324B5BAFFE53 = { isa = PBXBuildFile; fileRef = A618FC3255ECE14EC9259E6B; }; | A124FE5709D9324B5BAFFE53 = { isa = PBXBuildFile; fileRef = A618FC3255ECE14EC9259E6B; }; | ||||
| A84A5CA4654AE87192A6A096 = { isa = PBXBuildFile; fileRef = A59A5DCFCCAAEA79D03C2B27; }; | A84A5CA4654AE87192A6A096 = { isa = PBXBuildFile; fileRef = A59A5DCFCCAAEA79D03C2B27; }; | ||||
| 55EDB4D9B702B469DB4655C3 = { isa = PBXBuildFile; fileRef = ADE5F12AA5AD969E2C7002B3; }; | |||||
| 389351359BA78C682E1931A6 = { isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libjucedebug.a; sourceTree = BUILT_PRODUCTS_DIR; }; | 389351359BA78C682E1931A6 = { isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libjucedebug.a; sourceTree = BUILT_PRODUCTS_DIR; }; | ||||
| 144F56FCF3DF9EC922765901 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_Application.cpp; path = ../../src/application/juce_Application.cpp; sourceTree = SOURCE_ROOT; }; | 144F56FCF3DF9EC922765901 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_Application.cpp; path = ../../src/application/juce_Application.cpp; sourceTree = SOURCE_ROOT; }; | ||||
| F6A490BA93AC3558E9A6FBB0 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Application.h; path = ../../src/application/juce_Application.h; sourceTree = SOURCE_ROOT; }; | F6A490BA93AC3558E9A6FBB0 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Application.h; path = ../../src/application/juce_Application.h; sourceTree = SOURCE_ROOT; }; | ||||
| @@ -1021,6 +1022,8 @@ | |||||
| EECE464606AE845BFC4B941B = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoableAction.h; path = ../../src/utilities/juce_UndoableAction.h; sourceTree = SOURCE_ROOT; }; | EECE464606AE845BFC4B941B = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoableAction.h; path = ../../src/utilities/juce_UndoableAction.h; sourceTree = SOURCE_ROOT; }; | ||||
| A59A5DCFCCAAEA79D03C2B27 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UndoManager.cpp; path = ../../src/utilities/juce_UndoManager.cpp; sourceTree = SOURCE_ROOT; }; | A59A5DCFCCAAEA79D03C2B27 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UndoManager.cpp; path = ../../src/utilities/juce_UndoManager.cpp; sourceTree = SOURCE_ROOT; }; | ||||
| 3C9E6597968358B57374502C = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoManager.h; path = ../../src/utilities/juce_UndoManager.h; sourceTree = SOURCE_ROOT; }; | 3C9E6597968358B57374502C = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UndoManager.h; path = ../../src/utilities/juce_UndoManager.h; sourceTree = SOURCE_ROOT; }; | ||||
| ADE5F12AA5AD969E2C7002B3 = { isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = juce_UnitTest.cpp; path = ../../src/utilities/juce_UnitTest.cpp; sourceTree = SOURCE_ROOT; }; | |||||
| 75700D13513346310CEAC30D = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_UnitTest.h; path = ../../src/utilities/juce_UnitTest.h; sourceTree = SOURCE_ROOT; }; | |||||
| 2FD5C998952BE08F8ED3F262 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce.h; path = ../../juce.h; sourceTree = SOURCE_ROOT; }; | 2FD5C998952BE08F8ED3F262 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce.h; path = ../../juce.h; sourceTree = SOURCE_ROOT; }; | ||||
| 01778F26212AECCBF2452804 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Config.h; path = ../../juce_Config.h; sourceTree = SOURCE_ROOT; }; | 01778F26212AECCBF2452804 = { isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = juce_Config.h; path = ../../juce_Config.h; sourceTree = SOURCE_ROOT; }; | ||||
| D443FD24B52106986FC8A531 = { isa = PBXGroup; children = ( | D443FD24B52106986FC8A531 = { isa = PBXGroup; children = ( | ||||
| @@ -1803,7 +1806,9 @@ | |||||
| FA833EFA9E93C7DBE6624676, | FA833EFA9E93C7DBE6624676, | ||||
| EECE464606AE845BFC4B941B, | EECE464606AE845BFC4B941B, | ||||
| A59A5DCFCCAAEA79D03C2B27, | A59A5DCFCCAAEA79D03C2B27, | ||||
| 3C9E6597968358B57374502C ); name = utilities; sourceTree = "<group>"; }; | |||||
| 3C9E6597968358B57374502C, | |||||
| ADE5F12AA5AD969E2C7002B3, | |||||
| 75700D13513346310CEAC30D ); name = utilities; sourceTree = "<group>"; }; | |||||
| 9AA3D660772E3D4C64EC7859 = { isa = PBXGroup; children = ( | 9AA3D660772E3D4C64EC7859 = { isa = PBXGroup; children = ( | ||||
| D443FD24B52106986FC8A531, | D443FD24B52106986FC8A531, | ||||
| F2B0E44A08E127FD31184241, | F2B0E44A08E127FD31184241, | ||||
| @@ -2231,7 +2236,8 @@ | |||||
| D8B9941A1375579D6CE7C1C4, | D8B9941A1375579D6CE7C1C4, | ||||
| 0DE731ED3EC994B9227C2741, | 0DE731ED3EC994B9227C2741, | ||||
| A124FE5709D9324B5BAFFE53, | A124FE5709D9324B5BAFFE53, | ||||
| A84A5CA4654AE87192A6A096 ); runOnlyForDeploymentPostprocessing = 0; }; | |||||
| A84A5CA4654AE87192A6A096, | |||||
| 55EDB4D9B702B469DB4655C3 ); runOnlyForDeploymentPostprocessing = 0; }; | |||||
| 01555BA382FAED280FF5F58A = { isa = PBXNativeTarget; buildConfigurationList = D14EC3F0DC5861E37D35E15A; buildPhases = ( | 01555BA382FAED280FF5F58A = { isa = PBXNativeTarget; buildConfigurationList = D14EC3F0DC5861E37D35E15A; buildPhases = ( | ||||
| 8914D147048B9EE245989ACB ); buildRules = ( ); dependencies = ( ); name = Juce; productName = Juce; productReference = 389351359BA78C682E1931A6; productType = "com.apple.product-type.library.static"; }; | 8914D147048B9EE245989ACB ); buildRules = ( ); dependencies = ( ); name = Juce; productName = Juce; productReference = 389351359BA78C682E1931A6; productType = "com.apple.product-type.library.static"; }; | ||||
| FCFFEDFC83101B196BFA2AE2 = { isa = PBXProject; buildConfigurationList = 3A1CB6B5ECF4A79CDE35CC66; compatibilityVersion = "Xcode 3.0"; hasScannedForEncodings = 0; mainGroup = 992526B83B6AA618A4FAECEB; projectDirPath = ""; projectRoot = ""; targets = ( 01555BA382FAED280FF5F58A ); }; | FCFFEDFC83101B196BFA2AE2 = { isa = PBXProject; buildConfigurationList = 3A1CB6B5ECF4A79CDE35CC66; compatibilityVersion = "Xcode 3.0"; hasScannedForEncodings = 0; mainGroup = 992526B83B6AA618A4FAECEB; projectDirPath = ""; projectRoot = ""; targets = ( 01555BA382FAED280FF5F58A ); }; | ||||
| @@ -1494,6 +1494,10 @@ | |||||
| file="src/utilities/juce_UndoManager.cpp"/> | file="src/utilities/juce_UndoManager.cpp"/> | ||||
| <FILE id="ZMxSjySn" name="juce_UndoManager.h" compile="0" resource="0" | <FILE id="ZMxSjySn" name="juce_UndoManager.h" compile="0" resource="0" | ||||
| file="src/utilities/juce_UndoManager.h"/> | file="src/utilities/juce_UndoManager.h"/> | ||||
| <FILE id="6QJ8o3k" name="juce_UnitTest.cpp" compile="1" resource="0" | |||||
| file="src/utilities/juce_UnitTest.cpp"/> | |||||
| <FILE id="PQBhHBA" name="juce_UnitTest.h" compile="0" resource="0" | |||||
| file="src/utilities/juce_UnitTest.h"/> | |||||
| </GROUP> | </GROUP> | ||||
| <FILE id="Jp7xh1cg9" name="juce.h" compile="0" resource="0" file="juce.h"/> | <FILE id="Jp7xh1cg9" name="juce.h" compile="0" resource="0" file="juce.h"/> | ||||
| <FILE id="G2j0wJTna" name="juce_Config.h" compile="0" resource="0" | <FILE id="G2j0wJTna" name="juce_Config.h" compile="0" resource="0" | ||||
| @@ -147,6 +147,7 @@ | |||||
| #include "../src/threads/juce_ThreadPool.cpp" | #include "../src/threads/juce_ThreadPool.cpp" | ||||
| #include "../src/threads/juce_TimeSliceThread.cpp" | #include "../src/threads/juce_TimeSliceThread.cpp" | ||||
| #include "../src/utilities/juce_DeletedAtShutdown.cpp" | #include "../src/utilities/juce_DeletedAtShutdown.cpp" | ||||
| #include "../src/utilities/juce_UnitTest.cpp" | |||||
| #endif | #endif | ||||
| #if JUCE_BUILD_MISC | #if JUCE_BUILD_MISC | ||||
| @@ -1439,7 +1439,7 @@ private: | |||||
| class NonWavelabMMLock | class NonWavelabMMLock | ||||
| { | { | ||||
| public: | public: | ||||
| NonWavelabMMLock() : mm (getHostType().isWavelab() ? 0 : new MessageManagerLock()) {} | |||||
| NonWavelabMMLock() : mm (getHostType().isWavelab() || getHostType().isCubaseBridged() ? 0 : new MessageManagerLock()) {} | |||||
| ~NonWavelabMMLock() {} | ~NonWavelabMMLock() {} | ||||
| private: | private: | ||||
| @@ -1448,7 +1448,7 @@ private: | |||||
| static void checkWhetherWavelabHasChangedThread() | static void checkWhetherWavelabHasChangedThread() | ||||
| { | { | ||||
| if (getHostType().isWavelab()) | |||||
| if (getHostType().isWavelab() || getHostType().isCubaseBridged()) | |||||
| MessageManager::getInstance()->setCurrentThreadAsMessageThread(); | MessageManager::getInstance()->setCurrentThreadAsMessageThread(); | ||||
| } | } | ||||
| #else | #else | ||||
| @@ -51,6 +51,7 @@ public: | |||||
| MackieTracktionGeneric, | MackieTracktionGeneric, | ||||
| SteinbergCubase4, | SteinbergCubase4, | ||||
| SteinbergCubase5, | SteinbergCubase5, | ||||
| SteinbergCubase5Bridged, | |||||
| SteinbergCubaseGeneric, | SteinbergCubaseGeneric, | ||||
| SteinbergWavelab5, | SteinbergWavelab5, | ||||
| SteinbergWavelab6, | SteinbergWavelab6, | ||||
| @@ -68,7 +69,12 @@ public: | |||||
| bool isCubase() const throw() | bool isCubase() const throw() | ||||
| { | { | ||||
| return type == SteinbergCubase4 || type == SteinbergCubase5 || type == SteinbergCubaseGeneric; | |||||
| return type == SteinbergCubase4 || type == SteinbergCubase5 || type == SteinbergCubase5Bridged || type == SteinbergCubaseGeneric; | |||||
| } | |||||
| bool isCubaseBridged() const throw() | |||||
| { | |||||
| return type == SteinbergCubase5Bridged; | |||||
| } | } | ||||
| bool isTracktion() const throw() | bool isTracktion() const throw() | ||||
| @@ -125,6 +131,7 @@ private: | |||||
| if (hostFilename.containsIgnoreCase ("Tracktion")) return MackieTracktionGeneric; | if (hostFilename.containsIgnoreCase ("Tracktion")) return MackieTracktionGeneric; | ||||
| if (hostFilename.containsIgnoreCase ("Cubase4")) return SteinbergCubase4; | if (hostFilename.containsIgnoreCase ("Cubase4")) return SteinbergCubase4; | ||||
| if (hostFilename.containsIgnoreCase ("Cubase5")) return SteinbergCubase5; | if (hostFilename.containsIgnoreCase ("Cubase5")) return SteinbergCubase5; | ||||
| if (hostFilename.containsIgnoreCase ("VSTBridgeApp")) return SteinbergCubase5Bridged; | |||||
| if (hostFilename.containsIgnoreCase ("Cubase")) return SteinbergCubaseGeneric; | if (hostFilename.containsIgnoreCase ("Cubase")) return SteinbergCubaseGeneric; | ||||
| if (hostFilename.containsIgnoreCase ("Wavelab 5")) return SteinbergWavelab5; | if (hostFilename.containsIgnoreCase ("Wavelab 5")) return SteinbergWavelab5; | ||||
| if (hostFilename.containsIgnoreCase ("Wavelab 6" )) return SteinbergWavelab6; | if (hostFilename.containsIgnoreCase ("Wavelab 6" )) return SteinbergWavelab6; | ||||
| @@ -17,12 +17,12 @@ ifeq ($(CONFIG),Debug) | |||||
| LIBDIR := build | LIBDIR := build | ||||
| OBJDIR := build/intermediate/Debug | OBJDIR := build/intermediate/Debug | ||||
| OUTDIR := build | OUTDIR := build | ||||
| CPPFLAGS := $(DEPFLAGS) -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| CPPFLAGS := $(DEPFLAGS) -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -D "JUCE_UNIT_TESTS=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -g -ggdb -O0 | CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -g -ggdb -O0 | ||||
| CXXFLAGS += $(CFLAGS) | CXXFLAGS += $(CFLAGS) | ||||
| LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../../../../juce/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound | LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../../../../juce/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound | ||||
| LDDEPS := | LDDEPS := | ||||
| RESFLAGS := -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| RESFLAGS := -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "DEBUG=1" -D "_DEBUG=1" -D "JUCE_UNIT_TESTS=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| TARGET := JuceDemo | TARGET := JuceDemo | ||||
| BLDCMD = $(CXX) -o $(OUTDIR)/$(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(TARGET_ARCH) | BLDCMD = $(CXX) -o $(OUTDIR)/$(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(TARGET_ARCH) | ||||
| endif | endif | ||||
| @@ -32,12 +32,12 @@ ifeq ($(CONFIG),Release) | |||||
| LIBDIR := build | LIBDIR := build | ||||
| OBJDIR := build/intermediate/Release | OBJDIR := build/intermediate/Release | ||||
| OUTDIR := build | OUTDIR := build | ||||
| CPPFLAGS := $(DEPFLAGS) -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "NDEBUG=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| CPPFLAGS := $(DEPFLAGS) -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "NDEBUG=1" -D "JUCE_UNIT_TESTS=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -Os | CFLAGS += $(CPPFLAGS) $(TARGET_ARCH) -Os | ||||
| CXXFLAGS += $(CFLAGS) | CXXFLAGS += $(CFLAGS) | ||||
| LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../../../../juce/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound | LDFLAGS += -L$(BINDIR) -L$(LIBDIR) -L"/usr/X11R6/lib/" -L"../../../../../juce/bin" -lfreetype -lpthread -lrt -lX11 -lGL -lGLU -lXinerama -lasound | ||||
| LDDEPS := | LDDEPS := | ||||
| RESFLAGS := -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "NDEBUG=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| RESFLAGS := -D "JUCER_LINUX_MAKE_7346DA2A=1" -D "LINUX=1" -D "NDEBUG=1" -D "JUCE_UNIT_TESTS=1" -I "/usr/include" -I "/usr/include/freetype2" | |||||
| TARGET := JuceDemo | TARGET := JuceDemo | ||||
| BLDCMD = $(CXX) -o $(OUTDIR)/$(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(TARGET_ARCH) | BLDCMD = $(CXX) -o $(OUTDIR)/$(TARGET) $(OBJECTS) $(LDFLAGS) $(RESOURCES) $(TARGET_ARCH) | ||||
| endif | endif | ||||
| @@ -190,7 +190,8 @@ | |||||
| GCC_PREPROCESSOR_DEFINITIONS = ( | GCC_PREPROCESSOR_DEFINITIONS = ( | ||||
| "JUCER_XCODE_MAC_F6D2F4CF=1", | "JUCER_XCODE_MAC_F6D2F4CF=1", | ||||
| "_DEBUG=1", | "_DEBUG=1", | ||||
| "DEBUG=1 "); }; name = Debug; }; | |||||
| "DEBUG=1 ", | |||||
| "JUCE_UNIT_TESTS=1"); }; name = Debug; }; | |||||
| 8EF7C7FFD55219581A5075F3 = { isa = XCBuildConfiguration; buildSettings = { | 8EF7C7FFD55219581A5075F3 = { isa = XCBuildConfiguration; buildSettings = { | ||||
| ARCHS = "$(ARCHS_STANDARD_32_BIT)"; | ARCHS = "$(ARCHS_STANDARD_32_BIT)"; | ||||
| PREBINDING = NO; | PREBINDING = NO; | ||||
| @@ -204,7 +205,8 @@ | |||||
| GCC_PREPROCESSOR_DEFINITIONS = ( | GCC_PREPROCESSOR_DEFINITIONS = ( | ||||
| "JUCER_XCODE_MAC_F6D2F4CF=1", | "JUCER_XCODE_MAC_F6D2F4CF=1", | ||||
| "_NDEBUG=1", | "_NDEBUG=1", | ||||
| "NDEBUG=1 "); }; name = Release; }; | |||||
| "NDEBUG=1 ", | |||||
| "JUCE_UNIT_TESTS=1"); }; name = Release; }; | |||||
| 7FA986B99AFC795723E00AB0 = { isa = XCBuildConfiguration; buildSettings = { | 7FA986B99AFC795723E00AB0 = { isa = XCBuildConfiguration; buildSettings = { | ||||
| ALWAYS_SEARCH_USER_PATHS = NO; | ALWAYS_SEARCH_USER_PATHS = NO; | ||||
| GCC_C_LANGUAGE_STANDARD = c99; | GCC_C_LANGUAGE_STANDARD = c99; | ||||
| @@ -33,7 +33,7 @@ | |||||
| BufferSecurityCheck="" | BufferSecurityCheck="" | ||||
| DebugInformationFormat="4" | DebugInformationFormat="4" | ||||
| AdditionalIncludeDirectories="" | AdditionalIncludeDirectories="" | ||||
| PreprocessorDefinitions="JUCER_VS2005_78A5003;WIN32;_WINDOWS;_DEBUG" | |||||
| PreprocessorDefinitions="JUCER_VS2005_78A5003;WIN32;_WINDOWS;_DEBUG;JUCE_UNIT_TESTS=1" | |||||
| RuntimeLibrary="1" | RuntimeLibrary="1" | ||||
| RuntimeTypeInfo="true" | RuntimeTypeInfo="true" | ||||
| UsePrecompiledHeader="0" | UsePrecompiledHeader="0" | ||||
| @@ -89,7 +89,7 @@ | |||||
| InlineFunctionExpansion="1" | InlineFunctionExpansion="1" | ||||
| StringPooling="true" | StringPooling="true" | ||||
| AdditionalIncludeDirectories="" | AdditionalIncludeDirectories="" | ||||
| PreprocessorDefinitions="JUCER_VS2005_78A5003;WIN32;_WINDOWS;NDEBUG" | |||||
| PreprocessorDefinitions="JUCER_VS2005_78A5003;WIN32;_WINDOWS;NDEBUG;JUCE_UNIT_TESTS=1" | |||||
| RuntimeLibrary="0" | RuntimeLibrary="0" | ||||
| RuntimeTypeInfo="true" | RuntimeTypeInfo="true" | ||||
| UsePrecompiledHeader="0" | UsePrecompiledHeader="0" | ||||
| @@ -33,7 +33,7 @@ | |||||
| BufferSecurityCheck="" | BufferSecurityCheck="" | ||||
| DebugInformationFormat="4" | DebugInformationFormat="4" | ||||
| AdditionalIncludeDirectories="" | AdditionalIncludeDirectories="" | ||||
| PreprocessorDefinitions="JUCER_VS2008_78A5006;WIN32;_WINDOWS;_DEBUG" | |||||
| PreprocessorDefinitions="JUCER_VS2008_78A5006;WIN32;_WINDOWS;_DEBUG;JUCE_UNIT_TESTS=1" | |||||
| RuntimeLibrary="1" | RuntimeLibrary="1" | ||||
| RuntimeTypeInfo="true" | RuntimeTypeInfo="true" | ||||
| UsePrecompiledHeader="0" | UsePrecompiledHeader="0" | ||||
| @@ -89,7 +89,7 @@ | |||||
| InlineFunctionExpansion="1" | InlineFunctionExpansion="1" | ||||
| StringPooling="true" | StringPooling="true" | ||||
| AdditionalIncludeDirectories="" | AdditionalIncludeDirectories="" | ||||
| PreprocessorDefinitions="JUCER_VS2008_78A5006;WIN32;_WINDOWS;NDEBUG" | |||||
| PreprocessorDefinitions="JUCER_VS2008_78A5006;WIN32;_WINDOWS;NDEBUG;JUCE_UNIT_TESTS=1" | |||||
| RuntimeLibrary="0" | RuntimeLibrary="0" | ||||
| RuntimeTypeInfo="true" | RuntimeTypeInfo="true" | ||||
| UsePrecompiledHeader="0" | UsePrecompiledHeader="0" | ||||
| @@ -54,7 +54,7 @@ | |||||
| <Optimization>Disabled</Optimization> | <Optimization>Disabled</Optimization> | ||||
| <DebugInformationFormat>EditAndContinue</DebugInformationFormat> | <DebugInformationFormat>EditAndContinue</DebugInformationFormat> | ||||
| <AdditionalIncludeDirectories>%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> | <AdditionalIncludeDirectories>%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> | ||||
| <PreprocessorDefinitions>JUCER_VS2010_78A501D;WIN32;_WINDOWS;_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||||
| <PreprocessorDefinitions>JUCER_VS2010_78A501D;WIN32;_WINDOWS;_DEBUG;JUCE_UNIT_TESTS=1;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||||
| <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary> | <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary> | ||||
| <RuntimeTypeInfo>true</RuntimeTypeInfo> | <RuntimeTypeInfo>true</RuntimeTypeInfo> | ||||
| <PrecompiledHeader/> | <PrecompiledHeader/> | ||||
| @@ -92,7 +92,7 @@ | |||||
| <ClCompile> | <ClCompile> | ||||
| <Optimization>MaxSpeed</Optimization> | <Optimization>MaxSpeed</Optimization> | ||||
| <AdditionalIncludeDirectories>%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> | <AdditionalIncludeDirectories>%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories> | ||||
| <PreprocessorDefinitions>JUCER_VS2010_78A501D;WIN32;_WINDOWS;NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||||
| <PreprocessorDefinitions>JUCER_VS2010_78A501D;WIN32;_WINDOWS;NDEBUG;JUCE_UNIT_TESTS=1;%(PreprocessorDefinitions)</PreprocessorDefinitions> | |||||
| <RuntimeLibrary>MultiThreaded</RuntimeLibrary> | <RuntimeLibrary>MultiThreaded</RuntimeLibrary> | ||||
| <RuntimeTypeInfo>true</RuntimeTypeInfo> | <RuntimeTypeInfo>true</RuntimeTypeInfo> | ||||
| <PrecompiledHeader/> | <PrecompiledHeader/> | ||||
| @@ -175,7 +175,8 @@ | |||||
| GCC_PREPROCESSOR_DEFINITIONS = ( | GCC_PREPROCESSOR_DEFINITIONS = ( | ||||
| "JUCER_XCODE_IPHONE_25ADD7EF=1", | "JUCER_XCODE_IPHONE_25ADD7EF=1", | ||||
| "_DEBUG=1", | "_DEBUG=1", | ||||
| "DEBUG=1 "); }; name = Debug; }; | |||||
| "DEBUG=1 ", | |||||
| "JUCE_UNIT_TESTS=1"); }; name = Debug; }; | |||||
| 8EF7C7FFD55219581A5075F3 = { isa = XCBuildConfiguration; buildSettings = { | 8EF7C7FFD55219581A5075F3 = { isa = XCBuildConfiguration; buildSettings = { | ||||
| ARCHS = "$(ARCHS_STANDARD_32_BIT)"; | ARCHS = "$(ARCHS_STANDARD_32_BIT)"; | ||||
| PREBINDING = NO; | PREBINDING = NO; | ||||
| @@ -189,7 +190,8 @@ | |||||
| GCC_PREPROCESSOR_DEFINITIONS = ( | GCC_PREPROCESSOR_DEFINITIONS = ( | ||||
| "JUCER_XCODE_IPHONE_25ADD7EF=1", | "JUCER_XCODE_IPHONE_25ADD7EF=1", | ||||
| "_NDEBUG=1", | "_NDEBUG=1", | ||||
| "NDEBUG=1 "); }; name = Release; }; | |||||
| "NDEBUG=1 ", | |||||
| "JUCE_UNIT_TESTS=1"); }; name = Release; }; | |||||
| 7FA986B99AFC795723E00AB0 = { isa = XCBuildConfiguration; buildSettings = { | 7FA986B99AFC795723E00AB0 = { isa = XCBuildConfiguration; buildSettings = { | ||||
| ALWAYS_SEARCH_USER_PATHS = NO; | ALWAYS_SEARCH_USER_PATHS = NO; | ||||
| GCC_C_LANGUAGE_STANDARD = c99; | GCC_C_LANGUAGE_STANDARD = c99; | ||||
| @@ -24,9 +24,9 @@ | |||||
| </EXPORTFORMATS> | </EXPORTFORMATS> | ||||
| <CONFIGURATIONS> | <CONFIGURATIONS> | ||||
| <CONFIGURATION name="Debug" isDebug="1" optimisation="1" targetName="JuceDemo" | <CONFIGURATION name="Debug" isDebug="1" optimisation="1" targetName="JuceDemo" | ||||
| osxSDK="default" osxCompatibility="default"/> | |||||
| osxSDK="default" osxCompatibility="default" defines="JUCE_UNIT_TESTS=1"/> | |||||
| <CONFIGURATION name="Release" isDebug="0" optimisation="2" targetName="JuceDemo" | <CONFIGURATION name="Release" isDebug="0" optimisation="2" targetName="JuceDemo" | ||||
| osxSDK="default" osxCompatibility="default"/> | |||||
| osxSDK="default" osxCompatibility="default" defines="JUCE_UNIT_TESTS=1"/> | |||||
| </CONFIGURATIONS> | </CONFIGURATIONS> | ||||
| <MAINGROUP id="0bU7ypLe" name="Juce Demo"> | <MAINGROUP id="0bU7ypLe" name="Juce Demo"> | ||||
| <GROUP id="BEJsSEFfF" name="Source"> | <GROUP id="BEJsSEFfF" name="Source"> | ||||
| @@ -64,7 +64,7 @@ | |||||
| */ | */ | ||||
| #define JUCE_MAJOR_VERSION 1 | #define JUCE_MAJOR_VERSION 1 | ||||
| #define JUCE_MINOR_VERSION 52 | #define JUCE_MINOR_VERSION 52 | ||||
| #define JUCE_BUILDNUMBER 59 | |||||
| #define JUCE_BUILDNUMBER 60 | |||||
| /** Current Juce version number. | /** Current Juce version number. | ||||
| @@ -1757,36 +1757,43 @@ public: | |||||
| int compareLexicographically (const String& other) const throw(); | int compareLexicographically (const String& other) const throw(); | ||||
| /** Tests whether the string begins with another string. | /** Tests whether the string begins with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool startsWith (const String& text) const throw(); | bool startsWith (const String& text) const throw(); | ||||
| /** Tests whether the string begins with a particular character. | /** Tests whether the string begins with a particular character. | ||||
| If the character is 0, this will always return false. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool startsWithChar (juce_wchar character) const throw(); | bool startsWithChar (juce_wchar character) const throw(); | ||||
| /** Tests whether the string begins with another string. | /** Tests whether the string begins with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-insensitive comparison. | Uses a case-insensitive comparison. | ||||
| */ | */ | ||||
| bool startsWithIgnoreCase (const String& text) const throw(); | bool startsWithIgnoreCase (const String& text) const throw(); | ||||
| /** Tests whether the string ends with another string. | /** Tests whether the string ends with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool endsWith (const String& text) const throw(); | bool endsWith (const String& text) const throw(); | ||||
| /** Tests whether the string ends with a particular character. | /** Tests whether the string ends with a particular character. | ||||
| If the character is 0, this will always return false. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool endsWithChar (juce_wchar character) const throw(); | bool endsWithChar (juce_wchar character) const throw(); | ||||
| /** Tests whether the string ends with another string. | /** Tests whether the string ends with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-insensitive comparison. | Uses a case-insensitive comparison. | ||||
| */ | */ | ||||
| bool endsWithIgnoreCase (const String& text) const throw(); | bool endsWithIgnoreCase (const String& text) const throw(); | ||||
| /** Tests whether the string contains another substring. | /** Tests whether the string contains another substring. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool contains (const String& text) const throw(); | bool contains (const String& text) const throw(); | ||||
| @@ -13870,7 +13877,6 @@ public: | |||||
| private: | private: | ||||
| File logFile; | File logFile; | ||||
| CriticalSection logLock; | CriticalSection logLock; | ||||
| ScopedPointer <FileOutputStream> logStream; | |||||
| void trimFileSize (int maxFileSizeBytes) const; | void trimFileSize (int maxFileSizeBytes) const; | ||||
| @@ -61385,6 +61391,221 @@ public: | |||||
| #endif | #endif | ||||
| #ifndef __JUCE_UNDOMANAGER_JUCEHEADER__ | #ifndef __JUCE_UNDOMANAGER_JUCEHEADER__ | ||||
| #endif | |||||
| #ifndef __JUCE_UNITTEST_JUCEHEADER__ | |||||
| /*** Start of inlined file: juce_UnitTest.h ***/ | |||||
| #ifndef __JUCE_UNITTEST_JUCEHEADER__ | |||||
| #define __JUCE_UNITTEST_JUCEHEADER__ | |||||
| class UnitTestRunner; | |||||
| /** | |||||
| This is a base class for classes that perform a unit test. | |||||
| To write a test using this class, your code should look something like this: | |||||
| @code | |||||
| class MyTest : public UnitTest | |||||
| { | |||||
| public: | |||||
| MyTest() : UnitTest ("Foobar testing") {} | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("Part 1"); | |||||
| expect (myFoobar.doesSomething()); | |||||
| expect (myFoobar.doesSomethingElse()); | |||||
| beginTest ("Part 2"); | |||||
| expect (myOtherFoobar.doesSomething()); | |||||
| expect (myOtherFoobar.doesSomethingElse()); | |||||
| ...etc.. | |||||
| } | |||||
| }; | |||||
| // Creating a static instance will automatically add the instance to the array | |||||
| // returned by UnitTest::getAllTests(), so the test will be included when you call | |||||
| // UnitTestRunner::runAllTests() | |||||
| static MyTest test; | |||||
| @endcode | |||||
| To run a test, use the UnitTestRunner class. | |||||
| @see UnitTestRunner | |||||
| */ | |||||
| class UnitTest | |||||
| { | |||||
| public: | |||||
| /** Creates a test with the given name. */ | |||||
| UnitTest (const String& name); | |||||
| /** Destructor. */ | |||||
| virtual ~UnitTest(); | |||||
| /** Returns the name of the test. */ | |||||
| const String getName() const throw() { return name; } | |||||
| /** Runs the test, using the specified UnitTestRunner. | |||||
| You shouldn't need to call this method directly - use | |||||
| UnitTestRunner::runTests() instead. | |||||
| */ | |||||
| void performTest (UnitTestRunner* runner); | |||||
| /** Returns the set of all UnitTest objects that currently exist. */ | |||||
| static Array<UnitTest*>& getAllTests(); | |||||
| /** Implement this method in your subclass to actually run your tests. | |||||
| The content of your implementation should call beginTest() and expect() | |||||
| to perform the tests. | |||||
| */ | |||||
| virtual void runTest() = 0; | |||||
| /** Tells the system that a new subsection of tests is beginning. | |||||
| This should be called from your runTest() method, and may be called | |||||
| as many times as you like, to demarcate different sets of tests. | |||||
| */ | |||||
| void beginTest (const String& testName); | |||||
| /** Checks that the result of a test is true, and logs this result. | |||||
| In your runTest() method, you should call this method for each condition that | |||||
| you want to check, e.g. | |||||
| @code | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("basic tests"); | |||||
| expect (x + y == 2); | |||||
| expect (getThing() == someThing); | |||||
| ...etc... | |||||
| } | |||||
| @endcode | |||||
| If testResult is true, a pass is logged; if it's false, a failure is logged. | |||||
| If the failure message is specified, it will be written to the log if the test fails. | |||||
| */ | |||||
| void expect (bool testResult, const String& failureMessage = String::empty); | |||||
| /** Writes a message to the test log. | |||||
| This can only be called from within your runTest() method. | |||||
| */ | |||||
| void logMessage (const String& message); | |||||
| private: | |||||
| const String name; | |||||
| UnitTestRunner* runner; | |||||
| UnitTest (const UnitTest&); | |||||
| UnitTest& operator= (const UnitTest&); | |||||
| }; | |||||
| /** | |||||
| Runs a set of unit tests. | |||||
| You can instantiate one of these objects and use it to invoke tests on a set of | |||||
| UnitTest objects. | |||||
| By using a subclass of UnitTestRunner, you can intercept logging messages and | |||||
| perform custom behaviour when each test completes. | |||||
| @see UnitTest | |||||
| */ | |||||
| class UnitTestRunner | |||||
| { | |||||
| public: | |||||
| /** */ | |||||
| UnitTestRunner(); | |||||
| /** Destructor. */ | |||||
| virtual ~UnitTestRunner(); | |||||
| /** Runs a set of tests. | |||||
| The tests are performed in order, and the results are logged. To run all the | |||||
| registered UnitTest objects that exist, use runAllTests(). | |||||
| */ | |||||
| void runTests (const Array<UnitTest*>& tests, bool assertOnFailure); | |||||
| /** Runs all the UnitTest objects that currently exist. | |||||
| This calls runTests() for all the objects listed in UnitTest::getAllTests(). | |||||
| */ | |||||
| void runAllTests (bool assertOnFailure); | |||||
| /** Contains the results of a test. | |||||
| One of these objects is instantiated each time UnitTest::beginTest() is called, and | |||||
| it contains details of the number of subsequent UnitTest::expect() calls that are | |||||
| made. | |||||
| */ | |||||
| struct TestResult | |||||
| { | |||||
| /** The main name of this test (i.e. the name of the UnitTest object being run). */ | |||||
| String unitTestName; | |||||
| /** The name of the current subcategory (i.e. the name that was set when UnitTest::beginTest() was called). */ | |||||
| String subcategoryName; | |||||
| /** The number of UnitTest::expect() calls that succeeded. */ | |||||
| int passes; | |||||
| /** The number of UnitTest::expect() calls that failed. */ | |||||
| int failures; | |||||
| /** A list of messages describing the failed tests. */ | |||||
| StringArray messages; | |||||
| }; | |||||
| /** Returns the number of TestResult objects that have been performed. | |||||
| @see getResult | |||||
| */ | |||||
| int getNumResults() const throw(); | |||||
| /** Returns one of the TestResult objects that describes a test that has been run. | |||||
| @see getNumResults | |||||
| */ | |||||
| const TestResult* getResult (int index) const throw(); | |||||
| protected: | |||||
| /** Called when the list of results changes. | |||||
| You can override this to perform some sort of behaviour when results are added. | |||||
| */ | |||||
| virtual void resultsUpdated(); | |||||
| /** Logs a message about the current test progress. | |||||
| By default this just writes the message to the Logger class, but you could override | |||||
| this to do something else with the data. | |||||
| */ | |||||
| virtual void logMessage (const String& message); | |||||
| private: | |||||
| friend class UnitTest; | |||||
| UnitTest* currentTest; | |||||
| String currentSubCategory; | |||||
| OwnedArray <TestResult, CriticalSection> results; | |||||
| bool assertOnFailure; | |||||
| void beginNewTest (UnitTest* test, const String& subCategory); | |||||
| void endTest(); | |||||
| void addPass(); | |||||
| void addFail (const String& failureMessage); | |||||
| UnitTestRunner (const UnitTestRunner&); | |||||
| UnitTestRunner& operator= (const UnitTestRunner&); | |||||
| }; | |||||
| #endif // __JUCE_UNITTEST_JUCEHEADER__ | |||||
| /*** End of inlined file: juce_UnitTest.h ***/ | |||||
| #endif | #endif | ||||
| #endif | #endif | ||||
| @@ -50,9 +50,6 @@ FileLogger::FileLogger (const File& logFile_, | |||||
| logFile_.create(); | logFile_.create(); | ||||
| } | } | ||||
| logStream = logFile_.createOutputStream (256); | |||||
| jassert (logStream != 0); | |||||
| String welcome; | String welcome; | ||||
| welcome << "\r\n**********************************************************\r\n" | welcome << "\r\n**********************************************************\r\n" | ||||
| << welcomeMessage | << welcomeMessage | ||||
| @@ -69,14 +66,12 @@ FileLogger::~FileLogger() | |||||
| //============================================================================== | //============================================================================== | ||||
| void FileLogger::logMessage (const String& message) | void FileLogger::logMessage (const String& message) | ||||
| { | { | ||||
| if (logStream != 0) | |||||
| { | |||||
| DBG (message); | |||||
| DBG (message); | |||||
| const ScopedLock sl (logLock); | |||||
| (*logStream) << message << "\r\n"; | |||||
| logStream->flush(); | |||||
| } | |||||
| const ScopedLock sl (logLock); | |||||
| FileOutputStream out (logFile, 256); | |||||
| out << message << "\r\n"; | |||||
| } | } | ||||
| @@ -100,7 +100,6 @@ public: | |||||
| private: | private: | ||||
| File logFile; | File logFile; | ||||
| CriticalSection logLock; | CriticalSection logLock; | ||||
| ScopedPointer <FileOutputStream> logStream; | |||||
| void trimFileSize (int maxFileSizeBytes) const; | void trimFileSize (int maxFileSizeBytes) const; | ||||
| @@ -50,125 +50,6 @@ BEGIN_JUCE_NAMESPACE | |||||
| extern void juce_CheckForDanglingStreams(); // (in juce_OutputStream.cpp) | extern void juce_CheckForDanglingStreams(); // (in juce_OutputStream.cpp) | ||||
| #endif | #endif | ||||
| //============================================================================== | |||||
| #if JUCE_DEBUG | |||||
| namespace SimpleUnitTests | |||||
| { | |||||
| template <typename Type> | |||||
| class AtomicTester | |||||
| { | |||||
| public: | |||||
| AtomicTester() {} | |||||
| static void testInteger() | |||||
| { | |||||
| Atomic<Type> a, b; | |||||
| a.set ((Type) 10); | |||||
| a += (Type) 15; | |||||
| a.memoryBarrier(); | |||||
| a -= (Type) 5; | |||||
| ++a; ++a; --a; | |||||
| a.memoryBarrier(); | |||||
| testFloat(); | |||||
| } | |||||
| static void testFloat() | |||||
| { | |||||
| Atomic<Type> a, b; | |||||
| a = (Type) 21; | |||||
| a.memoryBarrier(); | |||||
| /* These are some simple test cases to check the atomics - let me know | |||||
| if any of these assertions fail on your system! | |||||
| */ | |||||
| jassert (a.get() == (Type) 21); | |||||
| jassert (a.compareAndSetValue ((Type) 100, (Type) 50) == (Type) 21); | |||||
| jassert (a.get() == (Type) 21); | |||||
| jassert (a.compareAndSetValue ((Type) 101, a.get()) == (Type) 21); | |||||
| jassert (a.get() == (Type) 101); | |||||
| jassert (! a.compareAndSetBool ((Type) 300, (Type) 200)); | |||||
| jassert (a.get() == (Type) 101); | |||||
| jassert (a.compareAndSetBool ((Type) 200, a.get())); | |||||
| jassert (a.get() == (Type) 200); | |||||
| jassert (a.exchange ((Type) 300) == (Type) 200); | |||||
| jassert (a.get() == (Type) 300); | |||||
| b = a; | |||||
| jassert (b.get() == a.get()); | |||||
| } | |||||
| }; | |||||
| static void runBasicTests() | |||||
| { | |||||
| // Some simple test code, to keep an eye on things and make sure these functions | |||||
| // work ok on all platforms. Let me know if any of these assertions fail on your system! | |||||
| static_jassert (sizeof (pointer_sized_int) == sizeof (void*)); | |||||
| static_jassert (sizeof (int8) == 1); | |||||
| static_jassert (sizeof (uint8) == 1); | |||||
| static_jassert (sizeof (int16) == 2); | |||||
| static_jassert (sizeof (uint16) == 2); | |||||
| static_jassert (sizeof (int32) == 4); | |||||
| static_jassert (sizeof (uint32) == 4); | |||||
| static_jassert (sizeof (int64) == 8); | |||||
| static_jassert (sizeof (uint64) == 8); | |||||
| char a1[7]; | |||||
| jassert (numElementsInArray(a1) == 7); | |||||
| int a2[3]; | |||||
| jassert (numElementsInArray(a2) == 3); | |||||
| jassert (ByteOrder::swap ((uint16) 0x1122) == 0x2211); | |||||
| jassert (ByteOrder::swap ((uint32) 0x11223344) == 0x44332211); | |||||
| jassert (ByteOrder::swap ((uint64) literal64bit (0x1122334455667788)) == literal64bit (0x8877665544332211)); | |||||
| // Some quick stream tests.. | |||||
| int randomInt = Random::getSystemRandom().nextInt(); | |||||
| int64 randomInt64 = Random::getSystemRandom().nextInt64(); | |||||
| double randomDouble = Random::getSystemRandom().nextDouble(); | |||||
| String randomString; | |||||
| for (int i = 50; --i >= 0;) | |||||
| randomString << (juce_wchar) (Random::getSystemRandom().nextInt() & 0xffff); | |||||
| MemoryOutputStream mo; | |||||
| mo.writeInt (randomInt); | |||||
| mo.writeIntBigEndian (randomInt); | |||||
| mo.writeCompressedInt (randomInt); | |||||
| mo.writeString (randomString); | |||||
| mo.writeInt64 (randomInt64); | |||||
| mo.writeInt64BigEndian (randomInt64); | |||||
| mo.writeDouble (randomDouble); | |||||
| mo.writeDoubleBigEndian (randomDouble); | |||||
| MemoryInputStream mi (mo.getData(), mo.getDataSize(), false); | |||||
| jassert (mi.readInt() == randomInt); | |||||
| jassert (mi.readIntBigEndian() == randomInt); | |||||
| jassert (mi.readCompressedInt() == randomInt); | |||||
| jassert (mi.readString() == randomString); | |||||
| jassert (mi.readInt64() == randomInt64); | |||||
| jassert (mi.readInt64BigEndian() == randomInt64); | |||||
| jassert (mi.readDouble() == randomDouble); | |||||
| jassert (mi.readDoubleBigEndian() == randomDouble); | |||||
| AtomicTester <int>::testInteger(); | |||||
| AtomicTester <unsigned int>::testInteger(); | |||||
| AtomicTester <int32>::testInteger(); | |||||
| AtomicTester <uint32>::testInteger(); | |||||
| AtomicTester <long>::testInteger(); | |||||
| AtomicTester <void*>::testInteger(); | |||||
| AtomicTester <int*>::testInteger(); | |||||
| AtomicTester <float>::testFloat(); | |||||
| #if ! JUCE_64BIT_ATOMICS_UNAVAILABLE // 64-bit intrinsics aren't available on some old platforms | |||||
| AtomicTester <int64>::testInteger(); | |||||
| AtomicTester <uint64>::testInteger(); | |||||
| AtomicTester <double>::testFloat(); | |||||
| #endif | |||||
| } | |||||
| } | |||||
| #endif | |||||
| //============================================================================== | //============================================================================== | ||||
| static bool juceInitialisedNonGUI = false; | static bool juceInitialisedNonGUI = false; | ||||
| @@ -181,14 +62,22 @@ void JUCE_PUBLIC_FUNCTION initialiseJuce_NonGUI() | |||||
| JUCE_AUTORELEASEPOOL | JUCE_AUTORELEASEPOOL | ||||
| #if JUCE_DEBUG | |||||
| SimpleUnitTests::runBasicTests(); | |||||
| #endif | |||||
| DBG (SystemStats::getJUCEVersion()); | DBG (SystemStats::getJUCEVersion()); | ||||
| SystemStats::initialiseStats(); | SystemStats::initialiseStats(); | ||||
| Random::getSystemRandom().setSeedRandomly(); // (mustn't call this before initialiseStats() because it relies on the time being set up) | Random::getSystemRandom().setSeedRandomly(); // (mustn't call this before initialiseStats() because it relies on the time being set up) | ||||
| } | } | ||||
| // Some basic tests, to keep an eye on things and make sure these types work ok | |||||
| // on all platforms. Let me know if any of these assertions fail on your system! | |||||
| static_jassert (sizeof (pointer_sized_int) == sizeof (void*)); | |||||
| static_jassert (sizeof (int8) == 1); | |||||
| static_jassert (sizeof (uint8) == 1); | |||||
| static_jassert (sizeof (int16) == 2); | |||||
| static_jassert (sizeof (uint16) == 2); | |||||
| static_jassert (sizeof (int32) == 4); | |||||
| static_jassert (sizeof (uint32) == 4); | |||||
| static_jassert (sizeof (int64) == 8); | |||||
| static_jassert (sizeof (uint64) == 8); | |||||
| } | } | ||||
| void JUCE_PUBLIC_FUNCTION shutdownJuce_NonGUI() | void JUCE_PUBLIC_FUNCTION shutdownJuce_NonGUI() | ||||
| @@ -269,4 +158,95 @@ void JUCE_PUBLIC_FUNCTION shutdownJuce_GUI() | |||||
| #endif | #endif | ||||
| //============================================================================== | |||||
| #if JUCE_UNIT_TESTS | |||||
| #include "../utilities/juce_UnitTest.h" | |||||
| class AtomicTests : public UnitTest | |||||
| { | |||||
| public: | |||||
| AtomicTests() : UnitTest ("Atomics") {} | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("Misc"); | |||||
| char a1[7]; | |||||
| expect (numElementsInArray(a1) == 7); | |||||
| int a2[3]; | |||||
| expect (numElementsInArray(a2) == 3); | |||||
| expect (ByteOrder::swap ((uint16) 0x1122) == 0x2211); | |||||
| expect (ByteOrder::swap ((uint32) 0x11223344) == 0x44332211); | |||||
| expect (ByteOrder::swap ((uint64) literal64bit (0x1122334455667788)) == literal64bit (0x8877665544332211)); | |||||
| beginTest ("Atomic types"); | |||||
| AtomicTester <int>::testInteger (*this); | |||||
| AtomicTester <unsigned int>::testInteger (*this); | |||||
| AtomicTester <int32>::testInteger (*this); | |||||
| AtomicTester <uint32>::testInteger (*this); | |||||
| AtomicTester <long>::testInteger (*this); | |||||
| AtomicTester <void*>::testInteger (*this); | |||||
| AtomicTester <int*>::testInteger (*this); | |||||
| AtomicTester <float>::testFloat (*this); | |||||
| #if ! JUCE_64BIT_ATOMICS_UNAVAILABLE // 64-bit intrinsics aren't available on some old platforms | |||||
| AtomicTester <int64>::testInteger (*this); | |||||
| AtomicTester <uint64>::testInteger (*this); | |||||
| AtomicTester <double>::testFloat (*this); | |||||
| #endif | |||||
| } | |||||
| template <typename Type> | |||||
| class AtomicTester | |||||
| { | |||||
| public: | |||||
| AtomicTester() {} | |||||
| static void testInteger (UnitTest& test) | |||||
| { | |||||
| Atomic<Type> a, b; | |||||
| a.set ((Type) 10); | |||||
| a += (Type) 15; | |||||
| a.memoryBarrier(); | |||||
| a -= (Type) 5; | |||||
| ++a; ++a; --a; | |||||
| a.memoryBarrier(); | |||||
| testFloat (test); | |||||
| } | |||||
| static void testFloat (UnitTest& test) | |||||
| { | |||||
| Atomic<Type> a, b; | |||||
| a = (Type) 21; | |||||
| a.memoryBarrier(); | |||||
| /* These are some simple test cases to check the atomics - let me know | |||||
| if any of these assertions fail on your system! | |||||
| */ | |||||
| test.expect (a.get() == (Type) 21); | |||||
| test.expect (a.compareAndSetValue ((Type) 100, (Type) 50) == (Type) 21); | |||||
| test.expect (a.get() == (Type) 21); | |||||
| test.expect (a.compareAndSetValue ((Type) 101, a.get()) == (Type) 21); | |||||
| test.expect (a.get() == (Type) 101); | |||||
| test.expect (! a.compareAndSetBool ((Type) 300, (Type) 200)); | |||||
| test.expect (a.get() == (Type) 101); | |||||
| test.expect (a.compareAndSetBool ((Type) 200, a.get())); | |||||
| test.expect (a.get() == (Type) 200); | |||||
| test.expect (a.exchange ((Type) 300) == (Type) 200); | |||||
| test.expect (a.get() == (Type) 300); | |||||
| b = a; | |||||
| test.expect (b.get() == a.get()); | |||||
| } | |||||
| }; | |||||
| }; | |||||
| static AtomicTests atomicUnitTests; | |||||
| #endif | |||||
| END_JUCE_NAMESPACE | END_JUCE_NAMESPACE | ||||
| @@ -33,7 +33,7 @@ | |||||
| */ | */ | ||||
| #define JUCE_MAJOR_VERSION 1 | #define JUCE_MAJOR_VERSION 1 | ||||
| #define JUCE_MINOR_VERSION 52 | #define JUCE_MINOR_VERSION 52 | ||||
| #define JUCE_BUILDNUMBER 59 | |||||
| #define JUCE_BUILDNUMBER 60 | |||||
| /** Current Juce version number. | /** Current Juce version number. | ||||
| @@ -570,7 +570,8 @@ int File::findChildFiles (Array<File>& results, | |||||
| } | } | ||||
| if (searchRecursively && itemIsDirectory | if (searchRecursively && itemIsDirectory | ||||
| && fileTypeMatches (whatToLookFor | findDirectories, true, itemIsHidden)) | |||||
| && ((! itemIsHidden) || (whatToLookFor & File::ignoreHiddenFiles) == 0)) | |||||
| { | { | ||||
| total += fileFound.findChildFiles (results, whatToLookFor, true, wildCardPattern); | total += fileFound.findChildFiles (results, whatToLookFor, true, wildCardPattern); | ||||
| } | } | ||||
| @@ -92,4 +92,53 @@ int64 MemoryInputStream::getPosition() | |||||
| return position; | return position; | ||||
| } | } | ||||
| #if JUCE_UNIT_TESTS | |||||
| #include "../../utilities/juce_UnitTest.h" | |||||
| #include "../../core/juce_Random.h" | |||||
| #include "juce_MemoryOutputStream.h" | |||||
| class MemoryStreamTests : public UnitTest | |||||
| { | |||||
| public: | |||||
| MemoryStreamTests() : UnitTest ("MemoryInputStream & MemoryOutputStream") {} | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("Basics"); | |||||
| int randomInt = Random::getSystemRandom().nextInt(); | |||||
| int64 randomInt64 = Random::getSystemRandom().nextInt64(); | |||||
| double randomDouble = Random::getSystemRandom().nextDouble(); | |||||
| String randomString; | |||||
| for (int i = 50; --i >= 0;) | |||||
| randomString << (juce_wchar) (Random::getSystemRandom().nextInt() & 0xffff); | |||||
| MemoryOutputStream mo; | |||||
| mo.writeInt (randomInt); | |||||
| mo.writeIntBigEndian (randomInt); | |||||
| mo.writeCompressedInt (randomInt); | |||||
| mo.writeString (randomString); | |||||
| mo.writeInt64 (randomInt64); | |||||
| mo.writeInt64BigEndian (randomInt64); | |||||
| mo.writeDouble (randomDouble); | |||||
| mo.writeDoubleBigEndian (randomDouble); | |||||
| MemoryInputStream mi (mo.getData(), mo.getDataSize(), false); | |||||
| expect (mi.readInt() == randomInt); | |||||
| expect (mi.readIntBigEndian() == randomInt); | |||||
| expect (mi.readCompressedInt() == randomInt); | |||||
| expect (mi.readString() == randomString); | |||||
| expect (mi.readInt64() == randomInt64); | |||||
| expect (mi.readInt64BigEndian() == randomInt64); | |||||
| expect (mi.readDouble() == randomDouble); | |||||
| expect (mi.readDoubleBigEndian() == randomDouble); | |||||
| } | |||||
| }; | |||||
| static MemoryStreamTests memoryInputStreamUnitTests; | |||||
| #endif | |||||
| END_JUCE_NAMESPACE | END_JUCE_NAMESPACE | ||||
| @@ -758,5 +758,8 @@ | |||||
| #ifndef __JUCE_UNDOMANAGER_JUCEHEADER__ | #ifndef __JUCE_UNDOMANAGER_JUCEHEADER__ | ||||
| #include "utilities/juce_UndoManager.h" | #include "utilities/juce_UndoManager.h" | ||||
| #endif | #endif | ||||
| #ifndef __JUCE_UNITTEST_JUCEHEADER__ | |||||
| #include "utilities/juce_UnitTest.h" | |||||
| #endif | |||||
| #endif | #endif | ||||
| @@ -28,15 +28,6 @@ | |||||
| #if JUCE_INCLUDED_FILE | #if JUCE_INCLUDED_FILE | ||||
| //============================================================================== | //============================================================================== | ||||
| using ::free; | |||||
| namespace MidiConstants | |||||
| { | |||||
| static const int midiBufferSize = 1024 * 10; | |||||
| static const int numInHeaders = 32; | |||||
| static const int inBufferSize = 256; | |||||
| } | |||||
| class MidiInThread : public Thread | class MidiInThread : public Thread | ||||
| { | { | ||||
| public: | public: | ||||
| @@ -44,18 +35,19 @@ public: | |||||
| MidiInThread (MidiInput* const input_, | MidiInThread (MidiInput* const input_, | ||||
| MidiInputCallback* const callback_) | MidiInputCallback* const callback_) | ||||
| : Thread ("Juce Midi"), | : Thread ("Juce Midi"), | ||||
| hIn (0), | |||||
| deviceHandle (0), | |||||
| input (input_), | input (input_), | ||||
| callback (callback_), | callback (callback_), | ||||
| isStarted (false), | isStarted (false), | ||||
| startTime (0), | |||||
| pendingLength(0) | |||||
| startTime (0) | |||||
| { | { | ||||
| for (int i = MidiConstants::numInHeaders; --i >= 0;) | |||||
| pending.ensureSize ((int) defaultBufferSize); | |||||
| for (int i = (int) numInHeaders; --i >= 0;) | |||||
| { | { | ||||
| zeromem (&hdr[i], sizeof (MIDIHDR)); | zeromem (&hdr[i], sizeof (MIDIHDR)); | ||||
| hdr[i].lpData = inData[i]; | hdr[i].lpData = inData[i]; | ||||
| hdr[i].dwBufferLength = MidiConstants::inBufferSize; | |||||
| hdr[i].dwBufferLength = (int) inBufferSize; | |||||
| } | } | ||||
| }; | }; | ||||
| @@ -63,12 +55,12 @@ public: | |||||
| { | { | ||||
| stop(); | stop(); | ||||
| if (hIn != 0) | |||||
| if (deviceHandle != 0) | |||||
| { | { | ||||
| int count = 5; | int count = 5; | ||||
| while (--count >= 0) | while (--count >= 0) | ||||
| { | { | ||||
| if (midiInClose (hIn) == MMSYSERR_NOERROR) | |||||
| if (midiInClose (deviceHandle) == MMSYSERR_NOERROR) | |||||
| break; | break; | ||||
| Sleep (20); | Sleep (20); | ||||
| @@ -83,24 +75,11 @@ public: | |||||
| if (byte < 0x80) | if (byte < 0x80) | ||||
| return; | return; | ||||
| const int numBytes = MidiMessage::getMessageLengthFromFirstByte ((uint8) byte); | |||||
| const double time = timeStampToTime (timeStamp); | |||||
| const int time = timeStampToMs (timeStamp); | |||||
| { | { | ||||
| const ScopedLock sl (lock); | const ScopedLock sl (lock); | ||||
| if (pendingLength < MidiConstants::midiBufferSize - 12) | |||||
| { | |||||
| char* const p = pending + pendingLength; | |||||
| *(double*) p = time; | |||||
| *(uint32*) (p + 8) = numBytes; | |||||
| *(uint32*) (p + 12) = message; | |||||
| pendingLength += 12 + numBytes; | |||||
| } | |||||
| else | |||||
| { | |||||
| jassertfalse; // midi buffer overflow! You might need to increase the size.. | |||||
| } | |||||
| pending.addEvent (&message, 3, time); | |||||
| } | } | ||||
| notify(); | notify(); | ||||
| @@ -108,27 +87,14 @@ public: | |||||
| void handleSysEx (MIDIHDR* const hdr, const uint32 timeStamp) | void handleSysEx (MIDIHDR* const hdr, const uint32 timeStamp) | ||||
| { | { | ||||
| const int time = timeStampToMs (timeStamp); | |||||
| const int num = hdr->dwBytesRecorded; | const int num = hdr->dwBytesRecorded; | ||||
| if (num > 0) | if (num > 0) | ||||
| { | { | ||||
| const double time = timeStampToTime (timeStamp); | |||||
| { | { | ||||
| const ScopedLock sl (lock); | const ScopedLock sl (lock); | ||||
| if (pendingLength < MidiConstants::midiBufferSize - (8 + num)) | |||||
| { | |||||
| char* const p = pending + pendingLength; | |||||
| *(double*) p = time; | |||||
| *(uint32*) (p + 8) = num; | |||||
| memcpy (p + 12, hdr->lpData, num); | |||||
| pendingLength += 12 + num; | |||||
| } | |||||
| else | |||||
| { | |||||
| jassertfalse; // midi buffer overflow! You might need to increase the size.. | |||||
| } | |||||
| pending.addEvent (hdr->lpData, num, time); | |||||
| } | } | ||||
| notify(); | notify(); | ||||
| @@ -138,65 +104,52 @@ public: | |||||
| void writeBlock (const int i) | void writeBlock (const int i) | ||||
| { | { | ||||
| hdr[i].dwBytesRecorded = 0; | hdr[i].dwBytesRecorded = 0; | ||||
| MMRESULT res = midiInPrepareHeader (hIn, &hdr[i], sizeof (MIDIHDR)); | |||||
| MMRESULT res = midiInPrepareHeader (deviceHandle, &hdr[i], sizeof (MIDIHDR)); | |||||
| jassert (res == MMSYSERR_NOERROR); | jassert (res == MMSYSERR_NOERROR); | ||||
| res = midiInAddBuffer (hIn, &hdr[i], sizeof (MIDIHDR)); | |||||
| res = midiInAddBuffer (deviceHandle, &hdr[i], sizeof (MIDIHDR)); | |||||
| jassert (res == MMSYSERR_NOERROR); | jassert (res == MMSYSERR_NOERROR); | ||||
| } | } | ||||
| void run() | void run() | ||||
| { | { | ||||
| MemoryBlock pendingCopy (64); | |||||
| MidiBuffer newEvents; | |||||
| newEvents.ensureSize ((int) defaultBufferSize); | |||||
| while (! threadShouldExit()) | while (! threadShouldExit()) | ||||
| { | { | ||||
| for (int i = 0; i < MidiConstants::numInHeaders; ++i) | |||||
| for (int i = 0; i < (int) numInHeaders; ++i) | |||||
| { | { | ||||
| if ((hdr[i].dwFlags & WHDR_DONE) != 0) | if ((hdr[i].dwFlags & WHDR_DONE) != 0) | ||||
| { | { | ||||
| MMRESULT res = midiInUnprepareHeader (hIn, &hdr[i], sizeof (MIDIHDR)); | |||||
| MMRESULT res = midiInUnprepareHeader (deviceHandle, &hdr[i], sizeof (MIDIHDR)); | |||||
| (void) res; | (void) res; | ||||
| jassert (res == MMSYSERR_NOERROR); | jassert (res == MMSYSERR_NOERROR); | ||||
| writeBlock (i); | writeBlock (i); | ||||
| } | } | ||||
| } | } | ||||
| int len; | |||||
| newEvents.clear(); // (resets it without freeing allocated storage) | |||||
| { | { | ||||
| const ScopedLock sl (lock); | const ScopedLock sl (lock); | ||||
| len = pendingLength; | |||||
| if (len > 0) | |||||
| { | |||||
| pendingCopy.ensureSize (len); | |||||
| pendingCopy.copyFrom (pending, 0, len); | |||||
| pendingLength = 0; | |||||
| } | |||||
| newEvents.swapWith (pending); | |||||
| } | } | ||||
| //xxx needs to figure out if blocks are broken up or not | //xxx needs to figure out if blocks are broken up or not | ||||
| if (len == 0) | |||||
| if (newEvents.isEmpty()) | |||||
| { | { | ||||
| wait (500); | wait (500); | ||||
| } | } | ||||
| else | else | ||||
| { | { | ||||
| const char* p = (const char*) pendingCopy.getData(); | |||||
| MidiMessage message (0xf4, 0.0); | |||||
| int time; | |||||
| while (len > 0) | |||||
| for (MidiBuffer::Iterator i (newEvents); i.getNextEvent (message, time);) | |||||
| { | { | ||||
| const double time = *(const double*) p; | |||||
| const int messageLen = *(const int*) (p + 8); | |||||
| const MidiMessage message ((const uint8*) (p + 12), messageLen, time); | |||||
| message.setTimeStamp (time * 0.001); | |||||
| callback->handleIncomingMidiMessage (input, message); | callback->handleIncomingMidiMessage (input, message); | ||||
| p += 12 + messageLen; | |||||
| len -= 12 + messageLen; | |||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| @@ -204,26 +157,25 @@ public: | |||||
| void start() | void start() | ||||
| { | { | ||||
| jassert (hIn != 0); | |||||
| if (hIn != 0 && ! isStarted) | |||||
| jassert (deviceHandle != 0); | |||||
| if (deviceHandle != 0 && ! isStarted) | |||||
| { | { | ||||
| stop(); | stop(); | ||||
| activeMidiThreads.addIfNotAlreadyThere (this); | activeMidiThreads.addIfNotAlreadyThere (this); | ||||
| int i; | int i; | ||||
| for (i = 0; i < MidiConstants::numInHeaders; ++i) | |||||
| for (i = 0; i < (int) numInHeaders; ++i) | |||||
| writeBlock (i); | writeBlock (i); | ||||
| startTime = Time::getMillisecondCounter(); | startTime = Time::getMillisecondCounter(); | ||||
| MMRESULT res = midiInStart (hIn); | |||||
| MMRESULT res = midiInStart (deviceHandle); | |||||
| jassert (res == MMSYSERR_NOERROR); | jassert (res == MMSYSERR_NOERROR); | ||||
| if (res == MMSYSERR_NOERROR) | if (res == MMSYSERR_NOERROR) | ||||
| { | { | ||||
| isStarted = true; | isStarted = true; | ||||
| pendingLength = 0; | |||||
| pending.clear(); | |||||
| startThread (6); | startThread (6); | ||||
| } | } | ||||
| } | } | ||||
| @@ -235,19 +187,19 @@ public: | |||||
| { | { | ||||
| stopThread (5000); | stopThread (5000); | ||||
| midiInReset (hIn); | |||||
| midiInStop (hIn); | |||||
| midiInReset (deviceHandle); | |||||
| midiInStop (deviceHandle); | |||||
| activeMidiThreads.removeValue (this); | activeMidiThreads.removeValue (this); | ||||
| { const ScopedLock sl (lock); } | { const ScopedLock sl (lock); } | ||||
| for (int i = MidiConstants::numInHeaders; --i >= 0;) | |||||
| for (int i = (int) numInHeaders; --i >= 0;) | |||||
| { | { | ||||
| if ((hdr[i].dwFlags & WHDR_DONE) != 0) | if ((hdr[i].dwFlags & WHDR_DONE) != 0) | ||||
| { | { | ||||
| int c = 10; | int c = 10; | ||||
| while (--c >= 0 && midiInUnprepareHeader (hIn, &hdr[i], sizeof (MIDIHDR)) == MIDIERR_STILLPLAYING) | |||||
| while (--c >= 0 && midiInUnprepareHeader (deviceHandle, &hdr[i], sizeof (MIDIHDR)) == MIDIERR_STILLPLAYING) | |||||
| Sleep (20); | Sleep (20); | ||||
| jassert (c >= 0); | jassert (c >= 0); | ||||
| @@ -255,7 +207,7 @@ public: | |||||
| } | } | ||||
| isStarted = false; | isStarted = false; | ||||
| pendingLength = 0; | |||||
| pending.clear(); | |||||
| } | } | ||||
| } | } | ||||
| @@ -274,7 +226,7 @@ public: | |||||
| juce_UseDebuggingNewOperator | juce_UseDebuggingNewOperator | ||||
| HMIDIIN hIn; | |||||
| HMIDIIN deviceHandle; | |||||
| private: | private: | ||||
| static Array <void*, CriticalSection> activeMidiThreads; | static Array <void*, CriticalSection> activeMidiThreads; | ||||
| @@ -285,13 +237,16 @@ private: | |||||
| uint32 startTime; | uint32 startTime; | ||||
| CriticalSection lock; | CriticalSection lock; | ||||
| MIDIHDR hdr [MidiConstants::numInHeaders]; | |||||
| char inData [MidiConstants::numInHeaders] [MidiConstants::inBufferSize]; | |||||
| enum { defaultBufferSize = 8192, | |||||
| numInHeaders = 32, | |||||
| inBufferSize = 256 }; | |||||
| MIDIHDR hdr [(int) numInHeaders]; | |||||
| char inData [(int) numInHeaders] [(int) inBufferSize]; | |||||
| int pendingLength; | |||||
| char pending [MidiConstants::midiBufferSize]; | |||||
| MidiBuffer pending; | |||||
| double timeStampToTime (uint32 timeStamp) | |||||
| int timeStampToMs (uint32 timeStamp) | |||||
| { | { | ||||
| timeStamp += startTime; | timeStamp += startTime; | ||||
| @@ -304,7 +259,7 @@ private: | |||||
| timeStamp = now; | timeStamp = now; | ||||
| } | } | ||||
| return 0.001 * timeStamp; | |||||
| return (int) timeStamp; | |||||
| } | } | ||||
| MidiInThread (const MidiInThread&); | MidiInThread (const MidiInThread&); | ||||
| @@ -358,7 +313,7 @@ MidiInput* MidiInput::openDevice (const int index, MidiInputCallback* const call | |||||
| if (index == n) | if (index == n) | ||||
| { | { | ||||
| deviceId = i; | deviceId = i; | ||||
| name = String (mc.szPname, sizeof (mc.szPname)); | |||||
| name = String (mc.szPname, numElementsInArray (mc.szPname)); | |||||
| break; | break; | ||||
| } | } | ||||
| @@ -377,7 +332,7 @@ MidiInput* MidiInput::openDevice (const int index, MidiInputCallback* const call | |||||
| if (err == MMSYSERR_NOERROR) | if (err == MMSYSERR_NOERROR) | ||||
| { | { | ||||
| thread->hIn = h; | |||||
| thread->deviceHandle = h; | |||||
| in->internal = thread.release(); | in->internal = thread.release(); | ||||
| return in.release(); | return in.release(); | ||||
| } | } | ||||
| @@ -967,7 +967,7 @@ private: | |||||
| void createWindow() | void createWindow() | ||||
| { | { | ||||
| DWORD exstyle = WS_EX_ACCEPTFILES; | |||||
| DWORD exstyle = WS_EX_ACCEPTFILES; // | WS_EX_NOACTIVATE; | |||||
| DWORD type = WS_CLIPSIBLINGS | WS_CLIPCHILDREN; | DWORD type = WS_CLIPSIBLINGS | WS_CLIPCHILDREN; | ||||
| if (hasTitleBar()) | if (hasTitleBar()) | ||||
| @@ -2184,5 +2184,272 @@ void String::Concatenator::append (const String& s) | |||||
| } | } | ||||
| } | } | ||||
| #if JUCE_UNIT_TESTS | |||||
| #include "../utilities/juce_UnitTest.h" | |||||
| #include "../core/juce_Random.h" | |||||
| class StringTests : public UnitTest | |||||
| { | |||||
| public: | |||||
| StringTests() : UnitTest ("String class") {} | |||||
| void runTest() | |||||
| { | |||||
| { | |||||
| beginTest ("Basics"); | |||||
| expect (String().length() == 0); | |||||
| expect (String() == String::empty); | |||||
| String s1, s2 ("abcd"); | |||||
| expect (s1.isEmpty() && ! s1.isNotEmpty()); | |||||
| expect (s2.isNotEmpty() && ! s2.isEmpty()); | |||||
| expect (s2.length() == 4); | |||||
| s1 = "abcd"; | |||||
| expect (s2 == s1 && s1 == s2); | |||||
| expect (s1 == "abcd" && s1 == L"abcd"); | |||||
| expect (String ("abcd") == String (L"abcd")); | |||||
| expect (String ("abcdefg", 4) == L"abcd"); | |||||
| expect (String ("abcdefg", 4) == String (L"abcdefg", 4)); | |||||
| expect (String::charToString ('x') == "x"); | |||||
| expect (String::charToString (0) == String::empty); | |||||
| expect (s2 + "e" == "abcde" && s2 + 'e' == "abcde"); | |||||
| expect (s2 + L'e' == "abcde" && s2 + L"e" == "abcde"); | |||||
| expect (s1.equalsIgnoreCase ("abcD") && s1 < "abce" && s1 > "abbb"); | |||||
| expect (s1.startsWith ("ab") && s1.startsWith ("abcd") && ! s1.startsWith ("abcde")); | |||||
| expect (s1.startsWithIgnoreCase ("aB") && s1.endsWithIgnoreCase ("CD")); | |||||
| expect (s1.endsWith ("bcd") && ! s1.endsWith ("aabcd")); | |||||
| expect (s1.indexOf (String::empty) == 0); | |||||
| expect (s1.startsWith (String::empty) && s1.endsWith (String::empty) && s1.contains (String::empty)); | |||||
| expect (s1.contains ("cd") && s1.contains ("ab") && s1.contains ("abcd")); | |||||
| expect (s1.containsChar ('a') && ! s1.containsChar (0)); | |||||
| expect (String ("abc foo bar").containsWholeWord ("abc") && String ("abc foo bar").containsWholeWord ("abc")); | |||||
| } | |||||
| { | |||||
| beginTest ("Operations"); | |||||
| String s ("012345678"); | |||||
| expect (s.hashCode() != 0); | |||||
| expect (s.hashCode64() != 0); | |||||
| expect (s.hashCode() != (s + s).hashCode()); | |||||
| expect (s.hashCode64() != (s + s).hashCode64()); | |||||
| expect (s.compare (String ("012345678")) == 0); | |||||
| expect (s.compare (String ("012345679")) < 0); | |||||
| expect (s.compare (String ("012345676")) > 0); | |||||
| expect (s.substring (2, 3) == String::charToString (s[2])); | |||||
| expect (s.substring (0, 1) == String::charToString (s[0])); | |||||
| expect (s.getLastCharacter() == s [s.length() - 1]); | |||||
| expect (String::charToString (s.getLastCharacter()) == s.getLastCharacters (1)); | |||||
| expect (s.substring (0, 3) == L"012"); | |||||
| expect (s.substring (0, 100) == s); | |||||
| expect (s.substring (-1, 100) == s); | |||||
| expect (s.substring (3) == "345678"); | |||||
| expect (s.indexOf (L"45") == 4); | |||||
| expect (String ("444445").indexOf ("45") == 4); | |||||
| expect (String ("444445").lastIndexOfChar ('4') == 4); | |||||
| expect (String ("45454545x").lastIndexOf (L"45") == 6); | |||||
| expect (String ("45454545x").lastIndexOfAnyOf ("456") == 7); | |||||
| expect (String ("45454545x").lastIndexOfAnyOf (L"456x") == 8); | |||||
| expect (String ("abABaBaBa").lastIndexOfIgnoreCase ("Ab") == 6); | |||||
| expect (s.indexOfChar (L'4') == 4); | |||||
| expect (s + s == "012345678012345678"); | |||||
| expect (s.startsWith (s)); | |||||
| expect (s.startsWith (s.substring (0, 4))); | |||||
| expect (s.startsWith (s.dropLastCharacters (4))); | |||||
| expect (s.endsWith (s.substring (5))); | |||||
| expect (s.endsWith (s)); | |||||
| expect (s.contains (s.substring (3, 6))); | |||||
| expect (s.contains (s.substring (3))); | |||||
| expect (s.startsWithChar (s[0])); | |||||
| expect (s.endsWithChar (s.getLastCharacter())); | |||||
| expect (s [s.length()] == 0); | |||||
| expect (String ("abcdEFGH").toLowerCase() == String ("abcdefgh")); | |||||
| expect (String ("abcdEFGH").toUpperCase() == String ("ABCDEFGH")); | |||||
| String s2 ("123"); | |||||
| s2 << ((int) 4) << ((short) 5) << "678" << L"9" << '0'; | |||||
| s2 += "xyz"; | |||||
| expect (s2 == "1234567890xyz"); | |||||
| beginTest ("Numeric conversions"); | |||||
| expect (String::empty.getIntValue() == 0); | |||||
| expect (String::empty.getDoubleValue() == 0.0); | |||||
| expect (String::empty.getFloatValue() == 0.0f); | |||||
| expect (s.getIntValue() == 12345678); | |||||
| expect (s.getLargeIntValue() == (int64) 12345678); | |||||
| expect (s.getDoubleValue() == 12345678.0); | |||||
| expect (s.getFloatValue() == 12345678.0f); | |||||
| expect (String (-1234).getIntValue() == -1234); | |||||
| expect (String ((int64) -1234).getLargeIntValue() == -1234); | |||||
| expect (String (-1234.56).getDoubleValue() == -1234.56); | |||||
| expect (String (-1234.56f).getFloatValue() == -1234.56f); | |||||
| expect (("xyz" + s).getTrailingIntValue() == s.getIntValue()); | |||||
| expect (s.getHexValue32() == 0x12345678); | |||||
| expect (s.getHexValue64() == (int64) 0x12345678); | |||||
| expect (String::toHexString (0x1234abcd).equalsIgnoreCase ("1234abcd")); | |||||
| expect (String::toHexString ((int64) 0x1234abcd).equalsIgnoreCase ("1234abcd")); | |||||
| expect (String::toHexString ((short) 0x12ab).equalsIgnoreCase ("12ab")); | |||||
| unsigned char data[] = { 1, 2, 3, 4, 0xa, 0xb, 0xc, 0xd }; | |||||
| expect (String::toHexString (data, 8, 0).equalsIgnoreCase ("010203040a0b0c0d")); | |||||
| expect (String::toHexString (data, 8, 1).equalsIgnoreCase ("01 02 03 04 0a 0b 0c 0d")); | |||||
| expect (String::toHexString (data, 8, 2).equalsIgnoreCase ("0102 0304 0a0b 0c0d")); | |||||
| beginTest ("Subsections"); | |||||
| String s3; | |||||
| s3 = "abcdeFGHIJ"; | |||||
| expect (s3.equalsIgnoreCase ("ABCdeFGhiJ")); | |||||
| expect (s3.compareIgnoreCase (L"ABCdeFGhiJ") == 0); | |||||
| expect (s3.containsIgnoreCase (s3.substring (3))); | |||||
| expect (s3.indexOfAnyOf ("xyzf", 2, true) == 5); | |||||
| expect (s3.indexOfAnyOf (L"xyzf", 2, false) == -1); | |||||
| expect (s3.indexOfAnyOf ("xyzF", 2, false) == 5); | |||||
| expect (s3.containsAnyOf (L"zzzFs")); | |||||
| expect (s3.startsWith ("abcd")); | |||||
| expect (s3.startsWithIgnoreCase (L"abCD")); | |||||
| expect (s3.startsWith (String::empty)); | |||||
| expect (s3.startsWithChar ('a')); | |||||
| expect (s3.endsWith (String ("HIJ"))); | |||||
| expect (s3.endsWithIgnoreCase (L"Hij")); | |||||
| expect (s3.endsWith (String::empty)); | |||||
| expect (s3.endsWithChar (L'J')); | |||||
| expect (s3.indexOf ("HIJ") == 7); | |||||
| expect (s3.indexOf (L"HIJK") == -1); | |||||
| expect (s3.indexOfIgnoreCase ("hij") == 7); | |||||
| expect (s3.indexOfIgnoreCase (L"hijk") == -1); | |||||
| String s4 (s3); | |||||
| s4.append (String ("xyz123"), 3); | |||||
| expect (s4 == s3 + "xyz"); | |||||
| expect (String (1234) < String (1235)); | |||||
| expect (String (1235) > String (1234)); | |||||
| expect (String (1234) >= String (1234)); | |||||
| expect (String (1234) <= String (1234)); | |||||
| expect (String (1235) >= String (1234)); | |||||
| expect (String (1234) <= String (1235)); | |||||
| String s5 ("word word2 word3"); | |||||
| expect (s5.containsWholeWord (String ("word2"))); | |||||
| expect (s5.indexOfWholeWord ("word2") == 5); | |||||
| expect (s5.containsWholeWord (L"word")); | |||||
| expect (s5.containsWholeWord ("word3")); | |||||
| expect (s5.containsWholeWord (s5)); | |||||
| expect (s5.containsWholeWordIgnoreCase (L"Word2")); | |||||
| expect (s5.indexOfWholeWordIgnoreCase ("Word2") == 5); | |||||
| expect (s5.containsWholeWordIgnoreCase (L"Word")); | |||||
| expect (s5.containsWholeWordIgnoreCase ("Word3")); | |||||
| expect (! s5.containsWholeWordIgnoreCase (L"Wordx")); | |||||
| expect (!s5.containsWholeWordIgnoreCase ("xWord2")); | |||||
| expect (s5.containsNonWhitespaceChars()); | |||||
| expect (! String (" \n\r\t").containsNonWhitespaceChars()); | |||||
| expect (s5.matchesWildcard (L"wor*", false)); | |||||
| expect (s5.matchesWildcard ("wOr*", true)); | |||||
| expect (s5.matchesWildcard (L"*word3", true)); | |||||
| expect (s5.matchesWildcard ("*word?", true)); | |||||
| expect (s5.matchesWildcard (L"Word*3", true)); | |||||
| expect (s5.fromFirstOccurrenceOf (String::empty, true, false) == s5); | |||||
| expect (s5.fromFirstOccurrenceOf ("xword2", true, false) == s5.substring (100)); | |||||
| expect (s5.fromFirstOccurrenceOf (L"word2", true, false) == s5.substring (5)); | |||||
| expect (s5.fromFirstOccurrenceOf ("Word2", true, true) == s5.substring (5)); | |||||
| expect (s5.fromFirstOccurrenceOf ("word2", false, false) == s5.getLastCharacters (6)); | |||||
| expect (s5.fromFirstOccurrenceOf (L"Word2", false, true) == s5.getLastCharacters (6)); | |||||
| expect (s5.fromLastOccurrenceOf (String::empty, true, false) == s5); | |||||
| expect (s5.fromLastOccurrenceOf (L"wordx", true, false) == s5); | |||||
| expect (s5.fromLastOccurrenceOf ("word", true, false) == s5.getLastCharacters (5)); | |||||
| expect (s5.fromLastOccurrenceOf (L"worD", true, true) == s5.getLastCharacters (5)); | |||||
| expect (s5.fromLastOccurrenceOf ("word", false, false) == s5.getLastCharacters (1)); | |||||
| expect (s5.fromLastOccurrenceOf (L"worD", false, true) == s5.getLastCharacters (1)); | |||||
| expect (s5.upToFirstOccurrenceOf (String::empty, true, false).isEmpty()); | |||||
| expect (s5.upToFirstOccurrenceOf ("word4", true, false) == s5); | |||||
| expect (s5.upToFirstOccurrenceOf (L"word2", true, false) == s5.substring (0, 10)); | |||||
| expect (s5.upToFirstOccurrenceOf ("Word2", true, true) == s5.substring (0, 10)); | |||||
| expect (s5.upToFirstOccurrenceOf (L"word2", false, false) == s5.substring (0, 5)); | |||||
| expect (s5.upToFirstOccurrenceOf ("Word2", false, true) == s5.substring (0, 5)); | |||||
| expect (s5.upToLastOccurrenceOf (String::empty, true, false) == s5); | |||||
| expect (s5.upToLastOccurrenceOf ("zword", true, false) == s5); | |||||
| expect (s5.upToLastOccurrenceOf ("word", true, false) == s5.dropLastCharacters (1)); | |||||
| expect (s5.dropLastCharacters(1).upToLastOccurrenceOf ("word", true, false) == s5.dropLastCharacters (1)); | |||||
| expect (s5.upToLastOccurrenceOf ("Word", true, true) == s5.dropLastCharacters (1)); | |||||
| expect (s5.upToLastOccurrenceOf ("word", false, false) == s5.dropLastCharacters (5)); | |||||
| expect (s5.upToLastOccurrenceOf ("Word", false, true) == s5.dropLastCharacters (5)); | |||||
| expect (s5.replace ("word", L"xyz", false) == String ("xyz xyz2 xyz3")); | |||||
| expect (s5.replace (L"Word", "xyz", true) == "xyz xyz2 xyz3"); | |||||
| expect (s5.dropLastCharacters (1).replace ("Word", String ("xyz"), true) == L"xyz xyz2 xyz"); | |||||
| expect (s5.replace ("Word", "", true) == " 2 3"); | |||||
| expect (s5.replace ("Word2", L"xyz", true) == String ("word xyz word3")); | |||||
| expect (s5.replaceCharacter (L'w', 'x') != s5); | |||||
| expect (s5.replaceCharacter ('w', L'x').replaceCharacter ('x', 'w') == s5); | |||||
| expect (s5.replaceCharacters ("wo", "xy") != s5); | |||||
| expect (s5.replaceCharacters ("wo", "xy").replaceCharacters ("xy", L"wo") == s5); | |||||
| expect (s5.retainCharacters ("1wordxya") == String ("wordwordword")); | |||||
| expect (s5.retainCharacters (String::empty).isEmpty()); | |||||
| expect (s5.removeCharacters ("1wordxya") == " 2 3"); | |||||
| expect (s5.removeCharacters (String::empty) == s5); | |||||
| expect (s5.initialSectionContainingOnly ("word") == L"word"); | |||||
| expect (s5.initialSectionNotContaining (String ("xyz ")) == String ("word")); | |||||
| expect (! s5.isQuotedString()); | |||||
| expect (s5.quoted().isQuotedString()); | |||||
| expect (! s5.quoted().unquoted().isQuotedString()); | |||||
| expect (! String ("x'").isQuotedString()); | |||||
| expect (String ("'x").isQuotedString()); | |||||
| String s6 (" \t xyz \t\r\n"); | |||||
| expect (s6.trim() == String ("xyz")); | |||||
| expect (s6.trim().trim() == "xyz"); | |||||
| expect (s5.trim() == s5); | |||||
| expect (s6.trimStart().trimEnd() == s6.trim()); | |||||
| expect (s6.trimStart().trimEnd() == s6.trimEnd().trimStart()); | |||||
| expect (s6.trimStart().trimStart().trimEnd().trimEnd() == s6.trimEnd().trimStart()); | |||||
| expect (s6.trimStart() != s6.trimEnd()); | |||||
| expect (("\t\r\n " + s6 + "\t\n \r").trim() == s6.trim()); | |||||
| expect (String::repeatedString ("xyz", 3) == L"xyzxyzxyz"); | |||||
| } | |||||
| { | |||||
| beginTest ("UTF8"); | |||||
| String s ("word word2 word3"); | |||||
| { | |||||
| char buffer [100]; | |||||
| memset (buffer, 0xff, sizeof (buffer)); | |||||
| s.copyToUTF8 (buffer, 100); | |||||
| expect (String::fromUTF8 (buffer, 100) == s); | |||||
| juce_wchar bufferUnicode [100]; | |||||
| memset (bufferUnicode, 0xff, sizeof (bufferUnicode)); | |||||
| s.copyToUnicode (bufferUnicode, 100); | |||||
| expect (String (bufferUnicode, 100) == s); | |||||
| } | |||||
| { | |||||
| juce_wchar wideBuffer [50]; | |||||
| zerostruct (wideBuffer); | |||||
| for (int i = 0; i < numElementsInArray (wideBuffer) - 1; ++i) | |||||
| wideBuffer[i] = (juce_wchar) (1 + Random::getSystemRandom().nextInt (std::numeric_limits<juce_wchar>::max() - 1)); | |||||
| String wide (wideBuffer); | |||||
| expect (wide == (const juce_wchar*) wideBuffer); | |||||
| expect (wide.length() == numElementsInArray (wideBuffer) - 1); | |||||
| expect (String::fromUTF8 (wide.toUTF8()) == wide); | |||||
| expect (String::fromUTF8 (wide.toUTF8()) == wideBuffer); | |||||
| } | |||||
| } | |||||
| } | |||||
| }; | |||||
| static StringTests stringUnitTests; | |||||
| #endif | |||||
| END_JUCE_NAMESPACE | END_JUCE_NAMESPACE | ||||
| @@ -193,36 +193,43 @@ public: | |||||
| int compareLexicographically (const String& other) const throw(); | int compareLexicographically (const String& other) const throw(); | ||||
| /** Tests whether the string begins with another string. | /** Tests whether the string begins with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool startsWith (const String& text) const throw(); | bool startsWith (const String& text) const throw(); | ||||
| /** Tests whether the string begins with a particular character. | /** Tests whether the string begins with a particular character. | ||||
| If the character is 0, this will always return false. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool startsWithChar (juce_wchar character) const throw(); | bool startsWithChar (juce_wchar character) const throw(); | ||||
| /** Tests whether the string begins with another string. | /** Tests whether the string begins with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-insensitive comparison. | Uses a case-insensitive comparison. | ||||
| */ | */ | ||||
| bool startsWithIgnoreCase (const String& text) const throw(); | bool startsWithIgnoreCase (const String& text) const throw(); | ||||
| /** Tests whether the string ends with another string. | /** Tests whether the string ends with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool endsWith (const String& text) const throw(); | bool endsWith (const String& text) const throw(); | ||||
| /** Tests whether the string ends with a particular character. | /** Tests whether the string ends with a particular character. | ||||
| If the character is 0, this will always return false. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool endsWithChar (juce_wchar character) const throw(); | bool endsWithChar (juce_wchar character) const throw(); | ||||
| /** Tests whether the string ends with another string. | /** Tests whether the string ends with another string. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-insensitive comparison. | Uses a case-insensitive comparison. | ||||
| */ | */ | ||||
| bool endsWithIgnoreCase (const String& text) const throw(); | bool endsWithIgnoreCase (const String& text) const throw(); | ||||
| /** Tests whether the string contains another substring. | /** Tests whether the string contains another substring. | ||||
| If the parameter is an empty string, this will always return true. | |||||
| Uses a case-sensitive comparison. | Uses a case-sensitive comparison. | ||||
| */ | */ | ||||
| bool contains (const String& text) const throw(); | bool contains (const String& text) const throw(); | ||||
| @@ -0,0 +1,207 @@ | |||||
| /* | |||||
| ============================================================================== | |||||
| This file is part of the JUCE library - "Jules' Utility Class Extensions" | |||||
| Copyright 2004-10 by Raw Material Software Ltd. | |||||
| ------------------------------------------------------------------------------ | |||||
| JUCE can be redistributed and/or modified under the terms of the GNU General | |||||
| Public License (Version 2), as published by the Free Software Foundation. | |||||
| A copy of the license is included in the JUCE distribution, or can be found | |||||
| online at www.gnu.org/licenses. | |||||
| JUCE 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. | |||||
| ------------------------------------------------------------------------------ | |||||
| To release a closed-source product which uses JUCE, commercial licenses are | |||||
| available: visit www.rawmaterialsoftware.com/juce for more information. | |||||
| ============================================================================== | |||||
| */ | |||||
| #include "../core/juce_StandardHeader.h" | |||||
| BEGIN_JUCE_NAMESPACE | |||||
| #include "juce_UnitTest.h" | |||||
| #include "../threads/juce_ScopedLock.h" | |||||
| //============================================================================== | |||||
| UnitTest::UnitTest (const String& name_) | |||||
| : name (name_), runner (0) | |||||
| { | |||||
| getAllTests().add (this); | |||||
| } | |||||
| UnitTest::~UnitTest() | |||||
| { | |||||
| getAllTests().removeValue (this); | |||||
| } | |||||
| Array<UnitTest*>& UnitTest::getAllTests() | |||||
| { | |||||
| static Array<UnitTest*> tests; | |||||
| return tests; | |||||
| } | |||||
| void UnitTest::performTest (UnitTestRunner* const runner_) | |||||
| { | |||||
| jassert (runner_ != 0); | |||||
| runner = runner_; | |||||
| runTest(); | |||||
| } | |||||
| void UnitTest::logMessage (const String& message) | |||||
| { | |||||
| runner->logMessage (message); | |||||
| } | |||||
| void UnitTest::beginTest (const String& testName) | |||||
| { | |||||
| runner->beginNewTest (this, testName); | |||||
| } | |||||
| void UnitTest::expect (const bool result, const String& failureMessage) | |||||
| { | |||||
| if (result) | |||||
| runner->addPass(); | |||||
| else | |||||
| runner->addFail (failureMessage); | |||||
| } | |||||
| //============================================================================== | |||||
| UnitTestRunner::UnitTestRunner() | |||||
| : currentTest (0), assertOnFailure (false) | |||||
| { | |||||
| } | |||||
| UnitTestRunner::~UnitTestRunner() | |||||
| { | |||||
| } | |||||
| void UnitTestRunner::resultsUpdated() | |||||
| { | |||||
| } | |||||
| void UnitTestRunner::runTests (const Array<UnitTest*>& tests, const bool assertOnFailure_) | |||||
| { | |||||
| results.clear(); | |||||
| assertOnFailure = assertOnFailure_; | |||||
| resultsUpdated(); | |||||
| for (int i = 0; i < tests.size(); ++i) | |||||
| { | |||||
| try | |||||
| { | |||||
| tests.getUnchecked(i)->performTest (this); | |||||
| } | |||||
| catch (...) | |||||
| { | |||||
| addFail ("An unhandled exception was thrown!"); | |||||
| } | |||||
| } | |||||
| endTest(); | |||||
| } | |||||
| void UnitTestRunner::runAllTests (const bool assertOnFailure_) | |||||
| { | |||||
| runTests (UnitTest::getAllTests(), assertOnFailure_); | |||||
| } | |||||
| void UnitTestRunner::logMessage (const String& message) | |||||
| { | |||||
| Logger::writeToLog (message); | |||||
| } | |||||
| void UnitTestRunner::beginNewTest (UnitTest* const test, const String& subCategory) | |||||
| { | |||||
| endTest(); | |||||
| currentTest = test; | |||||
| TestResult* const r = new TestResult(); | |||||
| r->unitTestName = test->getName(); | |||||
| r->subcategoryName = subCategory; | |||||
| r->passes = 0; | |||||
| r->failures = 0; | |||||
| results.add (r); | |||||
| logMessage ("-----------------------------------------------------------------"); | |||||
| logMessage ("Starting test: " + r->unitTestName + " / " + subCategory + "..."); | |||||
| resultsUpdated(); | |||||
| } | |||||
| void UnitTestRunner::endTest() | |||||
| { | |||||
| if (results.size() > 0) | |||||
| { | |||||
| TestResult* const r = results.getLast(); | |||||
| if (r->failures > 0) | |||||
| { | |||||
| String m ("FAILED!!"); | |||||
| m << r->failures << (r->failures == 1 ? "test" : "tests") | |||||
| << " failed, out of a total of " << (r->passes + r->failures); | |||||
| logMessage (String::empty); | |||||
| logMessage (m); | |||||
| logMessage (String::empty); | |||||
| } | |||||
| else | |||||
| { | |||||
| logMessage ("All tests completed successfully"); | |||||
| } | |||||
| } | |||||
| } | |||||
| void UnitTestRunner::addPass() | |||||
| { | |||||
| { | |||||
| const ScopedLock sl (results.getLock()); | |||||
| TestResult* const r = results.getLast(); | |||||
| jassert (r != 0); // You need to call UnitTest::beginTest() before performing any tests! | |||||
| r->passes++; | |||||
| String message ("Test "); | |||||
| message << (r->failures + r->passes) << " passed"; | |||||
| logMessage (message); | |||||
| } | |||||
| resultsUpdated(); | |||||
| } | |||||
| void UnitTestRunner::addFail (const String& failureMessage) | |||||
| { | |||||
| { | |||||
| const ScopedLock sl (results.getLock()); | |||||
| TestResult* const r = results.getLast(); | |||||
| jassert (r != 0); // You need to call UnitTest::beginTest() before performing any tests! | |||||
| r->failures++; | |||||
| String message ("!!! Test "); | |||||
| message << (r->failures + r->passes) << " failed"; | |||||
| if (failureMessage.isNotEmpty()) | |||||
| message << ": " << failureMessage; | |||||
| r->messages.add (message); | |||||
| logMessage (message); | |||||
| } | |||||
| resultsUpdated(); | |||||
| if (assertOnFailure) { jassertfalse } | |||||
| } | |||||
| END_JUCE_NAMESPACE | |||||
| @@ -0,0 +1,245 @@ | |||||
| /* | |||||
| ============================================================================== | |||||
| This file is part of the JUCE library - "Jules' Utility Class Extensions" | |||||
| Copyright 2004-10 by Raw Material Software Ltd. | |||||
| ------------------------------------------------------------------------------ | |||||
| JUCE can be redistributed and/or modified under the terms of the GNU General | |||||
| Public License (Version 2), as published by the Free Software Foundation. | |||||
| A copy of the license is included in the JUCE distribution, or can be found | |||||
| online at www.gnu.org/licenses. | |||||
| JUCE 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. | |||||
| ------------------------------------------------------------------------------ | |||||
| To release a closed-source product which uses JUCE, commercial licenses are | |||||
| available: visit www.rawmaterialsoftware.com/juce for more information. | |||||
| ============================================================================== | |||||
| */ | |||||
| #ifndef __JUCE_UNITTEST_JUCEHEADER__ | |||||
| #define __JUCE_UNITTEST_JUCEHEADER__ | |||||
| #include "../text/juce_StringArray.h" | |||||
| #include "../containers/juce_OwnedArray.h" | |||||
| class UnitTestRunner; | |||||
| //============================================================================== | |||||
| /** | |||||
| This is a base class for classes that perform a unit test. | |||||
| To write a test using this class, your code should look something like this: | |||||
| @code | |||||
| class MyTest : public UnitTest | |||||
| { | |||||
| public: | |||||
| MyTest() : UnitTest ("Foobar testing") {} | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("Part 1"); | |||||
| expect (myFoobar.doesSomething()); | |||||
| expect (myFoobar.doesSomethingElse()); | |||||
| beginTest ("Part 2"); | |||||
| expect (myOtherFoobar.doesSomething()); | |||||
| expect (myOtherFoobar.doesSomethingElse()); | |||||
| ...etc.. | |||||
| } | |||||
| }; | |||||
| // Creating a static instance will automatically add the instance to the array | |||||
| // returned by UnitTest::getAllTests(), so the test will be included when you call | |||||
| // UnitTestRunner::runAllTests() | |||||
| static MyTest test; | |||||
| @endcode | |||||
| To run a test, use the UnitTestRunner class. | |||||
| @see UnitTestRunner | |||||
| */ | |||||
| class UnitTest | |||||
| { | |||||
| public: | |||||
| //============================================================================== | |||||
| /** Creates a test with the given name. */ | |||||
| UnitTest (const String& name); | |||||
| /** Destructor. */ | |||||
| virtual ~UnitTest(); | |||||
| /** Returns the name of the test. */ | |||||
| const String getName() const throw() { return name; } | |||||
| /** Runs the test, using the specified UnitTestRunner. | |||||
| You shouldn't need to call this method directly - use | |||||
| UnitTestRunner::runTests() instead. | |||||
| */ | |||||
| void performTest (UnitTestRunner* runner); | |||||
| /** Returns the set of all UnitTest objects that currently exist. */ | |||||
| static Array<UnitTest*>& getAllTests(); | |||||
| //============================================================================== | |||||
| /** Implement this method in your subclass to actually run your tests. | |||||
| The content of your implementation should call beginTest() and expect() | |||||
| to perform the tests. | |||||
| */ | |||||
| virtual void runTest() = 0; | |||||
| //============================================================================== | |||||
| /** Tells the system that a new subsection of tests is beginning. | |||||
| This should be called from your runTest() method, and may be called | |||||
| as many times as you like, to demarcate different sets of tests. | |||||
| */ | |||||
| void beginTest (const String& testName); | |||||
| //============================================================================== | |||||
| /** Checks that the result of a test is true, and logs this result. | |||||
| In your runTest() method, you should call this method for each condition that | |||||
| you want to check, e.g. | |||||
| @code | |||||
| void runTest() | |||||
| { | |||||
| beginTest ("basic tests"); | |||||
| expect (x + y == 2); | |||||
| expect (getThing() == someThing); | |||||
| ...etc... | |||||
| } | |||||
| @endcode | |||||
| If testResult is true, a pass is logged; if it's false, a failure is logged. | |||||
| If the failure message is specified, it will be written to the log if the test fails. | |||||
| */ | |||||
| void expect (bool testResult, const String& failureMessage = String::empty); | |||||
| //============================================================================== | |||||
| /** Writes a message to the test log. | |||||
| This can only be called from within your runTest() method. | |||||
| */ | |||||
| void logMessage (const String& message); | |||||
| private: | |||||
| //============================================================================== | |||||
| const String name; | |||||
| UnitTestRunner* runner; | |||||
| UnitTest (const UnitTest&); | |||||
| UnitTest& operator= (const UnitTest&); | |||||
| }; | |||||
| //============================================================================== | |||||
| /** | |||||
| Runs a set of unit tests. | |||||
| You can instantiate one of these objects and use it to invoke tests on a set of | |||||
| UnitTest objects. | |||||
| By using a subclass of UnitTestRunner, you can intercept logging messages and | |||||
| perform custom behaviour when each test completes. | |||||
| @see UnitTest | |||||
| */ | |||||
| class UnitTestRunner | |||||
| { | |||||
| public: | |||||
| //============================================================================== | |||||
| /** */ | |||||
| UnitTestRunner(); | |||||
| /** Destructor. */ | |||||
| virtual ~UnitTestRunner(); | |||||
| /** Runs a set of tests. | |||||
| The tests are performed in order, and the results are logged. To run all the | |||||
| registered UnitTest objects that exist, use runAllTests(). | |||||
| */ | |||||
| void runTests (const Array<UnitTest*>& tests, bool assertOnFailure); | |||||
| /** Runs all the UnitTest objects that currently exist. | |||||
| This calls runTests() for all the objects listed in UnitTest::getAllTests(). | |||||
| */ | |||||
| void runAllTests (bool assertOnFailure); | |||||
| //============================================================================== | |||||
| /** Contains the results of a test. | |||||
| One of these objects is instantiated each time UnitTest::beginTest() is called, and | |||||
| it contains details of the number of subsequent UnitTest::expect() calls that are | |||||
| made. | |||||
| */ | |||||
| struct TestResult | |||||
| { | |||||
| /** The main name of this test (i.e. the name of the UnitTest object being run). */ | |||||
| String unitTestName; | |||||
| /** The name of the current subcategory (i.e. the name that was set when UnitTest::beginTest() was called). */ | |||||
| String subcategoryName; | |||||
| /** The number of UnitTest::expect() calls that succeeded. */ | |||||
| int passes; | |||||
| /** The number of UnitTest::expect() calls that failed. */ | |||||
| int failures; | |||||
| /** A list of messages describing the failed tests. */ | |||||
| StringArray messages; | |||||
| }; | |||||
| /** Returns the number of TestResult objects that have been performed. | |||||
| @see getResult | |||||
| */ | |||||
| int getNumResults() const throw(); | |||||
| /** Returns one of the TestResult objects that describes a test that has been run. | |||||
| @see getNumResults | |||||
| */ | |||||
| const TestResult* getResult (int index) const throw(); | |||||
| protected: | |||||
| /** Called when the list of results changes. | |||||
| You can override this to perform some sort of behaviour when results are added. | |||||
| */ | |||||
| virtual void resultsUpdated(); | |||||
| /** Logs a message about the current test progress. | |||||
| By default this just writes the message to the Logger class, but you could override | |||||
| this to do something else with the data. | |||||
| */ | |||||
| virtual void logMessage (const String& message); | |||||
| private: | |||||
| //============================================================================== | |||||
| friend class UnitTest; | |||||
| UnitTest* currentTest; | |||||
| String currentSubCategory; | |||||
| OwnedArray <TestResult, CriticalSection> results; | |||||
| bool assertOnFailure; | |||||
| void beginNewTest (UnitTest* test, const String& subCategory); | |||||
| void endTest(); | |||||
| void addPass(); | |||||
| void addFail (const String& failureMessage); | |||||
| UnitTestRunner (const UnitTestRunner&); | |||||
| UnitTestRunner& operator= (const UnitTestRunner&); | |||||
| }; | |||||
| #endif // __JUCE_UNITTEST_JUCEHEADER__ | |||||