Библиотека мобильного разработчика | Android, iOS, Swift, Retrofit, Moshi, Chuck
9.73K subscribers
1.53K photos
72 videos
52 files
4.31K links
Все самое полезное для мобильного разработчика в одном канале.

По рекламе: @proglib_adv

Учиться у нас: https://proglib.io/w/b60af5a4

Для обратной связи: @proglibrary_feeedback_bot

РКН: https://gosuslugi.ru/snet/67a4adec1b17b35b6c0d8389
Download Telegram
💼🚫 Устроился на работу, но она разонравилась: 8 советов, что делать

Несколько советов, как адаптироваться и понять, стоит ли оставаться или лучше уволиться.

Читать статью
👍91
Создатель C++ Бьярне Страуструп поделился 👍👍 ценными жизненными советами, которыми могли бы воспользоваться все разработчики (и не только разработчики), независимо от их многолетнего опыта.

✏️ Не углубляйтесь в одно направление. Мы не знаем будущего, а наша карьера и жизнь — долгосрочная штука. Нужно и гвоздь уметь забить, грубо говоря😉. Будьте гибкими. Заводите знакомства вне компьютера, а лучше вообще не связанные с вашей деятельностью.

✏️ Больше общайтесь, доносите свои идеи, умейте слышать и слушать. Если вы напишете лучший код, и будете уметь делать только это, мир не изменится только благодаря этому.

✏️ Никогда не жалейте о чем-то, тем более, о потраченном времени на другие направления. Найдите время, чтобы вести сбалансированную жизнь и будьте готовы к новым возможностям.

✏️ Широкий набор навыков, приобретённых во время обучения, можно будет применить позже, когда придёт время. Сам Бьярне знал и изучал горы языков, предметов и информации, которые были полезны в разные периоды жизни.
👍133
А/Б тесты продуктовых и маркетинговых гипотез и внедрение изменений прямо в интерфейсе сервиса AppMetrica

В основе новой фичи «А/Б экспериментов» лежит «Конфигурация флагов». С её помощью можно задавать конкретные параметры тестирования: сделать флаг для нового рекламного баннера, раздела в интерфейсе.

Так продакт-менеджеры и аналитики смогут принимать более взвешенные и эффективные решения об изменениях, опираясь на статистику влияния на продуктовые метрики.

Начать пользоваться фичей в AppMetrica можно бесплатно: доступны 2 одновременных А/Б теста с выставлением 2 флагов. В платной версии масштабы увеличиваются до 2 000 различных флагов и 100 одновременных экспериментов.
👍51🥱1
😎 Очередной #дайджест по Kotlin, Swift и кроссплатформе.

✍️ Появился Dagger 2.48 — выполнено несколько крупных фиксов и включает в себя альфа-версию процессоров Dagger и Hilt KSP

✍️ Разработка под ОС АВРОРА — установка Aurora SDK, где найти примеры приложений на Аврору, пара слов о документации Авроры, запуск первого приложения

✍️ Lottielab — инструмент для создания анимаций, позволяет импортировать или создать свои с нуля.

✍️ Swift UI переходы с эффектом искажения и металлическими шейдерами — суммарный эффект .distortionEffect + .overlay + .stroke

✍️ Фундаментальное руководство по пакетам в Java — серьезный материал по назначению пакетов, правилам создания, импорту классов и компиляции с запуском

✍️ Анимированный Circular Progress Indicator на Jetpack Compose — индикатор с анимированным статусом выполнения на основе текущего и максимального значений.
👍61
🌍🌐 Разрабатываем карты в Android-приложении

Существует кроссплатформенная библиотека, позволяющая использовать картографические данные и технологии в мобильных приложениях — это Yandex MapKit. Штука очень масштабная, и разработчику, впервые столкнувшемуся с ней, заставить Яндекс-карты работать, может показаться сложной в использовании.

Начало

Чтобы создать и запустить приложение понадобится:

Получить ключ;
Установить библиотеку MapKit;
Настроить библиотеку;
Собрать и запустить приложение.

Особенности:

🔹 Необходим базовый уровень Kotlin; умение собрать проект, запустить приложение на эмуляторе или телефоне, загрузить необходимые библиотеки; View Binding.
🔹 Нельзя скрывать логотип Яндекса на карте; в приложении в разделе «о программе» должна быть ссылка на условия использования Яндекс-карт.
🔹 API-ключ должен быть задан единожды перед инициализацией MapKitFactory. Хорошо бы задать ключ при запуске приложения в методе Application.onCreate(), а инициализировать уже в других необходимых активити и фрагментах. Если же при каких-то условиях будет повторно вызван MapKitFactory.setApiKey("Ваш API-ключ"), вы получите краш приложения и ошибку в логах: "java.lang.AssertionError: You need to set the API key before using MapKit!".
🔹 Если логика и API-ключ находятся в одном активити/фрагменте, раздувать макет необходимо только после установки ключа.
🔹 Выполнять проверку установки ключа при пересоздания активити/фрагмента, например, для вызова метода MapKitFactory.setApiKey("Ваш API-ключ").

Подробнее

#туториал
👍61
Со всеми хоть раз бывало, что хочется узнать, как написан UI в приложение, какие инструменты использованы и прочее.
Узнать всю поднаготину можно на своем любимом девайсе, активировав в настройках разработчика Layout Bounds.

Как активировать

На сайте Android, есть дока с подробностями, но в целом, это делается так:

🔹 Google Pixel: Настройки > О телефоне > Номер сборки
🔹 Samsung Galaxy S8 и старше: Настройки > О телефоне > Информация о ПО > Номер сборки
🔹 LG G6 и старше: Настройки > О телефоне > Информация о ПО > Номер сборки
🔹 HTC U11 и старше: Настройки > Информация о ПО > Далее > Номер сборки или Настройки > Система > О телефоне > Информация о ПО > Далее > Номер сборки
🔹 OnePlus 5T и старше: Настройки > О телефоне > Номер сборки

И тыкаем по номеру сборки, пока не появится сообщение. Теперь все включено и можно идти активировать Layout Bounds.

Отображение границ макета

Обычно он отображается в разделе системных настроек. Кроме того, его можно найти в разделе «Для разработчиков» в разделе «Система и обновления».

Перейдите к опции «Показывать границы макета» в разделе «Рисование» и включите ее. Теперь все, что отображается на экране, будет обведено различными цветными рамками.

Подробнее тут

#туториал
25🔥14🥰13👏10👍5
Google play начал банить приложения, которые обещают ускорить работу смартфона (хотя этим и не ускоришь особо...). Теперь всякие клинеры продаваться не будут.

Gradle VS Bazel. Разработчики рассказали, как у кого проходит сборка, кто быстрее, причем тут ABI.

Android Studio Iguana. Запилили апдейт на новую версии IDEA 2023.2 со всеми фишками + Gradle 8.3, а еще, в baseline profile можно будет не писать все руками, а работать через UI Android Studio.

OK.Tech выпустил Tracer (замена Firebase Analytics) для анализа ошибок, крашей, собирать инфу о месте на диске, дампе памяти и много других полезностей.

Вышел ChatGPT Enterprise для корпоративных клиентов на базе GPT4.

Появился стабильный Compse Multiplatform 1.5.0 с поддержкой обновления библиотек Compose 1.5.0.

#новости
🔥7👍2
Как сохранять данные и управлять ими с помощью Core Data в Swift

В этом гайде вы познакомитесь с основами Core Data, которая позволяет сохранять или кэшировать данные локально на устройстве.

Спикер проведет сравнение между использованием structs и Core Data, показывая преимущества последнего.

Содержание:

