Advertisement
Guest User

Untitled

a guest
Feb 13th, 2023
46
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Swift 4.62 KB | Source Code | 0 0
  1. struct ContentView: View {
  2.     let diceTypes: [Int] = [4, 6, 8, 10, 12, 20, 100]
  3.     @Environment(\.accessibilityVoiceOverEnabled) var voiceOverEnabled
  4.    
  5.     @AppStorage("selectedDiceType") var selectedDiceType = 6
  6.     @AppStorage("numberToRoll") var numberToRoll = 4
  7.    
  8.    
  9.     @State private var currentResult = DiceResult(type: 0, number: 0)
  10.    
  11.     let columns: [GridItem] = [
  12.         .init(.adaptive(minimum: 60))
  13.     ]
  14.    
  15.     let timer = Timer.publish(every: 0.1, on: .main, in: .common).autoconnect()
  16.     @State private var stoppedDice = 0
  17.    
  18.     @State private var feedback = UIImpactFeedbackGenerator(style: .rigid)
  19.    
  20.     let savePath = FileManager.documentsDirectory.appendingPathComponent("SavedRolls.json")
  21.     @State private var savedResults = [DiceResult]()
  22.    
  23.     var body: some View {
  24.        
  25.         NavigationStack {
  26.             Form {
  27.                 Section {
  28.                     Picker("Type of dice", selection: $selectedDiceType) {
  29.                         ForEach(diceTypes, id: \.self) { type in
  30.                             Text("D\(type)")
  31.                         }
  32.                     }
  33.                     .pickerStyle(.segmented)
  34.                    
  35.                     Stepper("Number of dices: \(numberToRoll)", value: $numberToRoll, in: 1...20)
  36.                    
  37.                     Button("Roll them", action: rollDice)
  38.                    
  39.                    
  40.                 } footer: {
  41.                     LazyVGrid(columns: columns) {
  42.                         ForEach(0..<currentResult.rolls.count, id: \.self) { rollNumber in
  43.                             Text(String(currentResult.rolls[rollNumber]))
  44.                                 .frame(maxWidth: .infinity, maxHeight: .infinity)
  45.                                 .aspectRatio(1, contentMode: .fit)
  46.                                 .foregroundColor(.black)
  47.                                 .background(.white)
  48.                                 .cornerRadius(10)
  49.                                 .shadow(radius: 3)
  50.                                 .font(.title)
  51.                                 .padding(5)
  52.                         }
  53.                     }
  54.                     .accessibilityElement()
  55.                     .accessibilityLabel("LatestRoll: \(currentResult.description)")
  56.                 }
  57.                 .disabled(stoppedDice < currentResult.rolls.count)
  58.                
  59.                 if savedResults.isEmpty == false {
  60.                     Section("Previous results") {
  61.                         ForEach(savedResults) { result in
  62.                             VStack(alignment: .leading) {
  63.                                 Text("\(result.number) x D\(result.type)")
  64.                                     .font(.headline)
  65.                                
  66.                                 Text(result.description)
  67.                             }
  68.                             .accessibilityElement()
  69.                             .accessibilityLabel("\(result.number) D\(result.type), \(result.description)")
  70.                         }
  71.                     }
  72.                 }
  73.             }
  74.             .navigationTitle("HighRollers")
  75.             .onReceive(timer) { date in
  76.                 updateDice()
  77.             }
  78.             .onAppear(perform: load)
  79.         }
  80.     }
  81.        
  82.     func rollDice() {
  83.         currentResult = DiceResult(type: selectedDiceType, number: numberToRoll)
  84.         if voiceOverEnabled {
  85.             stoppedDice = numberToRoll
  86.             savedResults.insert(currentResult, at: 0)
  87.             save()
  88.         } else {
  89.             stoppedDice = -20
  90.         }
  91.     }
  92.    
  93.     func updateDice() {
  94.         guard stoppedDice < currentResult.rolls.count else { return }
  95.        
  96.         for i in stoppedDice..<numberToRoll {
  97.             if i < 0 { continue }
  98.             currentResult.rolls[i] = Int.random(in: 1...selectedDiceType)
  99.             feedback.impactOccurred()
  100.  
  101.         }
  102.         stoppedDice += 1
  103.        
  104.         if stoppedDice == numberToRoll {
  105.             savedResults.insert(currentResult, at: 0)
  106.             save()
  107.         }
  108.     }
  109.    
  110.     func load() {
  111.         if let data = try? Data(contentsOf: savePath) {
  112.             if let results = try? JSONDecoder().decode([DiceResult].self, from: data) {
  113.                 savedResults = results
  114.             }
  115.         }
  116.     }
  117.  
  118.     func save() {
  119.         if let data = try? JSONEncoder().encode(savedResults) {
  120.             try? data.write(to: savePath, options: [.atomic, .completeFileProtection])
  121.         }
  122.     }
  123.    
  124. }
  125.  
  126. struct ContentView_Previews: PreviewProvider {
  127.     static var previews: some View {
  128.         ContentView()
  129.     }
  130. }
  131.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement