Check if CGPoint is close to another CGPoint - iphone

In my app, I have two buttons and a timer that fires an action every second. Each second, it generates four random numbers. The numbers are used as X and Y values of the buttons, and the buttons move to the new points. However, sometimes the new points are close, so the buttons overlap. How can I check to make sure this doesn't happen? I already tried checking if CGRectIntersectsRect of the button frames, but that does nothing.
Thanks for any help!

Just to verify, your CGRectIntersectsRect code/structure looks somewhat similar to this right:
-(void)update {
// This is the method that gets called every second where your four numbers are randomly generated
// Generate random numbers here
// Position the buttons based on 2 of the random numbers
if (CGRectIntersectsRect(button1.frame, button2.frame) {
// regenerate the four numbers
// reposition your buttons
}
Also, I was just wondering, why each second? Maybe perform it on a different thread if you want, and make it 10 times a second so the button overlap does not show for too long, but it depends on how fast you want it I guess.... also why are you generating 4 random numbers if you are only using two (as far as we know).
But, ultimately we need to see your code, otherwise we cannot see what you may be doing wrong.

Related

Displaying decimal numbers on 2D array grid view

I am trying to create a 2D grid with the following features:
It will have more than 100 X and Y cells, so I cannot show them all on the screen. Therefore, I want the user to be able to slide it to see the rest.
Using text fields, the user needs to be able to enter some values and I want to display those values in the corresponding cell. If the user entered 5, then (X = 5), (Y = how many minutes have passed since the user started using the application.)
The user can also enter decimal numbers.
Except 3, I succeeded but I need help about entering decimal numbers.
Actually, I have something like this, but I would like to write on the lines that separate the cells. Because sometimes the user might want to enter, say, (5.3); and I am not sure how to display that.
I appreciate your help.
Reference I used: https://medium.com/codechai/flutter-grid-view-from-2d-array-5467e4da5243

How to make the set of possible values for UISlider an open interval?

I am using a UISlider to allow a user to choose among four options. I ask the user a question of the form "how much do you like this thing?", they respond by moving the slider, and then behind the scenes I map the value of the slider to one of four elements of an array. I want the first quarter of the slider to correspond to the first element of the array, the second quarter of the slider to correspond to the second element of the array, and so on.
By default, the range of a slider is [0,1], so one natural way to do what I want is:
let index = Int(rangedSlider.value * Float(currentAnswers.count) )
assuming that rangedSlider is the name of the outlet connected to the UISlider in question, and currentAnswers is the array of answers I'm mapping to. The issue with this is that if the user moves the slider all the way to the right, that sets the value of the slider to 1, which maps to index 4 by the formula above (assuming there are four answers). I can always add an additional line of code that takes care of that case separately,
if rangedSlider.value == 1 { index = currentAnswers.count - 1 }
but I prefer a one line solution.
I can also set the max value of the slider to 0.99 in the Storyboard and stick with the first line of code I wrote, but I want to know: is there a built-in way to make the range of UISlider values an open interval? Is there a better way to get the behavior I want?
Is this any more complicated than:
let index = Int(rangedSlider.value * Float(currentAnswers.count - 1))
Or have I misunderstood the problem you're having?
That way your index will be returned as a number between 0 and 3 with 0 corresponding to the first answer and 3 corresponding to the fourth answer.

Dynamically extendable ladder shape

My question is two parts, and answers to either would be helpful.
I want to make a Master shape that can be expanded on one axis only. When you expand it the image inside repeats itself. I still want to be able to resize the image proportionally. See the picture for example.
Discrete extendable ladder
The second part of my question is how to restrict this expansion to discrete segments, meaning that the expanded image snaps to the next segment when it gets close enough, but nothing in between. I think I can do this with the BOUND() function, just not sure how.

How to Create Customized Time Bar in iPhone?

I need to create a time bar like the image attached.The blue lines are the dates indicating some actions.The big Red Arrow mark is used to slide for selecting any of the blue line. At background the bar is divided into years.The small red circles are to indicate the years.
Any idea ,how do i start?
Thanks
If the blue bars don't move a lot, and you don't need to resize this view very often (which is usually the case on an iPhone), then I'd recommend subclassing UIControl (or UIView) and implement it yourself.
Have an NSArray property storing NSDate objects and methods like addDate:, removeDate:, removeDateAtIndex: to change it's content from an other object (like your view controller). In these methods you add or remove the passed date and call [self setNeedsDisplay]; to redraw the lines.
You will need a few methods to calculate the position (in pixels) of a date on the slider and to calculate the date at a specific coordinate. This should be easy to to (basic linear interpolation).
And assuming that the red slider is only able to point to blue lines (but not between them) add a NSDate pointer variable to the currently selected date. In the
In the drawRect: method, you need to draw all the lines using CoreGraphics functions. Look up the documentation if you need help with this. Apple has some great sample apps too.
To show the red slider, you could either add a custom UIImageView, with a UIPanGestureRecognizer and make sure it only moves vertically in the gesture handler. Or it might be possible to add a UISlider without track images (I'm not 100% sure about that). In either case, you need to adjust the slider's position once the user let's go and make it jump to the nearest blue line.
A rough idea,
1. Get the length of the entire TimeBar.Let it be t.
2. Divide by x=numberofYears*365.let it be t_eachday_pos=t/x
3. get the position of each day,calculate its offset as daycount*t_eachday_pos;
4. Add your blueLine as a customButton.
5. To do some action, pass the x daynumber(eg. day 245 of year 2 etc.)
Try this, I have used the same thing in one of my app, and it is working

how to efficiently find a rect # some x,y point with iphone sdk

I am looking for an efficient way to handle the image/frame detection from touch methods. Let's say i am building a keyboard or similar to this. I have 'n' number of images placed on the UI. When someone touches an alphabet (which is an image), i can do the following to detect the corresponding letter
1) CGRectIntersectsRect(..,..) : if i use this, then i need to check each & every letter to find out what letter exists at that touch point (let's say 100,100). This becomes O(n). If i move my finger accross the screen, then i will get m points & all corresponding image detection becomes O(n*m) which is not good.
2) Other way is building a hash for each & every x,y position so that the look up will be simply O(1). But again this will be a memory constraint as i need to store 300*300 ( assuming i am using 300*300 screen size). if i reshuffle my letters, then everything needs to calculated again. So this is not good
In other words, i need some thing like , given a point (x,y), i need some way of finding which rectangle is covering that point efficiently.
Sorry for long post & any help would be grateful.
Thanks
If there are in a regular grid, then integer division by the grid size. Assuming you've a small, fixed screen size, a bucket array gives as similar gain ( a 2D grid, where each entry is a list of the rectangles which intersect that part of the grid ) is very fast if tuned correctly so the lists only have a few members. For unbounded or large spaces, KD trees can be used.
It's useful to have the rects you want as final targets set up as subviews as a larger UIView (or subclass) where you expect all these related hits to occur. For example, if you're building your own keyboard, you could add a bunch of UIButton objects as subviews and hit test those.
So, the easy and traditional way of hit testing a bunch of subviews is to simply have code triggered by someone hitting those buttons. For example, you could add the subviews as UIControl objects (which is a subclass of UIView that adds some useful methods for catching user touch events), and call addTarget:action:forControlEvents: to specify some method to be triggered when the user does something in the rect of that UIControl. For example, you can catch things like UIControlEventTouchDown or UIControlEventTouchDragEnter. You can read the complete list in the UIControl class reference.
Now, it sounds like you might be going for something even more customized. If you really want to start with a random (x,y) coordinate and know which rect it's in, you can also use the hitTest:withEvent: method of UIView. This method takes a point in a view, and finds the most detailed (lowest in the hierarchy) subview which contains that point.
If you want to use these subviews purely for hit testing and not for displaying, then you can set their background color to [UIColor clearColor], but don't hide them (i.e. set the hidden property to YES), disable user interaction with them (via the userInteractionEnabled BOOL property), or set the alpha below 0.1, since any of those things will cause the hitTest:withEvent: method to skip over that subview. But you can still use an invisible subview with this method call, as long as it meets these criteria.
Look at UIView's tag property. If your images are in UIViews or subviews of UIView, then you can set each tag and use the tag to look up in an array.
If not, then you can improve the speed by dividing your array of rectangles into sets that fit into larger rectangles. Test the outer rectangles first, then the inner rectangles. 25 rectangles would need only 10 tests worst case as 5 sets of 5.
Thanks Pete Kirkham & Tyler for your answers which are really helpful. Lets say i dont wanna use buttons as i am mainly displaying images as a small rectangles. To check for the rect # (x,y) , i can trigger that easily by making my grid as a square & finding
gridcolumn = Math.floor(pos.x / cellwidth); gridrow = Math.floor(pos.y / cellheight);
But my problem is with touchesMoved. Lets say i started # grid-1 & dragged till grid-9 (in a 3*3 matrix), in this case, i am assuming i will get 100-300 (x,y) positions, so everytime i need to run above formula to determine corresponding grid. This results in 300 calculations which might effect the performance.
So when i display an image as a rect, can i associate some id for that image? so that i can simply just save the ids in a list (from grid-1 to grid-9) so that i can avoid the above calculation.
Thanks for your help