Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Level Up Your Skills: Menjadi iOS Developer Andal

Avatar for Zahrina Zahrina
January 17, 2025
10

Level Up Your Skills: Menjadi iOS Developer Andal

Dicoding Ignite: Path to iOS Engineering adalah acara spesial bagi para pembeli kelas satuan iOS di Dicoding. Event ini bertujuan untuk membantu iOS Developer yang sudah memiliki dasar pengetahuan untuk naik ke level berikutnya. Fokus utama adalah membangun aplikasi dengan SwiftUI, memahami manajemen data, dan menggunakan API. Peserta akan mendapatkan tips dan trik untuk meningkatkan kualitas aplikasi yang mereka buat.

Avatar for Zahrina

Zahrina

January 17, 2025
Tweet

More Decks by Zahrina

Transcript

  1. Learning Objectives • Menguasai SwiftUI untuk UI Modern • Integrasi

    API ke Aplikasi iOS • Manajemen Data di iOS • Meningkatkan Kinerja dan User Experience • Panduan untuk Karier Profesional Ignite #3: iOS Dev
  2. Perkembangan SwiftUI SwiftUI 5.0 - Macros - Improved Scroll Performance

    - Interactivity in Charts - Scene Management Updates - SwiftData - MapKit Improvements 2023 SwiftUI 4.0 - NavigationStack & NavigationSplitView - Resizable Bottom Sheets - Grid Layout - ShareLink - Improvements to Charts - Enhanced ScrollView 2022 SwiftUI 3.0 - List, Form, dan Grid Improvements - AsyncImage - Material - Accessibility Improvements - iOS 15 Focus Mode Support - Markdown Support in Text 2021 SwiftUI 2.0 - WidgetKit - Appearance Modifier - ProgressView - Menus dan Context Menus - Multiplatform app templates - Lifecycle API baru 2020 SwiftUI 1.0 - Debut rilis - Deklaratif dan reaktif - Cross-platform - Integrasi dengan UIKit dan AppKit - Hot-reload dengan Xcode Previews 2019 SwiftUI 6.0 - Custom Containers - Accessibility Enhancements - Improved Xcode Previews - Text Selection and Suggestions - Graphics and Animations - SF Symbols 6 2024 Ignite #3: iOS Dev
  3. Ignite #3: iOS Dev • Menambahkan TableView di Storyboard. •

    Hubungkan TableView dengan View Controller. • Membuat TableViewCell beserta XIB file-nya. • Susun tampilan TableViewCell. • Hubungkan TableViewCell dengan kelas UITableViewCell. • Siapkan data yang diperlukan. • Menambahkan delegation dataSource di TableView. • Mendaftarkan TableViewCell ke TableView. • Mengatur delegation dari TableView. • Menjalankan aplikasi. UIKit • Siapkan data yang diperlukan. • Menyusun AcademyItemView. • Menggabungkan AcademyItemView dengan ContentView. • Menjalankan aplikasi. SwiftUI
  4. Ignite #3: iOS Dev SwiftUI Perbedaan UIKit Menggunakan View sebagai

    elemen dasar untuk membangun UI, di mana semua tampilan dideklarasikan sebagai struktur fungsional. 2 Manajemen Tampilan Menggunakan UIView dan UIViewController sebagai elemen dasar. Dilengkapi dengan Xcode Previews, yang memungkinkan developer melihat pratinjau UI secara real-time saat menulis kode tanpa harus menjalankan aplikasi sepenuhnya. 3 Alat Pengembangan Tidak memiliki fitur preview langsung. Developer harus menjalankan aplikasi di simulator atau perangkat fisik setiap kali ingin melihat perubahan pada UI. Menggunakan property wrapper seperti State, Binding, ObservedObject, dan EnvironmentObject untuk manajemen data dan sinkronisasi antara UI dan data secara otomatis. 4 Pengelolaan Data Tidak memiliki konsep ini. Developer biasanya harus menggunakan delegates, closures, atau notifications untuk mengelola pembaruan data dan UI. Menggunakan struktur App untuk mendeklarasikan siklus hidup aplikasi, yang lebih ringkas dan mudah diatur dibandingkan UIKit. 5 Lifecycle Management Menggunakan UIApplicationDelegate dan UIViewController untuk mengelola siklus hidup aplikasi dan tampilan, yang lebih kompleks. Deklaratif, di mana developer mendeklarasikan apa yang harus ditampilkan dan bagaimana UI berinteraksi dengan data. 1 Pendekatan Pemrograman Imperatif, yang berarti developer harus secara eksplisit menentukan setiap perubahan pada UI melalui kode.
  5. Scene Architecture Ignite #3: iOS Dev @main struct DicodingApp: App

    { var body: some Scene { WindowGroup { ContentView() } } }
  6. task(priority:_:) execute asynchronously before the view appears on screen View

    Lifecycle Events Ignite #3: iOS Dev onAppear(perform:) any time the view appears on screen onDisappear(perform:) when a view disappears from screen active inactive
  7. Example Ignite #3: iOS Dev @State private var isPlaying: Bool

    = false var body: some View { VStack { Text("Apakah kamu menyukai Coding?") .padding() Button(action: { self.isLove.toggle() // false -> true }) { Image(systemName: isLove ? "heart.fill" : "heart") } } }
  8. Example Ignite #3: iOS Dev struct ContentView: View { @State

    private var isLove: Bool = false var body: some View { VStack { Text("Apakah kamu menyukai Coding?") .padding() LoveButton(isLove: $isLove) } } } struct LoveButton: View { @Binding var isLove: Bool var body: some View { Button(action: { self.isLove.toggle() }) { Image(systemName: isLove ? "heart.fill" : "heart") } } }
  9. Observable Class Ignite #3: iOS Dev @Published name @Published isEnabled

    DataModel @StateObject var model MySubView(model: model) MyView @ObservedObject var model MySubView
  10. struct MyView: View { @StateObject private var model = DataModel()

    var body: some View { Text(model.name) MySubView(model: model) } } Observable Class Ignite #3: iOS Dev class DataModel: ObservableObject { @Published var name = "Some Name" @Published var isEnabled = false } struct MySubView: View { @ObservedObject var model: DataModel var body: some View { Toggle("Enabled", isOn: $model.isEnabled) } }
  11. MySubView() .environmentObject(model) Observable Class Ignite #3: iOS Dev @Published name

    @Published isEnabled DataModel @StateObject var model MySubView(model: model) MyView @ObservedObject var model MySubView @EnvironmentObject var model MySubView
  12. struct MyView: View { @StateObject private var model = DataModel()

    var body: some View { Text(model.name) MySubView() .environmentObject(model) } } struct MySubView: View { @ObservedObject var model: DataModel var body: some View { Toggle("Enabled", isOn: $model.isEnabled) } } class DataModel: ObservableObject { @Published var name = "Some Name" @Published var isEnabled = false } Environment Object Ignite #3: iOS Dev class DataModel: ObservableObject { @Published var name = "Some Name" @Published var isEnabled = false }
  13. User Default Ignite #3: iOS Dev User Default tempat untuk

    menyimpan pasangan key-value secara persisten di seluruh peluncuran aplikasi Anda. Untuk menyimpan data sensitif seperti token dan password, jangan melakukannya di User Default, tetapi gunakan Keychain.
  14. Swift Data Ignite #3: iOS Dev @Model class Book {

    var title: String var author: String init(title: String, author: String) { self.title = title self.author = author } } class MemberProvider { lazy var persistentContainer: NSPersistentContainer = { let container = NSPersistentContainer(name: "MemberDicoding") container.loadPersistentStores { _, error in guard error == nil else { fatalError("Unresolved error \(error!)") } } container.viewContext.automaticallyMergesChangesFromParent = false container.viewContext.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy container.viewContext.shouldDeleteInaccessibleFaults = true container.viewContext.undoManager = nil return container }() }
  15. Ignite #3: iOS Dev struct ContentView: View { @Environment(\.modelContext) private

    var context @State private var title = "" @State private var author = "" // Menampilkan Data @Query var books: [Book] var body: some View { ... } // Menambahkan Data private func addBook() { let newBook = Book(title: title, author: author) context.insert(newBook) title = "" author = "" } // Menghapus Data private func deleteBook(at offsets: IndexSet) { for index in offsets { let book = books[index] context.delete(book) } } } @main struct MyApp: App { var body: some Scene { WindowGroup { ContentView() .modelContainer(for: Book.self) } } }
  16. Concurrency Concurrency adalah kemampuan komputer untuk melakukan beberapa tugas atau

    pekerjaan secara bersamaan. Setiap aplikasi yang prosesnya cukup memakan waktu sebaiknya menggunakan concurrency. Ignite #3: iOS Dev
  17. Thread Thread adalah sekumpulan instruksi yang akan dijalankan di runtime.

    Setiap proses memiliki minimal 1 thread. Di iOS, proses utama ketika aplikasi dijalankan disebut main thread. Di sinilah semua proses yang berhubungan dengan UI dibuat dan diatur. Ignite #3: iOS Dev
  18. Grand Central Dispatch Sebuah pendekatan desain untuk membantu kita melakukan

    manajemen thread tanpa perlu membuat thread secara manual. Pada dasarnya dispatch itu adalah antrian yang di dalamnya terdapat tugas-tugas yang harus dikerjakan. Ignite #3: iOS Dev
  19. Dispatch Queue • Main dispatch queue: dieksekusi secara serial dan

    bisa langsung digunakan. • Global queues: dieksekusi secara concurrent dan bisa langsung digunakan. • Private queues: dieksekusi secara serial atau concurrent. Developer harus membuatnya terlebih dahulu. Ignite #3: iOS Dev
  20. Serial vs Concurrent Queue • Serial Queue akan mengeksekusi tugas

    yang diberikan secara berurutan, dan tidak akan melanjutkan tugas berikutnya sebelum tugas yang sedang dikerjakan selesai. • Mengeksekusi tugas secara berurutan, tetapi antrian concurrent tidak perlu menunggu tugas pertama selesai untuk memulai tugas berikutnya. Dengan Concurrent Queue, sistem dapat membuat multiple threads untuk menyelesaikan tugas yang ada. Ignite #3: iOS Dev
  21. Synchronous vs Asynchronous Queue • Metode ini akan menyebabkan blocking

    di thread pemanggil. Dengan menggunakan sync maka thread pemanggil akan menunggu tugas-tugas yang ada di dalam antrian selesai dieksekusi baik secara serial ataupun concurrent. • Kebalikan dari metode sinkron, metode ini akan langsung mengembalikan kontrol ke thread pemanggil setelah task dimasukkan ke dalam antrian tanpa perlu menunggu sampai selesai. Metode asinkron tidak akan melakukan blocking di thread pemanggil. iOS Developer
  22. Contoh Kode iOS Developer Ignite #3: iOS Dev let serial

    = DispatchQueue( label: "com.dicoding.sync.serial" ) serial.sync { for _ in 0..<5 { print("red") } } serial.sync { for _ in 0..<5 { print("blue") } } print("Proses selanjutnya") let concurrent = DispatchQueue( label: "com.dicoding.sync.concurrent", attributes: .concurrent ) concurrent.async { for _ in 0..<5 { print("red") } } concurrent.async { for _ in 0..<5 { print("blue") } } print("Proses selanjutnya")
  23. func expensiveTask( data: String, completion: @escaping (String) -> Void )

    { let queue = DispatchQueue( label: "com.dicoding.completionblock" ) queue.async { print("Processing: \(data)") sleep(2) // Imitate expensive task completion("Processing \(data) finished") } } let mainQueue = DispatchQueue( label: "com.dicoding.main", qos: .userInteractive ) mainQueue.async { expensiveTask(data: "Get User") { result in print(result) } print("Main Queue Run") } Completion Block (callback) Sebuah kode di mana Anda memakainya untuk menghubungkan satu thread ke thread lainnya (thread dependency). Completion Block sendiri sebenarnya adalah sebuah Closure, yang artinya Anda harus mengirimkan sebuah fungsi (function) sebagai parameter. Ignite #3: iOS Dev
  24. Asynchronous Function Sebuah function atau method spesial yang dapat ditangguhkan

    (suspended) ketika runtime. Berbeda dengan synchronous function karena ketika function dipanggil, ia akan menjalankan completion, mengembalikan sebuah error, atau tidak mengembalikan apa pun. Ignite #3: iOS Dev
  25. Ignite #3: iOS Dev Membuat Function func getMovies(completionBlock: (_ movies:

    [MovieModel]) -> Void) { let movies = // Proses async untuk mendapatkan data movies dari API. completionBlock(movies) } func downloadPhoto(url: String, completionBlock: (_ poster: UIImage) -> Void) { let poster = // Proses async untuk mendapatkan poster dari API. completionBlock(poster) } Delegation func getMovies() async -> [MovieModel]) { let movies = // Proses async untuk mendapatkan data movies dari API. return movies } func downloadPhoto(url: String) async -> UIImage) { let poster = // Proses async untuk mendapatkan poster dari API. return poster } Async Await
  26. Ignite #3: iOS Dev Pemanggilan Function getMovies() { movies in

    let newMovie = movies[movies.count-1] downloadPhoto(url: newMovie.poster) { poster { show(poster) } } let movies = await getMovies() let newMovie = movies[movies.count-1] let poster = await downloadPhoto(url: newMovie.poster) show(poster) Delegation Async Await
  27. Combine Menangani secara khusus asynchronous events dengan mengombinasikan operator event-processing.

    • Publisher : sumber atau sesuatu yang menghasilkan nilai. • Operator : sesuatu yang dapat bekerja dengan nilai tersebut. • Subscriber : sesuatu yang peduli dengan nilai-nilai tersebut. Ignite #3: iOS Dev
  28. API Contract An API contract is like a formal agreement

    or set of rules between the Android (front-end) and back-end development teams when creating software. Communication Consistency • Accelerating Integration Processes • Improved Development Efficiency • Maintaining Good Documentation iOS Developer Endpoint Name: Get All User Base URL: https://reqres.in URL Params: /api/users?page=1&per_page=10 Method: GET Response (JSON): { "page": Int, "per_page": Int, "total": Int, "total_pages": Int, "data": [ { "id": Int, "email": String, "first_name": String, "last_name": String, "avatar": String } ] }
  29. API Parameter For Example : https://reqres.in/api/users?page=1&per_page=10 • Path : “usersˮ

    • Query 1 : “pageˮ with value “1ˮ. • Query 2 : “per_pageˮ with value “10ˮ. • Use “?ˮ as separator before first parameter. • Use “&ˮ as separator for the next parameter. • Use “=ˮ to fill query with value. Ignite #3: iOS Dev
  30. URL Session URLSession adalah objek yang disediakan oleh Apple untuk

    melakukan koordinasi tugas transfer data antar jaringan. Ignite #3: iOS Dev URLSession.shared.dataTask(with: url)
  31. URL Component Sebuah struktur yang membaca alamat web URL menjadi

    bagian-bagian kecilnya dan juga membangun alamat web dari bagian-bagian tersebut. Ignite #3: iOS Dev var components = URLComponents(string: "https://api.themoviedb.org/3/movie/popular")! components.queryItems = [ URLQueryItem(name: "api_key", value: apiKey), URLQueryItem(name: "language", value: language), URLQueryItem(name: "page", value: page) ] https://api.themoviedb.org/3/movie/popular?api_key=apiKey&language=language&page=page
  32. Method GET Gunakan Data Task untuk berkomunikasi dengan API melalui

    metode GET. DataTask terdiri dari 3 output. • data • response • error Ignite #3: iOS Dev let request = URLRequest(url: components.url!) let task = URLSession.shared .dataTask(with: request) { data, response, error in guard let response = response as? HTTPURLResponse else { return } if let data = data { // MARK: Di sini digunakan untuk mengelola data API. } }
  33. Parsing JSON Ignite #3: iOS Dev struct MovieResponse: Codable {

    let popularity: Double let posterPath: String let title: String let genres: [Int] let voteAverage: Double let overview: String let releaseDate: String enum CodingKeys: String, CodingKey { case popularity case posterPath = "poster_path" case title case genres = "genre_ids" case voteAverage = "vote_average" case overview case releaseDate = "release_date" } } struct MovieResponses: Codable { let page: Int let totalResults: Int let totalPages: Int let movies: [MovieResponse] enum CodingKeys: String, CodingKey { case page case totalResults = "total_results" case totalPages = "total_pages" case movies = "results" } }
  34. Parsing JSON Ignite #3: iOS Dev let decoder = JSONDecoder()

    if let movies = try? Decoder .decode(MovieResponses.self, from: data) as MovieResponses { print("PAGE: \(movies.page)") print("TOTAL RESULTS: \(movies.totalResults)") print("TOTAL PAGES: \(movies.totalPages)") movies.movies.forEach { movie in print("TITLE: \(movie.title)") print("POSTER: \(movie.posterPath)") print("DATE: \(movie.releaseDate)") } } else { print("ERROR: Can't Decode JSON") }
  35. Custom Value iOS Developer struct MovieResponse: Codable { ... init(from

    decoder: Decoder) throws { let container = try decoder.container(keyedBy: CodingKeys.self) // MARK: Menentukan alamat gambar let path = try container.decode(String.self, forKey: .posterPath) posterPath = "https://image.tmdb.org/t/p/w300\(path)" // MARK: Mementukan tanggal rilis let dateString = try container.decode(String.self, forKey: .releaseDate) let dateFormatter = DateFormatter() dateFormatter.dateFormat = "yyyy-MM-dd" releaseDate = dateFormatter.date(from: dateString)! // MARK: Untuk properti lainnya, cukup disesuaikan saja. popularity = try container.decode(Double.self, forKey: .popularity) ...
  36. Method Post Ignite #3: iOS Dev var request = URLRequest(url:

    components.url!) request.httpMethod = "POST" request.setValue("application/json", forHTTPHeaderField: "Content-Type") let jsonRequest = [ "value": 9.0 ] let jsonData = try! JSONSerialization.data(withJSONObject: jsonRequest, options: []) let task = URLSession.shared.uploadTask(with: request, from: jsonData) { data, response, error in guard let response = response as? HTTPURLResponse, let data = data else { return } if response.statusCode == 201 { print("DATA: \(data)") } } task.resume()
  37. Ignite #3: iOS Dev Kepuasan Pengguna adalah Segalanya 󰺖 Bintang

    satu dulu ya, kalau sudah diperbaiki saya kasih bintang lima
  38. Penentuan Warna Warna menjadi indikator yang penting. Color Emotion Guide:

    Setiap warna memiliki artinya masing-masing. Contohnya warna merah mencerminkan kasih sayang dan cinta. Ignite #3: iOS Dev
  39. Tipografi Tipografi adalah ilmu cetak atau seni percetakan. Teks yang

    sama, maknanya bisa menjadi berbeda. Oleh karena itu, kenali karakteristik setiap jenis font yang digunakan. Ignite #3: iOS Dev
  40. User Interface UI Desain antarmuka pengguna adalah desain untuk komputer,

    peralatan, mesin, perangkat komunikasi mobile, aplikasi perangkat lunak, dan situs web yang berfokus pada pengalaman dan interaksi pengguna. Ignite #3: iOS Dev
  41. Guide UI Design • Sebuah Aplikasi Memiliki Perjalanan/Journey • Efisien

    dalam Penggunaan Alignment • Interaction Design Ignite #3: iOS Dev
  42. Guide UI Design • Sebuah Aplikasi Memiliki Perjalanan/Journey • Efisien

    dalam Penggunaan Alignment • Interaction Design • Gunakanlah Lo Fi Design Ignite #3: iOS Dev
  43. Guide UI Design • Sebuah Aplikasi Memiliki Perjalanan/Journey • Efisien

    dalam Penggunaan Alignment • Interaction Design • Gunakanlah Lo Fi Design • Usahakan Teks Terlihat pada Gambar Ignite #3: iOS Dev
  44. Guide UI Design • Sebuah Aplikasi Memiliki Perjalanan/Journey • Efisien

    dalam Penggunaan Alignment • Interaction Design • Gunakanlah Lo Fi Design • Usahakan Teks Terlihat pada Gambar Ignite #3: iOS Dev
  45. Guide UI Design • Sebuah Aplikasi Memiliki Perjalanan/Journey • Efisien

    dalam Penggunaan Alignment • Interaction Design • Gunakanlah Lo Fi Design • Usahakan Teks Terlihat pada Gambar Ignite #3: iOS Dev
  46. User Experience User experience adalah cara seseorang merasakan ketika menggunakan

    sebuah produk, sistem, atau jasa. Ignite #3: iOS Dev
  47. Guide UX Design 1. Usability 2. Asking for Permission 3.

    User Profiling 4. Form vs Function Ignite #3: iOS Dev
  48. Guide UX Design 1. Usability 2. Asking for Permission 3.

    User Profiling 4. Form vs Function Ignite #3: iOS Dev
  49. Guide UX Design 1. Usability 2. Asking for Permission 3.

    User Profiling 4. Form vs Function 5. Consistency Ignite #3: iOS Dev
  50. Guide UX Design 1. Usability 2. Asking for Permission 3.

    User Profiling 4. Form vs Function 5. Consistency 6. Simplicity Ignite #3: iOS Dev
  51. iOS vs Android Dalam membangun aplikasi iOS, ada beberapa hal

    yang perlu Anda perhatikan. • Navigation • Judul Sebuah Halaman • Icon Ignite #3: iOS Dev
  52. iOS Design Guidelines Lakukan beberapa hal berikut sebelum membangun tampilan

    aplikasi iOS. 1. Design Pattern and Color Pattern Ignite #3: iOS Dev
  53. iOS Design Guidelines Lakukan beberapa hal berikut sebelum membangun tampilan

    aplikasi iOS. 1. Design Pattern and Color Pattern 2. User Flow Diagram Ignite #3: iOS Dev
  54. iOS Design Guidelines Lakukan beberapa hal berikut sebelum membangun tampilan

    aplikasi iOS. 1. Design Pattern and Color Pattern 2. User Flow Diagram 3. Wireframe (lo-fi) Ignite #3: iOS Dev
  55. iOS Design Guidelines Lakukan beberapa hal berikut sebelum membangun tampilan

    aplikasi iOS. 1. Design Pattern and Color Pattern 2. User Flow Diagram 3. Wireframe (lo-fi) 4. Mockup (hi-fi) Ignite #3: iOS Dev
  56. iOS Design Guidelines Lakukan beberapa hal berikut sebelum membangun tampilan

    aplikasi iOS. 1. Design Pattern and Color Pattern 2. User Flow Diagram 3. Wireframe (lo-fi) 4. Mockup (hi-fi) 5. Animated App Prototype Ignite #3: iOS Dev
  57. • Concurrency Model yang Diperbarui a. Global Actors b. Task

    Cancellation c. AsyncSequence Enhancements • Memperbaiki Penggunaan Memori a. Ownership Model • Peningkatan pada Error Handling • Swift Testing Swift 6.0 Ignite #3: iOS Dev
  58. Swift Testing is a new framework with expressive and intuitive

    APIs that make testing your Swift code a breeze. Swift Testing Ignite #3: iOS Dev
  59. SwiftData makes it easy to persist data using declarative code.

    You can query and filter data using regular Swift code. And itʼs designed to integrate seamlessly with SwiftUI. Swift Data Ignite #3: iOS Dev
  60. Swift Charts is a powerful and concise SwiftUI framework you

    can use to transform your data into informative visualizations. Swift Chart Ignite #3: iOS Dev