|
Hello, I have a problem with a challenge from a day no 35 of "100 Days of SwiftUI" course. Basically I'm somehow unable to initialize @State variable in my code and the whole view crashes (index out of range for Text(tasks[questionNumber].task) because the array is uninitialized). First, let me explain what my code should do. When the view changes from "Start View" to "Game View" (so, when the user selects options and clicks the button) Game View should generate questions before the view even shows up (I use .onAppear for that, so questions can be properly displayed). However, it just doesn't work - when I look at my code in the debugger I can see that questions are never generated. Quick things about the code: questions are kept as a class of objects and my code tries to initialize that class. Some data shared between Views is kept in a file with @Published variables. Here is my code (functions GenerateTasks and OnAppear are at the end). I also paste some other code that can be helpful to understand the program. Can you please explain me, how can I initialize @State private var tasks with tasks, so that it can finally work? I'm stuck with this problem for a day now and can't find any solution. Game View:
Task set:
Tasks class:
File with data:
I will be very thankful for any help or tips! |
|
First thing to note, is that you call it Second, you mention 2 views, but have only shared one view. The idea here is, the user is shown StartView when the app launches, where they will setup the game... correct? then upon hitting the "start" button, they are taken to GameView. This requires passing data from one view to the other. Accordingly, you should be initializing the data that GameView will be using before navigating to GameView and then pass it on. For that, it is easiest to use For your data, you certainly can use a class. But you could also consider using global constants. It is better to generate the tasks outside of your views. So your Model deals with it. In order to provide more clarity on next steps for you, you will need to share your Start View code. edit: Otherwise you should access the data from your observed object. That's how you gain access to the published properties. Which means your StartViewData should be setting up your game data. It will be accessible via dot syntax |
|
Thanks @MarcusKay. You're right - these are structs. I come from the world of C languages and Java, so I accidentaly used that word. Sorry for that. You're of course correct about Views logic. I'm posting more code (and can share more if needed): This View switches Views (from Start View to Game View after startGame from StartViewData changes it's state):
Start View is generally pretty long and boring (because it generally handles interface and some actions), but here it is. I update StartViewData in this file, so that it can be passed to the Game View:
Could you please give me some hint about |
|
Here's an example that uses 2 views, one as the start which sets up the data, then passes it to the next view.
and in GameView you just declare the binding:
The point of my mentioning You have added a couple layers of unnecessary complication. You could have simply done the following:
and in GameView, instead of using
You use the following only (no need for ObservedObject:
Then once you have the game setup properly, you just call
|
|
Point being, there is no need for classes and observedObject. GameView is only receiving the data. That's all it needs. StartView, is where you present the UI for the user to choose their settings, at which point, you use these details to generate the right questions. Again, what StartView really needs to know is the relevant data to be able to generate the questions, which will then be passed to GameView. |
|
Thank you so much @MarcusKay! Your answers were really helpful. I think that I understand now what should I do to make my program work. I will try to apply the necessary fixes in a few days (because right now I'm pretty overwhelmed with the university stuff). I will then post an update about my progress and whether everything went fine. |
|
I finally got it to work, thank you so much @MarcusKay. Now I clearly understand how passing data in that way works in Swift. I hope that I will finish the project without any more problems. |
SPONSORED Join a FREE crash course for mid/senior iOS devs who want to achieve an expert level of technical and practical skills – it’s the fast track to being a complete senior developer! Hurry up because it'll be available only until February 9th.
Sponsor Hacking with Swift and reach the world's largest Swift community!
This topic has been closed due to inactivity, so you can't reply. Please create a new topic if you need to.
All interactions here are governed by our code of conduct.
Link copied to your pasteboard.