Post

Replies

Boosts

Views

Activity

sourceImageURL in imagePlaygroundSheet isn't optional
I can't shake the "I don't think I did this correctly" feeling about a change I'm making for Image Playground support. When you create an image via an Image Playground sheet it returns a URL pointing to where the image is temporarily stored. Just like the Image Playground app I want the user to be able to decide to edit that image more. The Image Playground sheet lets you pass in a source URL for an image to start with, which is perfect because I could pass in the URL of that temp image. But the URL is NOT optional. So what do I populate it with when the user is starting from scratch? A friendly AI told me to use URL(string: "")! but that crashes when it gets forced unwrapped. URL(string: "about:blank")! seems to work in that it is ignored (and doesn't crash) when I have the user create the initial image (that shouldn't have a source image). This feels super clunky to me. Am I overlooking something?
0
0
58
1d
Problems trying to call reloadAllTimelines() multiple times from an AppIntent
My app focuses on a particular day and in the app I have arrow buttons that let you switch to the next or previous day. When one of them is pressed I call WidgetCenter.shared.reloadAllTimelines(). Almost immediately, regardless of how many times they are pressed, I will usually see my widgets immediately update to reflect the new day. I thought it would be nice to extend this functionality to Lock Screen controls. I had the AppIntent the Lock Screen buttons use call some of the same code that the arrow buttons in my app do, which includes a call to WidgetCenter.shared.reloadAllTimelines(). In the simulator it seemed to work great. I could see my Lock Screen widgets update almost immediately to focus on the new day. However, when I tried it on an actual device it was a much different story. Usually the first button press will update the widgets but after that it can be much, much longer before the Lock Screen widgets eventually refresh. It makes sense that the system is probably throttling my requests but is there a way to prevent this so that my Lock Screen controls operate the same way as buttons in my app?
0
0
168
Sep ’24
VoiceOver ignoring a data series when there are multiple ones
I can't figure out if I've found a VoiceOver problem with Swift Charts or if I'm doing something incorrectly. I have a loop within a loop showing 2 sets of data in the same chart. If I touch a month then VO correctly says there are two data series. But if I keep swiping down only data from the first series is read. ChatGPT said try referencing the outer loop and sure enough that worked if it done in BOTH the label and value. It sounds really awkward though. For example, "High 89 degrees F High October". Below the "bad" chart only says something such as "92 degrees F October" when swiping down. The "good" chart will read the high and low temperature data. VStack { headerText("BAD") Chart { ForEach(processedMonthlyInput) { oneMonth in ForEach(oneMonth.temperatures, id: \.month) { element in LineMark( x: .value("Month", element.month, unit: .month), y: .value("Temperature", element.tempVal.converted(to: .fahrenheit).value) ) .accessibilityLabel("\(element.month.formatted(.dateTime.month(.wide)))") .accessibilityValue(Text("\(element.tempVal.converted(to: tempUnit).formatted(.measurement(width: .abbreviated, numberFormatStyle: .number.precision(.fractionLength(0)))))")) } .symbol(by: .value("Type", oneMonth.theType)) .foregroundStyle(by: .value("Type", oneMonth.theType)) .interpolationMethod(.catmullRom) } } .frame(maxHeight: paddingAmount) .padding(.horizontal) headerText("GOOD") Chart { ForEach(processedMonthlyInput) { oneMonth in ForEach(oneMonth.temperatures, id: \.month) { element in LineMark( x: .value("Month", element.month, unit: .month), y: .value("Temperature", element.tempVal.converted(to: .fahrenheit).value) ) .accessibilityLabel("\(oneMonth.theType) \(element.month.formatted(.dateTime.month(.wide)))") .accessibilityValue(Text("\(oneMonth.theType) \(element.tempVal.converted(to: tempUnit).formatted(.measurement(width: .abbreviated, numberFormatStyle: .number.precision(.fractionLength(0)))))")) } .symbol(by: .value("Type", oneMonth.theType)) .foregroundStyle(by: .value("Type", oneMonth.theType)) .interpolationMethod(.catmullRom) } } .frame(maxHeight: paddingAmount) .padding(.horizontal) }
0
0
198
Sep ’24
Trouble using more than one color with SF Symbols in tinted mode
When a widget is using the new tinted mode in iOS 18 the Weather app shows the SF Symbols in both white and the tint color. For example, a tinted sun with a white arrow for sunrise. I can't figure out how to do this. If I add widgetAccentable to the Image(systemName:) the entire Image becomes the tint color. If I don't use it no combination of rendering mode or foreground style makes the tint color appear. I can't find any mention of this in the WWDC sessions.
1
0
303
Sep ’24
Change in behavior for .isToggle trait
One of my blind users reached out to me after they updated to iPadOS 18. I have a button that is used to mark/unmark a favorite location. He said that he could still tell the favorite status via the label and hint, but VoiceOver was always saying that the switch button is off. I'm able to recreate this on my iPad as well. The documentation for .isToggle is completely blank. Basically with iPadOS 17 adding the .isToggle trait makes VoiceOver state that my button is a toggle. With iPadOS 18 adding the .isToggle trait makes VoiceOver state that my button is a toggle AND try to state its current value. I don't know if this is intentional or a bug. Button { showFavActions() } label: { Image(systemName: SFSymbolShortcut.star.rawValue) .symbolVariant(weatherData.currentlyFavIndex == nil ? .none : .fill) } .buttonStyle(.plain) .accessibilityLabel(Text(weatherData.currentlyFavIndex == nil ? "Not a favorite location." : "Favorite location.")) .accessibilityHint(Text(weatherData.currentlyFavIndex == nil ? "Add to favorites." : "Remove from favorites.")) .accessibilityInputLabels(["Favorite"]) .accessibilityAddTraits(.isToggle) // iOS 17
2
0
371
Aug ’24
Mismatch between DayWeather date and HourWeather date
A year ago I filed feedback FB13055082 about this and I just realized that it was marked as "works as currently designed". I need help understanding why this is the expected behavior. For the feedback example I used Nepal, which is +5:45 from GMT. When the UTC offset is not at an hour interval, the dates returned by DayWeather and HourWeather do not match. I’ll request weather with a start date of Aug 25 at 12:0:0 AM GMT+5:45 and end date of Sep 3 at 12:0:0 AM GMT+5:45. The first daily forecast returns a date of Aug 25, 2023 at 12:0:0 AM GMT+5:45, which is what I expect. It's midnight in Nepal and the start of the day. If in my code I call (correct calendar).startOfDay(for: ) I'll also get this same time back. However, the first hourly forecast returned is for Aug 25, 2023 at 12:45:0 AM GMT+5:45 which is NOT the start of the day in Nepal or the start I asked for. It is 45 minutes off. How is the hourly data not starting at the time I requested the expected behavior? Especially when the day data does start at the time I requested.
1
0
333
Aug ’24
Location requested in WeatherService monthlyStatistics() does NOT match the location in the response
We pass a CLLocation to the new WeatherService monthlyStatistics() BUT in the returned metadata the CLLocation data does NOT match what we sent in the request. For example, send lat -27.1480114 long -109.4273371 in the monthly stat request and get back data for lat -27.148000717163086, long -109.427001953125. There’s no mention in the documentation of the returned location being “close to” the requested location. If this is working as designed how close are the results allowed to be? In my small sample they seem to be around 45-55 meters away. I’m considering less than 100 meters away to be a match, but don’t know if that’s correct.
1
0
355
Jul ’24
SwiftUI Gestures prevent scrolling with iOS 18
I added gesture support to my app that supports iOS 16 and 17 and have never had issues with it. However, when I compiled my app with Xcode 16 I immediately noticed a problem with the app when I ran it in the simulator. I couldn't scroll up or down. I figured out it’s because of my gesture support. My gesture support is pretty simple. let myDragGesture = DragGesture() .onChanged { gesture in self.offset = gesture.translation } .onEnded { _ in if self.offset.width > threshold { ...some logic } else if self.offset.width < -threshold { ...some other logic } logitUI.debug("drag gesture width was \(self.offset.width)") self.offset = .zero } If I pass nil to .gesture instead of myDragGesture then scrolling starts working again. Here’s some example output when I’m trying to scroll down. These messages do NOT appear when I run my app on an iOS 16/17 simulator with Xcode 15. drag gesture width was 5.333328 drag gesture width was -15.333344 drag gesture width was -3.000000 drag gesture width was -24.333328 drag gesture width was -30.666656 I opened FB14205678 about this.
12
17
3.0k
Jul ’24
Infinite loop using NavigationStack
Hello. I've seen some other posts about NavigationStack, but my variation seems a little different. FYI, I have not migrated from ObservableObject to Observable yet. However, having a path in either seems to be a factor in this issue. My code has no issues when built with Xcode 15. When built with Xcode 16 I keep hitting scenarios where the .onAppear for my first tab gets called over and over again endlessly. If I go to my second tab, which uses a NavStack with a path and then navigate anywhere my .onAppear for my FIRST tab gets call endlessly. I’ll sometimes see a “double push” to the stack. (Someone posted a video of this happening on Mastodon, which apparently I’m not allowed to link to here.) The second tab is accessing the path property via an @EnvironmentObject. I can stop this endless loop by removing @Published from the property in my ObservableObject that holds my path. But then if I go to my third tab, which does NOT use a path, the .onAppear for my FIRST tab again gets called endlessly. So far on Mastodon I’ve seen three people encountering problems possibly related to storing a path in something being observed. Feedback requires a sample project, which I am having trouble creating to show the problem.
8
1
831
Jul ’24
WeatherKit not returning gust in DayWeather
My SwiftUI weather app shows weather stats for the day that I'm pulling from DayWeather. I added wind speed to my app recently. I wanted to add Gusts but I hit a problem. Whenever I look at the results returned for DayWeather the "gust" inside of Wind is always nil. The iOS weather app includes gusts in a daily summary. For example, today for ****** River, OR it says "Wind is currently 15 mph from the southeast. Today, wind speeds are 8 to 26 mph, with gusts up to 50 mph." A query I just did to WeatherKit returned 18mph with compass direction SSE but nil for gusts. I've searched the documentation and I can't determine if this is working as designed or a bug.
2
0
753
Mar ’23
Widgets calling WeatherService.shared.weather multiple times at the same time
Hello. I noticed pretty early on that WeatherService.shared.weather seems to cache results. I realized this when I called it, killed network connectivity to my device, and then called it again I still got results back. My concern is about my widgets, which are also able to call WeatherService.shared.weather. I put my call inside of getTimeline(). After adding logging I realized that getTimeline() is called multiple times at the same time. For example, if I have two different widgets each with three different sizes (small, large, rectangular, etc) then six calls to getTimeline() are made for an update. I found a blog by Shopify iOS developers that describes how they found the same thing, but the forums aren't letting me link to their website's blog. My questions is which of these scenarios is happening: Even though WeatherService.shared.weather is called six times in the same second it's actually only the first call that goes out via the network and the remaining five calls just returned cached results. More than one of the six calls in the same second could be making a network call. If that's the case I'm going to need to add some form of throttling/caching because the number of free API calls per month is limited. Thank you!
1
0
720
Feb ’23
Hourly precipitation amounts seem drastically low
Hello. I took a closer look at the data I'm getting back for hourly forecasts and I'm baffled by results I'm seeing. For example, it's Dec 19, 2022 8:00am PT and I'm asking for the weather for Orchard Park NY (lat 42.766437 long -78.743855) for Dec 23, 2022. The daily forecast tells me they're expected to have 5.9" of snow. However, the hourly forecast with the most snow that day is reported as 0.071" (1.8mm). The Apple Weather app on iOS shows that hour as having 0.6". I wrote a 'for' loop to print the results of my call to WeatherService.shared.weather.         print(oneHour.precipitationAmount.formatted())         print(oneHour.precipitationAmount.description)         print(oneHour.precipitationAmount.unit)         print(oneHour.precipitationAmount.value) 0.071 in 1.8 mm <_NSStatic_NSUnitLength: 0x2010b0178> mm 1.8
7
0
2k
Dec ’22
VoiceOver ignoring UICalendarView day decorations
I'm using UICalendarView in my SwiftUI app. Inside of my func calendarView() I'm specifying emojis for decorations for certain days and they're showing up just fine. The problem is that VoiceOver completely ignores the decorations. If I touch a day it says the date and "button", which is exactly what I want. I've tried adding all of the accessibility items below but none of them cause VoiceOver to mention the day's decoration.        return .customView {         let emoji = UILabel()         emoji.text = foundEvent.emoji         emoji.isAccessibilityElement = true         emoji.accessibilityIdentifier = "identifier"         emoji.accessibilityTraits = .staticText         emoji.accessibilityLabel = "I like turtles."         emoji.accessibilityValue = foundEvent.emoji         emoji.accessibilityHint = "I also like turtles."         return emoji       }
1
1
1.2k
Sep ’22
SiriTipView showing ${APPLICATIONNAME} instead of my app's name.
Version 14.0 beta 4 (14A5284g) This is all referring to the simulator. When I run the Shortcuts app my phrase is properly shown for my app and the app's name is correctly populated. However, when I try to add a SiriTipView the same phrase shows the application name as ${APPLICATIONNAME}. I changed the first letter of the phrase and verified the change showed up in the Shortcuts app and my app tip. I'm not sure if I'm doing something wrong or should file feedback instead.
3
1
1.9k
Aug ’22