Skip to content

Commit

Permalink
Merge pull request aromajoin#120 from rezamagnet/master
Browse files Browse the repository at this point in the history
* Add 'Skip' button
* Support the feature to accept the collection view cell as the target view
  • Loading branch information
quangctkm9207 authored Jan 27, 2020
2 parents 49504dd + 05a2fbf commit c5a69fa
Show file tree
Hide file tree
Showing 14 changed files with 341 additions and 42 deletions.
2 changes: 1 addition & 1 deletion MaterialShowcase.podspec
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ s.author = { 'Quang Nguyen' => 'quangnguyen@aromajoin.com' }
s.source = { :git => 'https://github.com/aromajoin/material-showcase-ios.git', :tag => s.version.to_s }

s.swift_version = '5.0'
s.ios.deployment_target = '8.0'
s.ios.deployment_target = '10.0'
s.source_files = 'MaterialShowcase/*.swift'

end
Expand Down
12 changes: 6 additions & 6 deletions MaterialShowcase.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -178,11 +178,11 @@
};
buildConfigurationList = CE083A131EBACFEB0077666F /* Build configuration list for PBXProject "MaterialShowcase" */;
compatibilityVersion = "Xcode 3.2";
developmentRegion = English;
developmentRegion = en;
hasScannedForEncodings = 0;
knownRegions = (
English,
en,
Base,
);
mainGroup = CE083A0F1EBACFEB0077666F;
productRefGroup = CE083A1A1EBACFEB0077666F /* Products */;
Expand Down Expand Up @@ -341,7 +341,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos;
Expand Down Expand Up @@ -398,7 +398,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = iphoneos;
SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule";
Expand All @@ -423,7 +423,7 @@
DYLIB_INSTALL_NAME_BASE = "@rpath";
INFOPLIST_FILE = MaterialShowcase/Info.plist;
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
MARKETING_VERSION = 0.7.1;
ONLY_ACTIVE_ARCH = NO;
Expand All @@ -449,7 +449,7 @@
DYLIB_INSTALL_NAME_BASE = "@rpath";
INFOPLIST_FILE = MaterialShowcase/Info.plist;
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
MARKETING_VERSION = 0.7.1;
ONLY_ACTIVE_ARCH = NO;
Expand Down
4 changes: 2 additions & 2 deletions MaterialShowcase/MaterialShowcase+Calculations.swift
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,8 @@ extension MaterialShowcase {
let targetCenterY = targetBounds.midY

let expandedRadius = 1.1 * TARGET_HOLDER_RADIUS
let expandedBounds = CGRect(x: targetCenterX, y: targetCenterY, width: 0, height: 0)
expandedBounds.insetBy(dx: -expandedRadius, dy: -expandedRadius);
var expandedBounds = CGRect(x: targetCenterX, y: targetCenterY, width: 0, height: 0)
expandedBounds = expandedBounds.insetBy(dx: -expandedRadius, dy: -expandedRadius);

let textRadius = maxDistance(from: center, to: textBounds)
let targetRadius = maxDistance(from: center, to: expandedBounds)
Expand Down
70 changes: 64 additions & 6 deletions MaterialShowcase/MaterialShowcase.swift
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@ open class MaterialShowcase: UIView {
var offsetThreshold: CGFloat = 88

// MARK: Private view properties
var closeButton : UIButton!

var containerView: UIView!
var targetView: UIView!
var backgroundView: UIView!
Expand All @@ -52,9 +54,13 @@ open class MaterialShowcase: UIView {
var targetCopyView: UIView!
var instructionView: MaterialShowcaseInstructionView!


public var skipButton: (() -> Void)?
var onTapThrough: (() -> Void)?

// MARK: Public Properties
// setSkipImage
public var skipImage = "HintClose"

// Background
@objc public var backgroundAlpha: CGFloat = 1.0
Expand Down Expand Up @@ -169,8 +175,22 @@ extension MaterialShowcase {
targetHolderRadius = 0
}


/// Sets a UICollectionViewCell as target
@objc public func setTargetView(collectionView: UICollectionView, section: Int, item: Int) {
let indexPath = IndexPath(item: item, section: section)
targetView = collectionView.cellForItem(at: indexPath)
// for table viewcell, we do not need target holder (circle view)
// therefore, set its radius = 0
targetHolderRadius = 0
}

@objc func dismissTutorialButtonDidTouch() {
skipButton?()
}

/// Shows it over current screen after completing setup process
@objc public func show(animated: Bool = true, completion handler: (()-> Void)?) {
@objc public func show(animated: Bool = true,hasShadow: Bool = true, hasSkipButton: Bool = true, completion handler: (()-> Void)?) {
initViews()
alpha = 0.0
containerView.addSubview(self)
Expand All @@ -181,6 +201,36 @@ extension MaterialShowcase {

backgroundView.transform = CGAffineTransform(scaleX: scale, y: scale) // Initial set to support animation
backgroundView.center = targetHolderView.center





if hasSkipButton {

closeButton = UIButton()

closeButton.setImage(UIImage(named: skipImage), for: .normal)
addSubview(closeButton)
closeButton.addTarget(self, action: #selector(dismissTutorialButtonDidTouch), for: .touchUpInside)

let margins = layoutMarginsGuide
closeButton.translatesAutoresizingMaskIntoConstraints = false
closeButton.topAnchor.constraint(equalTo: margins.topAnchor, constant: 0).isActive = true
closeButton.rightAnchor.constraint(equalTo: margins.rightAnchor, constant: -8).isActive = true
closeButton.widthAnchor.constraint(equalTo: widthAnchor, multiplier: 0.13).isActive = true
closeButton.heightAnchor.constraint(equalTo: closeButton.widthAnchor, multiplier: 1.0/1.0).isActive = true
}


if hasShadow {
backgroundView.layer.shadowColor = UIColor.black.cgColor
backgroundView.layer.shadowRadius = 5.0
backgroundView.layer.shadowOpacity = 0.5
backgroundView.layer.shadowOffset = .zero
backgroundView.clipsToBounds = false
}

if animated {
UIView.animate(withDuration: aniComeInDuration, animations: {
self.targetHolderView.transform = CGAffineTransform(scaleX: 1, y: 1)
Expand Down Expand Up @@ -319,20 +369,24 @@ extension MaterialShowcase {
}

let center = targetRippleView.center

backgroundView = UIView(frame: CGRect(x: 0, y: 0, width: radius * 2,height: radius * 2))
backgroundView.center = center

backgroundView.asCircle()



case .full:
backgroundView = UIView(frame: CGRect(x: 0, y: 0, width: UIScreen.main.bounds.width,height: UIScreen.main.bounds.height))
}


backgroundView.backgroundColor = backgroundPromptColor.withAlphaComponent(backgroundPromptColorAlpha)
insertSubview(backgroundView, belowSubview: targetRippleView)
addBackgroundMask(with: targetHolderRadius, in: backgroundView)

// addBackgroundMask(with: targetHolderRadius, in: backgroundView)
}

private func getDefaultBackgroundRadius() -> CGFloat{
private func getDefaultBackgroundRadius() -> CGFloat {
var radius: CGFloat = 0.0
if UIDevice.current.userInterfaceIdiom == .pad {
radius = 300.0
Expand All @@ -344,6 +398,7 @@ extension MaterialShowcase {

private func addBackgroundMask(with radius: CGFloat, in view: UIView) {
let center = backgroundViewType == .circle ? view.bounds.center : targetRippleView.center

let mutablePath = CGMutablePath()
mutablePath.addRect(view.bounds)
mutablePath.addArc(center: center, radius: radius, startAngle: 0.0, endAngle: 2 * .pi, clockwise: false)
Expand Down Expand Up @@ -548,17 +603,20 @@ extension MaterialShowcase {
/// Detects the position of target view relative to its container
func getTargetPosition(target: UIView, container: UIView) -> TargetPosition {
let center = calculateCenter(at: targetView, to: container)
if center.y < container.frame.height / 2{
if center.y < container.frame.height / 2 {
return .above
} else {
return .below
}
}



// Calculates the center point based on targetview
func calculateCenter(at targetView: UIView, to containerView: UIView) -> CGPoint {
let targetRect = targetView.convert(targetView.bounds , to: containerView)
return targetRect.center

}

// Gets all UIView from TabBarItem.
Expand Down
3 changes: 2 additions & 1 deletion MaterialShowcase/MaterialShowcaseInstructionView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,7 @@ public class MaterialShowcaseInstructionView: UIView {
y: 0,
width: getWidth(),
height: 0)

primaryLabel.sizeToFitHeight()
addSubview(primaryLabel)
}
Expand Down Expand Up @@ -114,7 +115,7 @@ public class MaterialShowcaseInstructionView: UIView {
}

//Calculate width per device
private func getWidth() -> CGFloat{
private func getWidth() -> CGFloat {
//superview was left side
if (self.superview?.frame.origin.x)! < CGFloat(0) {
return frame.width - (frame.minX/2)
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@


## Requirement
* iOS 8.0+
* iOS 10.0+
* Swift 4.2+

## Installation
Expand Down
12 changes: 10 additions & 2 deletions Sample/MaterialShowcaseSample.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
CE9F24961EC2907700444781 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = CE9F24941EC2907700444781 /* LaunchScreen.storyboard */; };
CE9F249E1EC2945300444781 /* MaterialShowcase.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = CE9F249D1EC2945300444781 /* MaterialShowcase.framework */; };
CE9F249F1EC2945300444781 /* MaterialShowcase.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = CE9F249D1EC2945300444781 /* MaterialShowcase.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
E2F545EA23DB71F8009D9B77 /* CollectionViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = E2F545E923DB71F8009D9B77 /* CollectionViewController.swift */; };
E2F545EC23DB7251009D9B77 /* CollectionViewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = E2F545EB23DB7251009D9B77 /* CollectionViewCell.swift */; };
/* End PBXBuildFile section */

/* Begin PBXCopyFilesBuildPhase section */
Expand All @@ -39,6 +41,8 @@
CE9F24951EC2907700444781 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = "<group>"; };
CE9F24971EC2907700444781 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
CE9F249D1EC2945300444781 /* MaterialShowcase.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; path = MaterialShowcase.framework; sourceTree = BUILT_PRODUCTS_DIR; };
E2F545E923DB71F8009D9B77 /* CollectionViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollectionViewController.swift; sourceTree = "<group>"; };
E2F545EB23DB7251009D9B77 /* CollectionViewCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollectionViewCell.swift; sourceTree = "<group>"; };
/* End PBXFileReference section */

/* Begin PBXFrameworksBuildPhase section */
Expand Down Expand Up @@ -75,6 +79,8 @@
children = (
CE9F248B1EC2907700444781 /* AppDelegate.swift */,
CE9F248D1EC2907700444781 /* ViewController.swift */,
E2F545E923DB71F8009D9B77 /* CollectionViewController.swift */,
E2F545EB23DB7251009D9B77 /* CollectionViewCell.swift */,
CE9F248F1EC2907700444781 /* Main.storyboard */,
CE9F24921EC2907700444781 /* Assets.xcassets */,
CE9F24941EC2907700444781 /* LaunchScreen.storyboard */,
Expand Down Expand Up @@ -158,7 +164,9 @@
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
E2F545EA23DB71F8009D9B77 /* CollectionViewController.swift in Sources */,
CE9F248E1EC2907700444781 /* ViewController.swift in Sources */,
E2F545EC23DB7251009D9B77 /* CollectionViewCell.swift in Sources */,
CE9F248C1EC2907700444781 /* AppDelegate.swift in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
Expand Down Expand Up @@ -304,7 +312,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
DEVELOPMENT_TEAM = 4V6HDFWSR4;
INFOPLIST_FILE = MaterialShowcaseSample/Info.plist;
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = com.aromajoin.MaterialShowcaseSample;
PRODUCT_NAME = "$(TARGET_NAME)";
Expand All @@ -318,7 +326,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
DEVELOPMENT_TEAM = 4V6HDFWSR4;
INFOPLIST_FILE = MaterialShowcaseSample/Info.plist;
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
IPHONEOS_DEPLOYMENT_TARGET = 10.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = com.aromajoin.MaterialShowcaseSample;
PRODUCT_NAME = "$(TARGET_NAME)";
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
<?xml version="1.0" encoding="UTF-8"?>
<Scheme
LastUpgradeVersion = "1130"
version = "1.3">
<BuildAction
parallelizeBuildables = "YES"
buildImplicitDependencies = "YES">
<BuildActionEntries>
<BuildActionEntry
buildForTesting = "YES"
buildForRunning = "YES"
buildForProfiling = "YES"
buildForArchiving = "YES"
buildForAnalyzing = "YES">
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "CE9F24871EC2907700444781"
BuildableName = "MaterialShowcaseSample.app"
BlueprintName = "MaterialShowcaseSample"
ReferencedContainer = "container:MaterialShowcaseSample.xcodeproj">
</BuildableReference>
</BuildActionEntry>
</BuildActionEntries>
</BuildAction>
<TestAction
buildConfiguration = "Debug"
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
shouldUseLaunchSchemeArgsEnv = "YES">
<Testables>
</Testables>
</TestAction>
<LaunchAction
buildConfiguration = "Debug"
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
launchStyle = "0"
useCustomWorkingDirectory = "NO"
ignoresPersistentStateOnLaunch = "NO"
debugDocumentVersioning = "YES"
debugServiceExtension = "internal"
allowLocationSimulation = "YES">
<BuildableProductRunnable
runnableDebuggingMode = "0">
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "CE9F24871EC2907700444781"
BuildableName = "MaterialShowcaseSample.app"
BlueprintName = "MaterialShowcaseSample"
ReferencedContainer = "container:MaterialShowcaseSample.xcodeproj">
</BuildableReference>
</BuildableProductRunnable>
</LaunchAction>
<ProfileAction
buildConfiguration = "Release"
shouldUseLaunchSchemeArgsEnv = "YES"
savedToolIdentifier = ""
useCustomWorkingDirectory = "NO"
debugDocumentVersioning = "YES">
<BuildableProductRunnable
runnableDebuggingMode = "0">
<BuildableReference
BuildableIdentifier = "primary"
BlueprintIdentifier = "CE9F24871EC2907700444781"
BuildableName = "MaterialShowcaseSample.app"
BlueprintName = "MaterialShowcaseSample"
ReferencedContainer = "container:MaterialShowcaseSample.xcodeproj">
</BuildableReference>
</BuildableProductRunnable>
</ProfileAction>
<AnalyzeAction
buildConfiguration = "Debug">
</AnalyzeAction>
<ArchiveAction
buildConfiguration = "Release"
revealArchiveInOrganizer = "YES">
</ArchiveAction>
</Scheme>
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"images" : [
{
"idiom" : "universal",
"filename" : "HintClose.pdf"
}
],
"info" : {
"version" : 1,
"author" : "xcode"
}
}
Binary file not shown.
Loading

0 comments on commit c5a69fa

Please sign in to comment.