「SwiftUI」监听回调方法

前言:SwiftUI页面写法不再是像UIKit有ViewController,所以通常会在xxxx.delegate = self处报错,没有办法设置delegate,这也从而导致了监听回调函数全部无法使用,而回调函数在很多情况下都需要使用并且可以减少大量的能耗

实现在SwiftUI情况下可以正常使用delegate

ps:拿实现WebSocket功能为例,(WebSocket是一种客户端、服务端可以双向主动通信的网络协议,所以WebSocket需要监听是否有收到相应事件或消息)

  1. 下载添加WebSocket常用第三方库:Starscream

github链接:https://github.com/daltoniam/Starscream.git

  1. 查看GitHub使用方法
//使用方式
var request = URLRequest(url: URL(string: "http://localhost:8080")!)
request.timeoutInterval = 5
socket = WebSocket(request: request)
socket.delegate = self
socket.connect()

它出现了让我们头疼的socket.delegate = self

//监听回调函数
func didReceive(event: WebSocketEvent, client: WebSocket) {
	switch event {
	case .connected(let headers):
		isConnected = true
		print("websocket is connected: \(headers)")
	case .disconnected(let reason, let code):
		isConnected = false
		print("websocket is disconnected: \(reason) with code: \(code)")
	case .text(let string):
		print("Received text: \(string)")
	case .binary(let data):
		print("Received data: \(data.count)")
	case .ping(_):
		break
	case .pong(_):
		break
	case .viabilityChanged(_):
		break
	case .reconnectSuggested(_):
		break
	case .cancelled:
		isConnected = false
	case .error(let error):
		isConnected = false
		handleError(error)
	}
}
//发送String给服务端
socket.write(string: "Hi Server!") 
//example on how to write text over the socket!
  1. 在项目中搭建swift文件,将上述方法都添加进去
    但为了代码可以成功编译,所以将socket.delegate = self注释掉,稍做修改可以成功运行
Swift文件相应代码:
import Foundation
import Starscream

var request = URLRequest(url: URL(string: "ws://192.168.1.110:8001")!)
let socket = WebSocket(request: request)
var isConnected = false


func connect(){
//    socket.delegate = self
    request.timeoutInterval = 5
    socket.connect()
}

// MARK: - WebSocketDelegate
func didReceive(event: WebSocketEvent, client: WebSocket) {
    switch event {
    case .connected(let headers):
        isConnected = true
        print("websocket is connected: \(headers)")
    case .disconnected(let reason, let code):
        isConnected = false
        print("websocket is disconnected: \(reason) with code: \(code)")
    case .text(let string):
        print("Received text: \(string)")
    case .binary(let data):
        print("Received data: \(data.count)")
    case .ping(_):
        break
    case .pong(_):
        break
    case .viabilityChanged(_):
        break
    case .reconnectSuggested(_):
        break
    case .cancelled:
        isConnected = false
    case .error(let error):
        isConnected = false
        handleError(error)
    }
}

func handleError(_ error: Error?) {
    if let e = error as? WSError {
        print("websocket encountered an error: \(e.message)")
    } else if let e = error {
        print("websocket encountered an error: \(e.localizedDescription)")
    } else {
        print("websocket encountered an error")
    }
}

// MARK: Write Text Action
func start(){
    socket.write(string: "start")
}

func end(){
    socket.write(string: "end")
}

可以实现发数据给服务端,但是服务端发送的信息,客户端无法收到,问题应该就在没有添加delegate,导致监听函数没有起作用

解决办法:

新建一个xxWebSocket类,并设置为NSObject, WebSocketDelegate类,直接贴代码

相应xxWebSocket类
import Foundation
import Starscream

class xxWebSocket:NSObject, WebSocketDelegate{
    var socket:WebSocket?
    
    //收到事件回调
    func didReceive(event: WebSocketEvent, client: WebSocketClient) {
        debugPrint("didReceive event")
        switch event {
        case .connected(let headers):
            isConnected = true
            debugPrint("websocket is connected: \(headers)")
            debugPrint("socket connect")
        case .disconnected(let reason, let code):
            isConnected = false
            print("websocket is disconnected: \(reason) with code: \(code)")
        case .text(let string):
            print("Received text: \(string)")
        case .binary(let data):
            print("Received data: \(data.count)")
        case .ping(_):
            break
        case .pong(_):
            break
        case .viabilityChanged(_):
            break
        case .reconnectSuggested(_):
            break
        case .cancelled:
            isConnected = false
        case .error(let error):
            isConnected = false
            handleError(error)
        }
    }
   
   
   public func connectServer(urlStr:String){
       var request = URLRequest(url: URL(string: urlStr)!)
       request.timeoutInterval = 5
       socket = WebSocket(request: request)
       socket?.delegate = self
       socket?.connect()
   }
   
   public func disconnect(){
       socket?.disconnect()
   }
   
   public func sendData(data:Data){
       socket?.write(data: data) {
           debugPrint("sendData callback")
       }
   }
   
   public func sendString(str:String){
       socket?.write(string: str) {
           debugPrint("send string completion \(str)")
       }
   }
}

还可以写一个自定义方法类的Delegate,实现监听操作自定义

方法类:
protocol xxWebSocketDelegate : NSObjectProtocol{
     func websocketDidConnect(socket: xxWebSocket, data: Any)
    
     func websocketDidDisconnect(socket: xxWebSocket, error:NSError?)
    
     func websocketDidReceiveMessage(socket:xxWebSocket, text: String)
    
     func websocketDidReceiveData(socket: xxWebSocket, data: NSData)
}

//需要在xxWebSocket类中进行weak var webSocketDelegate: xxWebSocketDelegate?弱引用
//然后就可以在xxWebSocket中进行调用该自定义监听方法

以上方法即可实现在SwiftUI情况下也使用delegate,进行监听操作

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

淡酒交魂

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值