Integration Options/Custom Workout

Custom Workout

Create and execute personalized workout sequences with custom exercises, repetitions, durations, and rest periods. Define your own workout flow with full control over exercise order and timing.


How it works:

1. Initialize the SDK with custom workout integration option

2. Pass your custom workout exercises array

3. Wait for all_resources_loaded message

4. Send workout_activity_action: start to begin


WorkoutSequenceExercise Parameters:

  • exerciseId - Exercise ID from KinesteX API or admin panel
  • reps - Number of repetitions
  • duration - Duration in seconds (null = unlimited time for reps)
  • includeRestPeriod - Include rest period before exercise
  • restDuration - Rest duration in seconds

Tip: To create sets, duplicate the same exercise in the array multiple times.

Custom Workout Setup
1@State var workoutAction: [String: Any]? = nil
2
3let exercises = [
4    WorkoutSequenceExercise(
5        exerciseId: "jz73VFlUyZ9nyd64OjRb",
6        reps: 15,
7        duration: nil,
8        includeRestPeriod: true,
9        restDuration: 20
10    ),
11    WorkoutSequenceExercise(
12        exerciseId: "ZVMeLsaXQ9Tzr5JYXg29",
13        reps: 10,
14        duration: 30,
15        includeRestPeriod: true,
16        restDuration: 15
17    ),
18    WorkoutSequenceExercise(
19        exerciseId: "gJGOiZhCvJrhEP7sTy78",
20        reps: 20,
21        duration: nil,
22        includeRestPeriod: false,
23        restDuration: 0
24    )
25]
26
27kinestex.createCustomWorkoutView(
28    exercises: exercises,
29    user: userDetails,
30    style: nil,
31    isLoading: $isLoading,
32    workoutAction: $workoutAction,
33    onMessageReceived: { message in
34        if case .custom_type(let value) = message,
35           let type = value["type"] as? String,
36           type == "all_resources_loaded" {
37            // Start workout when resources are ready
38            workoutAction = ["workout_activity_action": "start"]
39        }
40    }
41)

Complete Example

Full implementation with state management, loading indicators, and proper message handling.

Complete Implementation
1import SwiftUI
2import KinesteXAIKit
3
4struct CustomWorkoutView: View {
5    @State private var showKinesteX = false
6    @State private var isLoading = false
7    @State private var allResourcesLoaded = false
8    @State var workoutAction: [String: Any]? = nil
9
10    // Initialize KinesteXAIKit with your credentials
11    let kinestex = KinesteXAIKit(
12        apiKey: "YOUR_API_KEY",
13        companyName: "YOUR_COMPANY_NAME",
14        userId: "YOUR_USER_ID"
15    )
16
17    // Define custom workout exercises
18    let exercises = [
19        WorkoutSequenceExercise(
20            exerciseId: "jz73VFlUyZ9nyd64OjRb",
21            reps: 15,
22            duration: nil,
23            includeRestPeriod: true,
24            restDuration: 20
25        ),
26        WorkoutSequenceExercise(
27            exerciseId: "ZVMeLsaXQ9Tzr5JYXg29",
28            reps: 10,
29            duration: 30,
30            includeRestPeriod: true,
31            restDuration: 15
32        ),
33        WorkoutSequenceExercise(
34            exerciseId: "gJGOiZhCvJrhEP7sTy78",
35            reps: 20,
36            duration: nil,
37            includeRestPeriod: false,
38            restDuration: 0
39        )
40    ]
41
42    var body: some View {
43        VStack {
44            Text("Custom Workout")
45                .font(.title)
46                .padding()
47
48            Spacer()
49
50            Button(action: {
51                showKinesteX.toggle()
52            }) {
53                Text("Start Custom Workout")
54                    .font(.title3)
55                    .foregroundColor(.white)
56                    .bold()
57                    .padding()
58                    .frame(maxWidth: .infinity)
59                    .background(Color.green.cornerRadius(10))
60                    .padding(.horizontal)
61            }
62
63            Spacer()
64        }
65        .fullScreenCover(isPresented: $showKinesteX) {
66            kinestex.createCustomWorkoutView(
67                exercises: exercises,
68                user: nil,
69                style: nil,
70                isLoading: $isLoading,
71                workoutAction: $workoutAction,
72                onMessageReceived: { message in
73                    switch message {
74                    case .custom_type(let value):
75                        guard let type = value["type"] as? String else { return }
76                        if type == "all_resources_loaded" {
77                            allResourcesLoaded = true
78                            // Start workout when resources are ready
79                            workoutAction = ["workout_activity_action": "start"]
80                        }
81                    case .exit_kinestex(_):
82                        showKinesteX = false
83                        allResourcesLoaded = false
84                    case .workout_overview(let data):
85                        print("Workout overview: \(data)")
86                    case .error_occurred(let data):
87                        print("Error: \(data)")
88                    default:
89                        print("Message received: \(message)")
90                    }
91                }
92            )
93        }
94    }
95}
96
97#Preview {
98    CustomWorkoutView()
99}

Need Help?

Our team is ready to assist with your integration.

Contact Support