Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/115.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios 在SwiftUI视图和ObserveObject的init()中调用函数_Ios_Swift_Swiftui_Agora.io_Observableobject - Fatal编程技术网

Ios 在SwiftUI视图和ObserveObject的init()中调用函数

Ios 在SwiftUI视图和ObserveObject的init()中调用函数,ios,swift,swiftui,agora.io,observableobject,Ios,Swift,Swiftui,Agora.io,Observableobject,因此,我有一些视图的数据获取任务(类型:View),需要在加载视图后立即运行这些任务。如果我把它们放在.onAppear{}中,它们不会在正确的时间加载。所以我必须把它们放在结构的init(){}块中 此外,我还有从视图模型获取数据的任务。这些也需要立即运行,如果我在.onAppear{}中调用它们,就太晚了,程序将无法加载数据。所以我把这些函数也放在init(){}块中 问题出在这里。它初始化了很多次。我每天在Firestore上阅读3K,我是唯一一个使用该应用程序的人。当我连接语音聊天应用程

因此,我有一些视图的数据获取任务(类型:
View
),需要在加载视图后立即运行这些任务。如果我把它们放在
.onAppear{}
中,它们不会在正确的时间加载。所以我必须把它们放在结构的
init(){}
块中

此外,我还有从视图模型获取数据的任务。这些也需要立即运行,如果我在
.onAppear{}
中调用它们,就太晚了,程序将无法加载数据。所以我把这些函数也放在
init(){}
块中

问题出在这里。它初始化了很多次。我每天在Firestore上阅读3K,我是唯一一个使用该应用程序的人。当我连接语音聊天应用程序时,它会加入
init(){}
上的频道,但随后它会尝试加入17次

所以我的问题是:如何在视图初始化的同时调用函数,但确保每次加载视图时只运行一次

下面是我的代码中的一些示例,以提供进一步的见解

struct VoiceChatView: View {
    @State var halfModalShown = false
    @State var settingsModalShown = false
    @Binding var topic : Topic
    @State var channel : Channel
    
    @State var isLocalAudioMuted = false
    private let audioEngine = AudioEngine()
    private var rtcEngine: AgoraRtcEngineKit {
        get {
            return audioEngine.agoraKit
        }
    }
    
    @State var currentUser = AuthViewModel.shared.user!
    
    @Environment(\.presentationMode) var presentationMode: Binding<PresentationMode>
    
    init(topic: Binding<Topic>, channel: Channel) {
        self._topic = topic
        self._channel = State(initialValue: channel)
        self.callOnce()
    }


    var body: some View {
        Text("Hello, world")
    }
}
structVoiceChatView:View{
@状态变量halfModalShown=false
@状态变量设置SmodalShowed=false
@绑定变量主题:主题
@状态变量通道:通道
@状态变量IsLocalLaudioMutte=false
私有let audioEngine=audioEngine()
专用var rtcEngine:AgoraRtcEngineKit{
得到{
return audioEngine.agoraKit
}
}
@状态变量currentUser=AuthViewModel.shared.user!
@环境(\.presentationMode)变量presentationMode:绑定
初始化(主题:绑定,通道:通道){
self.\u topic=主题
self.\u通道=状态(初始值:通道)
self.callOnce()
}
var body:一些观点{
文本(“你好,世界”)
}
}

如果查看
callOnce()
,您会注意到它被多次调用。我需要在其他事情发生之前打电话,是的。但是我不需要它不断地反复调用。

你能试试
init
方法中的措辞吗

init(主题:绑定,通道:通道){
self.\u topic=主题
self.\u通道=状态(初始值:通道)
//self.callOnce()
如果是自动通道{
self.callOnce()
}
}

您可以将正在执行的函数或工作放在视图的init中,放在类/模式的init中。千万不要在这类工作中使用View init,SwiftUI只需在这里和那里初始化视图,并且在它认为必须的任何时候,所以千万不要这样做

即使您可以定义控制某些数据的条件!这是错误的代码设计


您可以设置一个条件,让视图等待类开始渲染,以防万一。

您需要将模型与视图分离。视图是结构。它们应该是轻便的和一次性的;SwiftUI将根据需要创建和处理视图。您的模型通常是一个类。它将有更长的寿命。通过将模型作为参数传递或使用环境将其注入视图中。SwiftUI视图不需要
init
。在许多情况下,甚至在外观上也不需要
on