📄 pick.c
字号:
/*pick object codepick object contains screen pick, map axis, view configuration and picking*/#include <stdio.h>#include "main.h"#include "axis.h"#include "data.h"#include "map.h"#include "render.h"#include "plane.h"#include "view.h"#include "pick.h"PickLine picklist[PICKNLIST], lastpick = 0;string pickfile = "stdio";#define PICKDIR(pick,axis) pick iaxis[axis]#define PICKFRAME0(pick,axis) pick index[0][PICKDIR(pick,axis)]#define PICKFRAME(pick,axis) pick index[PICKDIR(pick,axis)]/* initialize pick object */PickInit () { int i; static first=1; for (i=0; i<PICKNLIST; i++) { if (!first) FREE(picklist[i]); picklist[i] = 0; } PickRead (); lastpick = 0; if (!first) ViewDrawAll(); first = 0; }/* decode an x,y by shadow lookup */PickDecode (x,y,pick,print)int x, y, print;PickPoint pick; { extern Render render; extern View view; extern Data data; Message message; int iaxis, jaxis, index1[DATA_NAXIS], i, diff, idiff, isame; Shadow_ shadow, shadow1; Buffer buffer; /* no pick made */ if (!render || !view || !data) return; /* no invalid pick */ for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pick->iaxis[iaxis] = NO_INDEX; pick->index[iaxis] = NO_INDEX; } /* decode directions; using neighboring horizontal & vertical pixels */ shadow = RenderShadowValue(render,x,y); if ((int)shadow == NO_INDEX) return; PickDecodeShadow (shadow,pick->index); for (i=1; ; i++) { shadow1 = RenderShadowValue(render,x+i,y+i); if ((int)shadow1 == NO_INDEX) break; if (shadow1 == shadow) continue; PickDecodeShadow (shadow1,index1); for (jaxis=1, diff=0; jaxis<DATA_NAXIS; jaxis++) diff += (index1[jaxis] != pick->index[jaxis]); if (diff == 2) break; } if ((int)shadow1 == NO_INDEX || shadow1 == shadow || diff < 2) { for (i= -1; ; i--) { shadow1 = RenderShadowValue(render,x+i,y+i); if ((int)shadow1 == NO_INDEX) break; if (shadow1 == shadow) continue; PickDecodeShadow (shadow1,index1); for (jaxis=1, diff=0; jaxis<DATA_NAXIS; jaxis++) diff += (index1[jaxis] != pick->index[jaxis]); if (diff == 2) break; } } for (iaxis=1, isame=diff+1, idiff=1; iaxis<DATA_NAXIS; iaxis++) { if (pick->index[iaxis] != index1[iaxis]) { pick->iaxis[idiff++] = iaxis; } else { pick->iaxis[isame++] = iaxis; } } pick->iaxis[AXIS_COLOR] = DATA_VALUE;/* if (diff != 2) { printf ("%d %d %d %d\n",shadow,i,shadow1,diff); for (i=0; i<DATA_NAXIS; i++) printf ("%7d: ",i); printf ("\n"); for (i=0; i<DATA_NAXIS; i++) printf ("%8d ",pick->iaxis[i]); printf ("\n"); for (i=0; i<DATA_NAXIS; i++) printf ("%8d ",pick->index[i]); printf ("\n"); for (i=0; i<DATA_NAXIS; i++) printf ("%8d ",index1[i]); printf ("\n"); printf ("\n"); return; }*/ buffer = DataBuffer (data); pick->index[DATA_VALUE] = buffer[shadow] - DATA_VALUE_BASE; /* print pick in message */ if (print) { sprintf (message,"dir=%s frame=%d,%d,%d %s=%g %s=%g %s=%g %s=%g %s=%g %s=%g", AxisLabel(DataAxis(data,pick->iaxis[AXIS_DEEP])), pick->index[pick->iaxis[AXIS_DEEP]], pick->index[pick->iaxis[AXIS_4D]], pick->index[pick->iaxis[AXIS_5D]], AxisLabel(DataAxis(data,DATA_AXIS1)), AxisValue(DataAxis(data,DATA_AXIS1),pick->index[DATA_AXIS1]), AxisLabel(DataAxis(data,DATA_AXIS2)), AxisValue(DataAxis(data,DATA_AXIS2),pick->index[DATA_AXIS2]), AxisLabel(DataAxis(data,DATA_AXIS3)), AxisValue(DataAxis(data,DATA_AXIS3),pick->index[DATA_AXIS3]), AxisLabel(DataAxis(data,DATA_AXIS4)), AxisValue(DataAxis(data,DATA_AXIS4),pick->index[DATA_AXIS4]), AxisLabel(DataAxis(data,DATA_AXIS5)), AxisValue(DataAxis(data,DATA_AXIS5),pick->index[DATA_AXIS5]), AxisLabel(DataAxis(data,DATA_VALUE)), AxisValue(DataAxis(data,DATA_VALUE),pick->index[DATA_VALUE])); UIMessage (message); } return; }PickDecodeShadow (shadow,index)Shadow_ shadow;int index[]; { extern Data data; int iaxis; for (iaxis=DATA_NAXIS-1; iaxis>0; iaxis--) { index[iaxis] = shadow / AxisStride(DataAxis(data,iaxis)); shadow = shadow % AxisStride(DataAxis(data,iaxis)); } }/* find a pick list */PickLinePickFind (dir3,frame3,dir4,frame4,dir5,frame5)int dir3, frame3, dir4, frame4, dir5, frame5; { int iset; for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset] && dir3 == PICKDIR(picklist[iset]->,AXIS_DEEP) && frame3 == PICKFRAME0(picklist[iset]->,AXIS_DEEP) && (dir4 == NO_INDEX || (dir4 == PICKDIR(picklist[iset]->,AXIS_4D) && frame4 == PICKFRAME0(picklist[iset]->,AXIS_4D) && dir5 == PICKDIR(picklist[iset]->,AXIS_5D) && frame5 == PICKFRAME0(picklist[iset]->,AXIS_5D) ))) return (lastpick=picklist[iset]); } return (lastpick=0); }/* return size of pick list */PickSize () { int iset, nset; for (iset=0, nset=0; iset<PICKNLIST; iset++) { if (picklist[iset]) nset++; } return (nset); }/* return pick axis */PickAxis () { int iset; for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset]) return (PICKDIR(picklist[iset]->,AXIS_DEEP)); } return (NO_INDEX); }/* return pick direction */PickDir (pickline)PickLine pickline; { if (!pickline) return (NO_INDEX); else return (PICKDIR(pickline->,AXIS_DEEP)); }/* return pick count */PickCount (pickline)PickLine pickline; { if (!pickline) return (NO_INDEX); else return (pickline->npick); }/* return pick sample ipick and idim */PickIndex (pickline,ipick,idim)PickLine pickline;int ipick, idim; { if (!pickline) return (NO_INDEX); if (ipick < 0 || ipick >= NPICK) return (NO_INDEX); if (idim < 0 || idim >= DATA_NAXIS) return (NO_INDEX); return (pickline->index[ipick][idim]); }/* return pick list frame */PickFrame (ipick)int ipick; { int iset; for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset]) ipick--; if (ipick < 0) return (PICKFRAME0(picklist[iset]->,AXIS_DEEP)); } return (NO_INDEX); }/* print information about pick object */PickInfo () { Message message; PickLine pickline = 0; int iset; pickline = lastpick; if (pickline == 0) { for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset]) { pickline = picklist[iset]; } } } if (pickline) { sprintf (message,"Pick: nset=%d dir=%d frame=%d npick=%d pickfile=%s", PickSize(), PICKDIR(pickline->,AXIS_DEEP), PICKFRAME0(pickline->,AXIS_DEEP), pickline->npick, pickfile); } else { sprintf (message,"Pick: nset=0 pickfile=%s",pickfile); } UIMessage (message); }/* add valid pick to current set */PickAdd (x,y)int x, y; { int i, iset, iaxis; PickPoint_ pick; PickLine pickline; /* recover set */ if (PickDecode (x,y,&pick,1) == NO_INDEX) return; /* find pick set */ if ((pickline = PickFind (PICKDIR(pick.,AXIS_DEEP),PICKFRAME(pick.,AXIS_DEEP), PICKDIR(pick.,AXIS_4D),PICKFRAME(pick.,AXIS_4D), PICKDIR(pick.,AXIS_5D),PICKFRAME(pick.,AXIS_5D))) == 0 ) { for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset] == 0) { NEW (PickLine,picklist[iset],1); pickline = picklist[iset]; pickline->npick = 0; for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pickline->iaxis[iaxis] = pick.iaxis[iaxis]; pickline->index[0][iaxis] = pick.index[iaxis]; } break; } } /* no more allocation */ if (iset == PICKNLIST) return; } if (pickline->npick == NPICK) return; for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pickline->index[pickline->npick][iaxis] = pick.index[iaxis]; } pickline->npick++; PickDraw (pickline,DRAW); }/* add valid pick to current set */PickInsert (x,y)int x, y; { int i, span, metric, near, inear, iset, iaxis, insert; PickPoint_ pick; PickLine pickline; /* recover set */ if (PickDecode (x,y,&pick,1) == NO_INDEX) return; /* find pick set */ if ((pickline = PickFind (PICKDIR(pick.,AXIS_DEEP),PICKFRAME(pick.,AXIS_DEEP), PICKDIR(pick.,AXIS_4D),PICKFRAME(pick.,AXIS_4D), PICKDIR(pick.,AXIS_5D),PICKFRAME(pick.,AXIS_5D))) == 0 ) { for (iset=0; iset<PICKNLIST; iset++) { if (picklist[iset] == 0) { NEW (PickLine,picklist[iset],1); pickline = picklist[iset]; pickline->npick = 0; for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pickline->iaxis[iaxis] = pick.iaxis[iaxis]; pickline->index[0][iaxis] = pick.index[iaxis]; } break; } } /* no more allocation */ if (iset == PICKNLIST) return; } if (pickline->npick == NPICK) return; /* find insert point */ /* if one or less existing points, add to end */ if (pickline->npick <= 1) { insert = pickline->npick; } /* base insertion point on nearest existing pick */ else { PickDraw (pickline,ERASE); near = 1000000; inear = 0; for (i=0; i<pickline->npick; i++) { metric = 0; for (iaxis=1; iaxis<DATA_NAXIS; iaxis++) { span = (pickline->index[i][iaxis] - pick.index[iaxis]); metric += span * span; } if (metric < near) { near = metric; inear = i; } } /* closest point is first point */ if (inear == 0) { /* between second point */ if (PickBetween (pick.index,pickline->index[0],pickline->index[1])) { insert = 1; } /* or before first point */ else { insert = 0; } } /* closest point is last point */ else if (inear >= pickline->npick-1) { /* between next to last point */ if (PickBetween (pick.index,pickline->index[pickline->npick-1],pickline->index[pickline->npick-2])) { insert = pickline->npick-1; } /* after last point */ else { insert = pickline->npick; } } /* closest point in middle of line */ else { /* between previous point */ if (PickBetween (pick.index,pickline->index[inear],pickline->index[inear-1])) { insert = inear; } /* between subsequent point */ else { insert = inear + 1; } } } /* shift points after insertion point */ for (i=pickline->npick; i>insert; i--) { for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pickline->index[i][iaxis] = pickline->index[i-1][iaxis]; } } /* insert */ for (iaxis=0; iaxis<DATA_NAXIS; iaxis++) { pickline->index[insert][iaxis] = pick.index[iaxis]; } pickline->npick++; /* redraw */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -