zoukankan      html  css  js  c++  java
  • YYFPSLabel的学习总结

    一个可以让你的App同步屏幕刷新帧率的定时器对象。在初始化CADisplayLink的时候,提供一个target和selector,这样当屏幕刷新的时候,会根据target调用对应的selector方法,需要将这个定时器添加到run loop中去同步屏幕的刷新loop。

    屏幕每秒的刷新次数在60次,所以selector方法会在一秒钟调用60次。

    _link = [CADisplayLink displayLinkWithTarget:[YYWeakProxy proxyWithTarget:self] selector:@selector(tick:)];
    
    [_link addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
    

    YYWeakProxy ???WTF?

    作者的解释:
    // 如果直接用 self 或者 weakSelf,都不能解决循环引用问题
    // 将 timer 的 target 从 self ,变成了中间人 NSProxy
    // timer 调用 target 的 selector 时,会被 NSProxy 内部转调用 self 的 selector

    似乎是个中间人传话筒的意思,如它英文所说,Proxy。通过这个类来持有一个weak对象,能够避免循环引用的情况,比如在NSTimer、CADisplayLink的使用中。

    - (id)forwardingTargetForSelector:(SEL)selector {
        return _target;
    }
    

    这一句是将YYWeakProxy不能处理的调用方法,转发给其持有的弱target来处理。也就是把上面的tick:方法交给self来处理,因为YYWeakProxy找不到tick:的方法。

    至于下面的两个方法:

    - (void)forwardInvocation:(NSInvocation *)invocation {
        void *null = NULL;
        [invocation setReturnValue:&null];
    }
    
    - (NSMethodSignature *)methodSignatureForSelector:(SEL)selector {
        return [NSObject instanceMethodSignatureForSelector:@selector(init)];
    }
    

    是当target被释放nil后,调用的保护代码,就是防止程序因为weak target释放后,直接crash掉。

    YYFPSLabel的工作原理是,是利用CADisplayLink的与屏幕刷新同步调用的特性,计算一秒钟程序的FPS,并展示出来。

    tick函数的核心代码并附上注释:

    //首次调用tick函数时候的调用,记录起始时间
    if (_lastTime == 0) {
        _lastTime = link.timestamp;
        return;
    }
    
    //记录tick函数调用次数
    _count++;
    
    //记录tick函数调用与起始时间的差值,如果小于一秒继续return,继续计数tick调用次数。
    NSTimeInterval delta = link.timestamp - _lastTime;
    if (delta < 1) return;
    
    //大于一秒后,记录当前的时间戳为下次的起始时间。
    _lastTime = link.timestamp;
    
    //计算大约一秒的tick调用次数,也就是一秒钟屏幕的刷新次数,即FPS数。
    float fps = _count / delta;
    
    //重置计数变量
    _count = 0;
    

    总结

    巧妙的利用CADisplayLink的特性,计算一秒钟因为屏幕刷新而调用的tick次数,算出一秒钟屏幕的刷新次数,进而算出FPS值。当然存在一定的不准确性,不过在辅助监测App性能方面,还是很有帮助的。

  • 相关阅读:
    CentOS7 下更改源
    /usr/bin/perl:bad interpreter:No such file or directory 的解决办法
    Centos7 安装wget命令
    Cannot find a valid baseurl for repo: base/7/x86_6 解决方法
    python 启动新进程执行脚本
    MongoDB数据类型
    pymongo.errors.OperationFailure: Authentication failed.
    python连接MongoDB(有密码有认证)
    Mongodb 创建管理员帐号与普通帐号
    python连接MongoDB(无密码无认证)
  • 原文地址:https://www.cnblogs.com/vokie/p/9282759.html
Copyright © 2011-2022 走看看