Glacially slow shake response


#1

I’ve entered all the code in chapter 8 but the response to the shake doesn’t leave me confident enough to layer the challenge on top of it. I know UIEventSubtypeMotionShake actually responds to the initiation of shaking as opposed to “while shaking” so my iPod has been quiet for several seconds before I try a new shake. But still, it takes an awfully mighty shake and even then there seems to be a latency period of many seconds where it won’t respond. It’s as if it’s super busy with the tilting and only sporadically avails itself to check for a shake. Is this expected behavior for this program?

I’ve played with the smoothing parameters but they affect the tilting appearance far more than any influence over shake sensitivity. And there doesn’t seem to be any way to regulate the sensitivity of motionBegan:withEvent:

Thanks,
Byrne

edit: I ran the shake program described above on the simulator instead of my iPod and it worked fine.
(My deployment targets are iPhone 4.3, my iPod4 is running 4.3.5)


#2

I hear you. Getting the iPhone 4 to respond to a shake “reliably” (or should I say “predictably”) was much more difficult than I expected, enough that I don’t see implementing this in an app as the only way to achieve some effect.

For me, it takes about five shakes at about 2/3 speed to get it to recognize the shake. (That’s with up/down, side-to-side [like hammering a nail in a wall in front of me with the edge of the device], and front-to-back [like hammering a nail on the table with the face of the device].)

And I sure wouldn’t want to risk slipping, heaving the device into the air. Clever demo a couple years ago; I think I’ll pass.

EDIT: Changing the accelerometer to update more often (I changed the interval from 0.1 to 0.01) appears to make shake detection much more reliable. Now it takes only a couple of shakes at about 1/4 speed to be recognized as a shake. Play with the interval to see what works best for you.

EDIT 2: The book alludes to this in the “For the More Curious” section, noting that “An application that detects shakes is updating at a high frequency.” For such applications it recommends an update interval between 1/70 and 1/100 seconds. Of course, that also means the device will use more battery power. Everything is a trade-off.


#3

Thanks for the feedback, I should have reread that section a third time. I guess the necessity of a higher frequency is due to the fact that if a sample is taken just before the shake and the shake is over by the time of the next sampling no event will be noticed.

One of my points of confusion has been the way the term acceleration is misused by Apple. (As a Physic’s teacher of 24 years, I can be audacious about this!) The device’s orientation is not reporting true accelerations but is measuring the earth’s field strength component along the three spacial axes. Otherwise all these axes would report zero if the device were stationary (or moving at uniform velocity). So shake is looking for changes in these field strength values which really does indicate acceleration. (So I guess you could measure the device’s acceleration by polling two nominal accel values at different times, finding their difference and dividing by the sampling time interval.)

Again, thanks for your help,
Byrne


#4

Apple’s use of “acceleration” confused me as well (and sometimes still does). Then again I never even understood a wall pushing back on me, so what do I know. :wink:


#5

Hmm, I don’t agree here.

Using my iPod, I get a reasonably fast shake response regardless of the rate I am receiving accelerometer information. I interpret the recommendation on page 155 as the rate you would need to detect shakes yourself, without using motionBegan:withEvent:.

The shake response (from motionBegan:withEvent:) does seem to deteriorate with increased cpu usage. If I set the update rate to 1/100 and also use the setNeedsDisplay every time, the shake response is not good. If I put in a counter to only setNeedsDisplay every 10 times, I get roughly the same shake response that I get with 1/10 rate and setNeedsDisplay every time.

(edit: Try implementing the motionCancelled:withEvent: and motionEnded:withEvent: methods to just NSLog the events. When I do this, there seem to be some occasions where a shake is started, then several seconds pass before the shake is cancelled. Why? Don’t know. All I do is shake until the Shake started message is received and then stop. At any rate, the time between shake started and shake cancelled is dead time where we can’t detect shakes. So if you are trying to detect shakes one after the other, this may be an issue for you.)

By the way, I’m sure a physics teacher can appreciate that, with only local information (no tidal forces), it is impossible to differentiate acceleration from gravity (Einstein’s equivalence principle). You can think of the data from UIAccelerometer as the equivalent acceleration, the acceleration that would be inferred from the accelerometer data if the device were in a region of zero gravitational field.

-K


#6

I need help… I searched the whole web and couldn’t find solution to my problem.

My UIView does not respond to shake, even though it becomes firstResponder successfully, i checked with isFirstResponder method.

What could be a problem? Anyone can help please?