/* * K Y C U R S . C * * Routines associated with cursor moving on the karyotype. * * Written: CAS * Image Recognition Systems * 720 Birchwood Boulevard * Birchwood Science Park * Warrington * Cheshire * WA3 7PX * * Date: 3rd March 1987 * * Derived from cursmove.c from identbis.c from ident.c * * Interactively identify displayed object by pointing, and * return a command. Use the objectlist, marklist, activelist * type of data structure used in multi-processor karyotyping. * * Modifications * * 14 Oct 1994 jimp Replaced MAXCLASS by alc->srcf->undefclass * 4 Jul 1989 SEAJ Check Cpgroup in atchromosome(). * 2 Dec 1988 CAS Move VIEWED_STACK to dispform.h (Now only one define) * 18 Nov 1988 CAS Moved atchromosome here fron karyfix * 30 Aug 1988 CAS Major revamp to cope with different * screen layouts * 23 Aug 1988 CAS Bottom line stack => alc->scrf * 19 Aug 1988 CAS Removed second definition of kdisppos struct * 2 Feb 1988 CAS remove unnecessary kcont init */ #include #include #include #include #include #include #include #define CENTERHEIGHT 200 /* Vertical offset into chrom 'box' for dist calculations */ /* * external variables */ extern FILE *debug_channel; extern struct pframe *idf; /* defined in cursmove.c */ extern struct allkontr *alc; extern struct kcontrol *kcont; extern int stackocc[]; /* defined in karysubs1.c */ /* * statics - are these really needed ?? */ static struct kident *kidp; /* pointer to kid structure in karyotype phase*/ /* * external functions */ extern int curscol(); /* * note that sr is pointer to object number in seg phase, * to kid structure in karyotype phase (kylocate) * * set mym as mouse info structure, sr as above, phase as indicator, * seg or kary */ initselect(mym , sr, curs, phase) struct m2mouse *mym; struct ipoint *curs; int *sr; { initident(kcont,curs,&mukont->umouse); if (phase != 0) { kidp = (struct kident *) sr; curs->type = 40; curs->style = 6; cursframe(phase); curscol(OVERLAY2); showcursor(500,500); /* see setkyframe() in cursmove.c */ } else cursframe(0); } /* * E N D S E L E C T -- end this identify/command session * */ endselect(curs,phase) struct ipoint *curs; int phase; { endident(kcont->ool,kcont,curs,&mukont->umouse); if (phase != 0) { nocursor(); markident(kcont->current_obj,kcont->ool,kcont,0); } } /* * K Y L O C A T E -- identify box in karyotype from cursor position. * */ kylocate(curs) register struct ipoint *curs; { static int lastnearest = -1, lastinstack = 0, lastjpos = -1, oldkclass = -1; int i, j, ckol, clin, jpos; int dist, mindist, lindist, nearest, instack; struct kdisppos *dispk; /* * calculate DDGS-coord cursor pos, * restrict to DDGS frame */ curs->k = limxdigfrm(curs->k,idf); curs->l = limydigfrm(curs->l,idf); ckol = frdigsxpos(curs->k,idf); clin = frdigsypos(curs->l,idf); if (clin <0) clin =0; nearest = -1; mindist = 99999999; instack = 0; for (i=0; iscrf->undefclass; i++) { dist = (clin - (alc->scrf->disppos[i].lin + CENTERHEIGHT)); dist = dist * dist + ((ckol - alc->scrf->disppos[i].col) * (ckol - alc->scrf->disppos[i].col)); if (dist < mindist) { mindist = dist; nearest = i; } } /* * Get distance to stack line - only check further if something potentially * nearer than mindist */ lindist = (clin - (alc->scrf->stacklin + CENTERHEIGHT)); lindist *= lindist; if (lindist < mindist) { for (i=1; iscrf->stackcol[i] == 0) || (i > VIEWED_STACK)) break; dist = lindist + (ckol - alc->scrf->stackcol[i]) * (ckol - alc->scrf->stackcol[i]); if (dist < mindist) { instack = 1; nearest = i; mindist = dist; } } } /* * If 'best' match is not in stack line.. work out which chromosome * position is nearest */ if (!instack) { dispk = &alc->scrf->disppos[nearest]; jpos = (ckol - (dispk->col - (dispk->space/2))) / (dispk->space / dispk->npos); if (jpos >= dispk->npos) jpos = (dispk->npos)-1; else if (jpos < 0) jpos = 0; } else jpos = 0; if ((nearest != lastnearest) || (instack != lastinstack) || (jpos != lastjpos)) { lastnearest = nearest; lastinstack = instack; lastjpos = jpos; unbox(); /* erase old rectangle */ /* * are we at a chromosome ? */ atchromosome(kidp,nearest,jpos,instack); /* * if at a chromosome, draw box round it */ if ( kidp->no >= 0 ) { boxobj( kcont->mol[kidp->no], kcont->ivf +kidp->no , OVERLAY2); } /* * in any case highlight the class selected (but only if changed) */ if (kidp->kclass != oldkclass) showclass(kidp->kclass + 1,1); oldkclass = kidp->kclass; } return(1); } /* * A T C H R O M O S O M E -- * * given class and position and stack occupancy, redetermine class and * position and whether or not there is a chromsome there - set kid. * In any case load class into kid->kclass [abn if in stack and * not at chrom ] */ atchromosome (kid,cnum,pnum,instack) register struct kident *kid; register int cnum,pnum,instack; { register struct chromplist *qlist; register int knum; if (instack) { knum = stackocc[cnum]; if (knum < 0) { kid->kclass = alc->scrf->undefclass; kid->no = -1; return(-1); } qlist = kcont->mol[knum-1]->plist; if (qlist->Cpgroup) cnum = qlist->Cpgroup - 1; else cnum = qlist->pgroup - 1; pnum = qlist-> disppos - 1; } if (! kdentify(kid,cnum,pnum) ) { kid->no = -1; kid->kclass = instack ? alc->scrf->undefclass: cnum ; } } /* * D O S E L E C T * * Note that "dummy" is unused........ */ doselect(dummy,kc,curs) register struct kcontrol *kc; struct ipoint *curs; { kc->current_obj = objident(kc->ool,kc,curs); markident(kc->current_obj,kc->ool,kc,1); }