Импортирование картинок и звуков в Swift Package
Введение
В качестве курсовой работы мне необходимо было разработать библиотеку с «успокаивающим» элементами на языке Swift. Ну знаете, это такие залипательные штуки, по типу спиннера или пузырчатой плёнки, которую лопаешь.
В качестве фреймворка был выбран SwiftUI. На нём можно было выполнить задачу в более короткие сроки, однако я совсем не думал, что столкнусь с некоторыми проблемами.
Все мы знаем функцию Image, которую с лёгкостью используем в обычных проектах. Так вот, она не работает в Swift Package… ну вернее как не работает, нужно погрузиться в Лимб, спасти своего товарища и путём четырёх выбросов вернуться, при этом не факт, что вы проснулись или картинки подключаться…
* Если эта штука упадёт, значит вы успешно подключили картинки:)
** Хорошая идея для очередного UI элемента:))
Проблема в том, что в Swift Package отсутствует папка с ресурсами (привычная нам папка Assets). Соответственно, при использовании функции Image или других функций, которые тянут данные из ресурсов, мы не будем ничего получать.
Решение
Создаём папку Resources в какой-либо поддиректории директории Sources. Я её поместил в папку по адресу Sources/FidgetUIElements.
У вас есть файл Package, там необходимо прописать путь к этой папке, указав, что она ресурсная. Это делается в поле targets следующим образом:
targets: [
.target(
name: "FidgetUIElements",
dependencies: [],
resources: [.process("Resources")]),
// other tergets
]
Далее вам нужно расширить функцию Image, перенаправив путь для поиска ресурсов на вашу новую папку. Вот код такого расширения:
import SwiftUI
extension Image {
// Наше расширение будет принимать имя файла и его тип
init(packageResource name: String, ofType type: String) {
guard let path = Bundle.module.path(forResource: name, ofType: type),
let image = UIImage(contentsOfFile: path) else {
self.init(name)
return
}
self.init(uiImage: image)
}
}
Также если вам необходимо подключить картинки, можно воспользоваться следующей функцией:
import Foundation
import AVFoundation
var player: AVAudioPlayer?
func playSound(_ soundName: String) {
guard let url = Bundle.module.url(forResource: soundName, withExtension: "mp3") else {
print("URL is wrong")
return
}
do {
player = try AVAudioPlayer(contentsOf: url)
guard let player = player else { print("URL is wrong 2"); return }
player.prepareToPlay()
player.play()
} catch {
print(error.localizedDescription)
}
}
Теперь, добавляя звуки или картинки в папку Resources, вы можете спокойно передавать название этих компонентов в ваши функции. В папке Resources вы можете создавать поддиректории и класть ваши файлы туда, это не имеет значения, функции всё равно найдут ваши файлы, если вы верно указали названия.
Всё равно не вижу картинки/не слышу звуки.
Передаём привет нашему любимому XCode и идём чистить папку с кешем. Не знаю у кого как, но мне приходилось это делать каждый раз, когда я добавлял очередной элемент в папку Resources, т.к. он не отображался.
Для этого:
Закрываем проект.
Открываем Finder.
Нажимаем в верхнем меню Переход --> Переход к папке…
Далее вбиваем /Users/{ваш юзернейм}/Library/developer/xcode/derivedData.
Откроется папка с кешем, удаляем оттуда всё, снова открываем проект и ВУАЛЯ.
На этом у меня всё, надеюсь, что было полезно и волчок всё-таки упал. Удачи и хорошего настроения!