简体   繁体   中英

iPhone detecting touches on a map image

I have a static map image with a bunch of circles and squares on it that depict cities. I have loaded the image into an imageView that is sub-classed under a scrollView so that I can capture user touches and zoom/scroll across the map. My challenge is that I want to pop-up a label whenever a user touches one of these circles/squares for a city to tell them which city it is and possibly load a detail view for the city. I figured I could pre-load all the relative CGPoints for the cities based on the imageView map into a dictionary so I can reference them during a "touchesBegan" event, but I'm quickly getting in over my head and possibly going about this the wrong way.

So far everything is working and I can capture the CGPoint x and y coordinates of touches. The biggest issue I have is determining the proximity of the user touches to a discrete point I may have in the dictionary. In other words if the dictionary has "Boston = NSPoint: {235, 118};" how can I tell when a user is close to that point without making them repeat the touch until it is exact? Is there an easy way to determine if a user touch is "close" to a pre-existing point? Am I going about this the right way?

Any advice or slaps in the back of the head are welcome.

Thanks, Mike

you can either use an R-Tree , or you can calculate the proximity of the touch to each visible point in the current view. To calculate the proximity you would normally use the Pythagorean theorem but in this case you can skip the square-root because you're only comparing the relative sizes. Also you can declare a distance cut off if you like say 50 pixels squared to 2500. So you'd put the result into an object containing distance and reference point and put the objects in an NSMutableArray, not adding the results under your cutoff, and select the minimum result.

So if you have a touched point pT , then for each point pN , you'd calculate:

d=(pT.x-pN.x)*(pT.x-pN.x) + (pT.y-pN.y)*(pT.y-pN.y); //d is the squared distance

The point pN with the minimum d is the point that was closest to pT . And like I said if you want only touches within 10 pixels to count, you can test that d <= 10*10 ;

The method of testing for touches within a 20x20 square area works too, except if two points are within 20 pixels of each other, then you need to know which is the closest touched point.

You could use UIButtons to represent the cities. Then you'll get the standard touch, highlight, etc, behaviors with less effort. Adding the buttons as subviews on your map should cause them to scale and scroll along with the map.

if i understand it correctly, you want to know if the point at which the user tapped is "close" enough to a point that is marked as a city.

you would have to quantify close ie set a threshold value after which the tap is farther, before which the tap is closer.

once you do that, calculate the cartesian coordinate distance sqrt ( (x1-x2)^2 + (y1-y2)^2) for each element ( read dictionary with x,y values for cities) in the array and store the results in another array. then take the minimum of the result. the index of that result is the city that is closest to the tap if it is lesser than the said threshold.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM