使用ICSDrawerController 实现侧滑功能

在ICSDrawerController 第三方上做了修改实现,QQ 点击头像打开关抽屉头像渐变的效果

- (void)hiddenHeadView:(hiddenHeadViewBlock)block;
@property(nonatomic,copy) hiddenHeadViewBlock hiddenBlock;
- (void)hiddenHeadView:(hiddenHeadViewBlock)block
{
self.hiddenBlock = block;
}

在拖拽滑动的手势方法中监听滑动的方法中来改变透明度

- (void)panGestureRecognized:(UIPanGestureRecognizer *)panGestureRecognizer
{
NSParameterAssert(self.leftView);
NSParameterAssert(self.centerView); UIGestureRecognizerState state = panGestureRecognizer.state;
CGPoint location = [panGestureRecognizer locationInView:self.view];
CGPoint velocity = [panGestureRecognizer velocityInView:self.view]; switch (state) { case UIGestureRecognizerStateBegan:
self.panGestureStartLocation = location;//记录当前的位置
if (self.drawerState == ICSDrawerControllerStateClosed) {
[self willOpen];
}
else {
[self willClose];
}
break; case UIGestureRecognizerStateChanged: { //每次拖拽滑动
CGFloat delta = 0.0f;
if (self.drawerState == ICSDrawerControllerStateOpening) {
delta = location.x - self.panGestureStartLocation.x;
}
else if (self.drawerState == ICSDrawerControllerStateClosing) {
delta = kICSDrawerControllerDrawerDepth - (self.panGestureStartLocation.x - location.x);
} CGRect l = self.leftView.frame;
CGRect c = self.centerView.frame;
if (delta > kICSDrawerControllerDrawerDepth) {
l.origin.x = 0.0f;
c.origin.x = kICSDrawerControllerDrawerDepth;
}
else if (delta < 0.0f) {
l.origin.x = kICSDrawerControllerLeftViewInitialOffset;
c.origin.x = 0.0f;
}
else {
// While the centerView can move up to kICSDrawerControllerDrawerDepth points, to achieve a parallax effect
// the leftView has move no more than kICSDrawerControllerLeftViewInitialOffset points
l.origin.x = kICSDrawerControllerLeftViewInitialOffset
- (delta * kICSDrawerControllerLeftViewInitialOffset) / kICSDrawerControllerDrawerDepth; c.origin.x = delta;
CGFloat alpha = - delta//2.6;
if (alpha > 1.0) {
alpha = 1.0;
}else if(alpha < ){
alpha = ;
}
//头像是否显示隐藏
self.hiddenBlock(alpha);
} self.leftView.frame = l;
self.centerView.frame = c; break;
} case UIGestureRecognizerStateEnded: { //拖拽结束 if (self.drawerState == ICSDrawerControllerStateOpening) {
CGFloat centerViewLocation = self.centerView.frame.origin.x;
if (centerViewLocation == kICSDrawerControllerDrawerDepth) {
// Open the drawer without animation, as it has already being dragged in its final position
[self setNeedsStatusBarAppearanceUpdate];
[self didOpen];
}
else if (centerViewLocation > self.view.bounds.size.width /
&& velocity.x > 0.0f) {
// Animate the drawer opening
[self animateOpening];
}
else {
// Animate the drawer closing, as the opening gesture hasn't been completed or it has
// been reverted by the user
[self didOpen];
[self willClose];
[self animateClosing];
} } else if (self.drawerState == ICSDrawerControllerStateClosing) {
CGFloat centerViewLocation = self.centerView.frame.origin.x;
if (centerViewLocation == 0.0f) {
// Close the drawer without animation, as it has already being dragged in its final position
[self setNeedsStatusBarAppearanceUpdate];
[self didClose];
}
else if (centerViewLocation < ( * self.view.bounds.size.width) /
&& velocity.x < 0.0f) {
// Animate the drawer closing
[self animateClosing];
}
else {
// Animate the drawer opening, as the opening gesture hasn't been completed or it has
// been reverted by the user
[self didClose]; // Here we save the current position for the leftView since
// we want the opening animation to start from the current position
// and not the one that is set in 'willOpen'
CGRect l = self.leftView.frame;
[self willOpen];
self.leftView.frame = l; [self animateOpening];
}
}
}
break; default:
break;
}
} #pragma mark - Animations
#pragma mark Opening animation
- (void)animateOpening
{
NSParameterAssert(self.drawerState == ICSDrawerControllerStateOpening);
NSParameterAssert(self.leftView);
NSParameterAssert(self.centerView); // Calculate the final frames for the container views
CGRect leftViewFinalFrame = self.view.bounds;
CGRect centerViewFinalFrame = self.view.bounds;
centerViewFinalFrame.origin.x = kICSDrawerControllerDrawerDepth; [UIView animateWithDuration:kICSDrawerControllerAnimationDuration
delay:
usingSpringWithDamping:kICSDrawerControllerOpeningAnimationSpringDamping
initialSpringVelocity:kICSDrawerControllerOpeningAnimationSpringInitialVelocity
options:UIViewAnimationOptionCurveLinear
animations:^{
self.centerView.frame = centerViewFinalFrame;
self.leftView.frame = leftViewFinalFrame;
self.hiddenBlock(); [self setNeedsStatusBarAppearanceUpdate];
}
completion:^(BOOL finished) {
[self didOpen];
}];
}
#pragma mark Closing animation
- (void)animateClosing
{
NSParameterAssert(self.drawerState == ICSDrawerControllerStateClosing);
NSParameterAssert(self.leftView);
NSParameterAssert(self.centerView); // Calculate final frames for the container views
CGRect leftViewFinalFrame = self.leftView.frame;
leftViewFinalFrame.origin.x = kICSDrawerControllerLeftViewInitialOffset;
CGRect centerViewFinalFrame = self.view.bounds; [UIView animateWithDuration:kICSDrawerControllerAnimationDuration
delay:
usingSpringWithDamping:kICSDrawerControllerClosingAnimationSpringDamping
initialSpringVelocity:kICSDrawerControllerClosingAnimationSpringInitialVelocity
options:UIViewAnimationOptionCurveLinear
animations:^{
self.centerView.frame = centerViewFinalFrame;
self.leftView.frame = leftViewFinalFrame;
self.hiddenBlock(); [self setNeedsStatusBarAppearanceUpdate];
}
completion:^(BOOL finished) {
[self didClose];
}];
}

