ios - Efficient way to find the nearest point from a set of points to the touched point inbetween a range? -
i have array of cgpoints used drawn catmull-rom bezierpath using cgpoint interpolation jnfisher want choose nearest point on path touch point when user touches anywhere inside range around point on path. range specified imaginary square containing point on path tolerance before , after every point on path along x , y axis. strategy 1. set tolerance each point on path observe if location of touch inside square these sides on x axis:(discoverypoint.x - tolerance discoverypoint.x + tolerance) , on y axis:(discoverypoint.y - tolerance discoverypoint.y + tolerance. 2.calculate distance between touched point , points in array contain touched point inside square. 3. choose minimum amount distances. 4. find point has least distance touched point. there easier , more efficient way? highly appreciate help.thanks in advance.
-(void)drawrect:(cgrect)rect{ self.modifiablepath = [uibezierpath interpolatecgpointswithcatmullrom:self.pointsarray closed:yes alpha:0.9]; self.modifiablepath.linewidth = 20.0; [[uicolor yellowcolor] setstroke]; [self.modifiablepath stroke]; } - (void)touchesbegan:(nsset *)touches withevent:(uievent *)event{ { cgpoint touchedpoint = [[touches anyobject]locationinview:self]; cgpoint discoverypoint; cgfloat tolerance = 20; int numofpointswithmindistance=0; nsdictionary* pointswithmindistancewithkeys = [nsdictionary new]; nsdictionary* mindistanceswithkeys = [nsdictionary new]; // had create these 2 arrays because there's no such thing [nsdictionary objectatindex:] nsarray *pointswithmindistancesarray = [nsarray new]; nsarray *mindistancearray = [nsarray new]; (nsvalue * cgpointval in self.pointsarray){ discoverypoint = cgpointval.cgpointvalue; if (fabs(touchedpoint.x - discoverypoint.x)<tolerance && fabs(touchedpoint.y - discoverypoint.y)<tolerance) { numofpointswithmindistance++; //adding points touchedpoint inside range(square). [pointswithmindistancewithkeys setvalue:[nsvalue valuewithcgpoint:discoverypoint] forkey:[nsstring stringwithformat:@"%d",numofpointswithmindistance]]; //calculating distance between points touchedpoint in range(square) , adding them array. cgfloat distance = hypotf(touchedpoint.x - discoverypoint.x, touchedpoint.y - discoverypoint.y); [mindistanceswithkeys setvalue:[nsnumber numberwithfloat:distance] forkey:[nsstring stringwithformat:@"%d",numofpointswithmindistance]]; } } //finding key minimum distance between distances touchedpoint. mindistancearray = [mindistanceswithkeys allvalues]; pointswithmindistancesarray = [pointswithmindistancewithkeys allvalues]; cgfloat k = [[mindistancearray objectatindex:0] floatvalue]; int keyofpointwithmindistance =0; (unsigned = 1; <[mindistancearray count]; i++){ if([[mindistancearray objectatindex:i] floatvalue] < k){ k = [[mindistancearray objectatindex:i] floatvalue]; keyofpointwithmindistance=i; }else{ keyofpointwithmindistance=0; } } //getting nearest cgpoint value smallest distance touchedpoint. nsvalue * valueofnearestpoint =[pointswithmindistancesarray objectatindex:keyofpointwithmindistance]; cgpoint nearestpointtotouchedpoint =valueofnearestpoint.cgpointvalue; }
- (void)touchesbegan:(nsset *)touches withevent:(uievent *)event{ cgpoint touchedpoint = [[touches anyobject]locationinview:self]; cgpoint discoverypoint; cgfloat tolerance = 20; // had create these 2 arrays because there's no such thing [nsdictionary objectatindex:] nsarray *pointsarray; cgfloat keyofpointwithmindistance = -1; cgpoint nearestpointtotouchedpoint = cgpointzero; int index = 0; int keyindex = nsnotfound; (nsvalue * cgpointval in self.pointsarray){ discoverypoint = cgpointval.cgpointvalue; if (fabs(touchedpoint.x - discoverypoint.x)<tolerance && fabs(touchedpoint.y - discoverypoint.y)<tolerance) { //calculating distance between points touchedpoint in range(square) , adding them array. cgfloat distance = hypotf(touchedpoint.x - discoverypoint.x, touchedpoint.y - discoverypoint.y); if (keyofpointwithmindistance == -1 || keyofpointwithmindistance < distance) { keyofpointwithmindistance = distance; nearestpointtotouchedpoint = discoverypoint; keyindex = index; } index++; } } //update self.pointsarray using keyindex if keyindex != nsnotfound { } }
Comments
Post a Comment