01:41 Что такое Core Data
06:02 Пример проекта
10:39 Определение модели для задачи
25:37 Добавление инициализатора
28:40 Что такое Core Data Stack
31:15 Как настроить ваш проект Xcode с помощью контейнера Core Data Container
35:01 Xcode превью на Core Data
38:29 Удаление объектов Core Data
40:56 Выборка данных с помощью NSFetchRequest
46:21 Работа над Sidebar view для использования Core Data
52:19 Изменение Task List View
58:45 Как использовать Relationships
1:08:25 Добавление Subtasks
1:18:57 Анимирование Core Data в Swiftui
1:19:40 Сохранение изменений в Core Data
8👏2
🔥✍️ Если вы пробовали писать виджеты, то знаете, насколько это больно и неприятно.
Но с появлением Compose, начали создавать интересный фреймоврк — Jetpack Glance, который позволяет создавать виджеты, используя Compose: а это значит, что стало меньше ограничений, больше возможностей для дебага, да и вообще создавать их приятнее.

Зависимости:

Чтобы добавить зависимость от Glance, пропишите репозиторий Google Maven в проект.
А для необходимых артефактов добавьте следующие зависимости в build.gradle:

dependencies {
// Для поддержки Glance
implementation("androidx.glance:glance:1.0.0-rc01")
// Для поддержки AppWidgets
implementation("androidx.glance:glance-appwidget:1.0.0-rc01")
// Для поддержки Wear-Tiles
implementation("androidx.glance:glance-wear-tiles:1.0.0-alpha05")
}
android {
buildFeatures {
compose = true
}
composeOptions {
kotlinCompilerExtensionVersion = "1.1.0-beta03"
}
kotlinOptions {
jvmTarget = "1.8"
}
}

Эта штука пока находится в стадии релиз-кандидата (до этого 5 альф и 1 бета), поэтому есть крупный шанс, что оно таки увидит свет, а значит, нужно готовиться 💪🧑‍💻

#софт
6👏4🥰1
Пишете под iOS или Android? Тогда скорее подавайте заявку на участие в мероприятии, которое пройдет 16–17 сентября.

Приглашаются разработчики на Swift под iOS и на Kotlin или Java под Android с опытом от трех лет.

Как проходит Mobile Weekend Offer:

Вступительная часть: 30 минут. Расскажут о проектах и процессе интервью
Кодинг и общение с экспертами: 120 минут. Попросят решить несколько задач, спросят про ваш подход к работе
Знакомство с командами: 60 минут. Познакомят вас с будущими коллегами из разных проектов
Оффер. Если все прошло хорошо, сделают оффер в течение трех дней

#мероприятие
7🥱7🤔2
😎 Очередной #дайджест по Kotlin, Swift и кроссплатформе

✍️ Простая анимация для всплывающего окна — реализация простой анимации для UIView из ViewController и кнопки

✍️ Изучаем новый Preview Macro на Swift UI и UIKit — работа с изображением с помощью PreviewProvider, UIViewController и кнопки с переходом

✍️ Кодогенерация. KAPT. KSP. Manual DI — для избавления от рефлексии, которая сильно тормозит скорость работы приложения в рантайме

✍️ Пошаговое руководство по тестированию скриншотов в Android — как реализовать тестирование скриншотов с помощью библиотеки Shot и отслеживать регрессию

✍️ Распознаем паспорт РФ в PWA — все работает через несколько скриптов: работа с камерой, передача потока изображений, сервис воркера и определение WASM сборки

✍️ Чего стоит ожидать в React Native — анализ развития опираясь на фреймворк Expo, работы группы Software Mansion, Callstack и Meta
👍21🔥42👏1
Еще лет 10 назад, только работники финансовой отрасли, помощники руководителей и менеджеры могли жаловаться на деградацию своих навыков и потерю знаний.

Учителя отмечают положительное влияние нынешней работы на профессиональное развитие. Рост и развитие в профессии отмечает большинство дизайнеров и медсестер. Программисты чаще системных администраторов отмечают, что развиваются в профессиональном плане на своей работе.

В целом по рынку труда 46% трудоустроенных россиян отмечают, что их работа позволяет развиваться в профессии, 35% не замечают роста и развития, но и не теряют навыки, 12% заявили о негативном влиянии работы на профессиональное развитие.
6👍2👏1
«Библиотека программиста» продолжает поиски контент-менеджера для ведения телеграм-каналов

Ищем человека, который грамотно пишет, разбирается в контенте и в одной из этих тем:
👉С++
👉Frontend
👉мобильная разработка
👉тестирование