给当前类扩充一个方法,拿到当前conroller的menuController

@interface UIViewController (ICSDrawerController)

//拿到当前conroller的menuController
//如果不存在,返回nil
@property (nonatomic, readonly) ICSDrawerController* menuController; @end
@implementation UIViewController (ICSDrawerController)

- (ICSDrawerController *)menuController {

    if (self.parentViewController == nil) {
return nil;
}else if ([self.parentViewController isKindOfClass:[ICSDrawerController class]]) {
return (ICSDrawerController* )self.parentViewController;
}else {
return self.parentViewController.menuController;
}
} @end

换皮肤功能使用 KVO 监听属性就可以实现,这里附上代码https://github.com/SummerHH/QQMenu


一个很好用的侧滑框架ICSDrawerController实现的 QQ 侧滑及换肤功能的更多相关文章

  1. qt之窗口换肤(一个qss的坑:当类属性发现变化时需要重置qss,使用rcc资源文件)

    1.相关文章 Qt 资源系统qt的moc,uic,rcc命令的使用 2.概要    毕业两年了,一直使用的是qt界面库来开发程序,使用过vs08.10.13等开发工具,并安装了qt的插件,最近在做客户 ...

  2. python 全栈开发,Day50(Javascript简介,第一个JavaScript代码,数据类型,运算符,数据类型转换,流程控制,百度换肤,显示隐藏)

    一.Javascript简介 Web前端有三层: HTML:从语义的角度,描述页面结构 CSS:从审美的角度,描述样式(美化页面) JavaScript:从交互的角度,描述行为(提升用户体验) Jav ...

  3. 前端JavaScript(1) --Javascript简介,第一个JavaScript代码,数据类型,运算符,数据类型转换,流程控制,百度换肤,显示隐藏

    一.Javascript简介 Web前端有三层: HTML:从语义的角度,描述页面结构 CSS:从审美的角度,描述样式(美化页面) JavaScript:从交互的角度,描述行为(提升用户体验) Jav ...

  4. 关于引入多个jquery冲突的问题(附一个很好用的validate前端验证框架及使用方法)

    废话不多说,进入正题: 如果一个jsp中想要使用两个不同版本的jquery怎么办呢?客官往下看: <script src="${ctxStatic}/jquery/jquery-1.8 ...

  5. 一个标准的,兼容性很好的div仿框架的基础模型!

    <!DOCTYPE html> <html > <head> <meta http-equiv="Content-Type" conten ...

  6. JDBC数据源(DataSource)数据源技术是Java操作数据库的一个很关键技术,流行的持久化框架都离不开数据源的应用。

    JDBC数据源(DataSource)的简单实现   数据源技术是Java操作数据库的一个很关键技术,流行的持久化框架都离不开数据源的应用. 2.数据源提供了一种简单获取数据库连接的方式,并能在内部通 ...

  7. Android开源框架之SwipeListView导入及模拟QQ侧滑

    SwipeListView是Github上的一个开源框架,地址:https://github.com/47deg/android-swipelistview SwipeListView was bor ...

  8. 如何创建一个简单的C++同步锁框架(译)

    翻译自codeproject上面的一篇文章,题目是:如何创建一个简单的c++同步锁框架 目录 介绍 背景 临界区 & 互斥 & 信号 临界区 互斥 信号 更多信息 建立锁框架的目的 B ...

  9. 【转】发布一个基于NGUI编写的UI框架

    发布一个基于NGUI编写的UI框架 1.加载,显示,隐藏,关闭页面,根据标示获得相应界面实例 2.提供界面显示隐藏动画接口 3.单独界面层级,Collider,背景管理 4.根据存储的导航信息完成界面 ...

