void update_cell(t_world *world, t_view *view, t_cell *cell) { int i; t_elem *cellrunner; float tmp_dist; int tmp_radius_add; t_cell *checked_cell; float area_increment; float dist_check; check_map_borders(cell); cell->pos.x += cell->dir.x; cell->pos.y += cell->dir.y; i = -1; while (++i < world->player_number) { cellrunner = world->players[i].cells->begin; while (cellrunner) { checked_cell = cellrunner->cell; if (cell != checked_cell) { tmp_dist = op_dist(&cell->pos, &checked_cell->pos); tmp_radius_add = cell->radius + checked_cell->radius; if (tmp_dist < tmp_radius_add) { dist_check = tmp_dist > (cell->radius - checked_cell->radius); if (dist_check) { if (cell->area >= checked_cell->area) { area_increment = get_area(cell, checked_cell, &tmp_dist); cell->area += area_increment; checked_cell->area -= area_increment; cell->radius = sqrtf(cell->area / M_PI); clear_cell(cell, view->surface); clear_cell(checked_cell, view->surface); checked_cell->radius = sqrtf(checked_cell->area / M_PI); draw_cell(checked_cell, view->surface); draw_cell(cell, view->surface); } } else { cell->area += checked_cell->area; checked_cell->area = 0; cell->radius = sqrtf(cell->area / M_PI); clear_cell(cell, view->surface); clear_cell(checked_cell, view->surface); checked_cell->radius = 0; draw_cell(checked_cell, view->surface); draw_cell(cell, view->surface); } } } cellrunner = cellrunner->next; } } }
/* Tries to fill the cell (i, j) with the next available number. Returns a flag to indicate if it succeeded. */ bool advance_cell(int i, int j) { int n = clear_cell(i, j); while (++n <= 9) { if (is_available(i, j, n)) { set_cell(i, j, n); return true; } } return false; }
void draw_player_cells(t_world *world, t_view *view, t_player *player) { t_elem *cellrunner; t_cell *cell; cellrunner = player->cells->begin; while (cellrunner) { cell = cellrunner->cell; clear_cell(cell, view->surface); if (cell->area < 9) { list_remove_elem(player->cells, cellrunner);/* dprintf(2, "\033[2J\033[HAlive cells: %d\n", player->cells->size);*/ } else { update_cell(world, view, cell); draw_cell(cell, view->surface); } cellrunner = cellrunner->next; } }
void browse(int type, int nc, int nr, void *in) { WINDOW *pdlscr, *wmenu, *wscroll, *warray, *whlab, *wvlab, *wtmp; char s[CHBUF],echobuf[CHBUF],line[CHBUF]; chtype ch; int i,j,eps,ioff,joff,iecho; int ncols, nrows, mycols; extern int colwid, dcols, drows, width[]; pdlscr = initscr(); /* sets LINES, COLS (which aren't macro constants...) */ clear(); /* Clear the screen before we start drawing */ colwid = width[type]; ncols = (COLS-HLAB)/colwid; dcols = MIN(nc,ncols); mycols = dcols*colwid; nrows = LINES-3; drows = MIN(nr,nrows); cbreak(); noecho(); nonl(); intrflush(pdlscr,FALSE); keypad(pdlscr,TRUE); /* Menu bar */ wmenu = subwin(pdlscr,1,COLS,0,0); wvlab = subwin(pdlscr,1,mycols,1,HLAB); wscroll= subwin(pdlscr,drows,mycols+HLAB,2,0); warray = subwin(wscroll,drows,mycols,2,HLAB); whlab = subwin(wscroll,drows,HLAB,2,0); keypad(warray,TRUE); scrollok(pdlscr,TRUE); scrollok(wscroll,TRUE); wmenu = subwin(pdlscr,1,COLS,0,0); sprintf(s,"Perldl data browser: type %d, (%d,%d), type q to quit\n", type,nc,nr); mvwaddstr(wmenu,0,10,s); wrefresh(wmenu); for (i=0;i<dcols;i++) { update_vlab(wvlab,i,0); } wrefresh(wvlab); for (j=0;j<drows;j++) { update_hlab(whlab,j,0); } wrefresh(whlab); for (j=0;j<drows;j++) { update_row(warray,j,0,0,type,nc,in); } i = j = eps = 0; ioff = joff = 0; while (tolower(ch=mvwgetch(warray,j-joff,(i-ioff)*colwid+ MIN(eps,colwid-2))) != 'q') { /* #define ECHOCH */ #ifdef ECHOCH sprintf(echobuf,"%8o",ch); mvwaddstr(wmenu,0,iecho,echobuf); iecho = (iecho < 72) ? iecho+8 :0; wrefresh(wmenu); #endif switch (ch) { case KEY_LEFT: case KEY_RIGHT: case KEY_UP: case KEY_DOWN: case '\t': case '\015': if (eps) { line[eps] = '\0'; set_value(i,j,type,nc,in,line); } set_cell(warray,i,j,ioff,joff,type,nc,in); eps = 0; wrefresh(warray); break; case '\b': case KEY_DL: case 0177: if (eps) { eps--; mvwaddch(warray,j-joff,(i-ioff)*colwid+MIN(eps,colwid-2),' '); wrefresh(warray); } continue; default: if (!eps && ch >= 32 && ch <= 127) { clear_cell(warray,i-ioff,j-joff); wrefresh(warray); } mvwaddch(warray,j-joff,(i-ioff)*colwid+MIN(eps,colwid-2),ch|A_UNDERLINE); line[eps++]=ch; continue; } switch (ch) { case KEY_LEFT: i = (i<2)?0:i-1; if (i-ioff == -1) { ioff--; wtmp = newwin(1,mycols-colwid,1,HLAB); overwrite(wvlab,wtmp); mvwin(wtmp,1,HLAB+colwid); overwrite(wtmp,wvlab); delwin(wtmp); update_vlab(wvlab,0,ioff); wtmp = newwin(drows,mycols-colwid,2,HLAB); overwrite(warray,wtmp); mvwin(wtmp,2,HLAB+colwid); overwrite(wtmp,warray); delwin(wtmp); update_col(warray,0,ioff,joff,type,nc,in); wrefresh(warray); wrefresh(wvlab); } break; case KEY_RIGHT: case '\t': i = (i>nc-2)?nc-1:i+1; if (i-ioff == dcols) { ioff++; wtmp = newwin(1,mycols-colwid,1,HLAB+colwid); overwrite(wvlab,wtmp); mvwin(wtmp,1,HLAB); overwrite(wtmp,wvlab); delwin(wtmp); update_vlab(wvlab,dcols-1,ioff); wtmp = newwin(drows,mycols-colwid,2,HLAB+colwid); overwrite(warray,wtmp); mvwin(wtmp,2,HLAB); overwrite(wtmp,warray); delwin(wtmp); update_col(warray,dcols-1,ioff,joff,type,nc,in); wrefresh(warray); wrefresh(wvlab); } break; case KEY_UP: j = (j<2)?0:j-1; if (j-joff == -1) { joff--; wscrl(wscroll,-1); wrefresh(wscroll); update_hlab(whlab,0,joff); wrefresh(whlab); update_row(warray,0,ioff,joff,type,nc,in); wrefresh(warray); } break; case KEY_DOWN: case '\015': j = (j>nr-2)?nr-1:j+1; if (j-joff == drows) { joff++; wscrl(wscroll,1); wrefresh(wscroll); update_hlab(whlab,drows-1,joff); wrefresh(whlab); update_row(warray,drows-1,ioff,joff,type,nc,in); wrefresh(warray); } break; } } nl(); echo(); nocbreak(); endwin(); }
void outopt(int ch, int count) { if (deadloop) { if (ch == '[') deadloop++; if (ch == ']') deadloop--; return; } if (ch == '[') { if (tape->is_set && tape->v == 0) { deadloop++; return; } } switch(ch) { case '[': case ']': case '!': case '~': case 'X': case '#': case 'I': case 'E': if (ch == '!') { flush_tape(1,0); tape->cleaned = tape->is_set = first_run = !disable_init_optim; } else if (ch == '~' && enable_optim && !disable_init_optim) flush_tape(1,0); else flush_tape(0,0); if (ch) outcmd(ch, count); /* Loops end with zero */ if (ch == ']') { tape->is_set = 1; tape->v = 0; tape->cleaned = 1; tape->cleaned_val = tape->v; } /* I could save the cleaned tape state at the beginning of a loop, * then when we find the matching end loop the two tapes could be * merged to give a tape of known values after the loop ends. * This would not break the pipeline style of this code. * * This would also give states where a cell is known to have one * of two or more different values. */ return; case '.': if (tape->is_set) { int c = tape->v; if (bytecell) c &= 0xFF; if (c > 0 && c < 128) { add_string(c); /* Limit the buffer size. */ if (sav_str_len >= 128*1024 - (tape->v=='\n')*1024) flush_string(); break; } } flush_tape(0,1); outcmd(ch, count); return; case ',': flush_tape(0,1); clear_cell(tape); outcmd(ch, count); return; case '>': while(count-->0) { if (tape->n == 0) new_n(tape); tape=tape->n; curroff++; } break; case '<': while(count-->0) { if (tape->p == 0) new_p(tape); tape=tape->p; curroff--; } break; case '+': if (be_interface.cells_are_ints || bytecell) { tape->v += count; if (bytecell) tape->v %= 256; /* -255..255 */ } else { int ov=0, res; res = ov_iadd(tape->v, count, &ov); if (!ov) tape->v = res; else { flush_tape(0,1); clear_cell(tape); outcmd(ch, count); } } break; case '-': if (be_interface.cells_are_ints || bytecell) { tape->v -= count; if (bytecell) tape->v %= 256; /* -255..255 */ } else { int ov=0, res; res = ov_isub(tape->v, count, &ov); if (!ov) tape->v = res; else { flush_tape(0,1); clear_cell(tape); outcmd(ch, count); } } break; case '=': tape->v = count; tape->is_set = 1; break; case 'B': flush_tape(0,1); if (be_interface.disable_be_optim) be_codegen_failure(); outcmd(ch, count); return; case 'M': case 'N': case 'S': case 'T': if (ch == 'N') count = -count; else if (ch == 'S') count = 1; else if (ch == 'T') count = -1; if (tape->is_set && tape->v == 0) { tape->is_set = 0 ; tape->v = 0; ch = 'C'; if (count == 1) ch = 'V'; else if (count == -1) { ch = 'W'; count = -count; } else if (count < 0) { ch = 'D'; count = -count; } } else { ch = 'M'; if (count == 1) ch = 'S'; else if (count == -1) { ch = 'T'; count = -count; } else if (count < 0) { ch = 'N'; count = -count; } } flush_tape(0,1); clear_cell(tape); if (be_interface.disable_be_optim) be_codegen_failure(); outcmd(ch, count); return; default: if (be_interface.disable_be_optim) be_codegen_failure(); if (ch>=0 && ch<256) fprintf(stderr, "Unknown token in bf2const.c (%d)\n", ch); flush_tape(0,0); outcmd(ch, count); return; } }
static void flush_tape(int no_output, int keep_knowns) { int outoff = 0, tapeoff = 0; int direction = 1; int flipcount = 2; struct mem *p; if (sav_str_len>0) flush_string(); p = tapezero; if(tapezero) { if (curroff > 0) direction = -1; for(;;) { if (no_output) clear_cell(p); if (bytecell) p->v %= 256; /* Note: preserves sign but limits range. */ if ((p->v || p->is_set) && (curroff != 0 || (tapeoff != 0 || flipcount == 0)) && (!keep_knowns || p == tape)) { if (p->cleaned && p->cleaned_val == p->v && p->is_set) { if (!keep_knowns) clear_cell(p); } else { if (tapeoff > outoff) { outcmd('>', tapeoff-outoff); outoff=tapeoff; } if (tapeoff < outoff) { outcmd('<', outoff-tapeoff); outoff=tapeoff; } if (p->is_set) { int c = p->v; if (bytecell) c &= 0xFF; outcmd('=', c); } else { if (p->v > 0) outcmd('+', p->v); if (p->v < 0) outcmd('-', -p->v); } if (keep_knowns && p->is_set) { p->cleaned = p->is_set; p->cleaned_val = p->v; } else clear_cell(p); } } if (direction > 0 && p->n) { p=p->n; tapeoff ++; } else if (direction < 0 && p->p) { p=p->p; tapeoff --; } else if (flipcount) { flipcount--; direction = -direction; } else break; } } if (no_output) outoff = curroff; if (curroff > outoff) { outcmd('>', curroff-outoff); outoff=curroff; } if (curroff < outoff) { outcmd('<', outoff-curroff); outoff=curroff; } if (!tapezero) tape = tapezero = calloc(1, sizeof*tape); if (!keep_knowns) { while(tape->p) tape = tape->p; while(tapezero->n) tapezero = tapezero->n; if (tape != tapezero) { tapezero->n = freelist; freelist = tape->n; tape->n = 0; } } tapezero = tape; curroff = 0; first_run = 0; }
void outopt(int ch, int count) { if (deadloop) { if (ch == '[') deadloop++; if (ch == ']') deadloop--; return; } if (ch == '[' && enable_mov_optim) { if (tape->is_set && tape->v == 0) { deadloop++; return; } } switch(ch) { default: if (ch == '!') { flush_tape(1,0); tape->cleaned = tape->is_set = first_run = !disable_init_optim; } else if (ch == '~' && enable_optim && !disable_init_optim) flush_tape(1,0); else flush_tape(0,0); if (ch) outcmd(ch, count); /* Loops end with zero */ if (ch == ']') { tape->is_set = 1; tape->v = 0; tape->cleaned = 1; tape->cleaned_val = tape->v; } /* I could save the cleaned tape state at the beginning of a loop, * then when we find the matching end loop the two tapes could be * merged to give a tape of known values after the loop ends. * This would not break the pipeline style of this code. * * This would also give states where a cell is known to have one * of two or more different values. */ return; case '.': if (!disable_savestring && enable_be_optim && tape->is_set && tape->v > 0 && tape->v < 128) { add_string(tape->v); if (sav_str_len >= 128*1024) /* Limit the buffer size. */ { add_string(0); outcmd('"', 0); sav_str_len = 0; } break; } flush_tape(0,1); outcmd(ch, count); return; case ',': flush_tape(0,1); clear_cell(tape); outcmd(ch, count); return; case '>': while(count-->0) { if (tape->n == 0) new_n(tape); tape=tape->n; curroff++; } break; case '<': while(count-->0) { if (tape->p == 0) new_p(tape); tape=tape->p; curroff--; } break; case '+': tape->v += count; break; case '-': tape->v -= count; break; case '=': tape->v = count; tape->is_set = 1; break; case 'B': /* Some BE are not 32 bits, try to avoid cell size mistakes */ if (!cells_are_ints && (tape->v > 65536 || tape->v < -65536)) ; else if (tape->is_set) { if (bytecell) tape->v %= 256; /* Note: preserves sign but limits range. */ reg_known = 1; reg_val = tape->v; break; } flush_tape(0,1); reg_known = 0; reg_val = 0; if (enable_be_optim) { outcmd(ch, count); } else { outcmd('[', 1); } return; case 'M': case 'N': case 'S': case 'Q': case 'm': case 'n': case 's': case 'E': if (!reg_known) { flush_tape(0,1); clear_cell(tape); if (enable_be_optim) { outcmd(ch, count); } else switch(ch) { case 'M': case 'm': outcmd('+', count); break; case 'N': case 'n': outcmd('-', count); break; case 'S': case 's': outcmd('+', 1); break; case 'Q': outcmd('[', 1); outcmd('-', 1); outcmd(']', 1); if (count) outcmd('+', count); break; case 'E': outcmd(']', 1); break; } return; } switch(ch) { case 'm': case 'M': tape->v += reg_val * count; break; case 'n': case 'N': tape->v -= reg_val * count; break; case 's': case 'S': tape->v += reg_val; break; case 'Q': if (reg_val != 0) { tape->v = count; tape->is_set = 1; } break; } if (bytecell) tape->v %= 256; /* Note: preserves sign but limits range. */ } }