Мы предлагаем частичную занятость и полностью удаленный формат работы — можно совмещать с основной и находиться в любом месте🌴

Подробнее о вакансии и форма для отклика — по ссылке.

Ждем вас в команде!
4
Почему Swift может заменить Python в мл?

Статья про перспективы языка Swift, поддержку от некоторых популярных фреймворков (TensorFlow) и плюсы языка относительно Python.

Основные тезисы:
🔸 Поддержка от передовых фреймворков из мл
🔸 Математические функции
🔸 Скорость
🔸 Импортируемость Python в Swift
🔸 Возможность писать как высокоуровневый, так и низкоуровневый код

Статье уже почти 4 года, но существенные обновления для Swift происходят только последнее время, так что будет интересно как уже в ближайшие пол года изменится индустрия и какую роль в этом сыграет Swift.

Ссылка на статью
8👍2🔥2🥱2
В iOS 17 появилось несколько очень интересных улучшений, которые значительно упростят работу с картами в SwiftUI и MapKit. На примере небольшого компонента карты с возможностью поиска, попробуем разобраться, что тут к чему.

Создание map view

Делается это с помощью создания нового Swift UIView с Mapkit Map view внутри и автоматическим масштабированием и панорамой:

import SwiftUI
import MapKit

struct SearchableMap: View {
@State private var position = MapCameraPosition.automatic

var body: some View {
Map(position: $position)
.ignoresSafeArea()
}
}

Теперь необходимо добавить sheet overlay на custom view, которое позволит выполнять поиск местоположений (вставляем после .ignoresSafeArea):

.sheet(isPresented: $isSheetPresented) {
SheetView()
}

Вот так должен выглядеть SheetView.swift на данный момент:

import SwiftUI
import MapKit

struct SheetView: View {
@State private var search: String = ""

var body: some View {
VStack {
// 1
HStack {
Image(systemName: "magnifyingglass")
TextField("Search for a restaurant", text: $search)
.autocorrectionDisabled()
}
.modifier(TextFieldGrayBackgroundColor())

Spacer()
}
.padding()
// 2
.interactiveDismissDisabled()
// 3
.presentationDetents([.height(200), .large])
// 4
.presentationBackground(.regularMaterial)
// 5
.presentationBackgroundInteraction(.enabled(upThrough: .large))
}
}

struct TextFieldGrayBackgroundColor: ViewModifier {
func body(content: Content) -> some View {
content
.padding(12)
.background(.gray.opacity(0.1))
.cornerRadius(8)
.foregroundColor(.primary)
}
}

Читать статью

#туториал
👍27👏21
🤩Подборка бесплатных API на любой случай жизни

Здесь вам и база данных продуктов/рецептов для приложений о ЗОЖ, и коллекция цитат знаменитых людей, и база данных с видеоиграми, и многое другое. Одним словом, маст хэв для ваших проектов.
8👍3😁2🤔2
🤨💥 Еще один подход к дебагу приложений на iOS. LLD-команды могут значительно помочь в отладке приложений для iOS, особенно когда вы сталкиваетесь со сложными проблемами, которые стандартные средства отладки могут не полностью устранить.

🔹 frame variable -T
Use Case: когда у вас есть переменная с неясным типом и необходимо быстро определить ее тип данных.
Пример: если у вас есть переменная с именем response и вы хотите узнать ее тип, используйте переменную frame -T response.

🔹 settings set target.language swift
Use Case: когда вы отлаживаете смешанный проект Swift и Objective-C и хотите обеспечить правильную оценку выражений.
Пример: settings set target.language swift.

🔹 expr -l Swift — myArray.map { $0 + 1 }
Use Case: для вычисления выражения Swift без изменения кода.
Пример: если у вас есть массив myArray, вы можете использовать expr -l Swift -- myArray.map { $0 + 1 }, чтобы добавить 1 к каждому элементу.

🔹 image list -o -f
Use Case: для просмотра списка загруженных модулей с путями к их файлам для устранения неполадок.
Пример: использование image list -o -f, для просмотра всех загруженных модулей и путей к ним.

🔹 register read
Use Case: когда нужно проверить значения регистров процессора, чтобы понять состояние софта.
Пример: использование register read для проверки значений регистра во время сбоя или неожиданного поведения.

🔹 memory write -s 4–0x12345678 0xdeadbeef
Use Case: для изменения определенного адреса памяти во время отладки.
Пример: использование memory write -s 4 -- 0x12345678 0xdeadbeef, чтобы изменить данные по адресу 0x12345678 на 0xdeadbeef.

🔹 watchpoint modify -c ‘(old_val != new_val)’ variable
Use Case: когда необходимо отслеживать изменения значения переменной с определенным условием.
Пример: изменение watchpoint в myVariable, чтобы она запускалась при изменении ее значения, используя watchpoint modify -c '(old_val != new_val)' myVariable.

🔹 disassemble -c 10 — name functionName
Use Case: для проверки ассемблерного кода конкретной функции, чтобы понять ее поведение.
Пример: разбор первых 10 инструкций функции с именем myFunction с помощью disassemble -c 10 --name myFunction.

🔹 breakpoint command add — one-shot true 1.1
Use Case: когда необходимо выполнить определенную команду один раз при достижении точки останова.
Пример: добавление команды в точку останова 1.1, которая выводит сообщение с помощью breakpoint command add --one-shot true 1.1.

🔹 type lookup -r ‘^Swift.Array’
Use Case: необходимо найти все типы Swift, соответствующие определенному шаблону.
Пример: найти все типы, начинающиеся со Swift.Array, используя поиск по типу -r ^Swift.Array.

#туториал
👍112
😎💪🔥 Интеграция Jetpack Compose UI в существующую базу Epoxy

Шаг 1: Рассмотрим модель Epoxy в текущей кодовой базе, которая имеет Epoxy RecyclerView для отображения списка элементов:

@EpoxyModelClass(layout = R.layout.epoxy_item_layout)
abstract class SampleEpoxyModel : EpoxyModelWithHolder() {

@EpoxyAttribute
lateinit var title: String

override fun bind(holder: Holder) {
holder.titleTextView.text = title
}

class Holder : EpoxyHolder() {
lateinit var titleTextView: TextView

override fun bindView(itemView: View) {
titleTextView = itemView.findViewById(R.id.titleTextView)
}
}
}

Шаг 2: Создадим простой компонент compose, который нужно интегрировать в приведенную выше модель:

@Composable
fun ComposeItem(name: String) {
Row(
modifier = Modifier
.fillMaxWidth()
.padding(16.dp)
) {
Text(text = "Hello, $name!")
}
}

Шаг 3: Теперь интегрируем компонент UI Jetpack Compose в существующую модель:

@EpoxyModelClass(layout = R.layout.epoxy_item_layout)
abstract class ComposeEpoxyModel : EpoxyModelWithHolder() {

@EpoxyAttribute
lateinit var title: String

override fun bind(holder: Holder) {
// Set up the Compose UI within the existing view holder
val composeContainer = holder.itemView.findViewById(R.id.composeContainer)
composeContainer.setContent {
ComposeItem(title = title)
}
}

class Holder : EpoxyHolder() {
lateinit var itemView: View

override fun bindView(itemView: View) {
this.itemView = itemView
}
}
}

Шаг 4: Создадим контроллер Epoxy, который заполняет RecyclerView экземплярами модели Epoxy

class MyEpoxyController : TypedEpoxyController>() {
override fun buildModels(data: List?) {
data?.forEach { name ->
composeEpoxyModel {
id(name)
name(name)
}
}
}
}

Шаг 5: Интегрируем контроллер Epoxy с RecyclerView в активити или фрагмент:

class MainActivity : AppCompatActivity() {

private val epoxyController = MyEpoxyController()

override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)

val recyclerView: EpoxyRecyclerView = findViewById(R.id.recycler_view)
recyclerView.setController(epoxyController)

val data = listOf("Alice", "Bob", "Charlie")
epoxyController.setData(data)
}
}

#туториал
👍16🔥21