/// get_next_nav_cmd - gets next "navigation" command found at or after start_index /// returns true if found, false if not found (i.e. reached end of mission command list) /// accounts for do_jump commands but never increments the jump's num_times_run (advance_current_nav_cmd is responsible for this) bool AP_Mission::get_next_nav_cmd(uint16_t start_index, Mission_Command& cmd) { uint16_t cmd_index = start_index; Mission_Command temp_cmd; // search until the end of the mission command list while(cmd_index < (unsigned)_cmd_total) { // get next command if (!get_next_cmd(cmd_index, temp_cmd, false)) { // no more commands so return failure return false; }else{ // if found a "navigation" command then return it if (is_nav_cmd(temp_cmd)) { cmd = temp_cmd; return true; }else{ // move on in list cmd_index++; } } } // if we got this far we did not find a navigation command return false; }
/// advance_current_nav_cmd - moves current nav command forward /// do command will also be loaded /// accounts for do-jump commands // returns true if command is advanced, false if failed (i.e. mission completed) bool AP_Mission::advance_current_nav_cmd() { Mission_Command cmd; uint16_t cmd_index; // exit immediately if we're not running if (_flags.state != MISSION_RUNNING) { return false; } // exit immediately if current nav command has not completed if (_flags.nav_cmd_loaded) { return false; } // stop the current running do command _do_cmd.index = AP_MISSION_CMD_INDEX_NONE; _flags.do_cmd_loaded = false; _flags.do_cmd_all_done = false; // get starting point for search cmd_index = _nav_cmd.index; if (cmd_index == AP_MISSION_CMD_INDEX_NONE) { // start from beginning of the mission command list cmd_index = AP_MISSION_FIRST_REAL_COMMAND; }else{ // start from one position past the current nav command cmd_index++; } // search until we find next nav command or reach end of command list while (!_flags.nav_cmd_loaded) { // get next command if (!get_next_cmd(cmd_index, cmd, true)) { return false; } // check if navigation or "do" command if (is_nav_cmd(cmd)) { // save previous nav command index _prev_nav_cmd_index = _nav_cmd.index; // set current navigation command and start it _nav_cmd = cmd; _flags.nav_cmd_loaded = true; _cmd_start_fn(_nav_cmd); }else{ // set current do command and start it (if not already set) if (!_flags.do_cmd_loaded) { _do_cmd = cmd; _flags.do_cmd_loaded = true; _cmd_start_fn(_do_cmd); } } // move onto next command cmd_index = cmd.index+1; } // if we got this far we must have successfully advanced the nav command return true; }
/* This getch behaves like normal getch, except if we're running a macro, it * gets the next key in that macro instead of user input */ int Getch(){ int to_ret = 0; if((recording_macro || (to_ret = get_next_cmd()) == 0)){ while((to_ret = getch()) == ERR); record_cmd(to_ret); } return to_ret; }
/// get_next_do_cmd - gets next "do" or "conditional" command after start_index /// returns true if found, false if not found /// stops and returns false if it hits another navigation command before it finds the first do or conditional command /// accounts for do_jump commands but never increments the jump's num_times_run (advance_current_nav_cmd is responsible for this) bool AP_Mission::get_next_do_cmd(uint16_t start_index, Mission_Command& cmd) { Mission_Command temp_cmd; // check we have not passed the end of the mission list if (start_index >= (unsigned)_cmd_total) { return false; } // get next command if (!get_next_cmd(start_index, temp_cmd, false)) { // no more commands so return failure return false; }else if (is_nav_cmd(temp_cmd)) { // if it's a "navigation" command then return false because we do not progress past nav commands return false; }else{ // this must be a "do" or "conditional" and is not a do-jump command so return it cmd = temp_cmd; return true; } }
// set_current_cmd - jumps to command specified by index bool AP_Mission::set_current_cmd(uint16_t index) { Mission_Command cmd; // sanity check index and that we have a mission if (index >= (unsigned)_cmd_total || _cmd_total == 1) { return false; } // stop the current running do command _do_cmd.index = AP_MISSION_CMD_INDEX_NONE; _flags.do_cmd_loaded = false; _flags.do_cmd_all_done = false; // stop current nav cmd _flags.nav_cmd_loaded = false; // if index is zero then the user wants to completely restart the mission if (index == 0 || _flags.state == MISSION_COMPLETE) { _prev_nav_cmd_index = AP_MISSION_CMD_INDEX_NONE; // reset the jump tracking to zero init_jump_tracking(); if (index == 0) { index = 1; } } // if the mission is stopped or completed move the nav_cmd index to the specified point and set the state to stopped // so that if the user resumes the mission it will begin at the specified index if (_flags.state != MISSION_RUNNING) { // search until we find next nav command or reach end of command list while (!_flags.nav_cmd_loaded) { // get next command if (!get_next_cmd(index, cmd, true)) { _nav_cmd.index = AP_MISSION_CMD_INDEX_NONE; return false; } // check if navigation or "do" command if (is_nav_cmd(cmd)) { // set current navigation command _nav_cmd = cmd; _flags.nav_cmd_loaded = true; }else{ // set current do command if (!_flags.do_cmd_loaded) { _do_cmd = cmd; _flags.do_cmd_loaded = true; } } // move onto next command index = cmd.index+1; } // if we got this far then the mission can safely be "resumed" from the specified index so we set the state to "stopped" _flags.state = MISSION_STOPPED; return true; } // the state must be MISSION_RUNNING // search until we find next nav command or reach end of command list while (!_flags.nav_cmd_loaded) { // get next command if (!get_next_cmd(index, cmd, true)) { // if we run out of nav commands mark mission as complete complete(); // return true because we did what was requested // which was apparently to jump to a command at the end of the mission return true; } // check if navigation or "do" command if (is_nav_cmd(cmd)) { // save previous nav command index _prev_nav_cmd_index = _nav_cmd.index; // set current navigation command and start it _nav_cmd = cmd; _flags.nav_cmd_loaded = true; _cmd_start_fn(_nav_cmd); }else{ // set current do command and start it (if not already set) if (!_flags.do_cmd_loaded) { _do_cmd = cmd; _flags.do_cmd_loaded = true; _cmd_start_fn(_do_cmd); } } // move onto next command index = cmd.index+1; } // if we got this far we must have successfully advanced the nav command return true; }
gboolean get_next_command(gpointer data) { get_next_cmd(); return TRUE; }
void readline(shell_struct *shell) { int i; int end = 0; /*stoppe la saisie lorsqu'il vaut 1*/ int cur_col = 0; /*dans le terminal, indique la position du pointeur*/ struct winsize ws; ioctl(STDOUT_FILENO, TIOCGWINSZ, &ws); int colonnes = ws.ws_col; cur_col = shellPrompt(0); fflush(stdout); printf("\033[s"); struct termios oldt; if (tcgetattr(0, &oldt) != 0) { perror("Erreur tcget"); } struct termios newt = oldt; cfmakeraw(&newt); /* On change la structure termios default, on ajout un retour chariot a chaque newline detecté */ //newt.c_oflag |= (ONLCR | OPOST); if (tcsetattr(0, TCSANOW, &newt) != 0) { perror("Erreur tcset"); } char *com_hist; int count = 0;/*sauvegarde le nombre de char dans le buffer*/ int pos = 0;/*position du curseur dans le buffer buf*/ /*variables pour la tabulation*/ struct tab tabu; init_tab(&tabu); shell->buf[count] = '\0'; do { int t, m; int c = getbigchar(); switch (c) { case 1: /*C^a*/ while (pos > 0) { move_left(&pos,&cur_col,colonnes); } break; case 3: /*C^c*/ shell->buf[0] = '\0'; break; case 4: /*C^D*/ shell->end_b = 1; end = 1; shell->buf[0] = '\n'; break; case 5: /*C^e*/ while (pos != count) { move_right(&pos,&cur_col,colonnes,count); } break; case 9:/*TAB autocompletion */ tabu.tab = 1; /*tab est pressé pour la première fois*/ if (tabu.noccur == 0){ /*on récupère le dernier mot*/ tabu.lw = lastword(shell->buf, &(shell->buf[pos]), &(tabu.after_com), ' '); /*on sauvegarde la position*/ tabu.save_pos = pos - strlen(tabu.lw); } /*on efface*/ while( pos > tabu.save_pos){ move_left(&pos,&cur_col,colonnes); del_char(&pos, &cur_col, colonnes, &count, shell); } ++tabu.noccur; tabu.suggest = look_up_command(tabu.lw, tabu.noccur, tabu.after_com); if (!strncmp(tabu.suggest, "",1)){ tabu.noccur = 1; tabu.suggest = tabu.lw; /*on reprend le mot de base*/ } /*on insère*/ i = 0; while (tabu.suggest[i] != '\0') { insert_char(&pos, &cur_col, colonnes, &count, shell, tabu.suggest[i]); i++; } break; case 11:/*^Ck*/ strncpy(shell->save_buf, &shell->buf[pos], count - pos); shell->save_buf[(count + 1) - pos] = '\0'; while(pos != count) { del_char(&pos,&cur_col,colonnes,&count,shell); } break; case 13:/*Enter*/ end = 1; while (pos != count) { move_right(&pos,&cur_col,colonnes,count); } strncmp(shell->buf, "\0", 1) ? insert_new_cmd(shell->buf) : 0; shell->buf[pos] = '\0'; break; case 25:/*C^y*/ i = 0; while (shell->save_buf[i] != '\0') { insert_char(&pos, &cur_col, colonnes, &count, shell, shell->save_buf[i]); i++; } break; case 2: /*C^b*/ case KLEFT: move_left(&pos, &cur_col, colonnes); break; case 6:/*C^f*/ case KRIGHT: move_right(&pos, &cur_col, colonnes, count); break; case KUP:/*historique -*/ if (!is_empty_hist()){ printf("\033[u"); printf("\033[K"); cur_col = shellPrompt(0); com_hist = get_prev_cmd(); printf("%s", com_hist); strncpy(shell->buf, com_hist, strlen(com_hist) + 1); cur_col += strlen(com_hist); count = strlen(com_hist); pos = count; } break; case KDOWN:/*historique +*/ if (!is_empty_hist()){ printf("\033[u"); printf("\033[K"); cur_col = shellPrompt(0); com_hist = get_next_cmd(); printf("%s", com_hist); strncpy(shell->buf, com_hist, strlen(com_hist) + 1); cur_col += strlen(com_hist); count = strlen(com_hist); pos = count; } break; case KDEL: /* Touche suppr */ del_char(&pos,&cur_col,colonnes,&count,shell); break; case 127: /* Touche retour (del) */ tabu.noccur = 0; if (pos == 0) { break; } if (pos < count) { for (i = pos - 1; i < count; i++) { shell->buf[i] = shell->buf[i + 1]; } } else { shell->buf[pos - 1] = '\0'; } if (cur_col > 0) { printf("\033[D"); cur_col--; } else { printf("\033[A\033[%dC", colonnes - 1); cur_col = colonnes - 1; } count--; pos--; printf("%s ", &shell->buf[pos]); t = count - pos + 1; m = (t + cur_col - 1) / colonnes; if (m > 0) { printf("\033[%dA", m); } t -= m * colonnes; if (t > 0) { printf("\033[%dD", t); } else if (t < 0) { printf("\033[%dC", -t); } break; default: if (tabu.tab){ tabu.noccur = 0; } insert_char(&pos, &cur_col, colonnes, &count, shell, c); break; } fflush(stdout); } while (!end); if (tcsetattr(0, TCSANOW, &oldt) != 0) { perror("erreur tcset"); } printf("\n"); }