Я реализую горизонтальный Scrollview в Swiftui, чтобы пользователи прокручивали список дней (dayPickerView). В холсте Xcode все работает так же, как и ожидалось, а прокрутка строго горизонтальна. Однако при запуске приложения на реальном устройстве прокручиваемая область может быть слегка перемещена во всех направлениях (вверх, вниз и даже по диагонали). < /P>
Это неожиданное поведение иногда даже запускает жест, показывающий проблему. Пробое:
[*] оберток Scrollview в GeometryReader для обнаружения смещений.
Добавить. .contentshape (rectangle ()) для ограничения взаимодействий.var body: some View {
ZStack {
Color("Background")
.ignoresSafeArea()
VStack(spacing: 0) {
customHeader
// Content in white card with rounded corners
ZStack {
RoundedRectangle(cornerRadius: 40)
.fill(Color.white)
.shadow(color: Color.black.opacity(0.1), radius: 5, x: 0, y: 0)
ScrollView {
VStack(spacing: 20) {
viewModePicker
if viewModel.isLoading {
loadingView
} else if isDataEmpty {
emptyStateView
} else {
statisticsView
chartView
if hasDataToShow {
recordsListView
}
}
// Add bottom padding for better scrolling experience
Spacer()
.frame(height: 20)
}
.padding(.bottom)
}
.padding(.horizontal, 2) // Small horizontal padding for scroll view
}
.padding(.horizontal, 0)
.padding(.top, 10)
.padding(.bottom, 5)
.edgesIgnoringSafeArea(.bottom)
}
}
.navigationBarHidden(true)
.sheet(isPresented: $showingAddRecord) {
NavigationView {
AddSleepRecordView(childId: childId)
}
}
.onChange(of: showingAddRecord) { oldValue, newValue in
if !newValue { // Если форма была закрыта
refreshData()
}
}
.alert("Помилка", isPresented: $showingAlert) {
Button("OK", role: .cancel) {
viewModel.errorMessage = nil
}
} message: {
if let error = viewModel.errorMessage {
Text(error)
}
}
.onChange(of: viewModel.errorMessage) { _, newValue in
showingAlert = newValue != nil
}
.onAppear {
let currentTime = Date().timeIntervalSince1970
let shouldRefresh = currentTime - lastUpdateTime > 300 // 5 минут
if shouldRefresh {
refreshData()
} else {
Task { @MainActor in
await viewModel.fetchData(forceRefresh: false)
}
}
// Подписываемся на уведомление о добавлении/обновлении/удалении записи
NotificationCenter.default.addObserver(
forName: .newSleepRecordAdded,
object: nil,
queue: .main
) { _ in
self.refreshData()
}
}
.onDisappear {
// Отписываемся при исчезновении представления
NotificationCenter.default.removeObserver(self, name: .newSleepRecordAdded, object: nil)
}
.refreshable {
// Сбрасываем кэш для режима, который сейчас не отображается
if viewModel.viewMode == .daily {
viewModel.weeklyData = [] // Сбрасываем недельные данные
} else {
viewModel.dailyData = [] // Сбрасываем дневные данные
}
await viewModel.fetchData(forceRefresh: true)
await MainActor.run {
lastUpdateTime = Date().timeIntervalSince1970
}
}
}
// Custom header component
private var customHeader: some View {
VStack(spacing: 0) {
HStack(spacing: 16) {
// Back button
IconButtonCircle(systemName: "chevron.left", style: .primary, size: .medium, buttonSize: 40) {
presentationMode.wrappedValue.dismiss()
}
Spacer()
// Add record button
TextIconButtonLeft("Додати запис", systemName: "plus.circle.fill", style: .primary, size: .small) {
showingAddRecord = true
}
.frame(maxWidth: 200)
}
.padding(.horizontal)
.padding(.vertical, 12)
// Only show day selector in daily mode
if viewModel.viewMode == .daily {
dayPickerView
.padding(.top, 20)
.padding(.bottom, 20)
}
}
.background(Color("Background"))
}
// Day picker component with horizontal scrolling
private var dayPickerView: some View {
ScrollView(.horizontal, showsIndicators: false) {
HStack(spacing: 20) {
// Show today's day first, followed by the 6 previous days
// Form an array with negative offsets (0 - today, -1 - yesterday, etc.)
ForEach(0..
Подробнее здесь: https://stackoverflow.com/questions/794 ... horizontal
Движение во всех направлениях при использовании Scrollview (.horizontal) ⇐ IOS
Программируем под IOS
1740827788
Anonymous
Я реализую горизонтальный Scrollview в Swiftui, чтобы пользователи прокручивали список дней (dayPickerView). В холсте Xcode все работает так же, как и ожидалось, а прокрутка строго горизонтальна. Однако при запуске приложения на реальном устройстве прокручиваемая область может быть слегка перемещена во всех направлениях (вверх, вниз и даже по диагонали). < /P>
Это неожиданное поведение иногда даже запускает жест, показывающий проблему. Пробое:
[*] оберток Scrollview в GeometryReader для обнаружения смещений.
Добавить. .contentshape (rectangle ()) для ограничения взаимодействий.var body: some View {
ZStack {
Color("Background")
.ignoresSafeArea()
VStack(spacing: 0) {
customHeader
// Content in white card with rounded corners
ZStack {
RoundedRectangle(cornerRadius: 40)
.fill(Color.white)
.shadow(color: Color.black.opacity(0.1), radius: 5, x: 0, y: 0)
ScrollView {
VStack(spacing: 20) {
viewModePicker
if viewModel.isLoading {
loadingView
} else if isDataEmpty {
emptyStateView
} else {
statisticsView
chartView
if hasDataToShow {
recordsListView
}
}
// Add bottom padding for better scrolling experience
Spacer()
.frame(height: 20)
}
.padding(.bottom)
}
.padding(.horizontal, 2) // Small horizontal padding for scroll view
}
.padding(.horizontal, 0)
.padding(.top, 10)
.padding(.bottom, 5)
.edgesIgnoringSafeArea(.bottom)
}
}
.navigationBarHidden(true)
.sheet(isPresented: $showingAddRecord) {
NavigationView {
AddSleepRecordView(childId: childId)
}
}
.onChange(of: showingAddRecord) { oldValue, newValue in
if !newValue { // Если форма была закрыта
refreshData()
}
}
.alert("Помилка", isPresented: $showingAlert) {
Button("OK", role: .cancel) {
viewModel.errorMessage = nil
}
} message: {
if let error = viewModel.errorMessage {
Text(error)
}
}
.onChange(of: viewModel.errorMessage) { _, newValue in
showingAlert = newValue != nil
}
.onAppear {
let currentTime = Date().timeIntervalSince1970
let shouldRefresh = currentTime - lastUpdateTime > 300 // 5 минут
if shouldRefresh {
refreshData()
} else {
Task { @MainActor in
await viewModel.fetchData(forceRefresh: false)
}
}
// Подписываемся на уведомление о добавлении/обновлении/удалении записи
NotificationCenter.default.addObserver(
forName: .newSleepRecordAdded,
object: nil,
queue: .main
) { _ in
self.refreshData()
}
}
.onDisappear {
// Отписываемся при исчезновении представления
NotificationCenter.default.removeObserver(self, name: .newSleepRecordAdded, object: nil)
}
.refreshable {
// Сбрасываем кэш для режима, который сейчас не отображается
if viewModel.viewMode == .daily {
viewModel.weeklyData = [] // Сбрасываем недельные данные
} else {
viewModel.dailyData = [] // Сбрасываем дневные данные
}
await viewModel.fetchData(forceRefresh: true)
await MainActor.run {
lastUpdateTime = Date().timeIntervalSince1970
}
}
}
// Custom header component
private var customHeader: some View {
VStack(spacing: 0) {
HStack(spacing: 16) {
// Back button
IconButtonCircle(systemName: "chevron.left", style: .primary, size: .medium, buttonSize: 40) {
presentationMode.wrappedValue.dismiss()
}
Spacer()
// Add record button
TextIconButtonLeft("Додати запис", systemName: "plus.circle.fill", style: .primary, size: .small) {
showingAddRecord = true
}
.frame(maxWidth: 200)
}
.padding(.horizontal)
.padding(.vertical, 12)
// Only show day selector in daily mode
if viewModel.viewMode == .daily {
dayPickerView
.padding(.top, 20)
.padding(.bottom, 20)
}
}
.background(Color("Background"))
}
// Day picker component with horizontal scrolling
private var dayPickerView: some View {
ScrollView(.horizontal, showsIndicators: false) {
HStack(spacing: 20) {
// Show today's day first, followed by the 6 previous days
// Form an array with negative offsets (0 - today, -1 - yesterday, etc.)
ForEach(0..
Подробнее здесь: [url]https://stackoverflow.com/questions/79477466/movement-in-all-directions-when-using-scrollview-horizontal[/url]
Ответить
1 сообщение
• Страница 1 из 1
Перейти
- Кемерово-IT
- ↳ Javascript
- ↳ C#
- ↳ JAVA
- ↳ Elasticsearch aggregation
- ↳ Python
- ↳ Php
- ↳ Android
- ↳ Html
- ↳ Jquery
- ↳ C++
- ↳ IOS
- ↳ CSS
- ↳ Excel
- ↳ Linux
- ↳ Apache
- ↳ MySql
- Детский мир
- Для души
- ↳ Музыкальные инструменты даром
- ↳ Печатная продукция даром
- Внешняя красота и здоровье
- ↳ Одежда и обувь для взрослых даром
- ↳ Товары для здоровья
- ↳ Физкультура и спорт
- Техника - даром!
- ↳ Автомобилистам
- ↳ Компьютерная техника
- ↳ Плиты: газовые и электрические
- ↳ Холодильники
- ↳ Стиральные машины
- ↳ Телевизоры
- ↳ Телефоны, смартфоны, плашеты
- ↳ Швейные машинки
- ↳ Прочая электроника и техника
- ↳ Фототехника
- Ремонт и интерьер
- ↳ Стройматериалы, инструмент
- ↳ Мебель и предметы интерьера даром
- ↳ Cантехника
- Другие темы
- ↳ Разное даром
- ↳ Давай меняться!
- ↳ Отдам\возьму за копеечку
- ↳ Работа и подработка в Кемерове
- ↳ Давай с тобой поговорим...
Мобильная версия