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

iOSのウィジェットでも猫走らせたい / iOSDC Japan 2022 Day2 Unconference

iOSのウィジェットでも猫走らせたい / iOSDC Japan 2022 Day2 Unconference

iOSDC Japan 2022 Day2 14:00~ Unconference トーク

Kyome (Takuto Nakamura)

September 12, 2022
Tweet

More Decks by Kyome (Takuto Nakamura)

Other Decks in Programming

Transcript

  1. iOSDC Japan 2022 - Unconference #iosdc #unconference ࣗݾ঺հ IUUQTLZPNFJP ,ZPNF

    ,ZPNFTVLF macOS޲͚ͷϢʔςΟϦςΟΞϓϦ։ൃऀʢझຯ݉෭ۀʣ ϝχϡʔόʔৗறܕΞϓϦɺApp Extension ͕ಘҙ෼໺ ීஈ͸αΠϘ΢ζͰ kintoneϞόΠϧ ։ൃ͍ͯ͠·͢ʂ
  2. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? RunCat

    macOS ޲͚ͷϝχϡʔόʔৗறܕΞϓϦ ೣͷ૸ΔεϐʔυͰ CPU ෛՙ͕Θ͔Δ
 ΞΫςΟϏςΟɾΠϯδέʔλʔ
  3. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? macOS൛ͷRunCat͸

    CAKeyframeAnimation Λ࢖ͬͯύϥύϥອը ͷཁྖͰΞχϝʔγϣϯ͍ͯ͠Δʢແݶϧʔϓʣ ఆظతʹCPUෛՙΛऔಘͯ͠ɺͦͷ஋ʹج͍ͮͯΞχϝʔγϣϯͷ speed Λߋ৽͍ͯ͠Δ cat-0 cat-1 cat-2 cat-3 cat-4 Speed
  4. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? speed

    Λߋ৽͢ΔࡍʹΞχϝʔγϣϯ͕Ϧηοτ͞ΕΔͷͰɺ
 ରࡦ͠ͳ͍ͱΞχϝʔγϣϯ͕ΨΫΨΫͯ͠͠·͏ ☝︎ ͜Μͳײ͡
  5. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? speed

    Λߋ৽͢ΔࡍʹΞχϝʔγϣϯ͕Ϧηοτ͞ΕΔͷͰɺ
 ରࡦ͠ͳ͍ͱΞχϝʔγϣϯ͕ΨΫΨΫͯ͠͠·͏ cat-0 cat-1 cat-2 cat-3 cat-4 Speed มߋ
  6. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? speed

    Λߋ৽͢ΔࡍʹΞχϝʔγϣϯ͕Ϧηοτ͞ΕΔͷͰɺ
 ରࡦ͠ͳ͍ͱΞχϝʔγϣϯ͕ΨΫΨΫͯ͠͠·͏ cat-0 cat-1 cat-2 cat-3 cat-4 Speed มߋ ☝︎ ࣍ͷΞχϝʔγϣϯ͸ cat-3 ͔Β
 ࢝Ίͳ͍ͱεϜʔζʹͳΒͳ͍
  7. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? speed

    Λߋ৽͢ΔࡍʹΞχϝʔγϣϯ͕Ϧηοτ͞ΕΔͷͰɺ
 ରࡦ͠ͳ͍ͱΞχϝʔγϣϯ͕ΨΫΨΫͯ͠͠·͏ γʔϜϨεʹ੾Γସ͑ΔͨΊɺߋ৽લʹ CALayer ͷ timeO ff set ͱ beginTime Λ੍ޚ్ͯ͠த͔ΒΞχϝʔγϣϯ͕࢝·ΔΑ͏ʹ͢Δ ☝︎ cat-3 ͔Β࢝·Γ cat-2 ͰऴΘΔΞχϝʹ͢Δ cat-3 cat-4 cat-0 cat-1 cat-2
  8. iOSDC Japan 2022 - Unconference #iosdc #unconference What’s RunCat? ͜ͷΑ͏ͳεϐʔυ్͕தͰมԽ͢ΔແݶϧʔϓͷίϚૹΓ


    ΞχϝʔγϣϯΛ࣮ݱͰ͖Δ࠷దखஈ͕ CAKeyframeAnimation Core Animation ͍͢͝ʂ
  9. iOSDC Japan 2022 - Unconference #iosdc #unconference Try 1: ͱΓ͋͑ͣૉ௚ʹΞχϝʔγϣϯࢼͯ͠ΈΔ

    in App struct RotateItemView: View { @State var flag: Bool = false var body: some View { Image(systemName: "paperplane") .resizable() .frame(width: 100, height: 100, alignment: .center) .rotationEffect(Angle(degrees: flag ? 0 : 360)) .animation( Animation.linear(duration: 2) .repeatForever(autoreverses: false), value: flag ) .onAppear { flag.toggle() } } }
  10. iOSDC Japan 2022 - Unconference #iosdc #unconference Try 1: ͱΓ͋͑ͣૉ௚ʹΞχϝʔγϣϯࢼͯ͠ΈΔ

    in Widget struct RotateItemView: View { @State var flag: Bool = false var body: some View { Image(systemName: "paperplane") .resizable() .frame(width: 100, height: 100, alignment: .center) .rotationEffect(Angle(degrees: flag ? 0 : 360)) .animation( Animation.linear(duration: 2) .repeatForever(autoreverses: false), value: flag ) .onAppear { flag.toggle() } } } Ξχϝʔγϣϯ͠ͳ͍ 💦
  11. iOSDC Japan 2022 - Unconference #iosdc #unconference struct CatTimerView: View

    { @State var catIndex: Int = 0 let timer = Timer .publish(every: 0.1, on: .main, in: .default) .autoconnect() var body: some View { Image("cat-\(catIndex)") .onReceive(timer) { _ in catIndex = (catIndex + 1) % 5 } .padding() } } Try 2: TimerΛ࢖ͬͯίϚૹΓͯ͠ΈΔ in App
  12. iOSDC Japan 2022 - Unconference #iosdc #unconference struct CatTimerView: View

    { @State var catIndex: Int = 0 let timer = Timer .publish(every: 0.1, on: .main, in: .default) .autoconnect() var body: some View { Image("cat-\(catIndex)") .onReceive(timer) { _ in catIndex = (catIndex + 1) % 5 } .padding() } } Try 2: TimerΛ࢖ͬͯίϚૹΓͯ͠ΈΔ in Widget ΍͸Γಈ͔ͳ͍ 💧
  13. iOSDC Japan 2022 - Unconference #iosdc #unconference var animatedCatImage: Image?

    { if let uiImage = UIImage.animatedImageNamed("cat-", duration: 1) { return Image(uiImage: uiImage) } return nil } Try 3: ͦ͏ͩ UIKit ʹཔΖ͏ʂ in App UIImage.animatedImageNamed(_:duration:) Λ࢖͑͹ɺ
 ࿈൪ʹͳ͍ͬͯΔϑΝΠϧ໊ͷը૾ΛΞχϝʔγϣϯԽ
 ͞ΕͨҰͭͷ UIImageʹͰ͖Δ͕… UIImageView ͩͱಈ͚͘Ͳ
 SwiftUIͷImageʹೖΕΔͱಈ͔ͳ͍
  14. iOSDC Japan 2022 - Unconference #iosdc #unconference struct CatRepView: UIViewRepresentable

    { typealias UIViewType = UIImageView let uiImage: UIImage? init() { uiImage = UIImage.animatedImageNamed("cat-", duration: 1) } func makeUIView(context: Context) -> UIImageView { let imageView = UIImageView(image: uiImage) imageView.contentMode = .scaleAspectFit return imageView } func updateUIView(_ uiView: UIImageView, context: Context) {} } Try 4: UIViewRepresentable ͰͲ͏ͩʂ ౰࣌ͷදࣔΛ࠶ݱͨ͠΋ͷ ❗ ͔ͯɺφχίϨ!! UIKit ༝དྷͷ View ͸΢ΟδΣοτͷதͰ͸ແޮ
  15. iOSDC Japan 2022 - Unconference #iosdc #unconference var catGIFImage: Image?

    { if let asset = NSDataAsset(name: "runcat-gif"), let uiImage = UIImage(data: asset.data) { return Image(uiImage: uiImage) } return nil } Try 5: GIFΛ௚઀ಡΈࠐΜͰΈΔ in App ͦ΋ͦ΋΢ΟδΣοτ͡Όͳͯ͘΋ಈ͔ͳ͍
  16. iOSDC Japan 2022 - Unconference #iosdc #unconference Live Activities ref:

    AppleɺiOS 16Ͱಋೖ͞ΕΔڞ༗ͱίϛϡχέʔγϣϯͷͨΊͷ৽͍͠ํ๏Λൃද - Apple (೔ຊ) https://www.apple.com/jp/newsroom/2022/06/apple-unveils-new-ways-to-share-and-communicate-in-ios-16/
  17. iOSDC Japan 2022 - Unconference #iosdc #unconference Live Activities ref:

    Keynote (ASL) - WWDC22 - Videos - Apple Developer. https://developer.apple.com/videos/play/wwdc2022/111/
  18. iOSDC Japan 2022 - Unconference #iosdc #unconference Live Activities ref:

    Keynote (ASL) - WWDC22 - Videos - Apple Developer. https://developer.apple.com/videos/play/wwdc2022/111/
  19. iOSDC Japan 2022 - Unconference #iosdc #unconference Try 6: Live

    Activities Λ࢖ͬͯΈΔ Live Activities ͸ ActivityKit Framework Λ࢖࣮ͬͯ૷͢Δ ActivityKit ͸ Xcode 14 beta 4~6 Ͱ࢖͑Δ Xcode 14 RC ʹ͸ೖ͍ͬͯͳ͍ ૣ଎ࢼ͍ͯ͠Δਓͷهࣄ΍GitHubͷιʔε*͕͋ΔͷͰ࣮૷͸ ͦΜͳʹ೉͘͠ͳ͍ * Create Live Activities With ActivityKit on iOS 16 | by Batikan Sosun | Aug, 2022 | Better Programming
 https://betterprogramming.pub/create-live-activities-with-activitykit-on-ios-16-beta-4766a347035b
  20. iOSDC Japan 2022 - Unconference #iosdc #unconference Try 6: Live

    Activities Λ࢖ͬͯΈΔ ࢼͯ͠Θ͔ͬͨ͜ͱ Live Activities ͸جຊతʹ͸΢ΟδΣοτͱҰॹ
 ϩοΫεΫϦʔϯʹදࣔͰ͖Δ΢ΟδΣοτͱ͍͏ײ͡ ΍͸ΓΞχϝʔγϣϯ͸Ͱ͖ͳ͍😫 ं͕ಈ͍͍ͯΔΑ͏ʹݟ͑ͨͷ͸ɺSliderͷϊϒͷը૾Λม͍͚͑ͯͨͩ
 ߋ৽࣌ʹϊϒͷҠಈΞχϝʔγϣϯ͕࣮ߦ͞ΕΔ λΠϚʔ͸ Text(date: Date, style: Text.DateStyle) Λ࢖͑͹࣮૷Ͱ͖Δ ͔͠΋ɺiOS 14͔Β͜Ε͸͋ͬͨʢ஌Βͳ͔ͬͨ..ʣ
  21. iOSDC Japan 2022 - Unconference #iosdc #unconference Calligraphr ͱ͍͏ϑΥϯτΛࣗ࡞Ͱ͖Δ
 αʔϏεΛ࢖ͬͯೣϑΥϯτΛ࡞੒

    ૸Δೣ͸̑ϑϨʔϜͳͷͰɺ
 0~4ͱ5~9ͷ̎प෼ࢦఆ͢Δ ग़དྷ্͕ͬͨOpenTypeϑΥϯτΛ
 ϓϩδΣΫτʹऔΓࠐΉ Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ ref: Calligraphr. https://www.calligraphr.com/en/webapp/app_home/?/
  22. iOSDC Japan 2022 - Unconference #iosdc #unconference struct ContentView: View

    { var body: some View { Text(Date(), style: .timer) .font(.custom("Runningcat-Regular", size: 150)) } } in App ͱΓ͋͑ͣී௨ͷSwiftUI AppͳΒػೳͨ͠ʂ ͳΜ͔ΧϫΠΠ Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ ❗
  23. iOSDC Japan 2022 - Unconference #iosdc #unconference ͚ͩ͘͜͜Γൈ͖͍ͨ Try 7:

    λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍
  24. iOSDC Japan 2022 - Unconference #iosdc #unconference struct ContentView: View

    { var body: some View { Text(Date(), style: .timer) .lineLimit(1) .font(.custom("Runningcat-Regular", size: 200)) .fixedSize(horizontal: true, vertical: false) .frame(width: 120, alignment: .trailing) .clipped() } } in App Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ .lineLimit(1) ͱ . fi xedSize() ͰվߦΛڐ͞ͳ͍Α͏ʹ͢Δ .frame(width: 120, alignment: .trailing) Ͱ෯ΛೣҰඖ෼ʹ ͭͭ͠ɺTextΛӈدͤʹ͢Δ .clipped() Ͱ༨෼ͳೣΛফ͢
  25. iOSDC Japan 2022 - Unconference #iosdc #unconference struct ContentView: View

    { var body: some View { Text(Date(), style: .timer) .lineLimit(1) .font(.custom("Runningcat-Regular", size: 200)) .fixedSize(horizontal: true, vertical: false) .frame(width: 120, alignment: .trailing) .clipped() } } in Widget Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ ΢ΟδΣοτͩͱ Text(Date(), style: .timer) ͱ . fi xedSize() ͷ૬ੑ͕ѱ͍Β͘͠ɺText͕ফ͑ͯ͠·͏ ͱʃ͓ʃ͠ʃͯʃͨʃΑʃ͓ʃ͓ʃ͓ʃʂ 💢
  26. iOSDC Japan 2022 - Unconference #iosdc #unconference ͍ͭʹ΢ΟδΣοτͰೣಈ͖·ͨ͠ʂʂ Try 7:

    λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ ΍Γ·ͨ͠🎉 ༏উ🏆 👑
  27. iOSDC Japan 2022 - Unconference #iosdc #unconference in Widget Try

    7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ . fi xedSize() ͸ Group ͰแΜͰ͔Β࢖͑͹༗ޮ .clipped() ΋͞Βʹ Group ͰแΜͰ͔Β࢖͑͹༗ޮ var body: some View { Group { Group { Text(Date(), style: .timer) .lineLimit(1) .truncationMode(.head) .font(.custom("Runningcat-Regular", size: 120)) .frame(width: 200) } .fixedSize() } .frame(width: 90, alignment: .trailing) .clipped() }
  28. iOSDC Japan 2022 - Unconference #iosdc #unconference var body: some

    View { Group { Group { Text(Date(), style: .timer) .lineLimit(1) .truncationMode(.head) .font(.custom("Runningcat-Regular", size: 120)) .frame(width: 200) } .fixedSize() } .frame(width: 90, alignment: .trailing) .clipped() } in Widget Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ .truncationMode(.head) Ͱ෯͕଍Γͳ͍ͱ͖ઌ಄͕
 ʮ…ʯͰলུ͞ΕΔΑ͏ʹ͓ͯ͘͜͠ͱ͕ॏཁ লུͭͭ͠෯Λݻఆͤ͞ΔͨΊʹɺframe(width: 200) Ͱ
 ೋจࣈ෼ͷ෯Λࢦఆ͢Δ
  29. iOSDC Japan 2022 - Unconference #iosdc #unconference var body: some

    View { Group { Group { Text(Date(), style: .timer) .lineLimit(1) .truncationMode(.head) .font(.custom("Runningcat-Regular", size: 120)) .frame(width: 200) } .fixedSize() } .frame(width: 90, alignment: .trailing) .clipped() } in Widget Try 7: λΠϚʔ͕ಈ͔ͤΔͳΒೣϑΥϯτͰࠩ͠ସ͑Ε͹͍͍͡Όͳ͍ .clipped() ͢Δલʹ .frame(width: 90, alignment: .trailing)
 Ͱද͍ࣔͤͨ͞ೣҰඖ෼ͷ෯Λ֬อ͢Δ