- add method - (void) setBackgroundLayerWithColors:(NSArray *) colors startPoint:(CGPoint) startPoint angle:(CGFloat) angle

- add method - (void) setBackgroundLayerWithColors:(NSArray *) colors startPoint:(CGPoint) startPoint endPoint:(CGPoint) endPoint
This commit is contained in:
Giuseppe Nucifora 2018-03-21 19:56:43 +01:00
parent 2bc7881ba0
commit 07e9807316
152 changed files with 11539 additions and 8262 deletions

View File

@ -7,7 +7,7 @@
objects = {
/* Begin PBXBuildFile section */
3735765942C92DFF386546C9 /* Pods_PNGradientView_Example.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 2B6FC9D963B92695B921DF96 /* Pods_PNGradientView_Example.framework */; };
23C7E232205C2D45CAB997C5 /* Pods_PNGradientView_Tests.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 870C10D07996D64E37D43186 /* Pods_PNGradientView_Tests.framework */; };
6003F58E195388D20070C39A /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6003F58D195388D20070C39A /* Foundation.framework */; };
6003F590195388D20070C39A /* CoreGraphics.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6003F58F195388D20070C39A /* CoreGraphics.framework */; };
6003F592195388D20070C39A /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6003F591195388D20070C39A /* UIKit.framework */; };
@ -22,8 +22,8 @@
6003F5BA195388D20070C39A /* InfoPlist.strings in Resources */ = {isa = PBXBuildFile; fileRef = 6003F5B8195388D20070C39A /* InfoPlist.strings */; };
6003F5BC195388D20070C39A /* Tests.m in Sources */ = {isa = PBXBuildFile; fileRef = 6003F5BB195388D20070C39A /* Tests.m */; };
687207931C45207D0062BDEF /* QuartzCore.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 687207921C45207D0062BDEF /* QuartzCore.framework */; };
7B292E6333798F6CF1875617 /* Pods_PNGradientView_Tests.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 639D62CD5105D2FB1311CF6C /* Pods_PNGradientView_Tests.framework */; };
873B8AEB1B1F5CCA007FD442 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 873B8AEA1B1F5CCA007FD442 /* Main.storyboard */; };
DA435EAB7EBADF1E4514C851 /* Pods_PNGradientView_Example.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B3ECFB9B4E3A7249535F0CC2 /* Pods_PNGradientView_Example.framework */; };
/* End PBXBuildFile section */
/* Begin PBXContainerItemProxy section */
@ -37,9 +37,9 @@
/* End PBXContainerItemProxy section */
/* Begin PBXFileReference section */
2B6FC9D963B92695B921DF96 /* Pods_PNGradientView_Example.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_PNGradientView_Example.framework; sourceTree = BUILT_PRODUCTS_DIR; };
2FE460B6A0468ACFF2967E9D /* Pods-PNGradientView_Tests.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Tests.release.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests.release.xcconfig"; sourceTree = "<group>"; };
3805F31C8115CA8E6230D5F2 /* LICENSE */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; name = LICENSE; path = ../LICENSE; sourceTree = "<group>"; };
56C5384844A9C776A152F9A1 /* Pods-PNGradientView_Example.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Example.release.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example.release.xcconfig"; sourceTree = "<group>"; };
3C09E0D66235582FF2E562EB /* Pods-PNGradientView_Example.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Example.release.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example.release.xcconfig"; sourceTree = "<group>"; };
6003F58A195388D20070C39A /* PNGradientView_Example.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = PNGradientView_Example.app; sourceTree = BUILT_PRODUCTS_DIR; };
6003F58D195388D20070C39A /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = System/Library/Frameworks/Foundation.framework; sourceTree = SDKROOT; };
6003F58F195388D20070C39A /* CoreGraphics.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreGraphics.framework; path = System/Library/Frameworks/CoreGraphics.framework; sourceTree = SDKROOT; };
@ -59,14 +59,14 @@
6003F5B9195388D20070C39A /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/InfoPlist.strings; sourceTree = "<group>"; };
6003F5BB195388D20070C39A /* Tests.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = Tests.m; sourceTree = "<group>"; };
606FC2411953D9B200FFA9A0 /* Tests-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Tests-Prefix.pch"; sourceTree = "<group>"; };
639D62CD5105D2FB1311CF6C /* Pods_PNGradientView_Tests.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_PNGradientView_Tests.framework; sourceTree = BUILT_PRODUCTS_DIR; };
687207921C45207D0062BDEF /* QuartzCore.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = QuartzCore.framework; path = System/Library/Frameworks/QuartzCore.framework; sourceTree = SDKROOT; };
77BF0B8F84FC0C090AA5E4E4 /* Pods-PNGradientView_Tests.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Tests.debug.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests.debug.xcconfig"; sourceTree = "<group>"; };
870C10D07996D64E37D43186 /* Pods_PNGradientView_Tests.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_PNGradientView_Tests.framework; sourceTree = BUILT_PRODUCTS_DIR; };
873B8AEA1B1F5CCA007FD442 /* Main.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = Main.storyboard; sourceTree = "<group>"; };
A239C4D589940246CC5DC957 /* README.md */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = net.daringfireball.markdown; name = README.md; path = ../README.md; sourceTree = "<group>"; };
B5EC290C37FF2FD2B44F36D4 /* Pods-PNGradientView_Tests.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Tests.release.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests.release.xcconfig"; sourceTree = "<group>"; };
BB58A17ABCC08A9C0CBC1746 /* Pods-PNGradientView_Example.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Example.debug.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example.debug.xcconfig"; sourceTree = "<group>"; };
BDA9272291DEEAB307029A1B /* Pods-PNGradientView_Tests.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Tests.debug.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests.debug.xcconfig"; sourceTree = "<group>"; };
B3ECFB9B4E3A7249535F0CC2 /* Pods_PNGradientView_Example.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_PNGradientView_Example.framework; sourceTree = BUILT_PRODUCTS_DIR; };
C946A6D019B0F23F14758B0F /* PNGradientView.podspec */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; name = PNGradientView.podspec; path = ../PNGradientView.podspec; sourceTree = "<group>"; };
D81B6350FDFC86A4077FC757 /* Pods-PNGradientView_Example.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-PNGradientView_Example.debug.xcconfig"; path = "Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example.debug.xcconfig"; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
@ -78,7 +78,7 @@
6003F590195388D20070C39A /* CoreGraphics.framework in Frameworks */,
6003F592195388D20070C39A /* UIKit.framework in Frameworks */,
6003F58E195388D20070C39A /* Foundation.framework in Frameworks */,
3735765942C92DFF386546C9 /* Pods_PNGradientView_Example.framework in Frameworks */,
DA435EAB7EBADF1E4514C851 /* Pods_PNGradientView_Example.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@ -89,13 +89,24 @@
6003F5B0195388D20070C39A /* XCTest.framework in Frameworks */,
6003F5B2195388D20070C39A /* UIKit.framework in Frameworks */,
6003F5B1195388D20070C39A /* Foundation.framework in Frameworks */,
7B292E6333798F6CF1875617 /* Pods_PNGradientView_Tests.framework in Frameworks */,
23C7E232205C2D45CAB997C5 /* Pods_PNGradientView_Tests.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
393A880D672758E195917D2B /* Pods */ = {
isa = PBXGroup;
children = (
D81B6350FDFC86A4077FC757 /* Pods-PNGradientView_Example.debug.xcconfig */,
3C09E0D66235582FF2E562EB /* Pods-PNGradientView_Example.release.xcconfig */,
77BF0B8F84FC0C090AA5E4E4 /* Pods-PNGradientView_Tests.debug.xcconfig */,
2FE460B6A0468ACFF2967E9D /* Pods-PNGradientView_Tests.release.xcconfig */,
);
name = Pods;
sourceTree = "<group>";
};
6003F581195388D10070C39A = {
isa = PBXGroup;
children = (
@ -104,7 +115,7 @@
6003F5B5195388D20070C39A /* Tests */,
6003F58C195388D20070C39A /* Frameworks */,
6003F58B195388D20070C39A /* Products */,
87032DB5317E025A454AF1A7 /* Pods */,
393A880D672758E195917D2B /* Pods */,
);
sourceTree = "<group>";
};
@ -125,8 +136,8 @@
6003F58F195388D20070C39A /* CoreGraphics.framework */,
6003F591195388D20070C39A /* UIKit.framework */,
6003F5AF195388D20070C39A /* XCTest.framework */,
2B6FC9D963B92695B921DF96 /* Pods_PNGradientView_Example.framework */,
639D62CD5105D2FB1311CF6C /* Pods_PNGradientView_Tests.framework */,
B3ECFB9B4E3A7249535F0CC2 /* Pods_PNGradientView_Example.framework */,
870C10D07996D64E37D43186 /* Pods_PNGradientView_Tests.framework */,
);
name = Frameworks;
sourceTree = "<group>";
@ -186,17 +197,6 @@
name = "Podspec Metadata";
sourceTree = "<group>";
};
87032DB5317E025A454AF1A7 /* Pods */ = {
isa = PBXGroup;
children = (
BB58A17ABCC08A9C0CBC1746 /* Pods-PNGradientView_Example.debug.xcconfig */,
56C5384844A9C776A152F9A1 /* Pods-PNGradientView_Example.release.xcconfig */,
BDA9272291DEEAB307029A1B /* Pods-PNGradientView_Tests.debug.xcconfig */,
B5EC290C37FF2FD2B44F36D4 /* Pods-PNGradientView_Tests.release.xcconfig */,
);
name = Pods;
sourceTree = "<group>";
};
/* End PBXGroup section */
/* Begin PBXNativeTarget section */
@ -204,12 +204,12 @@
isa = PBXNativeTarget;
buildConfigurationList = 6003F5BF195388D20070C39A /* Build configuration list for PBXNativeTarget "PNGradientView_Example" */;
buildPhases = (
64FF49B673FD33CB7FB9A1C1 /* Check Pods Manifest.lock */,
D8E29BB91CF367F3F0F1DE5F /* [CP] Check Pods Manifest.lock */,
6003F586195388D20070C39A /* Sources */,
6003F587195388D20070C39A /* Frameworks */,
6003F588195388D20070C39A /* Resources */,
8BF5CEAC8AEA37C053AED557 /* Embed Pods Frameworks */,
958F4C0CBE5AF250F2A32885 /* Copy Pods Resources */,
C71329DBE47E914B7A6AA37A /* [CP] Embed Pods Frameworks */,
637A99967A45EB17DDFB54E8 /* [CP] Copy Pods Resources */,
);
buildRules = (
);
@ -224,12 +224,12 @@
isa = PBXNativeTarget;
buildConfigurationList = 6003F5C2195388D20070C39A /* Build configuration list for PBXNativeTarget "PNGradientView_Tests" */;
buildPhases = (
C805B4923787CE84EF9795B6 /* Check Pods Manifest.lock */,
3E089AA3F68B2357A17AA6E0 /* [CP] Check Pods Manifest.lock */,
6003F5AA195388D20070C39A /* Sources */,
6003F5AB195388D20070C39A /* Frameworks */,
6003F5AC195388D20070C39A /* Resources */,
B4F757BFEFE5CEA10E006C00 /* Embed Pods Frameworks */,
49E99BB4DFD223B91FC00094 /* Copy Pods Resources */,
A41F150D6282997619D85E30 /* [CP] Embed Pods Frameworks */,
31C1EAE0E15E3D6C77F136EF /* [CP] Copy Pods Resources */,
);
buildRules = (
);
@ -297,14 +297,14 @@
/* End PBXResourcesBuildPhase section */
/* Begin PBXShellScriptBuildPhase section */
49E99BB4DFD223B91FC00094 /* Copy Pods Resources */ = {
31C1EAE0E15E3D6C77F136EF /* [CP] Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
);
name = "Copy Pods Resources";
name = "[CP] Copy Pods Resources";
outputPaths = (
);
runOnlyForDeploymentPostprocessing = 0;
@ -312,44 +312,32 @@
shellScript = "\"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests-resources.sh\"\n";
showEnvVarsInLog = 0;
};
64FF49B673FD33CB7FB9A1C1 /* Check Pods Manifest.lock */ = {
3E089AA3F68B2357A17AA6E0 /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "Check Pods Manifest.lock";
name = "[CP] Check Pods Manifest.lock";
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-PNGradientView_Tests-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_ROOT}/../Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [[ $? != 0 ]] ; then\n cat << EOM\nerror: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\nEOM\n exit 1\nfi\n";
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
8BF5CEAC8AEA37C053AED557 /* Embed Pods Frameworks */ = {
637A99967A45EB17DDFB54E8 /* [CP] Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
);
name = "Embed Pods Frameworks";
outputPaths = (
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
958F4C0CBE5AF250F2A32885 /* Copy Pods Resources */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
);
name = "Copy Pods Resources";
name = "[CP] Copy Pods Resources";
outputPaths = (
);
runOnlyForDeploymentPostprocessing = 0;
@ -357,34 +345,70 @@
shellScript = "\"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example-resources.sh\"\n";
showEnvVarsInLog = 0;
};
B4F757BFEFE5CEA10E006C00 /* Embed Pods Frameworks */ = {
A41F150D6282997619D85E30 /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests-frameworks.sh",
"${BUILT_PRODUCTS_DIR}/PNGradientView/PNGradientView.framework",
"${BUILT_PRODUCTS_DIR}/RZDataBinding/RZDataBinding.framework",
"${BUILT_PRODUCTS_DIR}/Expecta/Expecta.framework",
"${BUILT_PRODUCTS_DIR}/Expecta+Snapshots/Expecta_Snapshots.framework",
"${BUILT_PRODUCTS_DIR}/FBSnapshotTestCase/FBSnapshotTestCase.framework",
"${BUILT_PRODUCTS_DIR}/Specta/Specta.framework",
);
name = "Embed Pods Frameworks";
name = "[CP] Embed Pods Frameworks";
outputPaths = (
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/PNGradientView.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/RZDataBinding.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/Expecta.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/Expecta_Snapshots.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/FBSnapshotTestCase.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/Specta.framework",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Tests/Pods-PNGradientView_Tests-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
C805B4923787CE84EF9795B6 /* Check Pods Manifest.lock */ = {
C71329DBE47E914B7A6AA37A /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example-frameworks.sh",
"${BUILT_PRODUCTS_DIR}/PNGradientView/PNGradientView.framework",
"${BUILT_PRODUCTS_DIR}/RZDataBinding/RZDataBinding.framework",
);
name = "Check Pods Manifest.lock";
name = "[CP] Embed Pods Frameworks";
outputPaths = (
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/PNGradientView.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/RZDataBinding.framework",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_ROOT}/../Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [[ $? != 0 ]] ; then\n cat << EOM\nerror: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\nEOM\n exit 1\nfi\n";
shellScript = "\"${SRCROOT}/Pods/Target Support Files/Pods-PNGradientView_Example/Pods-PNGradientView_Example-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
D8E29BB91CF367F3F0F1DE5F /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "[CP] Check Pods Manifest.lock";
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-PNGradientView_Example-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
/* End PBXShellScriptBuildPhase section */
@ -513,7 +537,7 @@
};
6003F5C0195388D20070C39A /* Debug */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = BB58A17ABCC08A9C0CBC1746 /* Pods-PNGradientView_Example.debug.xcconfig */;
baseConfigurationReference = D81B6350FDFC86A4077FC757 /* Pods-PNGradientView_Example.debug.xcconfig */;
buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
@ -529,7 +553,7 @@
};
6003F5C1195388D20070C39A /* Release */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = 56C5384844A9C776A152F9A1 /* Pods-PNGradientView_Example.release.xcconfig */;
baseConfigurationReference = 3C09E0D66235582FF2E562EB /* Pods-PNGradientView_Example.release.xcconfig */;
buildSettings = {
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage;
@ -545,7 +569,7 @@
};
6003F5C3195388D20070C39A /* Debug */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = BDA9272291DEEAB307029A1B /* Pods-PNGradientView_Tests.debug.xcconfig */;
baseConfigurationReference = 77BF0B8F84FC0C090AA5E4E4 /* Pods-PNGradientView_Tests.debug.xcconfig */;
buildSettings = {
BUNDLE_LOADER = "$(TEST_HOST)";
FRAMEWORK_SEARCH_PATHS = (
@ -569,7 +593,7 @@
};
6003F5C4195388D20070C39A /* Release */ = {
isa = XCBuildConfiguration;
baseConfigurationReference = B5EC290C37FF2FD2B44F36D4 /* Pods-PNGradientView_Tests.release.xcconfig */;
baseConfigurationReference = 2FE460B6A0468ACFF2967E9D /* Pods-PNGradientView_Tests.release.xcconfig */;
buildSettings = {
BUNDLE_LOADER = "$(TEST_HOST)";
FRAMEWORK_SEARCH_PATHS = (

View File

@ -19,8 +19,8 @@
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
[(PNGradientView*)self.view setBackgroundLayerWithColors:@[[UIColor greenColor],[UIColor whiteColor],[UIColor redColor]] startPoint:CGPointMake(0, 0)];
self.view.translatesAutoresizingMaskIntoConstraints = NO;
[(PNGradientView*)self.view setBackgroundLayerWithColors:@[[UIColor greenColor],[UIColor redColor]] startPoint:CGPointMake(0, 0) angle:0.5];
}
- (void)didReceiveMemoryWarning

View File

@ -1,18 +1,18 @@
PODS:
- Expecta (1.0.5)
- Expecta+Snapshots (3.0.0):
- Expecta (1.0.6)
- Expecta+Snapshots (3.1.1):
- Expecta (~> 1.0)
- FBSnapshotTestCase/Core (~> 2.0)
- Specta (~> 1.0)
- FBSnapshotTestCase (2.1.0):
- FBSnapshotTestCase/SwiftSupport (= 2.1.0)
- FBSnapshotTestCase/Core (2.1.0)
- FBSnapshotTestCase/SwiftSupport (2.1.0):
- FBSnapshotTestCase (2.1.4):
- FBSnapshotTestCase/SwiftSupport (= 2.1.4)
- FBSnapshotTestCase/Core (2.1.4)
- FBSnapshotTestCase/SwiftSupport (2.1.4):
- FBSnapshotTestCase/Core
- PNGradientView (0.1.5):
- PNGradientView (0.2.0):
- RZDataBinding
- RZDataBinding (2.0.3)
- Specta (1.0.5)
- RZDataBinding (2.1.0)
- Specta (1.0.7)
DEPENDENCIES:
- Expecta
@ -26,11 +26,13 @@ EXTERNAL SOURCES:
:path: ../
SPEC CHECKSUMS:
Expecta: e1c022fcd33910b6be89c291d2775b3fe27a89fe
Expecta+Snapshots: c343f410c7a6392f3e22e78f94c44b6c0749a516
FBSnapshotTestCase: 366ecd378511d7716c79991cd8067d1eed23578d
PNGradientView: e8b91f023a3037ba0442f76ddb1724a8c8635c64
RZDataBinding: 00d468ebe667f02c2bd5416f87b4b5d826188c4d
Specta: ac94d110b865115fe60ff2c6d7281053c6f8e8a2
Expecta: 3b6bd90a64b9a1dcb0b70aa0e10a7f8f631667d5
Expecta+Snapshots: dcff217eef506dabd6dfdc7864ea2da321fafbb8
FBSnapshotTestCase: 094f9f314decbabe373b87cc339bea235a63e07a
PNGradientView: 3c8f5b3ddbb7b957b8ecf0c72b5ceff2b36ee24f
RZDataBinding: 6981e90ddaae2f5e02028323b1043f8c31013109
Specta: 3e1bd89c3517421982dc4d1c992503e48bd5fe66
COCOAPODS: 0.39.0
PODFILE CHECKSUM: cd7860932a2fb17c979c3a4af42606b114244376
COCOAPODS: 1.4.0

View File

@ -1,3 +1,4 @@
#import <CoreGraphics/CoreGraphics.h>
#import <Expecta/Expecta.h>
#import "ExpectaObject+FBSnapshotTest.h"
@ -12,3 +13,6 @@ EXPMatcherInterface(recordSnapshot, (void));
EXPMatcherInterface(haveValidSnapshotNamed, (NSString *snapshot));
EXPMatcherInterface(recordSnapshotNamed, (NSString *snapshot));
EXPMatcherInterface(haveValidSnapshotNamedWithTolerance, (NSString *snapshot, CGFloat tolerance));
EXPMatcherInterface(haveValidSnapshotWithTolerance, (CGFloat tolerance));

View File

@ -18,14 +18,15 @@
return instance;
}
+ (BOOL)compareSnapshotOfViewOrLayer:(id)viewOrLayer snapshot:(NSString *)snapshot testCase:(id)testCase record:(BOOL)record referenceDirectory:(NSString *)referenceDirectory error:(NSError **)error
+ (BOOL)compareSnapshotOfViewOrLayer:(id)viewOrLayer snapshot:(NSString *)snapshot testCase:(id)testCase record:(BOOL)record referenceDirectory:(NSString *)referenceDirectory tolerance:(CGFloat)tolerance error:(NSError **)error
{
FBSnapshotTestController *snapshotController = [[FBSnapshotTestController alloc] initWithTestClass:[testCase class]];
snapshotController.recordMode = record;
snapshotController.referenceImagesDirectory = referenceDirectory;
snapshotController.usesDrawViewHierarchyInRect = [Expecta usesDrawViewHierarchyInRect];
snapshotController.deviceAgnostic = [Expecta isDeviceAgnostic];
if (! snapshotController.referenceImagesDirectory) {
[NSException raise:@"Missing value for referenceImagesDirectory" format:@"Call [[EXPExpectFBSnapshotTest instance] setReferenceImagesDirectory"];
}
@ -33,7 +34,7 @@
return [snapshotController compareSnapshotOfViewOrLayer:viewOrLayer
selector:NSSelectorFromString(snapshot)
identifier:nil
tolerance:0
tolerance:tolerance
error:error];
}
@ -79,18 +80,36 @@ void setGlobalReferenceImageDir(char *reference) {
NSString *testFileName = [NSString stringWithCString:self.fileName encoding:NSUTF8StringEncoding];
NSArray *pathComponents = [testFileName pathComponents];
for (NSString *folder in pathComponents) {
NSString *firstFolderFound = nil;
for (NSString *folder in pathComponents.reverseObjectEnumerator) {
if ([folder.lowercaseString rangeOfString:@"tests"].location != NSNotFound) {
NSArray *folderPathComponents = [pathComponents subarrayWithRange:NSMakeRange(0, [pathComponents indexOfObject:folder] + 1)];
return [NSString stringWithFormat:@"%@/ReferenceImages", [folderPathComponents componentsJoinedByString:@"/"]];
NSString *referenceImagesPath = [NSString stringWithFormat:@"%@/ReferenceImages", [folderPathComponents componentsJoinedByString:@"/"]];
if (!firstFolderFound) {
firstFolderFound = referenceImagesPath;
}
BOOL isDirectory = NO;
BOOL referenceDirExists = [[NSFileManager defaultManager] fileExistsAtPath:referenceImagesPath isDirectory:&isDirectory];
// if the folder exists, this is the reference dir for sure
if (referenceDirExists && isDirectory) {
return referenceImagesPath;
}
}
}
// if a reference folder wasn't found, we should create one
if (firstFolderFound) {
return firstFolderFound;
}
[NSException raise:@"Could not infer reference image folder" format:@"You should provide a reference dir using setGlobalReferenceImageDir(FB_REFERENCE_IMAGE_DIR);"];
return nil;
}
@end
@ -114,11 +133,11 @@ NSString *sanitizedTestPath(){
return name;
}
EXPMatcherImplementationBegin(haveValidSnapshot, (void)){
EXPMatcherImplementationBegin(haveValidSnapshotWithTolerance, (CGFloat tolerance)){
__block NSError *error = nil;
prerequisite(^BOOL{
return actual;
return actual != nil;
});
@ -132,7 +151,7 @@ EXPMatcherImplementationBegin(haveValidSnapshot, (void)){
actual = [actual view];
}
return [EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:name testCase:[self testCase] record:NO referenceDirectory:referenceImageDir error:&error];
return [EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:name testCase:[self testCase] record:NO referenceDirectory:referenceImageDir tolerance:tolerance error:&error];
});
failureMessageForTo(^NSString *{
@ -149,18 +168,22 @@ EXPMatcherImplementationBegin(haveValidSnapshot, (void)){
}
EXPMatcherImplementationEnd
EXPMatcherImplementationBegin(haveValidSnapshot, (void)) {
return self.haveValidSnapshotWithTolerance(0);
}
EXPMatcherImplementationEnd
EXPMatcherImplementationBegin(recordSnapshot, (void)) {
__block NSError *error = nil;
BOOL actualIsViewLayerOrViewController = ([actual isKindOfClass:UIView.class] || [actual isKindOfClass:CALayer.class] || [actual isKindOfClass:UIViewController.class]);
prerequisite(^BOOL{
return actual && actualIsViewLayerOrViewController;
return actual != nil && actualIsViewLayerOrViewController;
});
match(^BOOL{
NSString *referenceImageDir = [self _getDefaultReferenceDirectory];
// For view controllers do the viewWill/viewDid dance, then pass view through
if ([actual isKindOfClass:UIViewController.class]) {
@ -169,7 +192,7 @@ EXPMatcherImplementationBegin(recordSnapshot, (void)) {
actual = [actual view];
}
[EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:sanitizedTestPath() testCase:[self testCase] record:YES referenceDirectory:referenceImageDir error:&error];
[EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:sanitizedTestPath() testCase:[self testCase] record:YES referenceDirectory:referenceImageDir tolerance:0 error:&error];
return NO;
});
@ -198,12 +221,12 @@ EXPMatcherImplementationBegin(recordSnapshot, (void)) {
}
EXPMatcherImplementationEnd
EXPMatcherImplementationBegin(haveValidSnapshotNamed, (NSString *snapshot)){
EXPMatcherImplementationBegin(haveValidSnapshotNamedWithTolerance, (NSString *snapshot, CGFloat tolerance)) {
BOOL snapshotIsNil = (snapshot == nil);
__block NSError *error = nil;
prerequisite(^BOOL{
return actual && !(snapshotIsNil);
return actual != nil && !(snapshotIsNil);
});
match(^BOOL{
@ -214,7 +237,7 @@ EXPMatcherImplementationBegin(haveValidSnapshotNamed, (NSString *snapshot)){
actual = [actual view];
}
return [EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:snapshot testCase:[self testCase] record:NO referenceDirectory:referenceImageDir error:&error];
return [EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:snapshot testCase:[self testCase] record:NO referenceDirectory:referenceImageDir tolerance:tolerance error:&error];
});
failureMessageForTo(^NSString *{
@ -232,6 +255,11 @@ EXPMatcherImplementationBegin(haveValidSnapshotNamed, (NSString *snapshot)){
}
EXPMatcherImplementationEnd
EXPMatcherImplementationBegin(haveValidSnapshotNamed, (NSString *snapshot)) {
return self.haveValidSnapshotNamedWithTolerance(snapshot, 0);
}
EXPMatcherImplementationEnd
EXPMatcherImplementationBegin(recordSnapshotNamed, (NSString *snapshot)) {
BOOL snapshotExists = (snapshot != nil);
BOOL actualIsViewLayerOrViewController = ([actual isKindOfClass:UIView.class] || [actual isKindOfClass:CALayer.class] || [actual isKindOfClass:UIViewController.class]);
@ -239,12 +267,11 @@ EXPMatcherImplementationBegin(recordSnapshotNamed, (NSString *snapshot)) {
id actualRef = actual;
prerequisite(^BOOL{
return actualRef && snapshotExists && actualIsViewLayerOrViewController;
return actualRef != nil && snapshotExists && actualIsViewLayerOrViewController;
});
match(^BOOL{
NSString *referenceImageDir = [self _getDefaultReferenceDirectory];
// For view controllers do the viewWill/viewDid dance, then pass view through
if ([actual isKindOfClass:UIViewController.class]) {
[actual beginAppearanceTransition:YES animated:NO];
@ -252,7 +279,7 @@ EXPMatcherImplementationBegin(recordSnapshotNamed, (NSString *snapshot)) {
actual = [actual view];
}
[EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:snapshot testCase:[self testCase] record:YES referenceDirectory:referenceImageDir error:&error];
[EXPExpectFBSnapshotTest compareSnapshotOfViewOrLayer:actual snapshot:snapshot testCase:[self testCase] record:YES referenceDirectory:referenceImageDir tolerance:0 error:&error];
return NO;
});

View File

@ -14,4 +14,8 @@
+ (BOOL)usesDrawViewHierarchyInRect;
+ (void)setDeviceAgnostic:(BOOL)deviceAgnostic;
+ (BOOL)isDeviceAgnostic;
@end

View File

@ -22,4 +22,15 @@ static NSString const *kUsesDrawViewHierarchyInRectKey = @"ExpectaObject+FBSnaps
return usesDrawViewHierarchyInRect.boolValue;
}
+ (void)setDeviceAgnostic:(BOOL)deviceAgnostic
{
objc_setAssociatedObject(self, @selector(isDeviceAgnostic), @(deviceAgnostic), OBJC_ASSOCIATION_ASSIGN);
}
+ (BOOL)isDeviceAgnostic
{
NSNumber *isDeviceAgnostic = objc_getAssociatedObject(self, @selector(isDeviceAgnostic));
return isDeviceAgnostic.boolValue;
}
@end

View File

@ -3,7 +3,7 @@ Expecta Matchers for FBSnapshotTestCase
[Expecta](https://github.com/specta/expecta) matchers for [ios-snapshot-test-case](https://github.com/facebook/ios-snapshot-test-case).
[![Build Status](https://travis-ci.org/dblock/ios-snapshot-test-case-expecta.png)](https://travis-ci.org/dblock/ios-snapshot-test-case-expecta)
[![Build Status](https://travis-ci.org/dblock/ios-snapshot-test-case-expecta.svg)](https://travis-ci.org/dblock/ios-snapshot-test-case-expecta)
### Usage
@ -63,6 +63,15 @@ describe(@"test name derived matching", ^{
SpecEnd
```
### Approximation support
If for some reason you want to specify a tolerance for your test, you can use either named or unnamed matchers, where the `tolerance` parameter is a `CGFloat` in the interval `[0, 1]` and it represents the minimum ratio of unmatched points by the total number of points in your snapshot. In the example below, a tolerance of `0.01` means our `view` could be up to `1%` different from the reference image.
``` Objective-C
expect(view).to.haveValidSnapshotWithTolerance(0.01);
expect(view).to.haveValidSnapshotNamedWithTolerance(@"unique snapshot name", 0.01);
```
### Sane defaults
`EXPMatchers+FBSnapshotTest` will automatically figure out the tests folder, and [add a reference image](https://github.com/dblock/ios-snapshot-test-case-expecta/blob/master/EXPMatchers%2BFBSnapshotTest.m#L84-L85) directory, if you'd like to override this, you should include a `beforeAll` block setting the `setGlobalReferenceImageDir` in each file containing tests.

View File

@ -9,9 +9,9 @@
#ifndef Expecta_EXPDefines_h
#define Expecta_EXPDefines_h
typedef void (^EXPBasicBlock)();
typedef id (^EXPIdBlock)();
typedef BOOL (^EXPBoolBlock)();
typedef NSString *(^EXPStringBlock)();
typedef void (^EXPBasicBlock)(void);
typedef id (^EXPIdBlock)(void);
typedef BOOL (^EXPBoolBlock)(void);
typedef NSString *(^EXPStringBlock)(void);
#endif

View File

@ -4,12 +4,16 @@
EXPMatcherImplementationBegin(respondTo, (SEL expected)) {
BOOL actualIsNil = (actual == nil);
BOOL expectedIsNull = (expected == NULL);
prerequisite (^BOOL {
return !(actualIsNil || expectedIsNull);
});
match(^BOOL {
if ([actual respondsToSelector:@selector(instancesRespondToSelector:)] &&
[actual instancesRespondToSelector:expected]) {
return YES;
}
return [actual respondsToSelector:expected];
});

View File

@ -1,13 +1,8 @@
#Expecta
[![Build Status](http://img.shields.io/travis/specta/expecta/master.svg?style=flat)](https://travis-ci.org/specta/expecta)
[![Pod Version](http://img.shields.io/cocoapods/v/Expecta.svg?style=flat)](http://cocoadocs.org/docsets/Expecta/)
[![Pod Platform](http://img.shields.io/cocoapods/p/Expecta.svg?style=flat)](http://cocoadocs.org/docsets/Expecta/)
[![Pod License](http://img.shields.io/cocoapods/l/Expecta.svg?style=flat)](https://www.apache.org/licenses/LICENSE-2.0.html)
# Expecta [![Build Status](http://img.shields.io/travis/specta/expecta/master.svg?style=flat)](https://travis-ci.org/specta/expecta) [![Pod Version](http://img.shields.io/cocoapods/v/Expecta.svg?style=flat)](http://cocoadocs.org/docsets/Expecta/)
A matcher framework for Objective-C and Cocoa.
## Introduction
## FEATURES
The main advantage of using Expecta over other matcher frameworks is that you do not have to specify the data types. Also, the syntax of Expecta matchers is much more readable and does not suffer from parenthesitis.
@ -18,63 +13,10 @@ expect([bar isBar]).to.equal(YES);
expect(baz).to.equal(3.14159);
```
Expecta is framework-agnostic: it works well with XCTest and XCTest-compatible test frameworks such as [Specta](http://github.com/petejkim/specta/).
Expecta is framework-agnostic: it works well with XCTest and XCTest-compatible test frameworks such as [Specta](http://github.com/petejkim/specta/), or [Kiwi](https://github.com/kiwi-bdd/Kiwi/).
## Installation
You can setup Expecta using [Carthage](https://github.com/Carthage/Carthage), [CocoaPods](http://github.com/CocoaPods/CocoaPods) or [completely manually](#setting-up-manually).
### Carthage
1. Add Expecta to your project's `Cartfile.private`:
```ruby
github "specta/expecta" "master"
```
2. Run `carthage update` in your project directory.
3. Drag the appropriate **Expecta.framework** for your platform (located in `Carthage/Build/`) into your applications Xcode project, and add it to your test target(s).
### CocoaPods
1. Add Expecta to your project's `Podfile`:
```ruby
target :MyApp do
# Your app's dependencies
end
target :MyAppTests do
pod 'Expecta', '~> 1.0.0'
end
```
2. Run `pod update` or `pod install` in your project directory.
### Setting Up Manually
1. Clone Expecta from Github.
2. Run `rake` in your project directory to build the frameworks and libraries.
3. Add a Cocoa or Cocoa Touch Unit Testing Bundle target to your Xcode project if you don't already have one.
4. For **OS X projects**, copy and add `Expecta.framework` in the `Products/osx` folder to your project's test target.
For **iOS projects**, copy and add `Expecta.framework` in the `Products/ios` folder to your project's test target.
You can also use `libExpecta.a` if you prefer to link Expecta as a static library — iOS 7.x and below require this.
6. Add `-ObjC` and `-all_load` to the **Other Linker Flags** build setting for the test target in your Xcode project.
7. You can now use Expecta in your test classes by adding the following import:
```objective-c
@import Expecta; // If you're using Expecta.framework
// OR
#import <Expecta/Expecta.h> // If you're using the static library, or the framework
```
## Built-in Matchers
## MATCHERS
> `expect(x).to.equal(y);` compares objects or primitives x and y and passes if they are identical (==) or equivalent isEqual:).
@ -132,13 +74,13 @@ You can setup Expecta using [Carthage](https://github.com/Carthage/Carthage), [C
> `expect(x).to.match(y);` passes if an instance of NSString `x` matches regular expression (given as NSString) `y` one or more times.
## Inverting Matchers
### Inverting Matchers
Every matcher's criteria can be inverted by prepending `.notTo` or `.toNot`:
>`expect(x).notTo.equal(y);` compares objects or primitives x and y and passes if they are *not* equivalent.
## Asynchronous Testing
### Asynchronous Testing
Every matcher can be made to perform asynchronous testing by prepending `.will`, `.willNot` or `after(...)`:
@ -172,14 +114,14 @@ describe(@"Foo", ^{
});
```
## Forced Failing
### Forced Failing
You can fail a test by using the `failure` attribute. This can be used to test branching.
> `failure(@"This should not happen");` outright fails a test.
## Writing New Matchers
### WRITING NEW MATCHERS
Writing a new matcher is easy with special macros provided by Expecta. Take a look at how `.beKindOf()` matcher is defined:
@ -246,7 +188,7 @@ EXPMatcherImplementationBegin(beKindOf, (Class expected)) {
EXPMatcherImplementationEnd
```
## Dynamic Predicate Matchers
## DYNAMIC PREDICATE MATCHERS
It is possible to add predicate matchers by simply defining the matcher interface, with the matcher implementation being handled at runtime by delegating to the predicate method on your object.
@ -282,6 +224,68 @@ You can now write your assertion as follows:
expect(lightSwitch).isTurnedOn();
```
## INSTALLATION
You can setup Expecta using [CocoaPods](http://github.com/CocoaPods/CocoaPods), [Carthage](https://github.com/Carthage/Carthage) or [completely manually](#setting-up-manually).
### CocoaPods
1. Add Expecta to your project's `Podfile`:
```ruby
target :MyApp do
# your app dependencies
target :MyAppTests do
inherit! search_paths
pod 'Expecta', '~> 1.0'
end
end
```
### Carthage
1. Add Expecta to your project's `Cartfile.private`:
```ruby
github "specta/expecta" "master"
```
2. Run `carthage update` in your project directory.
3. Drag the appropriate **Expecta.framework** for your platform (located in `Carthage/Build/`) into your applications Xcode project, and add it to your test target(s).
2. Run `pod update` or `pod install` in your project directory.
### Setting Up Manually
1. Clone Expecta from Github.
2. Run `rake` in your project directory to build the frameworks and libraries.
3. Add a Cocoa or Cocoa Touch Unit Testing Bundle target to your Xcode project if you don't already have one.
4. For **OS X projects**, copy and add `Expecta.framework` in the `Products/osx` folder to your project's test target.
For **iOS projects**, copy and add `Expecta.framework` in the `Products/ios` folder to your project's test target.
You can also use `libExpecta.a` if you prefer to link Expecta as a static library — iOS 7.x and below require this.
6. Add `-ObjC` and `-all_load` to the **Other Linker Flags** build setting for the test target in your Xcode project.
7. You can now use Expecta in your test classes by adding the following import:
```objective-c
@import Expecta; // If you're using Expecta.framework
// OR
#import <Expecta/Expecta.h> // If you're using the static library, or the framework
```
## STATUS
Expecta, and Specta are considered done projects, there are no plans for _active_ development on the project at the moment aside from ensuring future Xcode compatability.
Therefore it is a stable dependency, but will not be moving into the Swift world. If you are looking for that, we recommend you consider [Quick](https://github.com/quick/quick) and [Nimble](https://github.com/quick/nimble).
## Contribution Guidelines
* Please use only spaces and indent 2 spaces at a time.
@ -290,4 +294,4 @@ expect(lightSwitch).isTurnedOn();
## License
Copyright (c) 2012-2015 [Specta Team](https://github.com/specta?tab=members). This software is licensed under the [MIT License](http://github.com/specta/specta/raw/master/LICENSE).
Copyright (c) 2012-2016 [Specta Team](https://github.com/specta?tab=members). This software is licensed under the [MIT License](http://github.com/specta/specta/raw/master/LICENSE).

View File

@ -1,15 +0,0 @@
framework module FBSnapshotTestCase {
umbrella header "FBSnapshotTestCase.h"
export *
module * { export * }
header "FBSnapshotTestCase.h"
header "FBSnapshotTestCasePlatform.h"
header "FBSnapshotTestController.h"
private header "UIImage+Compare.h"
private header "UIImage+Diff.h"
private header "UIImage+Snapshot.h"
}

View File

@ -62,43 +62,9 @@
#define FBSnapshotVerifyViewOrLayerWithOptions(what__, viewOrLayer__, identifier__, suffixes__, tolerance__) \
{ \
NSString *referenceImageDirectory = [self getReferenceImageDirectoryWithDefault:(@ FB_REFERENCE_IMAGE_DIR)]; \
XCTAssertNotNil(referenceImageDirectory, @"Missing value for referenceImagesDirectory - Set FB_REFERENCE_IMAGE_DIR as Environment variable in your scheme.");\
XCTAssertTrue((suffixes__.count > 0), @"Suffixes set cannot be empty %@", suffixes__); \
\
BOOL testSuccess__ = NO; \
NSError *error__ = nil; \
NSMutableArray *errors__ = [NSMutableArray array]; \
\
if (self.recordMode) { \
\
NSString *referenceImagesDirectory__ = [NSString stringWithFormat:@"%@%@", referenceImageDirectory, suffixes__.firstObject]; \
BOOL referenceImageSaved__ = [self compareSnapshotOf ## what__ :(viewOrLayer__) referenceImagesDirectory:referenceImagesDirectory__ identifier:(identifier__) tolerance:(tolerance__) error:&error__]; \
if (!referenceImageSaved__) { \
[errors__ addObject:error__]; \
} \
} else { \
\
for (NSString *suffix__ in suffixes__) { \
NSString *referenceImagesDirectory__ = [NSString stringWithFormat:@"%@%@", referenceImageDirectory, suffix__]; \
BOOL referenceImageAvailable = [self referenceImageRecordedInDirectory:referenceImagesDirectory__ identifier:(identifier__) error:&error__]; \
\
if (referenceImageAvailable) { \
BOOL comparisonSuccess__ = [self compareSnapshotOf ## what__ :(viewOrLayer__) referenceImagesDirectory:referenceImagesDirectory__ identifier:(identifier__) tolerance:(tolerance__) error:&error__]; \
[errors__ removeAllObjects]; \
if (comparisonSuccess__) { \
testSuccess__ = YES; \
break; \
} else { \
[errors__ addObject:error__]; \
} \
} else { \
[errors__ addObject:error__]; \
} \
} \
} \
XCTAssertTrue(testSuccess__, @"Snapshot comparison failed: %@", errors__.firstObject); \
XCTAssertFalse(self.recordMode, @"Test ran in record mode. Reference image is now saved. Disable record mode to perform an actual snapshot comparison!"); \
NSString *errorDescription = [self snapshotVerifyViewOrLayer:viewOrLayer__ identifier:identifier__ suffixes:suffixes__ tolerance:tolerance__]; \
BOOL noErrors = (errorDescription == nil); \
XCTAssertTrue(noErrors, @"%@", errorDescription); \
}
@ -148,6 +114,19 @@
- (void)setUp NS_REQUIRES_SUPER;
- (void)tearDown NS_REQUIRES_SUPER;
/**
Performs the comparison or records a snapshot of the layer if recordMode is YES.
@param viewOrLayer The UIView or CALayer to snapshot
@param identifier An optional identifier, used if there are multiple snapshot tests in a given -test method.
@param suffixes An NSOrderedSet of strings for the different suffixes
@param tolerance The percentage difference to still count as identical - 0 mean pixel perfect, 1 means I don't care
@returns nil if the comparison (or saving of the reference image) succeeded. Otherwise it contains an error description.
*/
- (NSString *)snapshotVerifyViewOrLayer:(id)viewOrLayer
identifier:(NSString *)identifier
suffixes:(NSOrderedSet *)suffixes
tolerance:(CGFloat)tolerance;
/**
Performs the comparison or records a snapshot of the layer if recordMode is YES.
@param layer The Layer to snapshot

View File

@ -65,6 +65,62 @@
#pragma mark - Public API
- (NSString *)snapshotVerifyViewOrLayer:(id)viewOrLayer
identifier:(NSString *)identifier
suffixes:(NSOrderedSet *)suffixes
tolerance:(CGFloat)tolerance
{
if (nil == viewOrLayer) {
return @"Object to be snapshotted must not be nil";
}
NSString *referenceImageDirectory = [self getReferenceImageDirectoryWithDefault:(@ FB_REFERENCE_IMAGE_DIR)];
if (referenceImageDirectory == nil) {
return @"Missing value for referenceImagesDirectory - Set FB_REFERENCE_IMAGE_DIR as Environment variable in your scheme.";
}
if (suffixes.count == 0) {
return [NSString stringWithFormat:@"Suffixes set cannot be empty %@", suffixes];
}
BOOL testSuccess = NO;
NSError *error = nil;
NSMutableArray *errors = [NSMutableArray array];
if (self.recordMode) {
NSString *referenceImagesDirectory = [NSString stringWithFormat:@"%@%@", referenceImageDirectory, suffixes.firstObject];
BOOL referenceImageSaved = [self _compareSnapshotOfViewOrLayer:viewOrLayer referenceImagesDirectory:referenceImagesDirectory identifier:(identifier) tolerance:tolerance error:&error];
if (!referenceImageSaved) {
[errors addObject:error];
}
} else {
for (NSString *suffix in suffixes) {
NSString *referenceImagesDirectory = [NSString stringWithFormat:@"%@%@", referenceImageDirectory, suffix];
BOOL referenceImageAvailable = [self referenceImageRecordedInDirectory:referenceImagesDirectory identifier:(identifier) error:&error];
if (referenceImageAvailable) {
BOOL comparisonSuccess = [self _compareSnapshotOfViewOrLayer:viewOrLayer referenceImagesDirectory:referenceImagesDirectory identifier:identifier tolerance:tolerance error:&error];
[errors removeAllObjects];
if (comparisonSuccess) {
testSuccess = YES;
break;
} else {
[errors addObject:error];
}
} else {
[errors addObject:error];
}
}
}
if (!testSuccess) {
return [NSString stringWithFormat:@"Snapshot comparison failed: %@", errors.firstObject];
}
if (self.recordMode) {
return @"Test ran in record mode. Reference image is now saved. Disable record mode to perform an actual snapshot comparison!";
}
return nil;
}
- (BOOL)compareSnapshotOfLayer:(CALayer *)layer
referenceImagesDirectory:(NSString *)referenceImagesDirectory
identifier:(NSString *)identifier

View File

@ -8,6 +8,64 @@
*
*/
#if swift(>=3)
public extension FBSnapshotTestCase {
public func FBSnapshotVerifyView(_ view: UIView, identifier: String = "", suffixes: NSOrderedSet = FBSnapshotTestCaseDefaultSuffixes(), tolerance: CGFloat = 0, file: StaticString = #file, line: UInt = #line) {
FBSnapshotVerifyViewOrLayer(view, identifier: identifier, suffixes: suffixes, tolerance: tolerance, file: file, line: line)
}
public func FBSnapshotVerifyLayer(_ layer: CALayer, identifier: String = "", suffixes: NSOrderedSet = FBSnapshotTestCaseDefaultSuffixes(), tolerance: CGFloat = 0, file: StaticString = #file, line: UInt = #line) {
FBSnapshotVerifyViewOrLayer(layer, identifier: identifier, suffixes: suffixes, tolerance: tolerance, file: file, line: line)
}
private func FBSnapshotVerifyViewOrLayer(_ viewOrLayer: AnyObject, identifier: String = "", suffixes: NSOrderedSet = FBSnapshotTestCaseDefaultSuffixes(), tolerance: CGFloat = 0, file: StaticString = #file, line: UInt = #line) {
let envReferenceImageDirectory = self.getReferenceImageDirectory(withDefault: FB_REFERENCE_IMAGE_DIR)
var error: NSError?
var comparisonSuccess = false
if let envReferenceImageDirectory = envReferenceImageDirectory {
for suffix in suffixes {
let referenceImagesDirectory = "\(envReferenceImageDirectory)\(suffix)"
if viewOrLayer.isKind(of: UIView.self) {
do {
try compareSnapshot(of: viewOrLayer as! UIView, referenceImagesDirectory: referenceImagesDirectory, identifier: identifier, tolerance: tolerance)
comparisonSuccess = true
} catch let error1 as NSError {
error = error1
comparisonSuccess = false
}
} else if viewOrLayer.isKind(of: CALayer.self) {
do {
try compareSnapshot(of: viewOrLayer as! CALayer, referenceImagesDirectory: referenceImagesDirectory, identifier: identifier, tolerance: tolerance)
comparisonSuccess = true
} catch let error1 as NSError {
error = error1
comparisonSuccess = false
}
} else {
assertionFailure("Only UIView and CALayer classes can be snapshotted")
}
assert(recordMode == false, message: "Test ran in record mode. Reference image is now saved. Disable record mode to perform an actual snapshot comparison!", file: file, line: line)
if comparisonSuccess || recordMode {
break
}
assert(comparisonSuccess, message: "Snapshot comparison failed: \(error)", file: file, line: line)
}
} else {
XCTFail("Missing value for referenceImagesDirectory - Set FB_REFERENCE_IMAGE_DIR as Environment variable in your scheme.")
}
}
func assert(_ assertion: Bool, message: String, file: StaticString, line: UInt) {
if !assertion {
XCTFail(message, file: file, line: line)
}
}
}
#else
public extension FBSnapshotTestCase {
public func FBSnapshotVerifyView(view: UIView, identifier: String = "", suffixes: NSOrderedSet = FBSnapshotTestCaseDefaultSuffixes(), tolerance: CGFloat = 0, file: StaticString = #file, line: UInt = #line) {
FBSnapshotVerifyViewOrLayer(view, identifier: identifier, suffixes: suffixes, tolerance: tolerance, file: file, line: line)
@ -64,3 +122,4 @@ public extension FBSnapshotTestCase {
}
}
}
#endif

View File

@ -1 +0,0 @@
../../../Expecta+Snapshots/EXPMatchers+FBSnapshotTest.h

View File

@ -1 +0,0 @@
../../../Expecta+Snapshots/ExpectaObject+FBSnapshotTest.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPBlockDefinedMatcher.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPDefines.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPDoubleTuple.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPExpect.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPFloatTuple.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPMatcher.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatcherHelpers.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beCloseTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beFalsy.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beGreaterThan.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beGreaterThanOrEqualTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beIdenticalTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beInTheRangeOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beInstanceOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beKindOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beLessThan.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beLessThanOrEqualTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beNil.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beSubclassOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beSupersetOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beTruthy.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+beginWith.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+conformTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+contain.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+endWith.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+equal.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+haveCountOf.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+match.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+postNotification.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+raise.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+raiseWithReason.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers+respondTo.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Matchers/EXPMatchers.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/EXPUnsupportedObject.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/Expecta.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/ExpectaObject.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/ExpectaSupport.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/NSObject+Expecta.h

View File

@ -1 +0,0 @@
../../../Expecta/Expecta/NSValue+Expecta.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/FBSnapshotTestCase.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/FBSnapshotTestCasePlatform.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/FBSnapshotTestController.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/Categories/UIApplication+StrictKeyWindow.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/Categories/UIImage+Compare.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/Categories/UIImage+Diff.h

View File

@ -1 +0,0 @@
../../../FBSnapshotTestCase/FBSnapshotTestCase/Categories/UIImage+Snapshot.h

View File

@ -1 +0,0 @@
../../../../../Pod/Classes/PNGradientView.h

View File

@ -1 +0,0 @@
../../../RZDataBinding/RZDataBinding/NSObject+RZDataBinding.h

View File

@ -1 +0,0 @@
../../../RZDataBinding/RZDataBinding/RZDBCoalesce.h

View File

@ -1 +0,0 @@
../../../RZDataBinding/RZDataBinding/RZDBMacros.h

View File

@ -1 +0,0 @@
../../../RZDataBinding/RZDataBinding/RZDBTransforms.h

View File

@ -1 +0,0 @@
../../../RZDataBinding/RZDataBinding/RZDataBinding.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTCallSite.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTCompiledExample.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTExample.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTExampleGroup.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTExcludeGlobalBeforeAfterEach.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTGlobalBeforeAfterEach.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTSharedExampleGroups.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTSpec.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SPTTestSuite.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/Specta.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SpectaDSL.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SpectaTypes.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/SpectaUtility.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/XCTest+Private.h

View File

@ -1 +0,0 @@
../../../Specta/Specta/Specta/XCTestCase+Specta.h

View File

@ -1,6 +1,6 @@
{
"name": "PNGradientView",
"version": "0.1.5",
"version": "0.2.0",
"summary": "PNGradientView is a UIView subclassing with gradient support",
"homepage": "https://github.com/giuseppenucifora/PNGradientView",
"license": "MIT",
@ -9,18 +9,13 @@
},
"source": {
"git": "https://github.com/giuseppenucifora/PNGradientView.git",
"tag": "0.1.5"
"tag": "0.2.0"
},
"platforms": {
"ios": "7.0"
},
"requires_arc": true,
"source_files": "Pod/Classes/**/*",
"resource_bundles": {
"PNGradientView": [
"Pod/Assets/*.png"
]
},
"frameworks": "QuartzCore",
"dependencies": {
"RZDataBinding": [

View File

@ -1,18 +1,18 @@
PODS:
- Expecta (1.0.5)
- Expecta+Snapshots (3.0.0):
- Expecta (1.0.6)
- Expecta+Snapshots (3.1.1):
- Expecta (~> 1.0)
- FBSnapshotTestCase/Core (~> 2.0)
- Specta (~> 1.0)
- FBSnapshotTestCase (2.1.0):
- FBSnapshotTestCase/SwiftSupport (= 2.1.0)
- FBSnapshotTestCase/Core (2.1.0)
- FBSnapshotTestCase/SwiftSupport (2.1.0):
- FBSnapshotTestCase (2.1.4):
- FBSnapshotTestCase/SwiftSupport (= 2.1.4)
- FBSnapshotTestCase/Core (2.1.4)
- FBSnapshotTestCase/SwiftSupport (2.1.4):
- FBSnapshotTestCase/Core
- PNGradientView (0.1.5):
- PNGradientView (0.2.0):
- RZDataBinding
- RZDataBinding (2.0.3)
- Specta (1.0.5)
- RZDataBinding (2.1.0)
- Specta (1.0.7)
DEPENDENCIES:
- Expecta
@ -26,11 +26,13 @@ EXTERNAL SOURCES:
:path: ../
SPEC CHECKSUMS:
Expecta: e1c022fcd33910b6be89c291d2775b3fe27a89fe
Expecta+Snapshots: c343f410c7a6392f3e22e78f94c44b6c0749a516
FBSnapshotTestCase: 366ecd378511d7716c79991cd8067d1eed23578d
PNGradientView: e8b91f023a3037ba0442f76ddb1724a8c8635c64
RZDataBinding: 00d468ebe667f02c2bd5416f87b4b5d826188c4d
Specta: ac94d110b865115fe60ff2c6d7281053c6f8e8a2
Expecta: 3b6bd90a64b9a1dcb0b70aa0e10a7f8f631667d5
Expecta+Snapshots: dcff217eef506dabd6dfdc7864ea2da321fafbb8
FBSnapshotTestCase: 094f9f314decbabe373b87cc339bea235a63e07a
PNGradientView: 3c8f5b3ddbb7b957b8ecf0c72b5ceff2b36ee24f
RZDataBinding: 6981e90ddaae2f5e02028323b1043f8c31013109
Specta: 3e1bd89c3517421982dc4d1c992503e48bd5fe66
COCOAPODS: 0.39.0
PODFILE CHECKSUM: cd7860932a2fb17c979c3a4af42606b114244376
COCOAPODS: 1.4.0

File diff suppressed because it is too large Load Diff

View File

@ -49,8 +49,17 @@ static void* const kRZDBSwizzledDeallocKey = (void *)&kRZDBSwizzledDeallocKey;
static void* const kRZDBKVOContext = (void *)&kRZDBKVOContext;
static void* const kRZDBRegisteredObserversKey = (void *)&kRZDBRegisteredObserversKey;
static void* const kRZDBDependentObserversKey = (void *)&kRZDBDependentObserversKey;
#define RZDBNotNull(obj) ((obj) != nil && ![(obj) isEqual:[NSNull null]])
#define rz_registeredObservers(obj) objc_getAssociatedObject(obj, kRZDBRegisteredObserversKey)
#define rz_setRegisteredObservers(obj, observers) objc_setAssociatedObject(obj, kRZDBRegisteredObserversKey, observers, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
#define rz_dependentObservers(obj) objc_getAssociatedObject(obj, kRZDBDependentObserversKey)
#define rz_setDependentObservers(obj, observers) objc_setAssociatedObject(obj, kRZDBDependentObserversKey, observers, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
#pragma mark - RZDataBinding_Private interface
// methods used to implement RZDB_AUTOMATIC_CLEANUP
@ -59,12 +68,6 @@ void rz_swizzleDeallocIfNeeded(Class class);
@interface NSObject (RZDataBinding_Private)
- (NSMutableArray *)rz_registeredObservers;
- (void)rz_setRegisteredObservers:(NSMutableArray *)registeredObservers;
- (RZDBObserverContainer *)rz_dependentObservers;
- (void)rz_setDependentObservers:(RZDBObserverContainer *)dependentObservers;
- (void)rz_addTarget:(id)target action:(SEL)action boundKey:(NSString *)boundKey bindingTransform:(RZDBKeyBindingTransform)bindingTransform forKeyPath:(NSString *)keyPath withOptions:(NSKeyValueObservingOptions)options;
- (void)rz_removeTarget:(id)target action:(SEL)action boundKey:(NSString *)boundKey forKeyPath:(NSString *)keyPath;
- (void)rz_observeBoundKeyChange:(NSDictionary *)change;
@ -99,11 +102,14 @@ void rz_swizzleDeallocIfNeeded(Class class);
@interface RZDBObserverContainer : NSObject
@property (strong, nonatomic) NSHashTable *observers;
+ (instancetype)strongContainer;
+ (instancetype)weakContainer;
- (void)addObserver:(RZDBObserver *)observer;
- (void)removeObserver:(RZDBObserver *)observer;
- (void)enumerateObserversUsingBlock:(void (^)(RZDBObserver *observer, BOOL *stop))block;
@end
#pragma mark - RZDataBinding implementation
@ -195,29 +201,9 @@ void rz_swizzleDeallocIfNeeded(Class class);
@implementation NSObject (RZDataBinding_Private)
- (NSMutableArray *)rz_registeredObservers
{
return objc_getAssociatedObject(self, @selector(rz_registeredObservers));
}
- (void)rz_setRegisteredObservers:(NSMutableArray *)registeredObservers
{
objc_setAssociatedObject(self, @selector(rz_registeredObservers), registeredObservers, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}
- (RZDBObserverContainer *)rz_dependentObservers
{
return objc_getAssociatedObject(self, @selector(rz_dependentObservers));
}
- (void)rz_setDependentObservers:(RZDBObserverContainer *)dependentObservers
{
objc_setAssociatedObject(self, @selector(rz_dependentObservers), dependentObservers, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}
- (void)rz_addTarget:(id)target action:(SEL)action boundKey:(NSString *)boundKey bindingTransform:(RZDBKeyBindingTransform)bindingTransform forKeyPath:(NSString *)keyPath withOptions:(NSKeyValueObservingOptions)options
{
NSMutableArray *registeredObservers = nil;
RZDBObserverContainer *registeredObservers = nil;
RZDBObserverContainer *dependentObservers = nil;
RZDBObserver *observer = [[RZDBObserver alloc] initWithObservedObject:self keyPath:keyPath observationOptions:options];
@ -225,27 +211,27 @@ void rz_swizzleDeallocIfNeeded(Class class);
[observer setTarget:target action:action boundKey:boundKey bindingTransform:bindingTransform];
@synchronized (self) {
registeredObservers = [self rz_registeredObservers];
registeredObservers = rz_registeredObservers(self);
if ( registeredObservers == nil ) {
registeredObservers = [NSMutableArray array];
[self rz_setRegisteredObservers:registeredObservers];
registeredObservers = [RZDBObserverContainer strongContainer];
rz_setRegisteredObservers(self, registeredObservers);
}
[registeredObservers addObject:observer];
}
[registeredObservers addObserver:observer];
@synchronized (target) {
dependentObservers = [target rz_dependentObservers];
dependentObservers = rz_dependentObservers(target);
if ( dependentObservers == nil ) {
dependentObservers = [[RZDBObserverContainer alloc] init];
[target rz_setDependentObservers:dependentObservers];
dependentObservers = [RZDBObserverContainer weakContainer];
rz_setDependentObservers(target, dependentObservers);
}
[dependentObservers addObserver:observer];
}
[dependentObservers addObserver:observer];
#if RZDB_AUTOMATIC_CLEANUP
rz_swizzleDeallocIfNeeded([self class]);
rz_swizzleDeallocIfNeeded([target class]);
@ -254,22 +240,18 @@ void rz_swizzleDeallocIfNeeded(Class class);
- (void)rz_removeTarget:(id)target action:(SEL)action boundKey:(NSString *)boundKey forKeyPath:(NSString *)keyPath
{
@synchronized (self) {
NSMutableArray *registeredObservers = [self rz_registeredObservers];
[rz_registeredObservers(self) enumerateObserversUsingBlock:^(RZDBObserver *observer, BOOL *stop) {
BOOL targetsEqual = (target == observer.target);
BOOL actionsEqual = (action == NULL || action == observer.action);
BOOL boundKeysEqual = (boundKey == observer.boundKey || [boundKey isEqualToString:observer.boundKey]);
BOOL keyPathsEqual = [keyPath isEqualToString:observer.keyPath];
[registeredObservers enumerateObjectsUsingBlock:^(RZDBObserver *observer, NSUInteger idx, BOOL *stop) {
BOOL targetsEqual = (target == observer.target);
BOOL actionsEqual = (action == NULL || action == observer.action);
BOOL boundKeysEqual = (boundKey == observer.boundKey || [boundKey isEqualToString:observer.boundKey]);
BOOL keyPathsEqual = [keyPath isEqualToString:observer.keyPath];
BOOL allEqual = (targetsEqual && actionsEqual && boundKeysEqual && keyPathsEqual);
BOOL allEqual = (targetsEqual && actionsEqual && boundKeysEqual && keyPathsEqual);
if ( allEqual ) {
[observer invalidate];
}
}];
}
if ( allEqual ) {
[observer invalidate];
}
}];
}
- (void)rz_observeBoundKeyChange:(NSDictionary *)change
@ -298,14 +280,11 @@ void rz_swizzleDeallocIfNeeded(Class class);
- (void)rz_cleanupObservers
{
NSMutableArray *registeredObservers = [self rz_registeredObservers];
RZDBObserverContainer *dependentObservers = [self rz_dependentObservers];
[[registeredObservers copy] enumerateObjectsUsingBlock:^(RZDBObserver *obs, NSUInteger idx, BOOL *stop) {
[rz_registeredObservers(self) enumerateObserversUsingBlock:^(RZDBObserver *obs, BOOL *stop) {
[obs invalidate];
}];
[[dependentObservers.observers allObjects] enumerateObjectsUsingBlock:^(RZDBObserver *obs, NSUInteger idx, BOOL *stop) {
[rz_dependentObservers(self) enumerateObserversUsingBlock:^(RZDBObserver *obs, BOOL *stop) {
[obs invalidate];
}];
}
@ -343,13 +322,24 @@ void rz_swizzleDeallocIfNeeded(Class class);
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
if ( context == kRZDBKVOContext ) {
if ( self.methodSignature.numberOfArguments > 2 ) {
NSDictionary *changeDict = [self changeDictForKVOChange:change];
id target = nil;
SEL action = NULL;
NSDictionary *changeDict = nil;
((void(*)(id, SEL, NSDictionary *))objc_msgSend)(self.target, self.action, changeDict);
@synchronized (self) {
target = self.target;
action = self.action;
if ( self.methodSignature.numberOfArguments > 2 ) {
changeDict = [self changeDictForKVOChange:change];
}
}
if ( changeDict != nil ) {
((void(*)(id, SEL, NSDictionary *))objc_msgSend)(target, action, changeDict);
}
else {
((void(*)(id, SEL))objc_msgSend)(self.target, self.action);
((void(*)(id, SEL))objc_msgSend)(target, action);
}
}
}
@ -387,35 +377,51 @@ void rz_swizzleDeallocIfNeeded(Class class);
- (void)invalidate
{
[[self.target rz_dependentObservers] removeObserver:self];
[[self.observedObject rz_registeredObservers] removeObject:self];
id observedObject = self.observedObject;
[rz_dependentObservers(self.target) removeObserver:self];
[rz_registeredObservers(observedObject) removeObserver:self];
// KVO throws an exception when removing an observer that was never added.
// This should never be a problem given how things are setup, but make sure to avoid a crash.
@try {
[self.observedObject removeObserver:self forKeyPath:self.keyPath context:kRZDBKVOContext];
[observedObject removeObserver:self forKeyPath:self.keyPath context:kRZDBKVOContext];
}
@catch (__unused NSException *exception) {
RZDBLog(@"RZDataBinding attempted to remove an observer from object:%@, but the observer was never added. This shouldn't have happened, but won't affect anything going forward.", self.observedObject);
RZDBLog(@"RZDataBinding attempted to remove an observer from object:%@, but the observer was never added. This shouldn't have happened, but won't affect anything going forward.", observedObject);
}
@synchronized (self) {
self.observedObject = nil;
self.target = nil;
self.action = NULL;
self.methodSignature = nil;
}
self.observedObject = nil;
self.target = nil;
self.action = NULL;
self.methodSignature = nil;
}
@end
#pragma mark - RZDBObserverContainer implementation
@implementation RZDBObserverContainer
@implementation RZDBObserverContainer {
NSHashTable *_observers;
}
- (instancetype)init
+ (instancetype)strongContainer
{
return [[self alloc] initWithBackingStore:[NSHashTable hashTableWithOptions:NSPointerFunctionsStrongMemory | NSPointerFunctionsObjectPersonality]];
}
+ (instancetype)weakContainer
{
return [[self alloc] initWithBackingStore:[NSHashTable weakObjectsHashTable]];
}
- (instancetype)initWithBackingStore:(NSHashTable *)backingStore
{
self = [super init];
if ( self != nil ) {
_observers = [NSHashTable weakObjectsHashTable];
_observers = backingStore;
}
return self;
}
@ -423,14 +429,36 @@ void rz_swizzleDeallocIfNeeded(Class class);
- (void)addObserver:(RZDBObserver *)observer
{
@synchronized (self) {
[self.observers addObject:observer];
[_observers addObject:observer];
}
}
- (void)removeObserver:(RZDBObserver *)observer
{
@synchronized (self) {
[self.observers removeObject:observer];
[_observers removeObject:observer];
}
}
- (void)enumerateObserversUsingBlock:(void (^)(RZDBObserver *, BOOL *))block
{
@synchronized (self) {
NSHashTable *observers = ^{
@synchronized (_observers) {
return [_observers copy];
}
}();
BOOL stop = NO;
for ( RZDBObserver *observer in observers ) {
if ( observer != nil ) {
block(observer, &stop);
}
if ( stop ) {
break;
}
}
}
}

View File

@ -1,11 +1,7 @@
# Specta
# Specta [![Build Status](https://travis-ci.org/specta/specta.svg)](https://travis-ci.org/specta/specta) [![Coverage Status](https://coveralls.io/repos/specta/specta/badge.svg)](https://coveralls.io/r/specta/specta)
A light-weight TDD / BDD framework for Objective-C.
### Status
[![Build Status](https://travis-ci.org/specta/specta.png)](https://travis-ci.org/specta/specta)
[![Coverage Status](https://coveralls.io/repos/specta/specta/badge.svg)](https://coveralls.io/r/specta/specta)
## FEATURES
* An Objective-C RSpec-like BDD DSL
@ -15,56 +11,7 @@ A light-weight TDD / BDD framework for Objective-C.
## SCREENSHOT
![Specta Screenshot](https://raw.githubusercontent.com/specta/specta/master/misc/specta_screenshot.jpg)
## SETUP
Use [CocoaPods](http://github.com/CocoaPods/CocoaPods), [Carthage](https://github.com/carthage/carthage) or [Set up manually](#setting-up-manually)
### CocoaPods
1. Add Specta to your project's `Podfile`:
```ruby
target :MyApp do
# your app dependencies
end
target :MyAppTests do
pod 'Specta', '~> 1.0'
# pod 'Expecta', '~> 1.0' # expecta matchers
# pod 'OCMock', '~> 2.2' # OCMock
# pod 'OCHamcrest', '~> 3.0' # hamcrest matchers
# pod 'OCMockito', '~> 1.0' # OCMock
# pod 'LRMocky', '~> 0.9' # LRMocky
end
```
2. Run `pod update` or `pod install` in your project directory.
### Carthage
1. Add Specta to your project's `Cartfile.private`
```
github "specta/specta" ~> 1.0
```
2. Run `carthage update` in your project directory
3. Drag the appropriate `Specta.framework` for your platform (located in Carthage/Build/) into your applications Xcode project, and add it to your test target(s).
4. If you are building for iOS, a new `Run Script Phase` must be added to copy the framework. The instructions can be found on [Carthage's getting started instructions](https://github.com/carthage/carthage#getting-started)
### SETTING UP MANUALLY
1. Clone from Github.
2. Run `rake` in project root to build.
3. Add a "Cocoa/Cocoa Touch Unit Testing Bundle" target if you don't already have one.
4. Copy and add all header files in `Products` folder to the Test target in your Xcode project.
5. For **OS X projects**, copy and add `Specta.framework` in `Products/osx` folder to the test target in your Xcode project.
For **iOS projects**, copy and add `Specta.framework` in `Products/ios` folder to the test target in your Xcode project.
You can alternatively use `libSpecta.a`, if you prefer to add it as a static library for your project. (iOS 7 and below require this)
6. Add `-ObjC` and `-all_load` to the "Other Linker Flags" build setting for the test target in your Xcode project.
7. If you encounter linking issues with `_llvm_*` symbols, ensure your target's "Generate Test Coverage Files" and "Instrument Program Flow" build settings are set to `Yes`.
<img src="https://raw.githubusercontent.com/specta/specta/master/misc/specta_screenshot.jpg" width="100%">
## EXAMPLE
@ -156,12 +103,17 @@ SpecEnd
* Do `#define SPT_CEDAR_SYNTAX` before importing Specta if you prefer to write `SPEC_BEGIN` and `SPEC_END` instead of `SpecBegin` and `SpecEnd`.
* Prepend `f` to your `describe`, `context`, `example`, `it`, and `specify` to set focus on examples or groups. When specs are focused, all unfocused specs are skipped.
* To use original XCTest reporter, set an environment variable named `SPECTA_REPORTER_CLASS` to `SPTXCTestReporter` in your test scheme.
* Set an environment variable `SPECTA_NO_SHUFFLE` with value `1` to disable test shuffling.
* Set an environment variable `SPECTA_SHUFFLE` with value `1` to enable test shuffling.
* Set an environment variable `SPECTA_SEED` to specify the random seed for test shuffling.
Standard XCTest matchers such as `XCTAssertEqualObjects` and `XCTAssertNil` work, but you probably want to add a nicer matcher framework - [Expecta](http://github.com/specta/expecta/) to your setup. Or if you really prefer, [OCHamcrest](https://github.com/jonreid/OCHamcrest) works fine too. Also, add a mocking framework: [OCMock](http://ocmock.org/).
Standard XCTest matchers such as `XCTAssertEqualObjects` and `XCTAssertNil` work, but you probably want to add a nicer matcher framework - [Expecta](https://github.com/specta/expecta/) to your setup. Or if you really prefer, [OCHamcrest](https://github.com/hamcrest/OCHamcrest) works fine too. Also, add a mocking framework: [OCMock](http://ocmock.org/).
## RUNNING TESTS IN COMMAND LINE
## STATUS
Specta is considered a done project, there are no plans for _active_ development on the project at the moment aside from ensuring future Xcode compatability.
Therefore it is a stable dependency, but will not be moving into the Swift world. If you are looking for that, we recommend you consider [Quick](https://github.com/quick/quick).
## RUNNING SPECTA'S TESTS IN COMMAND LINE
* Run `rake test` in the cloned folder.
@ -171,6 +123,57 @@ Standard XCTest matchers such as `XCTAssertEqualObjects` and `XCTAssertNil` work
* Please prefix instance variable names with a single underscore (`_`).
* Please prefix custom classes and functions defined in the global scope with `SPT`.
## Installation
Use [CocoaPods](https://github.com/CocoaPods/CocoaPods), [Carthage](https://github.com/carthage/carthage) or [Set up manually](#setting-up-manually)
### CocoaPods
1. Add Specta to your project's `Podfile`:
```ruby
target :MyApp do
# your app dependencies
target :MyAppTests do
inherit! :search_paths
pod 'Specta', '~> 1.0'
# pod 'Expecta', '~> 1.0' # expecta matchers
# pod 'OCMock', '~> 2.2' # OCMock
# pod 'OCHamcrest', '~> 3.0' # hamcrest matchers
# pod 'OCMockito', '~> 1.0' # OCMock
# pod 'LRMocky', '~> 0.9' # LRMocky
end
end
```
2. Run `pod install` in your project directory.
### Carthage
1. Add Specta to your project's `Cartfile.private`
```
github "specta/specta" ~> 1.0
```
2. Run `carthage update` in your project directory
3. Drag the appropriate `Specta.framework` for your platform (located in Carthage/Build/) into your applications Xcode project, and add it to your test target(s).
4. If you are building for iOS, a new `Run Script Phase` must be added to copy the framework. The instructions can be found on [Carthage's getting started instructions](https://github.com/carthage/carthage#getting-started)
### SETTING UP MANUALLY
1. Clone from Github.
2. Run `rake` in project root to build.
3. Add a "Cocoa/Cocoa Touch Unit Testing Bundle" target if you don't already have one.
4. Copy and add all header files in `Products` folder to the Test target in your Xcode project.
5. For **OS X projects**, copy and add `Specta.framework` in `Products/osx` folder to the test target in your Xcode project.
For **iOS projects**, copy and add `Specta.framework` in `Products/ios` folder to the test target in your Xcode project.
You can alternatively use `libSpecta.a`, if you prefer to add it as a static library for your project. (iOS 7 and below require this)
6. Add `-ObjC` and `-all_load` to the "Other Linker Flags" build setting for the test target in your Xcode project.
7. If you encounter linking issues with `_llvm_*` symbols, ensure your target's "Generate Test Coverage Files" and "Instrument Program Flow" build settings are set to `Yes`.
## LICENSE
Copyright (c) 2012-2015 [Specta Team](https://github.com/specta?tab=members). This software is licensed under the [MIT License](http://github.com/specta/specta/raw/master/LICENSE).
Copyright (c) 2012-2016 [Specta Team](https://github.com/orgs/specta/people). This software is licensed under the [MIT License](http://github.com/specta/specta/raw/master/LICENSE).

View File

@ -19,7 +19,7 @@
[spec spec];
}
@catch (NSException *exception) {
fprintf(stderr, "%s: An exception has occured outside of tests, aborting.\n\n%s (%s) \n", [specName UTF8String], [[exception name] UTF8String], [[exception reason] UTF8String]);
fprintf(stderr, "%s: An exception has occurred outside of tests, aborting.\n\n%s (%s) \n", [specName UTF8String], [[exception name] UTF8String], [[exception reason] UTF8String]);
if ([exception respondsToSelector:@selector(callStackSymbols)]) {
NSArray *callStackSymbols = [exception callStackSymbols];
if (callStackSymbols) {
@ -145,6 +145,7 @@
example.block(self);
} else if (!example.pending) {
self.spt_skipped = YES;
NSLog(@"Skipping '%@'", example.name);
}
[[[NSThread currentThread] threadDictionary] removeObjectForKey:spt_kCurrentSpecKey];

View File

@ -10,20 +10,20 @@
typedef void (^DoneCallback)(void);
OBJC_EXTERN void describe(NSString *name, void (^block)());
OBJC_EXTERN void fdescribe(NSString *name, void (^block)());
OBJC_EXTERN void describe(NSString *name, void (^block)(void));
OBJC_EXTERN void fdescribe(NSString *name, void (^block)(void));
OBJC_EXTERN void context(NSString *name, void (^block)());
OBJC_EXTERN void fcontext(NSString *name, void (^block)());
OBJC_EXTERN void context(NSString *name, void (^block)(void));
OBJC_EXTERN void fcontext(NSString *name, void (^block)(void));
OBJC_EXTERN void it(NSString *name, void (^block)());
OBJC_EXTERN void fit(NSString *name, void (^block)());
OBJC_EXTERN void it(NSString *name, void (^block)(void));
OBJC_EXTERN void fit(NSString *name, void (^block)(void));
OBJC_EXTERN void example(NSString *name, void (^block)());
OBJC_EXTERN void fexample(NSString *name, void (^block)());
OBJC_EXTERN void example(NSString *name, void (^block)(void));
OBJC_EXTERN void fexample(NSString *name, void (^block)(void));
OBJC_EXTERN void specify(NSString *name, void (^block)());
OBJC_EXTERN void fspecify(NSString *name, void (^block)());
OBJC_EXTERN void specify(NSString *name, void (^block)(void));
OBJC_EXTERN void fspecify(NSString *name, void (^block)(void));
#define pending(...) spt_pending_(__VA_ARGS__, nil)
#define xdescribe(...) spt_pending_(__VA_ARGS__, nil)
@ -32,14 +32,14 @@ OBJC_EXTERN void fspecify(NSString *name, void (^block)());
#define xit(...) spt_pending_(__VA_ARGS__, nil)
#define xspecify(...) spt_pending_(__VA_ARGS__, nil)
OBJC_EXTERN void beforeAll(void (^block)());
OBJC_EXTERN void afterAll(void (^block)());
OBJC_EXTERN void beforeAll(void (^block)(void));
OBJC_EXTERN void afterAll(void (^block)(void));
OBJC_EXTERN void beforeEach(void (^block)());
OBJC_EXTERN void afterEach(void (^block)());
OBJC_EXTERN void beforeEach(void (^block)(void));
OBJC_EXTERN void afterEach(void (^block)(void));
OBJC_EXTERN void before(void (^block)());
OBJC_EXTERN void after(void (^block)());
OBJC_EXTERN void before(void (^block)(void));
OBJC_EXTERN void after(void (^block)(void));
OBJC_EXTERN void sharedExamplesFor(NSString *name, void (^block)(NSDictionary *data));
OBJC_EXTERN void sharedExamples(NSString *name, void (^block)(NSDictionary *data));
@ -54,7 +54,7 @@ OBJC_EXTERN void waitUntil(void (^block)(DoneCallback done));
*
* @param timeout timeout for this @c block only; does not affect the global
* timeout, as @c setAsyncSpecTimeout() does.
* @param ^block runs test code
* @param block runs test code
*/
OBJC_EXTERN void waitUntilTimeout(NSTimeInterval timeout, void (^block)(DoneCallback done));
@ -83,8 +83,8 @@ OBJC_EXTERN void setAsyncSpecTimeout(NSTimeInterval timeout);
} \
@end
OBJC_EXTERN void spt_it_(NSString *name, NSString *fileName, NSUInteger lineNumber, void (^block)());
OBJC_EXTERN void spt_fit_(NSString *name, NSString *fileName, NSUInteger lineNumber, void (^block)());
OBJC_EXTERN void spt_it_(NSString *name, NSString *fileName, NSUInteger lineNumber, void (^block)(void));
OBJC_EXTERN void spt_fit_(NSString *name, NSString *fileName, NSUInteger lineNumber, void (^block)(void));
OBJC_EXTERN void spt_pending_(NSString *name, ...);
OBJC_EXTERN void spt_itShouldBehaveLike_(NSString *fileName, NSUInteger lineNumber, NSString *name, id dictionaryOrBlock);
OBJC_EXTERN void spt_itShouldBehaveLike_block(NSString *fileName, NSUInteger lineNumber, NSString *name, NSDictionary *(^block)());
OBJC_EXTERN void spt_itShouldBehaveLike_block(NSString *fileName, NSUInteger lineNumber, NSString *name, NSDictionary *(^block)(void));

View File

@ -52,12 +52,15 @@ void spt_itShouldBehaveLike_(NSString *fileName, NSUInteger lineNumber, NSString
beforeEach(^{
NSDictionary *blockData = dataBlock();
[dataDict removeAllObjects];
[dataDict addEntriesFromDictionary:blockData];
});
block(dataDict);
afterEach(^{
[dataDict removeAllObjects];
});
afterAll(^{
dataDict = nil;
});

View File

@ -1,5 +1,5 @@
@class SPTSpec;
typedef void (^SPTVoidBlock)();
typedef void (^SPTVoidBlock)(void);
typedef void (^SPTSpecBlock)(SPTSpec *spec);
typedef void (^SPTDictionaryBlock)(NSDictionary *dictionary);

View File

@ -15,4 +15,4 @@ BOOL spt_isSpecClass(Class aClass);
NSString *spt_underscorize(NSString *string);
NSArray *spt_map(NSArray *array, id (^block)(id obj, NSUInteger idx));
NSArray *spt_shuffle(NSArray *array);
unsigned int spt_seed();
unsigned int spt_seed(void);

View File

@ -42,7 +42,10 @@
[self spt_dequeueFailures];
};
if ([NSThread isMainThread]) {
BOOL isMainThread = [NSThread isMainThread];
BOOL isSpectaTest = [self isKindOfClass:[SPTSpec class]];
if (!isSpectaTest || isMainThread) {
dequeueFailures();
} else {
dispatch_sync(dispatch_get_main_queue(), dequeueFailures);

View File

@ -1,4 +1,12 @@
#ifdef __OBJC__
#import <UIKit/UIKit.h>
#else
#ifndef FOUNDATION_EXPORT
#if defined(__cplusplus)
#define FOUNDATION_EXPORT extern "C"
#else
#define FOUNDATION_EXPORT extern
#endif
#endif
#endif

View File

@ -1,4 +1,14 @@
#ifdef __OBJC__
#import <UIKit/UIKit.h>
#else
#ifndef FOUNDATION_EXPORT
#if defined(__cplusplus)
#define FOUNDATION_EXPORT extern "C"
#else
#define FOUNDATION_EXPORT extern
#endif
#endif
#endif
#import "ExpectaObject+FBSnapshotTest.h"
#import "EXPMatchers+FBSnapshotTest.h"

View File

@ -1,6 +1,12 @@
FRAMEWORK_SEARCH_PATHS = $(inherited) "$(PLATFORM_DIR)/Developer/Library/Frameworks"
CONFIGURATION_BUILD_DIR = ${PODS_CONFIGURATION_BUILD_DIR}/Expecta+Snapshots
ENABLE_BITCODE = NO
FRAMEWORK_SEARCH_PATHS = $(inherited) "$(PLATFORM_DIR)/Developer/Library/Frameworks" "${PODS_CONFIGURATION_BUILD_DIR}/Expecta" "${PODS_CONFIGURATION_BUILD_DIR}/FBSnapshotTestCase" "${PODS_CONFIGURATION_BUILD_DIR}/Specta"
GCC_PREPROCESSOR_DEFINITIONS = $(inherited) COCOAPODS=1
HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Private" "${PODS_ROOT}/Headers/Private/Expecta+Snapshots" "${PODS_ROOT}/Headers/Public"
HEADER_SEARCH_PATHS = "${PODS_ROOT}/Headers/Private" "${PODS_ROOT}/Headers/Public"
OTHER_LDFLAGS = -framework "Foundation" -framework "XCTest"
PODS_BUILD_DIR = ${BUILD_DIR}
PODS_CONFIGURATION_BUILD_DIR = ${PODS_BUILD_DIR}/$(CONFIGURATION)$(EFFECTIVE_PLATFORM_NAME)
PODS_ROOT = ${SRCROOT}
SKIP_INSTALL = YES
PODS_TARGET_SRCROOT = ${PODS_ROOT}/Expecta+Snapshots
PRODUCT_BUNDLE_IDENTIFIER = org.cocoapods.${PRODUCT_NAME:rfc1034identifier}
SKIP_INSTALL = YES

View File

@ -7,7 +7,7 @@
<key>CFBundleExecutable</key>
<string>${EXECUTABLE_NAME}</string>
<key>CFBundleIdentifier</key>
<string>org.cocoapods.${PRODUCT_NAME:rfc1034identifier}</string>
<string>${PRODUCT_BUNDLE_IDENTIFIER}</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
@ -15,7 +15,7 @@
<key>CFBundlePackageType</key>
<string>FMWK</string>
<key>CFBundleShortVersionString</key>
<string>3.0.0</string>
<string>3.1.1</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleVersion</key>

View File

@ -1,4 +1,12 @@
#ifdef __OBJC__
#import <UIKit/UIKit.h>
#else
#ifndef FOUNDATION_EXPORT
#if defined(__cplusplus)
#define FOUNDATION_EXPORT extern "C"
#else
#define FOUNDATION_EXPORT extern
#endif
#endif
#endif

Some files were not shown because too many files have changed in this diff Show More