随机推荐

  1. September Challenge 2017

    Little Chef and Sums 分析:水题,去维护一下前缀和以及后缀和就好,注意long long #include "iostream" #include " ...

  2. asm 兼容性、asm 主要参数管理

    一 ASM instance 与 Database instance 的版本兼容性说明 1. Oracle 11gR2 的ASM 支持11g和10g的数据库实例.但是在Oracle Clusterwa ...

  3. 物联网项目开发必读 深度分析MQTT协议优缺点

    物联网并不仅仅是一种网络,而是一个新的生态环境,它描述的本质是越来越多的使用物品通过网络连接在一起并可使用单个或者多个的终端设备对它们进行各种控制和使用—当然,工业上的物联网通常连接到的石鼓传感器或者 ...

  4. POJ1330(LCA入门题)

    Nearest Common Ancestors Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 23388   Accept ...

  5. QualType in clang

    http://clang.llvm.org/docs/InternalsManual.html#the-qualtype-class the QualType class is designed to ...

  6. QTableWidget笔记

    1.QTableWidget继承自QTableView. 2.头文件:QTableWidget 3.简单使用: #include "mainwindow.h" #include & ...

  7. FASTX-Toolkit组件用法

    FASTX-Toolkit组件用法 Command Line Arguments FASTQ-to-FASTA FASTQ/A Quality Statistics FASTQ Quality cha ...

  8. JAVA企业级开发-xml基础语法&约束&解析(04)

    一.什么是xml html:超文本标记语言.它主要是用来封装页面上要显示的数据,最后通过浏览器来解析html文件,然后把数据展示在浏览器上.同样我们可以使用JS和DOM技术对html文件进行解析和操作 ...

  9. 异步和多线程,委托异步调用,Thread,ThreadPool,Task,Parallel,CancellationTokenSource

    1 进程-线程-多线程,同步和异步2 异步使用和回调3 异步参数4 异步等待5 异步返回值 5 多线程的特点:不卡主线程.速度快.无序性7 thread:线程等待,回调,前台线程/后台线程, 8 th ...

  10. char和nchar,varchar和nvarchar的区别(转载)

    1)       定义: char:    固定长度,存储ANSI字符,不足的补英文半角空格. nchar:   固定长度,存储Unicode字符,不足的补英文半角空格 varchar:  可变长度, ...