Skip to content

Instantly share code, notes, and snippets.

@luismachado
Created June 23, 2017 13:53
Show Gist options
  • Star 29 You must be signed in to star a gist
  • Fork 8 You must be signed in to fork a gist
  • Save luismachado/1423427b4c60021d71a8772e4dabc140 to your computer and use it in GitHub Desktop.
Save luismachado/1423427b4c60021d71a8772e4dabc140 to your computer and use it in GitHub Desktop.
Custom UIScrollView with fade effect
//
// FadeScrollView.swift
//
// Created by Luís Machado on 23/06/2017.
// Copyright © 2017 Luis Machado. All rights reserved.
//
import UIKit
class FadeScrollView: UIScrollView, UIScrollViewDelegate {
let fadePercentage: Double = 0.2
let gradientLayer = CAGradientLayer()
let transparentColor = UIColor.clear.cgColor
let opaqueColor = UIColor.black.cgColor
var topOpacity: CGColor {
let scrollViewHeight = frame.size.height
let scrollContentSizeHeight = contentSize.height
let scrollOffset = contentOffset.y
let alpha:CGFloat = (scrollViewHeight >= scrollContentSizeHeight || scrollOffset <= 0) ? 1 : 0
let color = UIColor(white: 0, alpha: alpha)
return color.cgColor
}
var bottomOpacity: CGColor {
let scrollViewHeight = frame.size.height
let scrollContentSizeHeight = contentSize.height
let scrollOffset = contentOffset.y
let alpha:CGFloat = (scrollViewHeight >= scrollContentSizeHeight || scrollOffset + scrollViewHeight >= scrollContentSizeHeight) ? 1 : 0
let color = UIColor(white: 0, alpha: alpha)
return color.cgColor
}
override func layoutSubviews() {
super.layoutSubviews()
self.delegate = self
let maskLayer = CALayer()
maskLayer.frame = self.bounds
gradientLayer.frame = CGRect(x: self.bounds.origin.x, y: 0, width: self.bounds.size.width, height: self.bounds.size.height)
gradientLayer.colors = [topOpacity, opaqueColor, opaqueColor, bottomOpacity]
gradientLayer.locations = [0, NSNumber(floatLiteral: fadePercentage), NSNumber(floatLiteral: 1 - fadePercentage), 1]
maskLayer.addSublayer(gradientLayer)
self.layer.mask = maskLayer
}
func scrollViewDidScroll(_ scrollView: UIScrollView) {
gradientLayer.colors = [topOpacity, opaqueColor, opaqueColor, bottomOpacity]
}
}
@twodayslate
Copy link

The gradient does not appear until the scroll happens.

@Tulleb
Copy link

Tulleb commented Dec 27, 2020

Thanks for this 👏

@dwstar79
Copy link

@hanab
Copy link

hanab commented Aug 31, 2021

how can I make this work for horizontal scroll view to fade only at the right end?

@horchliam
Copy link

Two questions: why conform to UIScrollViewDelegate? The scroll view will call layoutSubviews whenever it is scrolled. Second, Why in line 46 did you use self.bounds.origin.x and not 0? Otherwise this is great! Saved me a ton of time!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment