Index: apps/plugins/superdom.c =================================================================== --- apps/plugins/superdom.c (revision 20089) +++ apps/plugins/superdom.c (working copy) @@ -29,6 +29,12 @@ #define MARGIN 5 +#if (LCD_DEPTH == 16) +#define MY_BITMAP_PART rb->lcd_bitmap_transparent_part +#else +#define MY_BITMAP_PART rb->lcd_mono_bitmap_part +#endif + #if LCD_WIDTH > LCD_HEIGHT #define BOX_WIDTH ((LCD_WIDTH-(MARGIN*2))/10) #define BOX_HEIGHT ((BOX_WIDTH*2)/3) @@ -172,7 +178,7 @@ void update_score(void); void gen_resources(void); void draw_cursor(void); -int calc_strength(bool colour, int x, int y); +int calc_strength(int colour, int x, int y); void draw_board(void); struct tile{ @@ -219,8 +225,8 @@ struct tile board[12][12]; void init_board(void) { - rb->srand(*rb->current_tick); int i,j; + rb->srand(*rb->current_tick); for(i=0;i<12;i++) { /* Hopefully about 50% each colour */ for(j=0;j<12;j++) { if((i<1)||(j<1)||(i>10)||(j>10)) @@ -242,7 +248,6 @@ if((board[i][j].colour == COLOUR_DARK) && (board[i][j].farm == false)) { board[i][j].farm = true; compres.farms++; - break; } } while(compres.inds < superdom_settings.compstartinds) { @@ -251,7 +256,6 @@ if((board[i][j].colour == COLOUR_DARK) && (board[i][j].ind == false)) { board[i][j].ind = true; compres.inds++; - break; } } while(humanres.farmslcd_clear_display(); int i,j; + rb->lcd_clear_display(); for(i=1;i<11;i++) { for(j=1;j<11;j++) { if(board[i][j].colour == COLOUR_DARK) { @@ -289,11 +293,7 @@ rb->lcd_set_drawmode(DRMODE_BG | DRMODE_INVERSEVID); #endif if(board[i][j].ind) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, 0, STRIDE, #if LCD_WIDTH > LCD_HEIGHT MARGIN+(BOX_WIDTH*(i-1))+1, @@ -305,33 +305,21 @@ ICON_WIDTH, ICON_HEIGHT); } if(board[i][j].farm) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, ICON_HEIGHT, STRIDE, MARGIN+(BOX_WIDTH*(i-1))+1, MARGIN+(BOX_HEIGHT*(j-1))+1, ICON_WIDTH, ICON_HEIGHT); } if(board[i][j].tank) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, ICON_HEIGHT*2, STRIDE, MARGIN+(BOX_WIDTH*(i-1))+ICON_WIDTH+1, MARGIN+(BOX_HEIGHT*(j-1))+ICON_HEIGHT+1, ICON_WIDTH, ICON_HEIGHT); } if(board[i][j].men) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, ICON_HEIGHT*3, #if LCD_WIDTH > LCD_HEIGHT STRIDE, MARGIN+(BOX_WIDTH*(i-1))+ICON_WIDTH+1, @@ -343,11 +331,7 @@ ICON_WIDTH, ICON_HEIGHT); } if(board[i][j].plane) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, ICON_HEIGHT*4, #if LCD_WIDTH > LCD_HEIGHT STRIDE,MARGIN+(BOX_WIDTH*(i-1))+ICON_WIDTH*2+1, @@ -359,11 +343,7 @@ ICON_WIDTH, ICON_HEIGHT); } if(board[i][j].nuke) { -#if (LCD_DEPTH == 16) - rb->lcd_bitmap_transparent_part(superdom_boarditems, -#else - rb->lcd_mono_bitmap_part(superdom_boarditems, -#endif + MY_BITMAP_PART(superdom_boarditems, board[i][j].colour?ICON_WIDTH:0, ICON_HEIGHT*5, #if LCD_WIDTH > LCD_HEIGHT STRIDE,MARGIN+(BOX_WIDTH*(i-1))+ICON_WIDTH*2+1, @@ -389,34 +369,22 @@ rb->lcd_update(); } -int calc_strength(bool colour, int x, int y) { +int calc_strength(int colour, int x, int y) { int a, b, score=0; for (a = -1; a < 2; a++){ - for (b = -1; b < 2; b++){ - if (b == 0){ - if(board[x + a][y].colour == colour) - score+=10; - if(((board[x + a][y].colour == colour) && board[x + a][y].tank) || ((board[x + a][y].colour == colour) && board[x + a][y].farm)) - score+=30; - if(((board[x + a][y].colour == colour) && board[x + a][y].plane) || ((board[x + a][y].colour == colour) && board[x + a][y].ind)) - score+=40; - if((board[x + a][y].colour == colour) && board[x + a][y].nuke) - score+=20; - if((board[x + a][y].colour == colour) && board[x + a][y].men) - score+=(board[x + a][y].men*133/1000); - } else if (a == 0){ - if(board[x][y + b].colour == colour) - score+=10; - if(((board[x][y + b].colour == colour) && board[x][y + b].tank) || ((board[x][y + b].colour == colour) && board[x][y + b].farm)) - score+=30; - if(((board[x][y + b].colour == colour) && board[x][y + b].plane) || ((board[x][y + b].colour == colour) && board[x][y + b].ind)) - score+=40; - if((board[x][y + b].colour == colour) && board[x][y + b].nuke) - score+=20; - if((board[x][y + b].colour == colour) && board[x][y + b].men) - score+=(board[x][y + b].men*133/1000); - } - } + for (b = -1; b < 2; b++){ + if ((b == 0 || a == 0) && (board[x + a][y + b].colour == colour)) { + score+=10; + if(board[x + a][y + b].tank || board[x + a][y + b].farm) + score += 30; + if(board[x + a][y + b].plane || board[x + a][y + b].ind) + score += 40; + if(board[x + a][y + b].nuke) + score += 20; + if(board[x + a][y + b].men) + score += (board[x + a][y + b].men*133/1000); + } + } } return score; } @@ -426,6 +394,7 @@ rb->srand(*rb->current_tick); int interest = 7+rb->rand()%6; humanres.bank = humanres.bank+(interest*humanres.bank/100); + compres.bank = compres.bank+(interest*compres.bank/100); } void draw_cursor(void) { @@ -437,10 +406,11 @@ } void gen_resources(void) { - gen_interest(); int inccash = 0; int incfood = 0; + int ratecash, ratefood; int i; + gen_interest(); rb->srand(*rb->current_tick); /* Generate Human's resources */ for(i=0;irand()%200); } - if(inccash/humanres.inds > 450) { - if(incfood/humanres.farms > 350) { + /* avoid dividing by zero */ + ratecash = (humanres.inds? inccash/humanres.inds: 0); + ratefood = (humanres.farms? incfood/humanres.farms: 0); + if(ratecash > 450) { + if(ratefood > 350) { rb->splash(HZ*2, "Patriotism sweeps the land, all production" " is up this year!"); } else { rb->splash(HZ*2, "Factories working at maximum efficiency," " cash production up this year!"); } - } else if((inccash/humanres.inds>350)&&(inccash/humanres.inds<=450)) { - if(incfood/humanres.farms > 350) { + } else if(ratecash > 350) { + if(ratefood > 350) { rb->splash(HZ*2, "Record crop harvest this year!"); - } else if((incfood/humanres.farms > 250) && - (incfood/humanres.farms <= 350)) { + } else if(ratefood > 250) { rb->splash(HZ*2, "Production continues as normal"); } else { rb->splash(HZ*2, "Spoilage of crops leads to reduced farm" " output this year"); } } else { - if(incfood/humanres.farms > 350) { + if(ratefood > 350) { rb->splash(HZ*2, "Record crop harvest this year!"); - } else if((incfood/humanres.farms > 250) && - (incfood/humanres.farms <= 350)) { + } else if(ratefood > 250) { rb->splash(HZ*2, "Factory unions introduced. Industrial" " production is down this year."); } else { @@ -496,17 +467,20 @@ } void update_score(void) { + int strength; + rb->lcd_setfont(FONT_SYSFIXED); rb->lcd_set_drawmode(DRMODE_BG|DRMODE_INVERSEVID); rb->lcd_fillrect(5,LCD_HEIGHT-20,105,20); rb->lcd_set_drawmode(DRMODE_SOLID); + strength = calc_strength(COLOUR_LIGHT, cursor.x, cursor.y); rb->snprintf(buf, sizeof(buf), "Your power: %d.%d", - calc_strength(COLOUR_LIGHT, cursor.x, cursor.y)/10, - calc_strength(COLOUR_LIGHT, cursor.x, cursor.y)%10); + strength/10, strength%10); rb->lcd_putsxy(5,LCD_HEIGHT-20, buf); + strength = calc_strength(COLOUR_DARK, cursor.x, cursor.y); rb->snprintf(buf, sizeof(buf), "Comp power: %d.%d", - calc_strength(COLOUR_DARK, cursor.x, cursor.y)/10, - calc_strength(COLOUR_DARK, cursor.x, cursor.y)%10); + strength/10, strength%10); rb->lcd_putsxy(5,LCD_HEIGHT-10, buf); + rb->lcd_setfont(FONT_UI); } int settings_menu_function(void) { @@ -516,55 +490,52 @@ "Computer starting farms","Computer starting factories", "Human starting farms","Human starting factories", "Starting cash","Starting food","Moves per turn"); -settings_menu: - selection=rb->do_menu(&settings_menu,&selection, NULL, false); - switch(selection) { + + while(1) { + selection=rb->do_menu(&settings_menu,&selection, NULL, false); + switch(selection) { case 0: rb->set_int("Computer starting farms", "", UNIT_INT, &superdom_settings.compstartfarms, NULL, 1, 0, 5, NULL); - goto settings_menu; break; case 1: rb->set_int("Computer starting factories", "", UNIT_INT, &superdom_settings.compstartinds, NULL, 1, 0, 5, NULL); - goto settings_menu; break; case 2: rb->set_int("Human starting farms", "", UNIT_INT, &superdom_settings.humanstartfarms, NULL, 1, 0, 5, NULL); - goto settings_menu; break; case 3: - superdom_settings.humanstartinds = - rb->set_int("Human starting factories", "", UNIT_INT, - &superdom_settings.humanstartinds, NULL, - 1, 0, 5, NULL); - goto settings_menu; + rb->set_int("Human starting factories", "", UNIT_INT, + &superdom_settings.humanstartinds, NULL, + 1, 0, 5, NULL); break; case 4: rb->set_int("Starting cash", "", UNIT_INT, &superdom_settings.startcash, NULL, 250, 0, 5000, NULL); - goto settings_menu; break; case 5: rb->set_int("Starting food", "", UNIT_INT, &superdom_settings.startfood, NULL, 250, 0, 5000, NULL); - goto settings_menu; break; case 6: rb->set_int("Moves per turn", "", UNIT_INT, &superdom_settings.movesperturn, NULL, 1, 1, 5, NULL); - goto settings_menu; break; case MENU_ATTACHED_USB: return PLUGIN_USB_CONNECTED; break; + case GO_TO_PREVIOUS: + return 0; + break; + } } return 0; } @@ -733,6 +704,9 @@ case MENU_ATTACHED_USB: return PLUGIN_USB_CONNECTED; break; + case GO_TO_PREVIOUS: + return 0; + break; } return 0; } @@ -740,6 +714,9 @@ int get_number(char* param, int* value) { //int numbers[3][3] = {{1, 2, 3}, {4, 5, 6}, {7, 8, 9}}; int numbers[3][3]; + int i,j,x=0,y=0; + int height, width; + int button = 0; numbers[0][0] = 1; numbers[0][1] = 2; numbers[0][2] = 3; @@ -751,7 +728,6 @@ numbers[2][2] = 9; rb->lcd_clear_display(); /* Draw a 3x4 grid */ - int i,j,x=0,y=0; for(i=0;i<=3;i++) { /* Vertical lines */ rb->lcd_vline(NUM_MARGIN_X+(NUM_BOX_WIDTH*i), NUM_MARGIN_Y, NUM_MARGIN_Y+(4*NUM_BOX_HEIGHT)); @@ -760,13 +736,11 @@ rb->lcd_hline(NUM_MARGIN_X, NUM_MARGIN_X+(3*NUM_BOX_WIDTH), NUM_MARGIN_Y+(NUM_BOX_HEIGHT*i)); } - int temp = 1; for(i=0;i<3;i++) { for(j=0;j<3;j++) { - rb->snprintf(buf, sizeof(buf), "%d", temp); + rb->snprintf(buf, sizeof(buf), "%d", numbers[i][j]); rb->lcd_putsxy(NUM_MARGIN_X+(j*NUM_BOX_WIDTH)+10, NUM_MARGIN_Y+(i*NUM_BOX_HEIGHT)+8, buf); - temp++; } } rb->lcd_putsxy(NUM_MARGIN_X+5, NUM_MARGIN_Y+(3*NUM_BOX_HEIGHT)+8, "CLR"); @@ -776,7 +750,6 @@ NUM_MARGIN_Y+(3*NUM_BOX_HEIGHT)+8, "OK"); rb->snprintf(buf,sizeof(buf), "%d", *value); rb->lcd_putsxy(NUM_MARGIN_X+10, NUM_MARGIN_Y+4*NUM_BOX_HEIGHT+10, buf); - int height, width; rb->lcd_getstringsize(param, &width, &height); rb->lcd_putsxy((LCD_WIDTH-width)/2, (NUM_MARGIN_Y-height)/2, param); rb->lcd_set_drawmode(DRMODE_COMPLEMENT); @@ -784,19 +757,18 @@ NUM_MARGIN_Y+(NUM_BOX_HEIGHT*y), NUM_BOX_WIDTH+1, NUM_BOX_HEIGHT+1); rb->lcd_set_drawmode(DRMODE_SOLID); - int button = 0; rb->lcd_update(); while(1) { button = rb->button_get(true); switch(button) { case SUPERDOM_OK: - *value *= 10; if(y!=3) { - *value += numbers[y][x]; - } else if(y==3 && x==0) { - *value /= 100; - } else if(y==3 && x==2) { + *value = *value * 10 + numbers[y][x]; + } else if(x==0) { *value /= 10; + } else if(x==1) { + *value *= 10; + } else if(x==2) { return 0; } rb->lcd_set_drawmode(DRMODE_BG|DRMODE_INVERSEVID); @@ -808,7 +780,8 @@ NUM_MARGIN_Y+4*NUM_BOX_HEIGHT+10, buf); break; case SUPERDOM_CANCEL: - return 0; + *value = 0; + return 2; break; #if CONFIG_KEYPAD != IRIVER_H10_PAD case SUPERDOM_LEFT: @@ -918,334 +891,390 @@ return 0; } -int buy_resources_menu(void) { - int selection,tempmenu,nummen; +bool tile_has_item(int type, int x, int y) { + switch(type) { + case 0: + return (board[x][y].men > 0); + case 1: + return board[x][y].tank; + case 2: + return board[x][y].plane; + case 3: + return board[x][y].farm; + case 4: + return board[x][y].ind; + case 5: + return board[x][y].nuke; + } + return false; +} - MENUITEM_STRINGLIST(res_menu, "Buy Resources", NULL, "Buy men ($1)", - "Buy tank ($300)", "Buy plane ($600)", "Buy Farm ($1150)", - "Buy Factory ($1300)", "Buy Nuke ($2000)", - "Finish buying", "Game menu"); +int buy_resources(int colour, int type, int x, int y, int nummen) { + const char *itemnames[][6] = { + { + "them", + "the tank", + "the plane", + "the farm", + "the industrial plant", + "the nuke", + }, { + "place men", + "place a tank", + "place a plane", + "build a farm", + "build an industrial plant", + "place a nuke", + }, { + NULL, + "a tank", + "a plane", + "a farm", + "an industrial plant", + "a nuke", + }, + }; -resources_menu: - selection=rb->do_menu(&res_menu,&selection, NULL, false); - switch(selection) { - case 0: - nummen = 0; - if(get_number("How many men would you like?", &nummen) - == PLUGIN_USB_CONNECTED) + bool human = (colour == COLOUR_LIGHT); + int price = 0; + struct resources *pres; + + if(human) { + pres = &humanres; + } else { + pres = &compres; + } + switch(type) { + case 0: /* men */ + price = nummen; + break; + case 1: /* tank */ + price = 300; + break; + case 2: /* plane */ + price = 600; + break; + case 3: /* Farm */ + price = 1150; + break; + case 4: /* Factory */ + price = 1300; + break; + case 5: /* nuke */ + price = 2000; + break; + } + if(pres->cash < price) { + if(human) + rb->splash(HZ, "Not enough money!"); + return 2; + } + if(human) { + rb->splashf(HZ, "Where do you want to place %s?", itemnames[0][type]); + switch(select_square()) { + case 2: + rb->splash(HZ, "Cancelled"); + return 2; + case PLUGIN_USB_CONNECTED: return PLUGIN_USB_CONNECTED; - if(humanres.cash>=nummen) { - rb->splash(HZ, "Where do you want to place them?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: - rb->splash(HZ, "Cancelled"); - break; - case 2: - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - humanres.men += nummen; - board[cursor.x][cursor.y].men += nummen; - humanres.cash -= nummen; - } else { - rb->splash(HZ,"Can't place men on enemy territory"); - } - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } - } else { - rb->splash(HZ, "Not enough money!"); - } - goto resources_menu; + } + x = cursor.x; + y = cursor.y; + } + if(board[x][y].colour != colour) { + if(human) + rb->splashf(HZ, "Can't %s on enemy territory", itemnames[1][type]); + return 2; + } + if(type != 0 && tile_has_item(type, x, y)) { + if(human) + rb->splashf(HZ, "There is already %s there", itemnames[2][type]); + return 2; + } + switch(type) { + case 0: + board[x][y].men += nummen; + pres->men += nummen; break; case 1: - if(humanres.cash>=300) { - rb->splash(HZ, "Where do you want to place the tank?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: - rb->splash(HZ, "Cancelled"); - goto resources_menu; - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].tank) { - rb->splash(HZ, "There is already a tank there"); - } else { - board[cursor.x][cursor.y].tank = true; - humanres.cash -= 300; - humanres.tanks++; - } - } else { - rb->splash(HZ, "Can't place men on enemy territory"); - } - } else { - rb->splash(HZ, "Not enough money!"); - } - goto resources_menu; + board[x][y].tank = true; + pres->tanks++; break; case 2: - if(humanres.cash>=600) { - rb->splash(HZ, "Where do you want to place the plane?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: - rb->splash(HZ, "Cancelled"); - goto resources_menu; - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].plane) { - rb->splash(HZ, "There is already a plane there"); - } else { - board[cursor.x][cursor.y].plane = true; - humanres.cash -= 600; - humanres.planes++; - } - } else { - rb->splash(HZ, "Can't place men on enemy territory"); - } - } else { - rb->splash(HZ, "Not enough money!"); - } - goto resources_menu; + board[x][y].plane = true; + pres->planes++; break; case 3: - if(humanres.cash>=1150) { - rb->splash(HZ, "Where do you want to place the farm?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: - rb->splash(HZ, "Cancelled"); - goto resources_menu; - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].farm) { - rb->splash(HZ, "There is already a farm there"); - } else { - board[cursor.x][cursor.y].farm = true; - humanres.cash -= 1150; - humanres.farms++; - } - } else { - rb->splash(HZ, "Can't build on enemy territory"); - } - } else { - rb->splash(HZ, "Not enough money!"); - } - goto resources_menu; + board[x][y].farm = true; + pres->farms++; break; case 4: - if(humanres.cash>=1300) { - rb->splash(HZ, "Where do you want to place the industrial" - " plant?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: - rb->splash(HZ, "Cancelled"); - goto resources_menu; - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].ind) { - rb->splash(HZ, "There is already an industrial" - " plant there"); - } else { - board[cursor.x][cursor.y].ind = true; - humanres.cash -= 1300; - humanres.inds++; - } - } else { - rb->splash(HZ, "Can't build on enemy territory"); - } - } else { - rb->splash(HZ, "Not enough money!"); - } - goto resources_menu; + board[x][y].ind = true; + pres->inds++; break; case 5: - if(humanres.cash>=2000) { - rb->splash(HZ, "Where do you want to place the nuke?"); - tempmenu = select_square(); - switch(tempmenu) { - case 0: + board[x][y].nuke = true; + pres->nukes++; + break; + } + pres->cash -= price; + + draw_board(); + rb->sleep(HZ); + + return 0; +} + +int buy_resources_menu(void) { + int selection,nummen; + + MENUITEM_STRINGLIST(res_menu, "Buy Resources", NULL, "Buy men ($1)", + "Buy tank ($300)", "Buy plane ($600)", "Buy Farm ($1150)", + "Buy Factory ($1300)", "Buy Nuke ($2000)", + "Finish buying"); + + while(1) { + selection=rb->do_menu(&res_menu,&selection, NULL, false); + switch(selection) { + case 0: + nummen = 0; + switch(get_number("How many men would you like?", &nummen)) { + case 2: rb->splash(HZ, "Cancelled"); - goto resources_menu; break; case PLUGIN_USB_CONNECTED: return PLUGIN_USB_CONNECTED; break; } - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].nuke) { - rb->splash(HZ, "There is already a nuke there"); - } else { - board[cursor.x][cursor.y].nuke = true; - humanres.cash -= 2000; - humanres.nukes++; - } - } else { - rb->splash(HZ, "Can't place a nuke on enemy territory"); - } - } else { - rb->splash(HZ, "Not enough money!"); + if(!nummen) + break; + /* fall through */ + case 1: + case 2: + case 3: + case 4: + case 5: + if(buy_resources(COLOUR_LIGHT, selection, 0, 0, nummen) + == PLUGIN_USB_CONNECTED) + return PLUGIN_USB_CONNECTED; + break; + case 6: + return 0; + break; + case MENU_ATTACHED_USB: + return PLUGIN_USB_CONNECTED; + break; + case GO_TO_PREVIOUS: + return 0; + break; + } + } + return 0; +} + +int move_unit(int colour, int type, int fromx, int fromy, + int tox, int toy, int nummen) { + const char *itemnames[][3] = { + { + "troops", + "the tank", + "the plane", + }, { + "any troops", + "a tank", + "a plane", + }, { + "the troops", + "the tank", + "the plane", + } + }; + bool human = (colour == COLOUR_LIGHT); + + if(human) { + rb->splashf(HZ, "Select where you want to move %s from", + itemnames[0][type]); + switch(select_square()) { + case 2: + rb->splash(HZ, "Cancelled"); + return 2; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + } + fromx = cursor.x; + fromy = cursor.y; + } + if(board[fromx][fromy].colour != colour) { + if(human) + rb->splash(HZ, "That isn't your territory"); + return 2; + } + if(!tile_has_item(type, fromx, fromy)) { + if(human) + rb->splashf(HZ, "You don't have %s there", itemnames[1][type]); + return 2; + } + if(type == 0) { + if(human) { + nummen = board[fromx][fromy].men; + switch(get_number("How many men do you want to move?", &nummen)) { + case 2: + rb->splash(HZ, "Cancelled"); + return 2; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; } - goto resources_menu; + } + if(nummen > board[fromx][fromy].men) { + if(human) + rb->splash(HZ, "You don't have that many troops."); + return 2; + } + } + if(human) { + rb->splashf(HZ, "Select where you want to move %s to", + itemnames[2][type]); + switch(select_square()) { + case 2: + rb->splash(HZ, "Cancelled"); + return 2; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + } + tox = cursor.x; + toy = cursor.y; + } + if((tox == fromx && toy == fromy) || + board[tox][toy].colour != colour || + (type != 2 && (abs(tox - fromx) > 1 || abs(toy - fromy) > 1))) { + if(human) + rb->splash(HZ, "Invalid move"); + return 2; + } + if(type != 0 && tile_has_item(type, tox, toy)) { + if(human) + rb->splashf(HZ, "There is already %s there", itemnames[1][type]); + return 2; + } + switch(type) { + case 0: + board[fromx][fromy].men -= nummen; + board[tox][toy].men += nummen; break; - case 6: - return 0; + case 1: + board[fromx][fromy].tank = false; + board[tox][toy].tank = true; break; - case MENU_ATTACHED_USB: - return PLUGIN_USB_CONNECTED; + case 2: + board[fromx][fromy].plane = false; + board[tox][toy].plane = true; break; } return 0; } -int move_unit(void) { - int selection, nummen; - struct cursor from; +int move_unit_menu(void) { + int selection; - MENUITEM_STRINGLIST(move_unit_menu, "Move unit", NULL, "Move men", + MENUITEM_STRINGLIST(move_menu, "Move unit", NULL, "Move men", "Move tank", "Move plane"); - selection=rb->do_menu(&move_unit_menu,&selection, NULL, false); + selection=rb->do_menu(&move_menu,&selection, NULL, false); switch(selection) { case 0: - rb->splash(HZ, "Select where to move troops from"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].men) { - from.x = cursor.x; - from.y = cursor.y; - nummen = board[from.x][from.y].men; - if(get_number("How many men do you want to move?", - &nummen) == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(nummen > board[from.x][from.y].men) { - rb->splash(HZ, "You don't have that many troops."); - } else { - rb->splash(HZ,"Select where to move the troops to"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if((board[cursor.x][cursor.y].colour == COLOUR_LIGHT) && - (abs(cursor.x - from.x) <= 1) && - abs(cursor.y - from.y) <= 1) { - board[from.x][from.y].men -= nummen; - board[cursor.x][cursor.y].men += nummen; - humanres.moves--; - return 0; - } - } - } else { - rb->splash(HZ, "You don't have any troops there"); - } - } else { - rb->splash(HZ, "Can't move enemy troops"); - } - break; case 1: - rb->splash(HZ, "Select where you want to move the tank from"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].tank) { - from.x = cursor.x; - from.y = cursor.y; - rb->splash(HZ, "Select where you want" - " to move the tank to"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if((board[cursor.x][cursor.y].colour == COLOUR_LIGHT)&& - (abs(cursor.x-from.x) <= 1) && - (abs(cursor.y-from.y) <= 1)) { - if(board[cursor.x][cursor.y].tank) { - rb->splash(HZ, "There is already a tank there"); - } else { - board[from.x][from.y].tank = false; - board[cursor.x][cursor.y].tank = true; - humanres.moves--; - return 0; - } - } else { - rb->splash(HZ, "Invalid move"); - } - } else { - rb->splash(HZ, "You don't have a tank there"); - } - } else { - rb->splash(HZ, "That isn't your territory"); - } - break; case 2: - rb->splash(HZ, "Select where you want" - " to move the plane from"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].plane) { - from.x = cursor.x; - from.y = cursor.y; - rb->splash(HZ, "Select where you want" - " to move the plane to"); - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(board[cursor.x][cursor.y].colour == COLOUR_LIGHT) { - if(board[cursor.x][cursor.y].plane) { - rb->splash(HZ,"There is already a plane there"); - } else { - board[from.x][from.y].plane = false; - board[cursor.x][cursor.y].plane = true; - humanres.moves--; - return 0; - } - } else { - rb->splash(HZ, "Invalid move"); - } - } else { - rb->splash(HZ, "You don't have a plane there"); - } - } else { - rb->splash(HZ, "That isn't your territory"); + switch(move_unit(COLOUR_LIGHT, selection, 0, 0, 0, 0, 0)) { + case 0: + humanres.moves--; + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; } break; + case MENU_ATTACHED_USB: + return PLUGIN_USB_CONNECTED; } return 0; } +int launch_nuke(int colour, int nukex, int nukey, int targetx, int targety) { + bool human = true; + + if(board[nukex][nukey].colour != colour) { + if(human) + rb->splash(HZ, "That isn't your territory"); + return 2; + } + if(! board[nukex][nukey].nuke) { + if(human) + rb->splashf(HZ, "You don't have %s there", "a nuke"); + return 2; + } + if(human) { + rb->splash(HZ, "Select place to target with nuke"); + switch(select_square()) { + case 2: + rb->splash(HZ, "Cancelled"); + return 2; + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; + } + targetx = cursor.x; + targety = cursor.y; + } + if(human) { + humanres.nukes -= board[nukex][nukey].nuke; + } else { + compres.nukes -= board[nukex][nukey].nuke; + } + board[nukex][nukey].nuke = false; + + if(board[targetx][targety].colour == COLOUR_LIGHT) { + humanres.men -= board[targetx][targety].men; + humanres.tanks -= board[targetx][targety].tank; + humanres.planes -= board[targetx][targety].plane; + humanres.nukes -= board[targetx][targety].nuke; + humanres.farms -= board[targetx][targety].farm; + humanres.inds -= board[targetx][targety].ind; + } else { + compres.men -= board[targetx][targety].men; + compres.tanks -= board[targetx][targety].tank; + compres.planes -= board[targetx][targety].plane; + compres.nukes -= board[targetx][targety].nuke; + compres.farms -= board[targetx][targety].farm; + compres.inds -= board[targetx][targety].ind; + } + board[targetx][targety].men = false; + board[targetx][targety].tank = false; + board[targetx][targety].plane = false; + board[targetx][targety].ind = false; + board[targetx][targety].nuke = false; + board[targetx][targety].farm = false; + + return 0; +} + int movement_menu(void) { - int selection, tempmenu; - bool menu_quit = false; + int selection; MENUITEM_STRINGLIST(move_menu, "Movement", NULL, "Move unit", "Buy additional moves ($100)", "Launch nuclear missile", "Check map", "Finish moving", "Game menu"); - while(!menu_quit) { + while(1) { selection=rb->do_menu(&move_menu,&selection, NULL, false); switch(selection) { case 0: - if(humanres.moves) { - if(move_unit()==PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - } else { + if(!humanres.moves) { rb->splash(HZ, "You have no more moves left." " You can buy more for $100 each."); + break; } + if(move_unit_menu()==PLUGIN_USB_CONNECTED) + return PLUGIN_USB_CONNECTED; break; case 1: if(humanres.cash > 100) { @@ -1257,26 +1286,23 @@ } break; case 2: - if(humanres.nukes==0) { + if(!humanres.nukes) { rb->splash(HZ, "You do not have any nukes to launch"); - } else { - rb->splash(HZ, "Select place to launch nuke from"); - if(select_square() == PLUGIN_USB_CONNECTED) { - return PLUGIN_USB_CONNECTED; - } - if(board[cursor.x][cursor.y].nuke) { - rb->splash(HZ, "Select place to target with nuke"); - if(select_square() == PLUGIN_USB_CONNECTED) { + break; + } + rb->splash(HZ, "Select place to launch nuke from"); + switch(select_square()) { + case 0: + if(launch_nuke(COLOUR_LIGHT, cursor.x, cursor.y, 0, 0) + == PLUGIN_USB_CONNECTED) return PLUGIN_USB_CONNECTED; - } - board[cursor.x][cursor.y].men = 0; - board[cursor.x][cursor.y].tank = 0; - board[cursor.x][cursor.y].plane = 0; - board[cursor.x][cursor.y].ind = 0; - board[cursor.x][cursor.y].nuke = 0; - board[cursor.x][cursor.y].farm = 0; - /* TODO: Fallout carried by wind */ - } + break; + case 2: + rb->splash(HZ, "Cancelled"); + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; } break; case 3: @@ -1287,8 +1313,7 @@ return 0; break; case 5: - tempmenu = ingame_menu(); - switch(tempmenu) { + switch(ingame_menu()) { case PLUGIN_USB_CONNECTED: return PLUGIN_USB_CONNECTED; break; @@ -1306,8 +1331,6 @@ } int show_inventory(void) { - rb->lcd_clear_display(); - rb->lcd_puts(1, 0, "Inventory"); char men[20], tanks[20], planes[20], inds[20], farms[20], nukes[20], cash[20], food[20], bank[20]; rb->snprintf(men, sizeof(men), "Men: %d", humanres.men); @@ -1319,6 +1342,8 @@ rb->snprintf(cash, sizeof(cash), "Cash: %d", humanres.cash); rb->snprintf(food, sizeof(food), "Food: %d", humanres.food); rb->snprintf(bank, sizeof(bank), "Bank: %d", humanres.bank); + rb->lcd_clear_display(); + rb->lcd_puts(1, 0, "Inventory"); rb->lcd_puts(2, 1, men); rb->lcd_puts(2, 2, tanks); rb->lcd_puts(2, 3, planes); @@ -1358,27 +1383,12 @@ } break; case 1: - tempmenu = show_inventory(); - switch(tempmenu) { - case 0: - break; - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - } + if(show_inventory() == PLUGIN_USB_CONNECTED) + return PLUGIN_USB_CONNECTED; break; case 2: - tempmenu = select_square(); - switch(tempmenu) { - case PLUGIN_USB_CONNECTED: - return PLUGIN_USB_CONNECTED; - break; - case SUPERDOM_QUIT: - return SUPERDOM_QUIT; - break; - case 0: - break; - } + if(select_square() == PLUGIN_USB_CONNECTED) + return PLUGIN_USB_CONNECTED; break; case 3: tempbank = humanres.cash; @@ -1454,10 +1464,12 @@ draw_cursor(); update_score(); #if LCD_WIDTH >= 220 + rb->lcd_setfont(FONT_SYSFIXED); rb->snprintf(buf, sizeof(buf), "Cash: %d", humanres.cash); rb->lcd_putsxy(125, LCD_HEIGHT-20, buf); rb->snprintf(buf, sizeof(buf), "Food: %d", humanres.food); rb->lcd_putsxy(125, LCD_HEIGHT-10, buf); + rb->lcd_setfont(FONT_UI); #endif rb->lcd_update(); int button = 0; @@ -1465,10 +1477,10 @@ button = rb->button_get(true); switch(button) { case SUPERDOM_CANCEL: - return 0; + return 2; break; case SUPERDOM_OK: - return 2; + return 0; break; #if CONFIG_KEYPAD != IRIVER_H10_PAD case SUPERDOM_LEFT: @@ -1551,7 +1563,8 @@ } } -int killmen(bool human) { +int killmen(int colour) { + bool human = (colour == COLOUR_LIGHT); int menkilled,i,j; int percent; if(human) { @@ -1564,7 +1577,7 @@ menkilled = 0; for(i=1;i<12;i++) { for(j=1;j<12;j++) { - if(board[i][j].colour == human) { + if(board[i][j].colour == colour) { menkilled += ((board[i][j].men * percent)/1000); board[i][j].men = (board[i][j].men * percent)/1000; } @@ -1578,8 +1591,65 @@ return menkilled; } +/* return -1 if error, 1 if attack succeeded, 0 otherwise */ +int attack_territory(int colour, int x, int y) { + bool human = (colour == COLOUR_LIGHT); + int str_diff; + + if(board[x][y].colour == colour) { + if(human) + rb->splash(HZ, "You can't attack your own territory"); + return -1; + } + str_diff = calc_strength(COLOUR_DARK, x, y) - + calc_strength(COLOUR_LIGHT, x, y); + if(human) { + str_diff = -str_diff; + } + rb->srand(*rb->current_tick); + if(str_diff > 0 || (str_diff == 0 && rb->rand()%2)) { + struct resources *offres ,*defres; + if(human) { + offres = &humanres; + defres = &compres; + } else { + offres = &compres; + defres = &humanres; + } + defres->men -= board[x][y].men; + defres->tanks -= board[x][y].tank; + defres->planes -= board[x][y].plane; + defres->nukes -= board[x][y].nuke; + defres->farms -= board[x][y].farm; + defres->inds -= board[x][y].ind; + offres->farms += board[x][y].farm; + offres->inds += board[x][y].ind; + board[x][y].colour = colour; + board[x][y].tank = 0; + board[x][y].men = 0; + board[x][y].plane = 0; + board[x][y].nuke = 0; + draw_board(); + if(human) + rb->sleep(HZ*2); + else + rb->sleep(HZ); + return 1; + } else { + if(human) + rb->splash(HZ, "Your troops were unable to overcome" + " the enemy troops"); + else + rb->splash(HZ*2, "The computer attempted to " + "attack, but the invasion was" + " pushed back"); + return 0; + } + return 0; +} + int war_menu(void) { - int selection, tempmenu; + int selection; MENUITEM_STRINGLIST(wartime_menu, "War!", NULL, "Select territory to attack", "Finish turn", "Game menu"); @@ -1589,51 +1659,25 @@ selection=rb->do_menu(&wartime_menu,&selection, NULL, false); switch(selection) { case 0: - if(select_square() == PLUGIN_USB_CONNECTED) - return PLUGIN_USB_CONNECTED; - if(board[cursor.x][cursor.y].colour == COLOUR_DARK) { - if(calc_strength(COLOUR_LIGHT, cursor.x, - cursor.y) > calc_strength(COLOUR_DARK, - cursor.x, cursor.y)) { - board[cursor.x][cursor.y].colour = COLOUR_LIGHT; - board[cursor.x][cursor.y].tank = 0; - board[cursor.x][cursor.y].men = 0; - board[cursor.x][cursor.y].plane = 0; - board[cursor.x][cursor.y].nuke = 0; - draw_board(); - rb->sleep(HZ*2); - humanres.moves--; - } else if(calc_strength(COLOUR_LIGHT, cursor.x, cursor.y)== - calc_strength(COLOUR_DARK, cursor.x, cursor.y)) { - if(rb->rand()%2) { - board[cursor.x][cursor.y].colour = COLOUR_LIGHT; - board[cursor.x][cursor.y].tank = 0; - board[cursor.x][cursor.y].men = 0; - board[cursor.x][cursor.y].plane = 0; - board[cursor.x][cursor.y].nuke = 0; - draw_board(); - rb->sleep(HZ*2); + switch(select_square()) { + case 0: + if(attack_territory(COLOUR_LIGHT, cursor.x, cursor.y) >= 0) { humanres.moves--; - } else { - rb->splash(HZ, "Your troops were unable to" - " overcome the enemy troops"); - humanres.moves--; } - } else { - rb->splash(HZ, "Your troops were unable to overcome" - " the enemy troops"); - humanres.moves--; - } - } else { - rb->splash(HZ, "You can't attack your own territory"); + break; + case 2: + rb->splash(HZ, "Cancelled"); + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; } break; case 1: return 0; break; case 2: - tempmenu = ingame_menu(); - switch(tempmenu) { + switch(ingame_menu()) { case PLUGIN_USB_CONNECTED: return PLUGIN_USB_CONNECTED; break; @@ -1654,58 +1698,23 @@ }; bool place_adjacent(bool tank, int x, int y) { - if(tank) { - if(!board[x-1][y].tank && (board[x][y].colour==board[x-1][y].colour)) { - compres.cash -= 300; - board[x-1][y].tank = true; - compres.tanks++; - return 0; - } - if(!board[x+1][y].tank && (board[x][y].colour==board[x+1][y].colour)) { - compres.cash -= 300; - board[x+1][y].tank = true; - compres.tanks++; - return 0; - } - if(!board[x][y-1].tank && (board[x][y].colour==board[x][y-1].colour)) { - compres.cash -= 300; - board[x][y-1].tank = true; - compres.tanks++; - return 0; - } - if(!board[x][y+1].tank && (board[x][y].colour==board[x][y+1].colour)) { - compres.cash -= 300; - board[x][y+1].tank = true; - compres.tanks++; - return 0; - } - } else { - if(!board[x-1][y].plane && (board[x][y].colour==board[x-1][y].colour)) { - compres.cash -= 600; - board[x-1][y].plane = true; - compres.planes++; - return 0; - } - if(!board[x+1][y].plane && (board[x][y].colour==board[x+1][y].colour)) { - compres.cash -= 600; - board[x+1][y].plane = true; - compres.planes++; - return 0; - } - if(!board[x][y-1].plane && (board[x][y].colour==board[x][y-1].colour)) { - compres.cash -= 600; - board[x][y-1].plane = true; - compres.planes++; - return 0; - } - if(!board[x][y+1].plane && (board[x][y].colour==board[x][y+1].colour)) { - compres.cash -= 600; - board[x][y+1].plane = true; - compres.planes++; - return 0; - } + int type = (tank? 1: 2); + if(buy_resources(COLOUR_DARK, type, x, y, 0) == 0) { + return true; } - return 1; + if(buy_resources(COLOUR_DARK, type, x-1, y, 0) == 0) { + return true; + } + if(buy_resources(COLOUR_DARK, type, x+1, y, 0) == 0) { + return true; + } + if(buy_resources(COLOUR_DARK, type, x, y-1, 0) == 0) { + return true; + } + if(buy_resources(COLOUR_DARK, type, x, y+1, 0) == 0) { + return true; + } + return false; } bool has_adjacent(int x, int y) { @@ -1719,61 +1728,28 @@ return 0; } -void find_adjacent(int x, int y, int* adj_x, int* adj_y, bool* full) { +void find_adjacent(int x, int y, int* adj_x, int* adj_y) { /* Finds adjacent squares, returning squares without tanks on them * in preference to those with them */ - if(((board[x-1][y].tank && (board[x-1][y].colour == COLOUR_DARK)) || - board[x-1][y].colour != COLOUR_DARK) && - ((board[x+1][y].tank && (board[x+1][y].colour == COLOUR_DARK)) || - board[x+1][y].colour != COLOUR_DARK) && - ((board[x][y-1].tank && (board[x][y-1].colour == COLOUR_DARK)) || - board[x][y-1].colour != COLOUR_DARK) && - ((board[x][y+1].tank && (board[x][y+1].colour == COLOUR_DARK)) || - board[x][y+1].colour != COLOUR_DARK)) { - *full = true; - } else { - *full = false; - } - if(board[x-1][y].colour == COLOUR_DARK) { *adj_x = x-1; *adj_y = y; - if(board[x-1][y].tank) { - if(*full) - return; - } else { - return; - } + return; } if(board[x+1][y].colour == COLOUR_DARK) { *adj_x = x+1; *adj_y = y; - if(board[x+1][y].tank) { - if(*full) - return; - } else { - return; - } + return; } if(board[x][y-1].colour == COLOUR_DARK) { *adj_x = x; *adj_y = y-1; - if(board[x][y-1].tank) { - if(*full) - return; - } else { - return; - } + return; } if(board[x][y+1].colour == COLOUR_DARK) { *adj_x = x; *adj_y = y+1; - if(board[x][y+1].tank) { - if(*full) - return; - } else { - return; - } + return; } } @@ -1786,24 +1762,27 @@ struct threat threats[4]; int numthreats = 0; int total_str_diff = 0; + int numterritory = 0; + int str_diff; int men_needed; struct threat targets[2]; int numtargets; struct cursor adj; - bool full = false; - for(i=1;i<12;i++) { - for(j=1;j<12;j++) { - if((board[i][j].colour == COLOUR_DARK) && - (calc_strength(COLOUR_DARK,i,j) < - calc_strength(COLOUR_LIGHT,i,j))) { - if(board[i][j].ind || board[i][j].farm) { + + compres.cash += compres.bank; + compres.bank = 0; + for(i=1;i<11;i++) { + for(j=1;j<11;j++) { + if(board[i][j].colour == COLOUR_DARK) { + numterritory++; + str_diff = calc_strength(COLOUR_LIGHT,i,j) - + calc_strength(COLOUR_DARK,i,j); + if(str_diff > 0 && (board[i][j].ind || board[i][j].farm)) { if(numthreats < 3) { offensive = false; threats[numthreats].x = i; threats[numthreats].y = j; - threats[numthreats].str_diff = - calc_strength(COLOUR_LIGHT,i,j) - - calc_strength(COLOUR_DARK,i,j); + threats[numthreats].str_diff = str_diff; numthreats++; } } @@ -1825,87 +1804,51 @@ * owned by the computer. If none are found just place troops in * random places around the map until we run out of money */ k = 0; - while(kyield(); + for(i=1;i<11;i++) { + for(j=1;j<11;j++) { + if(has_adjacent(i,j) && + (board[i][j].ind || board[i][j].farm)) { + targets[k].x = i; + targets[k].y = j; + targets[k].str_diff = calc_strength(COLOUR_LIGHT, i, j) - + calc_strength(COLOUR_DARK, i, j); + k++; } + rb->yield(); + if(k>=numtargets) + break; } } if(k == 0) { /* No targets found! Randomly pick squares and if they're owned * by the computer then stick a tank on it. */ rb->srand(*rb->current_tick); - while(compres.cash >= 300) { - i = rb->rand()%11 + 1; - j = rb->rand()%11 + 1; - if(board[i][j].colour == COLOUR_DARK) { - if(compres.cash >= 300) { - if(!board[i][j].tank) { - board[i][j].tank = true; - compres.tanks++; - compres.cash -= 300; - draw_board(); - rb->sleep(HZ); - } - } - } + while(compres.cash >= 300 && compres.tanks < numterritory) { + i = rb->rand()%10 + 1; + j = rb->rand()%10 + 1; + buy_resources(COLOUR_DARK, 1, i, j, 0); } - compres.bank += compres.cash; - compres.cash = 0; } else { for(i=0;i calc_strength(COLOUR_DARK, targets[i].x, - targets[i].y)) && compres.cash > 0) { + str_diff = targets[i].str_diff; + while(str_diff + 20 > 0 && compres.cash > 0) { /* While we still need them keep placing men */ - if(compres.cash >= 300 && !full) { - if(board[adj.x][adj.y].tank) { - find_adjacent(targets[i].x, targets[i].y, - &adj.x, &adj.y, &full); - } else { - board[adj.x][adj.y].tank = true; - compres.tanks++; - compres.cash -= 300; - draw_board(); - rb->sleep(HZ); + if(!place_adjacent(true, targets[i].x, targets[i].y)) { + find_adjacent(targets[i].x, targets[i].y, &adj.x, &adj.y); + men_needed = (str_diff + 20)*1000/133; + if(compres.cash < men_needed) { + men_needed = compres.cash; } - } else { - men_needed = (calc_strength(COLOUR_LIGHT, targets[i].x, - targets[i].y) + 20 - - calc_strength(COLOUR_DARK, targets[i].x, - targets[i].y))*1000/133; - if(compres.cash >= men_needed) { - board[adj.x][adj.y].men += men_needed; - compres.men += men_needed; - compres.cash -= men_needed; - compres.bank += compres.cash; - compres.cash = 0; - } else { - board[adj.x][adj.y].men += compres.cash; - compres.men += compres.cash; - compres.cash = 0; - } - draw_board(); - rb->sleep(HZ); + buy_resources(COLOUR_DARK, 0, adj.x, adj.y, + men_needed); + break; } + str_diff = calc_strength(COLOUR_LIGHT, + targets[i].x, targets[i].y) - + calc_strength(COLOUR_DARK, + targets[i].x, targets[i].y); } } - compres.bank += compres.cash; - compres.cash = 0; - rb->yield(); } } else { /* Work out what to place on each square to defend it. @@ -1923,93 +1866,39 @@ * use men as a backup */ for(i=0;i= men_needed) { - board[threats[i].x][threats[i].y].men += men_needed; - compres.cash -= men_needed; - compres.men += men_needed; - draw_board(); - rb->sleep(HZ); - } else { - board[threats[i].x][threats[i].y].men += compres.cash; - compres.men += compres.cash; - compres.cash = 0; - draw_board(); - rb->sleep(HZ); + if(compres.cash < men_needed) { + men_needed = compres.cash; } - rb->yield(); + buy_resources(COLOUR_DARK, 0, threats[i].x, threats[i].y, + men_needed); } - } else if((total_str_diff+20)*15 < compres.cash) { + } else { + bool tank = ((total_str_diff+20)*15 >= compres.cash); /* Enough money to pay their way by planes */ for(i=0;i= men_needed) { - compres.cash -= men_needed; - compres.men += men_needed; - board[threats[i].x][threats[i].y].men += - men_needed; - draw_board(); - rb->sleep(HZ); - } + str_diff = threats[i].str_diff; + while(str_diff + 20 > 0) { + if(!place_adjacent(tank, threats[i].x, threats[i].y)) { + /* No room for any more planes or tanks, revert to men */ + find_adjacent(threats[i].x, threats[i].y, &adj.x, &adj.y); + men_needed = (str_diff + 20)*1000/133; + if(compres.cash < men_needed) { + men_needed = compres.cash; } - } else { - if(compres.cash >= 600) { - board[threats[i].x][threats[i].y].plane = true; - compres.cash -= 600; - compres.planes++; - draw_board(); - rb->sleep(HZ); - } + buy_resources(COLOUR_DARK, 0, threats[i].x, + threats[i].y, men_needed); + break; } + str_diff = calc_strength(COLOUR_LIGHT, + threats[i].x, threats[i].y) - + calc_strength(COLOUR_DARK, + threats[i].x, threats[i].y); } - rb->yield(); } - } else { - /* Tanks it is */ - for(i=0;i 0) { - if(board[threats[i].x][threats[i].y].tank) { - if(place_adjacent(1, threats[i].x, threats[i].y)) { - /* No room for any more tanks, revert to men */ - men_needed = (calc_strength(COLOUR_LIGHT, - threats[i].x, threats[i].y) + 20 - - calc_strength(COLOUR_DARK, - threats[i].x, threats[i].y)*1000/133); - if(compres.cash >= men_needed) { - compres.cash -= men_needed; - compres.men += men_needed; - board[threats[i].x][threats[i].y].men += - men_needed; - draw_board(); - rb->sleep(HZ); - } - } - } else { - if(compres.cash >= 300) { - board[threats[i].x][threats[i].y].tank = true; - compres.tanks++; - compres.cash -= 300; - draw_board(); - rb->sleep(HZ); - } - } - } - rb->yield(); - } } - compres.bank += compres.cash; - compres.cash = 0; } + compres.bank += compres.cash; + compres.cash = 0; } int find_adj_target(int x, int y, struct cursor* adj) { @@ -2045,127 +1934,65 @@ void computer_war(void) { /* Work out where to attack - prioritise the defence of buildings */ int i, j; + bool found_target = true; struct cursor adj; - while(compres.moves) { - for(i=1;i<12;i++) { - for(j=1;j<12;j++) { + while(found_target) { + found_target = false; + for(i=1;i<11;i++) { + for(j=1;j<11;j++) { if((board[i][j].colour == COLOUR_DARK) && - (board[i][j].farm || board[i][j].ind)) { - if(find_adj_target(i, j, &adj) && compres.moves) { - if(calc_strength(COLOUR_LIGHT, adj.x, adj.y) == - calc_strength(COLOUR_DARK, adj.x, adj.y)) { - rb->srand(*rb->current_tick); - if(rb->rand()%2) { - board[adj.x][adj.y].colour = COLOUR_DARK; - board[adj.x][adj.y].tank = false; - board[adj.x][adj.y].plane = false; - board[adj.x][adj.y].nuke = false; - humanres.men -= board[adj.x][adj.y].men; - board[adj.x][adj.y].men = 0; - draw_board(); - rb->sleep(HZ); - compres.moves--; - } else { - rb->splash(HZ*2, "The computer attempted" - " to attack, but the" - " invasion was pushed" - " back"); - compres.moves--; - } - } else { - if(compres.moves) { - board[adj.x][adj.y].colour = COLOUR_DARK; - board[adj.x][adj.y].tank = false; - board[adj.x][adj.y].plane = false; - board[adj.x][adj.y].nuke = false; - humanres.men -= board[adj.x][adj.y].men; - board[adj.x][adj.y].men = 0; - draw_board(); - rb->sleep(HZ); - compres.moves--; - } - } + (board[i][j].farm || board[i][j].ind) && + find_adj_target(i, j, &adj)) { + found_target = true; + if(attack_territory(COLOUR_DARK, adj.x, adj.y) >= 0) { + compres.moves--; + if(!compres.moves) + return; } } rb->yield(); } } - if(compres.moves) { - /* Defence stage done, move on to OFFENCE */ - for(i=1;i<12;i++) { - for(j=1;j<12;j++) { - if(board[i][j].colour == COLOUR_LIGHT && compres.moves && - (board[i][j].ind || board[i][j].farm) && - (calc_strength(COLOUR_DARK, i, j) >= - calc_strength(COLOUR_LIGHT, i, j))) { - if(calc_strength(COLOUR_DARK, i, j) == - calc_strength(COLOUR_LIGHT, i, j)) { - if(rb->rand()%2) { - board[i][j].colour = COLOUR_DARK; - board[i][j].tank = false; - board[i][j].plane = false; - board[i][j].nuke = false; - board[i][j].men = 0; - draw_board(); - rb->sleep(HZ); - compres.moves--; - } else { - rb->splash(HZ*2, "The computer attempted to " - "attack, but the invasion was" - " pushed back"); - compres.moves--; - } - } else { - board[i][j].colour = COLOUR_DARK; - board[i][j].tank = false; - board[i][j].plane = false; - board[i][j].nuke = false; - board[i][j].men = 0; - draw_board(); - rb->sleep(HZ); - compres.moves--; - } + } + /* Defence stage done, move on to OFFENCE */ + found_target = true; + while(found_target) { + found_target = false; + for(i=1;i<11;i++) { + for(j=1;j<11;j++) { + if(board[i][j].colour == COLOUR_LIGHT && + (board[i][j].ind || board[i][j].farm) && + (calc_strength(COLOUR_DARK, i, j) >= + calc_strength(COLOUR_LIGHT, i, j))) { + found_target = true; + if(attack_territory(COLOUR_DARK, i, j) >= 0) { + compres.moves--; + if(!compres.moves) + return; } - rb->yield(); } + rb->yield(); } - while(compres.moves > 0) { - /* Spend leftover moves wherever attacking randomly */ - rb->srand(*rb->current_tick); - i = (rb->rand()%10)+1; - j = (rb->rand()%10)+1; - if(board[i][j].colour == COLOUR_LIGHT && - (calc_strength(COLOUR_DARK, i, j) >= - calc_strength(COLOUR_LIGHT, i, j))) { - if(calc_strength(COLOUR_DARK, i, j) == - calc_strength(COLOUR_LIGHT, i, j)) { - if(rb->rand()%2) { - board[i][j].colour = COLOUR_DARK; - board[i][j].tank = false; - board[i][j].plane = false; - board[i][j].nuke = false; - board[i][j].men = 0; - draw_board(); - rb->sleep(HZ); - compres.moves--; - } else { - rb->splash(HZ*2, "The computer attempted to" - " attack, but the invasion was" - " pushed back"); - compres.moves--; - } - } else { - board[i][j].colour = COLOUR_DARK; - board[i][j].tank = false; - board[i][j].plane = false; - board[i][j].nuke = false; - board[i][j].men = 0; - draw_board(); - rb->sleep(HZ); + } + } + /* Spend leftover moves wherever attacking randomly */ + found_target = true; + while(found_target) { + found_target = false; + for(i=1;i<11;i++) { + for(j=1;j<11;j++) { + if(board[i][j].colour == COLOUR_LIGHT && + (calc_strength(COLOUR_DARK, i, j) >= + calc_strength(COLOUR_LIGHT, i, j))) { + found_target = true; + if(attack_territory(COLOUR_DARK, i, j) >= 0) { compres.moves--; + if(!compres.moves) + return; } } + rb->yield(); } } } @@ -2181,7 +2008,7 @@ } rb->read(fd, buf, 5); if(rb->strcmp(buf, "SSGv2")) { - rb->splash(HZ, "Invalid/incompatible savegame\n"); + rb->splash(HZ, "Invalid/incompatible savegame"); return -1; } rb->read(fd, &humanres.cash, sizeof(humanres.cash)); @@ -2225,7 +2052,7 @@ superdom_settings.movesperturn = 2; } -int average_strength(bool colour) { +int average_strength(int colour) { /* This function calculates the average strength of the given player, * used to determine when the computer wins or loses. */ int i,j; @@ -2240,83 +2067,39 @@ return totalpower/100; } -enum plugin_status plugin_start(const void* parameter) -{ - int tempmenu; - bool statusbar_setting; - -#if LCD_DEPTH > 1 - rb->lcd_set_backdrop(NULL); - rb->lcd_set_foreground(LCD_BLACK); - rb->lcd_set_background(LCD_WHITE); -#endif - - statusbar_setting = rb->global_settings->statusbar; - rb->global_settings->statusbar = false; - cursor.x = 1; - cursor.y = 1; - default_settings(); - if(parameter) { - if(load_game(parameter) != 0) { - DEBUGF("Loading failed, generating new game\n"); - init_resources(); - init_board(); - } else { - goto startyear; - } - } else { - init_resources(); - init_board(); - } - - bool play = false; - while(!play) { - switch(menu()) { - case 0: - play = true; - break; - case 2: - rb->global_settings->statusbar = statusbar_setting; - return PLUGIN_OK; - break; - } - } - gen_resources(); -startyear: - if((average_strength(COLOUR_LIGHT) - average_strength(COLOUR_DARK)) > 15) { +int year(void) { + int avg_str_diff = (average_strength(COLOUR_LIGHT) - average_strength(COLOUR_DARK)); + if(avg_str_diff > 15) { rb->splash(HZ*4, "The computer has surrendered. You win."); - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_OK; } - if((average_strength(COLOUR_DARK) - average_strength(COLOUR_LIGHT)) > 15) { + if(avg_str_diff < -15) { rb->splash(HZ*4, "Your army have suffered terrible morale from the bleak prospects of winning. You lose"); - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_OK; } - tempmenu = production_menu(); - switch(tempmenu) { + + /* production */ + switch(production_menu()) { case PLUGIN_USB_CONNECTED: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_USB_CONNECTED; break; case SUPERDOM_QUIT: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_OK; break; } computer_allocate(); + + /* movement */ humanres.moves += superdom_settings.movesperturn; - tempmenu = movement_menu(); - switch(tempmenu) { + switch(movement_menu()) { case PLUGIN_USB_CONNECTED: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_USB_CONNECTED; break; case SUPERDOM_QUIT: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_OK; break; } + /* feed men */ if(humanres.men) { if(humanres.food > humanres.men) { rb->snprintf(buf, sizeof(buf), "Your men ate %d units of food", @@ -2330,28 +2113,77 @@ rb->splash(HZ*2, buf); } if(compres.men) { - if(compres.food < compres.men) { + if(compres.food > compres.men) { + compres.food -= compres.men; + } else { rb->snprintf(buf, sizeof(buf), "The computer does not have enough" - " food to feed its men. %d have ided of starvation", + " food to feed its men. %d have died of starvation", killmen(COLOUR_DARK)); rb->splash(HZ, buf); } } - tempmenu = war_menu(); - switch(tempmenu) { + /* war */ + switch(war_menu()) { case PLUGIN_USB_CONNECTED: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_USB_CONNECTED; break; case SUPERDOM_QUIT: - rb->global_settings->statusbar = statusbar_setting; return PLUGIN_OK; break; } compres.moves += superdom_settings.movesperturn; computer_war(); gen_resources(); - goto startyear; - rb->global_settings->statusbar = statusbar_setting; + return 2; +} + +enum plugin_status plugin_start(const void* parameter) +{ +#if LCD_DEPTH > 1 + rb->lcd_set_backdrop(NULL); + rb->lcd_set_foreground(LCD_BLACK); + rb->lcd_set_background(LCD_WHITE); +#endif + + cursor.x = 1; + cursor.y = 1; + default_settings(); + if(parameter) { + if(!load_game(parameter)) { + goto startyear; + } + DEBUGF("Loading failed, generating new game\n"); + } + + bool play = false; + while(!play) { + switch(menu()) { + case 0: + play = true; + break; + case 2: + return PLUGIN_OK; + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; + } + } + init_resources(); + init_board(); + gen_resources(); +startyear: + while(1) { + switch(year()) { + case 2: + break; + case PLUGIN_OK: + return PLUGIN_OK; + break; + case PLUGIN_USB_CONNECTED: + return PLUGIN_USB_CONNECTED; + break; + } + } return PLUGIN_OK; }