NSValue(CMTime: ) in swift 3? - ios

i have this code
var times = [NSValue]()
for time in timePoints {
times.append(NSValue(CMTime : time))
}
i get an error that their is nothing called CMTime in swift 3 i can't really find any param for cm time..

Check the reference of NSValue.
init(time: CMTime)
Use NSValue(time: time).
One more. If you want to convert [CMTime] to [NSValue], you can write something like this:
let times = timePoints.map(NSValue.init(time:))

Related

Which swift Document or video I need to read for me to understand how this ResultsHandler works?

HI I'm a newbi coder who is code for fun.
I want to get my stepscount from my iPhone
so I start to learn Xcode and swift.
I can write bash script and a little bit python.
but I really can't understand the following.
From https://developer.apple.com/documentation/healthkit/hkstatisticscollectionquery
query.initialResultsHandler = {
query, results, error in
// My Understanding This Handler is a unknow type or thing for me how can I know what is it and how to use it from apple's web page?
I can tell from reading apple's page it have three components and
Declaration says it's a var? like
var initialResultsHandler: ((HKStatisticsCollectionQuery, HKStatisticsCollection?, Error?) -> Void)? { get set }
so it's a var with three things in it? so it's a tuple? and can be get and set!?
So I think the above code means put var query to hander's HKStatisticsCollectionQuery, get from hander's HKStatisticsCollectionQuery to var results and handle's Error to local var error
The Most important thing is what is the "in" after the error?
I only know you can for xxxx in yyyy and create a loop but without a for use in means what? what document explain this in stuff?
guard let statsCollection = results else {
// Perform proper error handling here
fatalError("*** An error occurred while calculating the statistics: \(error?.localizedDescription) ***")
}
let endDate = NSDate()
guard let startDate = calendar.dateByAddingUnit(.Month, value: -3, toDate: endDate, options: []) else {
fatalError("*** Unable to calculate the start date ***")
}
That is a closure you are looking at. The three variables are the input arguments of the closure that you name query, results and error. You could give these any other name as well, since they only exist inside the closure and only their types are used in the function type signature.
The in keyword indicates the start of the closure body.
For more information on the topic, have a look at the Closures chapter of the Swift Programming Language.

XMPP last activity time shows in strange form. How to fix it?

I have added to the Bridging file XMPPLastActivity.h file and in Swift file I did the next:
let abc = XMPPLastActivity()
let a = abc.sendLastActivityQueryToJID(user.jid)
print("A is: \(a)")
but it returns me response like
1686F740-C50C-477B-BAE2-02C897826B97
How can I return it in human readable format?
UPDATE
Please, join to chat to help me: https://chat.stackoverflow.com/rooms/90972/ios-errors-fixing
You will get a response via the XMPP delegate. You need to implement:
func xmppLastActivityDidReceiveResponse(sender:XMPPLastActivity, response:XMPPIQ)
And get the time lag to now in seconds with:
let time : NSUInteger = response.lastActivitySeconds
Then it's NSDate all the way.

Subtracting time in swift

I have 2 NSDate object thats shows 24hour time. Is there a way I can subtract those two times and put the result in a label. Ive searched for a method but couldn't find one. The only thing I could find was cover it to a double with timeIntervalFromDate method, which returns a double and I need the 24hour representation of that.
It just returns an NSTimeInterval that is typedef double NSTimeInterval is a representation in seconds.
Doing the math to know how may hours are in x seconds, you just need to divide the retuned interval to 3600 seconds and round the result.
I've build a simple extension to be used in swift to help in calendrical calculation, you can find it here: AFSwiftDateExtension
This function may solve your problem:
func hoursFrom(earlierDate : NSDate, laterDate:NSDate) -> Int
{
return NSCalendar.currentCalendar().components(NSCalendarUnit.CalendarUnitHour, fromDate: earlierDate, toDate: laterDate, options: nil).hour
}
Adapted from this related question.
extension NSTimeInterval {
var time:String {
return String(format:"%02d:%02d:%02d", Int((self/3600.0)%24), Int((self/60.0)%60), Int((self)%60))
}
}
println(30.time) // "00:00:30"
println(60.time) // "00:01:00"
println(600.time) // "00:10:00"
println(3600.time) // "01:00:00"

Swift: can I add and subtract `dispatch_time_t` variables?

I need to do some time math in iOS, with Swift.
I have to use dispatch_walltime. I hope that can be taken as axiomatic. Where time math is concerned, I think I'm likely to get the response "just use NSDate," but please take it on faith: I am bound to dispatch_walltime.
Now, it's plain why someone might suggest NSDate, because when you're using NSTimeInterval and NSDate and that good stuff, it's pretty easy to make custom timestamps and compare them and do all kinds of time math.
But I have to use dispatch_time_t, and specifically dispatch_walltime created like this:
//Get the timeInterval of now.
let nowInterval = NSDate().timeIntervalSince1970
//Make a timespec from it.
var nowStruct = timespec(tv_sec: Int(nowInterval), tv_nsec: 0)
//Make a walltime definition from that.
let referenceWalltime = dispatch_walltime(&nowStruct, 0)
Later on I need to use that reference time in various ways. For instance, I need to get the time interval between the reference time and whatever time it happens to be.
I am attempting to do this the same way I would with NSTimeInterval, in other words, make a new one and subtract the old one from it:
//Repeat everything from before to make a new wall time.
let newNowInterval = NSDate().timeIntervalSince1970
var newNowStruct = timespec(tv_sec: Int(newNowInterval), tv_nsec: 0)
let newWalltime = dispatch_walltime(& newNowStruct, 0)
//Time math a la NSTimeInterval to find the interval:
let walltimeInterval = newWalltime - referenceWalltime
Will that work?
The short answer is: no. That code will crash.
The better answer is: no, but it can be done, and it's not all that different in the end.
I did some investigating on my own in a Playground and learned some interesting things, and I believe I figured out the right way to do this.
I'm pasting the entirety of my Playground here, so that others can copy-paste it and figure out how to do their own dispatch_time math.
Comments marked by //********* in the code denote the key things I learned.
import UIKit
import XCPlayground
XCPSetExecutionShouldContinueIndefinitely(continueIndefinitely: true)
public class IntervalMaker {
var referenceWalltime: dispatch_time_t = 0
var newWalltime: dispatch_time_t = 0
var walltimeInterval: dispatch_time_t = 0
func scheduleWalltimeSequence () {
let threeSeconds = Int64(NSEC_PER_SEC) * 3
let now = walltimeNow()
let dispatchTimeInThree = dispatch_time(now, threeSeconds)
let dispatchTimeInSix = dispatch_time(now,
2 * threeSeconds)
setReferenceWalltimeToNow()
dispatch_after(dispatchTimeInThree, dispatch_get_main_queue(),
setNewWalltimeToNow)
dispatch_after(dispatchTimeInSix,
dispatch_get_main_queue(), dispatchBasedOnDispatchMath)
}
func walltimeNow()->dispatch_time_t{
let nowInterval = NSDate().timeIntervalSince1970
var nowStruct = timespec(tv_sec: Int(nowInterval), tv_nsec: 0)
return dispatch_walltime(&nowStruct, 0)
}
func setReferenceWalltimeToNow () {
referenceWalltime = walltimeNow()
}
func setNewWalltimeToNow (){
newWalltime = walltimeNow()
}
func dispatchBasedOnDispatchMath () {
computeInterval() //Should be three seconds
let nineTheWrongWay = referenceWalltime + (walltimeInterval * 3)
let nineTheRightWay = dispatch_time(referenceWalltime,
Int64(walltimeInterval) * 3)
dispatch_after(nineTheWrongWay,
dispatch_get_main_queue(), finalPrintln)
//********** THE ABOVE DOES NOT WORK CORRECTLY - prints 6 seconds later
dispatch_after(nineTheRightWay,
dispatch_get_main_queue(), finalPrintln)
//********** THE ABOVE WORKS CORRECTLY - prints 9 seconds later
}
func finalPrintln () {
let now = walltimeNow()
println("I should be printing nine seconds from reference time.")
println("It's actually \(referenceWalltime - now) nanoseconds after")
}
func computeInterval () {
walltimeInterval = referenceWalltime - newWalltime
//********** dispatch_walltimes actually count backwards, and *CANNOT* be
//********** negative: writing `newWalltime - referenceWalltime` will crash
}
}
let intervaller = IntervalMaker()
intervaller.scheduleWalltimeSequence()

Apple Swift - Unable to retrieve data from CMPedometer's handler

I am trying out Swift with some of the new iOS 8 API's and have tried the best part of the day to get the CMPedometer queryPedometerDataFromDate API to return any data within the handler. I believe its an error on my part, getting a little confused with the syntax.
Here is my code, with comments on what prints out:
var ped = CMPedometer()
var stepsTaken = NSNumber(int: 0)
println(dateNow) // 2014-06-07 21:23:55 +0000
println(dateMidnight) // 2014-06-07 00:00:00 +0000
ped.queryPedometerDataFromDate(dateMidnight, toDate: dateNow, withHandler:{
data, error in
println("Test1") // Does not print
println(error) // Does not print
stepsTaken = data.numberOfSteps
})
println("My Int Value \(stepsTaken)") // My Int Value 0
It works for me with CMPedometer queryPedometerDataFromDate, if i define the CMPedometer as a class wide constant:
let pedometer = CMPedometer()
and then in a func i'm using:
self.pedometer.queryPedometerDataFromDate(today, toDate: now, withHandler: ...
A code sample from Hipster.
import CoreMotion
let lengthFormatter = NSLengthFormatter()
let pedometer = CMPedometer()
pedometer.startPedometerUpdatesFromDate(NSDate(), withHandler: { data, error in
if !error {
println("Steps Taken: \(data.numberOfSteps)")
var distance = data.distance.doubleValue
println("Distance: \(lengthFormatter.stringFromMeters(distance))")
var time = data.endDate.timeIntervalSinceDate(data.startDate)
var speed = distance / time
println("Speed: \(lengthFormatter.stringFromMeters(speed)) / s")
}
})
After many hours playing around with the syntax, thinking I have made a rookie error, I tried alternative API's and found that the following works to grab pedometer data:
var ped2 = CMStepCounter()
ped2.queryStepCountStartingFrom(dateMidnight, to: dateNow, toQueue: NSOperationQueue(), withHandler:{data, error in
println("Test 2") // "Test 2"
println(data) // 491 (I really should go for a walk!)
println(error) // nil
})
I will file a radar with Apple as it looks like a bug in the new API. Also the CMStepCounter class is due to be deprecated for CMPedometer. From CMStepCounter.h:
NS_CLASS_DEPRECATED_IOS(7_0,8_0,"Use CMPedometer instead")
You're querying the data, which goes onto another thread. The execution continues after your call, and your NSNumber is still at 0. By the time you've come back you've printed the message a long time ago, and have no way of recovering the stepsTaken.
You need to keep a reference to your ped variable. Something like:
self.ped = CMPedometer();
Currently your ped variable is going out of scope before the handler is even called.

Resources