void cmgoto (struct tty_display_info *tty, int row, int col) { int homecost, crcost, llcost, relcost, directcost; int use IF_LINT (= 0); char *p; const char *dcm; /* First the degenerate case */ if (row == curY (tty) && col == curX (tty)) /* already there */ return; if (curY (tty) >= 0 && curX (tty) >= 0) { /* We may have quick ways to go to the upper-left, bottom-left, * start-of-line, or start-of-next-line. Or it might be best to * start where we are. Examine the options, and pick the cheapest. */ relcost = calccost (tty, curY (tty), curX (tty), row, col, 0); use = USEREL; if ((homecost = tty->Wcm->cc_home) < BIG) homecost += calccost (tty, 0, 0, row, col, 0); if (homecost < relcost) relcost = homecost, use = USEHOME; if ((llcost = tty->Wcm->cc_ll) < BIG) llcost += calccost (tty, tty->Wcm->cm_rows - 1, 0, row, col, 0); if (llcost < relcost) relcost = llcost, use = USELL; if ((crcost = tty->Wcm->cc_cr) < BIG) { if (tty->Wcm->cm_autolf) if (curY (tty) + 1 >= tty->Wcm->cm_rows) crcost = BIG; else crcost += calccost (tty, curY (tty) + 1, 0, row, col, 0); else crcost += calccost (tty, curY (tty), 0, row, col, 0); } if (crcost < relcost) relcost = crcost, use = USECR; directcost = tty->Wcm->cc_abs, dcm = tty->Wcm->cm_abs; if (row == curY (tty) && tty->Wcm->cc_habs < BIG) directcost = tty->Wcm->cc_habs, dcm = tty->Wcm->cm_habs; else if (col == curX (tty) && tty->Wcm->cc_vabs < BIG) directcost = tty->Wcm->cc_vabs, dcm = tty->Wcm->cm_vabs; } else { directcost = 0, relcost = 100000; dcm = tty->Wcm->cm_abs; } /* * In the following comparison, the = in <= is because when the costs * are the same, it looks nicer (I think) to move directly there. */ if (directcost <= relcost) { /* compute REAL direct cost */ cost = 0; p = (dcm == tty->Wcm->cm_habs ? tgoto (dcm, row, col) : tgoto (dcm, col, row)); emacs_tputs (tty, p, 1, evalcost); if (cost <= relcost) { /* really is cheaper */ emacs_tputs (tty, p, 1, cmputc); curY (tty) = row, curX (tty) = col; return; } } switch (use) { case USEHOME: emacs_tputs (tty, tty->Wcm->cm_home, 1, cmputc); curY (tty) = 0, curX (tty) = 0; break; case USELL: emacs_tputs (tty, tty->Wcm->cm_ll, 1, cmputc); curY (tty) = tty->Wcm->cm_rows - 1, curX (tty) = 0; break; case USECR: emacs_tputs (tty, tty->Wcm->cm_cr, 1, cmputc); if (tty->Wcm->cm_autolf) curY (tty)++; curX (tty) = 0; break; } (void) calccost (tty, curY (tty), curX (tty), row, col, 1); curY (tty) = row, curX (tty) = col; }
void cmgoto(int row, int col) { int homecost, crcost, llcost, relcost, directcost; int use = USEREL; char *p, *dcm; /* First the degenerate case */ if (row == curY && col == curX) { return; /* already there */ } if (curY >= 0 && curX >= 0) { /* We may have quick ways to go to the upper-left, bottom-left, start-of-line, or start-of-next-line. Or it might be best to start where we are. Examine the options, and pick the cheapest. */ relcost = calccost(curY, curX, row, col, 0); use = USEREL; if ((homecost = Wcm.cc_home) < BIG) { homecost += calccost(0, 0, row, col, 0); } if (homecost < relcost) { relcost = homecost, use = USEHOME; } if ((llcost = Wcm.cc_ll) < BIG) { llcost += calccost(Wcm.cm_rows - 1, 0, row, col, 0); } if (llcost < relcost) { relcost = llcost, use = USELL; } if ((crcost = Wcm.cc_cr) < BIG) { if (Wcm.cm_autolf) if (curY + 1 >= Wcm.cm_rows) { crcost = BIG; } else { crcost += calccost(curY + 1, 0, row, col, 0); } else { crcost += calccost(curY, 0, row, col, 0); } } if (crcost < relcost) { relcost = crcost, use = USECR; } directcost = Wcm.cc_abs, dcm = Wcm.cm_abs; if (row == curY && Wcm.cc_habs < BIG) { directcost = Wcm.cc_habs, dcm = Wcm.cm_habs; } else if (col == curX && Wcm.cc_vabs < BIG) { directcost = Wcm.cc_vabs, dcm = Wcm.cm_vabs; } } else { directcost = 0, relcost = 100000; dcm = Wcm.cm_abs; } /* In the following comparison, the = in <= is because when the costs are the same, it looks nicer (I think) to move directly there. */ if (directcost <= relcost) { /* compute REAL direct cost */ cost = 0; p = dcm == Wcm.cm_habs ? tgoto(dcm, row, col) : tgoto(dcm, col, row); tputs(p, 1, evalcost); if (cost <= relcost) /* really is cheaper */ { tputs(p, 1, cmputc); curY = row, curX = col; return; } } switch (use) { case USEHOME: tputs(Wcm.cm_home, 1, cmputc); curY = 0, curX = 0; break; case USELL: tputs(Wcm.cm_ll, 1, cmputc); curY = Wcm.cm_rows - 1, curX = 0; break; case USECR: tputs(Wcm.cm_cr, 1, cmputc); if (Wcm.cm_autolf) { curY++; } curX = 0; break; } (void) calccost(curY, curX, row, col, 1); curY = row, curX = col; }