美文网首页实用工具iOS 知识库iOS Developer
Swift 开屏广告的实现 (支持本地与网络的图片,动态图,视频

Swift 开屏广告的实现 (支持本地与网络的图片,动态图,视频

作者: z小志 | 来源:发表于2018-01-11 13:37 被阅读42780次

原理

用户在使用app的时候,用户肯定会多次打开app的,但是如果网速慢图片大,总不能让用户看3秒默认启动图吧?那样体验太不好了,因此还是加入缓存机制比较好。我的实现思路是,第一次不让用户去看这个3秒广告了,直接略过,开一个线程去缓存这张图片。第二次用户再启动app的时候,判断广告有效时间显示图片 ,gif、视频同理。

效果图


Example.gif
![ gif.gif ]
vidio.gif

部分代码

AppDelegate  需要显示广告图的时候添加以下代码

import MDSplashScreen

    if type == .localImage{
        let adView = MDSplashScreenView.init(type: .localImage)
        adView.img = "localImage.JPG"
        adView.linkUrl = "https://www.baidu.com/"
        adView.imageValidTime = "03/02/2018 14:25"
        adView.showSplashScreenWithTime(showTime: 3)
    }else if type == .localGif{
        let adView = MDSplashScreenView.init(type: .localGif)
        adView.img = "localGIf"
        adView.linkUrl = "https://www.baidu.com/"
        adView.imageValidTime = "03/02/2018 14:25"
        adView.showSplashScreenWithTime(showTime: 3)
    }else if type == .localVidio{
        let adView = MDSplashScreenView.init(type: .localVidio)
        adView.img = "localVidio"
        adView.linkUrl = ""
        adView.imageValidTime = "03/02/2018 14:25"
        adView.videoCycleOnce = false //是否循环
        adView.showSplashScreenWithTime(showTime: 0)
    }else if type == .netImage{
        let splashScreenManager = MDSplashScreenManager.sharedManager
        if UserDefaults.standard.object(forKey: AdImageName) != nil{
            let imageName = UserDefaults.standard.object(forKey: AdImageName) as! String
            let filepath = splashScreenManager.getFilePathWithName(name: imageName)
            let isExist = splashScreenManager.isFileExistWithFilePath(filePath: filepath)
            if isExist{
                let adView = MDSplashScreenView.init(type: .netImage)
                adView.img = filepath
                adView.linkUrl = UserDefaults.standard.object(forKey: AdLinkUrl) as? String
                adView.imageValidTime = UserDefaults.standard.object(forKey: AdValidTime) as? String
                adView.showSplashScreenWithTime(showTime: 3)
            }
        }

        splashScreenManager.getAdvertisingData(url: "http://img1.126.net/channel6/2016/022471/0805/2.jpg?dpi=6401136", validTime: "03/02/2018 14:25", linkUrl: "https://www.jianshu.com/u/90028000c41d", type: .netImage)
    }else if type == .netGif{
        let splashScreenManager = MDSplashScreenManager.sharedManager
        if UserDefaults.standard.object(forKey: AdGifName) != nil{
            let gifName = UserDefaults.standard.object(forKey: AdGifName) as! String
            let filepath = splashScreenManager.getFilePathWithName(name: gifName)
            let isExist = splashScreenManager.isFileExistWithFilePath(filePath: filepath)
            if isExist{
                let adView = MDSplashScreenView.init(type: .netGif)
                adView.img = filepath
                adView.linkUrl = UserDefaults.standard.object(forKey: AdLinkUrl) as? String
                adView.imageValidTime = UserDefaults.standard.object(forKey: AdValidTime) as? String
                adView.showSplashScreenWithTime(showTime: 3)
            }
        }
        
        splashScreenManager.getAdvertisingData(url: "http://yun.it7090.com/image/XHLaunchAd/pic05.gif", validTime: "03/02/2018 14:25", linkUrl: "https://www.jianshu.com/u/90028000c41d", type: .netGif)
    }else if type == .netVidio{
        let splashScreenManager = MDSplashScreenManager.sharedManager
        if UserDefaults.standard.object(forKey: AdViedioName) != nil{
            let vidioName = UserDefaults.standard.object(forKey: AdViedioName) as! String
            let filepath = splashScreenManager.getFilePathWithName(name:vidioName)
            let isExist = splashScreenManager.isFileExistWithFilePath(filePath: filepath)
            if isExist{
                let adView = MDSplashScreenView.init(type: .netVidio)
                adView.img = filepath
                adView.linkUrl = UserDefaults.standard.object(forKey: AdLinkUrl) as? String
                adView.imageValidTime = UserDefaults.standard.object(forKey: AdValidTime) as? String
                adView.showSplashScreenWithTime(showTime: 0)
            }
        }
        
        splashScreenManager.getAdvertisingData(url: "http://yun.it7090.com/video/XHLaunchAd/video03.mp4", validTime: "03/02/2018 14:25", linkUrl: "https://www.jianshu.com/u/90028000c41d", type: .netVidio)
    }


MDSplashScreenView

显示广告图
    open func showSplashScreenWithTime(showTime:Int){
        if type == .localImage{
            self.adImageView.image = UIImage.init(named: img!)
        }else if type == .localGif{
            self.adImageView.loadGif(name: img!)
        }else if type == .netImage{
            self.adImageView.image = UIImage.init(contentsOfFile: self.img!)
        }else if type == .netGif{
            let data = try? Data.init(contentsOf: URL.init(fileURLWithPath: self.img!))
            if data == nil{
                self.dismiss()
            }else{
                self.adImageView.image = UIImage.gif(data: data!)
            }
        }else if type == .localVidio{
            let filePath = Bundle.main.path(forResource: img!, ofType: "mp4")
            let videoURL = URL(fileURLWithPath: filePath!)
            let playerItem = AVPlayerItem.init(url: videoURL)
            self.videoPlayer?.player = AVPlayer.init(playerItem: playerItem)
            self.videoPlayer?.player?.play()
        }else if type == .netVidio{
            let videoURL = URL(fileURLWithPath:  img!)
            let playerItem = AVPlayerItem.init(url: videoURL)
            self.videoPlayer?.player = AVPlayer.init(playerItem: playerItem)
            self.videoPlayer?.player?.play()
        }
    
        let dateFormatter = DateFormatter()
        dateFormatter.dateFormat = "MM/dd/yyyy HH:mm"
        dateFormatter.string(from: Date())

        let  timeStampString = self.imageValidTime
        if timeStampString == nil{
            print("结束时间存储失败")
            self.dismiss()
        }
        let validTimeDate = dateFormatter.date(from: timeStampString!)

        var result:ComparisonResult?
        result = validTimeDate?.compare(Date())
        //将存下来的日期和当前日期相比,如果当前日期小于存下来的时间,则可以显示广告页,反之则不显示
        if result == .orderedAscending{
            dismiss()
        }else{
            if showTime != 0{
                self.showTime = showTime
                countButton.setTitle("跳过\(showTime)", for: .normal)
                startTimer()
            }else{
                countButton.setTitle("跳过", for: .normal)
            }
            let window = UIApplication.shared.delegate?.window
            window??.isHidden = false
            window??.addSubview(self)
        }
        
    }

获取图片
open func getAdvertisingData(url:String,validTime:String,linkUrl:String,type:MDSplashScreenType){
        // 获取名称
        let stringArr = url.components(separatedBy: "/")
        let name: String? = stringArr.last
        // 拼接沙盒路径
        let filePath: String = getFilePathWithName(name: name!)
        let isExist: Bool = isFileExistWithFilePath(filePath: filePath)
        if !isExist {
            // 如果该资源不存在,则删除老的,下载新的
            if type == .netImage{
                downloadAdDataWithUrl(url: url, name: name!, linkUrl: linkUrl, validTime: validTime,key: AdImageName)
            }else if type == .netGif{
                downloadAdDataWithUrl(url: url, name: name!, linkUrl: linkUrl, validTime: validTime,key: AdGifName)
            }else if type == .netVidio{
                downloadAdDataWithUrl(url: url, name: name!, linkUrl: linkUrl, validTime: validTime,key: AdViedioName)
            }
        }
    }
异步下载图片
    //下载资源到本地
    fileprivate func downloadAdDataWithUrl(url:String,name:String,linkUrl:String,validTime:String,key:String){
        DispatchQueue.global().async {
            let data = try? Data.init(contentsOf: URL(string: url)!)
            if data != nil{
                let filePath  = self.getFilePathWithName(name: name)
                let gifData = NSData.init(data: data!)
                let isWrite = gifData.write(toFile: filePath, atomically: true)
                print(filePath)
                if isWrite{
                    let adImageName:String? = UserDefaults.standard.object(forKey: key) as? String
                    if name == adImageName{
                        self.deleteOldCache()
                    }
                    UserDefaults.standard.setValue(name, forKey: key)
                    UserDefaults.standard.setValue(linkUrl, forKey: AdLinkUrl)
                    UserDefaults.standard.setValue(validTime, forKey: AdValidTime)
                    UserDefaults.standard.synchronize()
                }else{
                    print("保存失败")
                }
            }else{
                print("Data为空,请检查您的网络或链接")
            }
        }
    }
    

//点击事件
@objc func toAdVC(){
        //点击广告图时,广告图消失,同时像首页发送通知,并把广告页对应的地址传给首页
        self.dismiss()
        NotificationCenter.default.post(name: NSNotification.Name.init(ToAdVC), object: linkUrl, userInfo: nil)
    }

支持 pod

pod 'MDSplashScreen'

附Demo地址

有什么问题欢迎提出。

相关文章

网友评论

  • 戏子吕戏西施:您好, 图片上的点击方法没有走 要怎么做啊
    z小志:NotificationCenter.default.addObserver(self, selector: #selector(ViewController.toAdVC(notification:)), name: NSNotification.Name.init(ToAdVC), object: nil)
    z小志:@Standingattheto 监听通知

本文标题:Swift 开屏广告的实现 (支持本地与网络的图片,动态图,视频

本文链接:https://www.haomeiwen.com/subject/lwpynxtx.html