calculator.c

来自「redboy for gba 是BPNS为GBA编写的一个小软件。软件的邹形是B」· C语言 代码 · 共 737 行 · 第 1/2 页

C
737
字号
				i++;
			}
			i--;
			type[i]=0;
			stack[sp]=calcu(type+start,val+start,R);//结果入栈
			sp++;
		}
		else if (type[i]==3 && val[i]==9.0)//常/变量调用
		{
			i++;
			stack[sp]=R[(int)val[i]];//常/变量入栈
			sp++;
		}
		else if (type[i]==3 && val[i]<7.0)//运算符
		{
			pre[sp]=OptPre((int)val[i]);//获得运算符优先级
			while (pre[sp]<=pre[sp-1])//先行运算
			{
				sp--;
				pre[sp]=pre[sp+1];
				switch(opt[sp])
				{
				case 1://+
					stack[sp-1]+=stack[sp];
					break;
				case 2://-
					stack[sp-1]-=stack[sp];
					break;
				case 3://*
					stack[sp-1]*=stack[sp];
					break;
				case 4:///
					stack[sp-1]/=stack[sp];
					break;
				case 5://%
					stack[sp-1]=(int)stack[sp-1]%(int)stack[sp];
					break;
				case 6://^
					stack[sp-1]=pow(stack[sp-1],stack[sp]);
					break;
				}
			}
			opt[sp]=(int)val[i];
		}
		i++;
	}
	if (sp>1)//还有运算没有完成
	{
		pre[sp]=1;//获得运算符优先级
		while (pre[sp]<=pre[sp-1])//先行运算
		{
			sp--;
			pre[sp]=pre[sp+1];
			switch(opt[sp])
			{
			case 1://+
				stack[sp-1]+=stack[sp];
				break;
			case 2://-
				stack[sp-1]-=stack[sp];
				break;
			case 3://*
				stack[sp-1]*=stack[sp];
				break;
			case 4:///
				stack[sp-1]/=stack[sp];
				break;
			case 5://%
				stack[sp-1]=(int)stack[sp-1]%(int)stack[sp];
				break;
			case 6://^
				stack[sp-1]=pow(stack[sp-1],stack[sp]);
				break;
			}
		}
	}
	return stack[0];
}

void cal_show(char *exp)
{
   int i=0;
   int xp,yp;
   sys_deamon=NULL;
   while (exp[i]!='\0')
   {
      xp=i%31;
      yp=i/31;
      Q_box(11+xp*7,23+16*yp,18+xp*7,33+16*yp,RGB(30,30,30));
      paint_eng(11+xp*7,23+16*yp,font_color,exp[i]);
      i++;
   }
   while (i<=exp_max_len)
   {
      xp=i%31;
      yp=i/31;
      Q_box(11+xp*7,23+16*yp,18+xp*7,33+16*yp,RGB(30,30,30));
      i++;
   }
   sys_deamon=cal_deamon;
   rb_yp=0;
}
   
char cal_input_num(char *exp,double *R)
{
   int i,j;
   int done=1;
   int xp=0,yp=0;
   char get[10],kk[3]="()";
   char num[24]="12345R67890M.E()DC+-*/%^";//24个字符
   char fun[16][6]={
      "sin","cos","tan","rad",
      "asin","acos","atan","deg",
      "sinh","cosh","tanh","sqr",
      "log","ln","pow","exp"};
   int len=str_len(exp);
   n_box(7,20,233,70,font_color,RGB(27,27,26));
   Q_box(8,21,232,69,RGB(30,30,30));
   n_box(7,77,233,140,RGB(30,30,29),RGB(27,27,26));
   cal_show(exp);
   sys_deamon=cal_deamon;
   for (i=0;i<4;i++)
   {
      for (j=0;j<4;j++)
      {
         n_box(101+j*33,80+i*15,132+j*33,92+i*15,font_color,RGB(27,27,26));
         Q_box(102+j*33,81+i*15,131+j*33,91+i*15,RGB(23,23,22));
         cwrite(103+j*33,80+i*15,font_color,fun[i*4+j]);
      }
   }
   for (i=0;i<4;i++)
   {
      for (j=0;j<6;j++)
      {
         n_box(10+j*15,80+i*15,22+j*15,92+i*15,font_color,RGB(27,27,26));
         Q_box(11+j*15,81+i*15,21+j*15,91+i*15,RGB(23,23,22));
         paint_en(13+j*15,83+i*15,font_color,num[i*6+j]);
      }
   }
   while (1)
   {
      readkey();
      if (CS_IsKeyDown(KEY_A))
      {
         if (xp<6)
         {
            get[0]=num[num_sel_yp*6+num_sel_xp];
            get[1]='\0';
            if (num[num_sel_yp*6+num_sel_xp]=='D')
            {
               exp[rb_xp]='\0';
               len=str_len(exp);
               cal_show(exp);
            }
            else if (len<exp_max_len-1)
            {
               str_insert(exp,get,rb_xp);
               rb_xp++;
               len++;
               cal_show(exp);
            }
         }
         else
         {
            i=yp;
            j=xp-6;
            get[0]='\0';
            str_cat(get,fun[i*4+j]);
            str_cat(get,kk);
            if (len+6<exp_max_len)
            {
               str_insert(exp,get,rb_xp);
               rb_xp+=str_len(get)-1;
               cal_show(exp);
               len=str_len(exp);
            }
         }
      }
      if (CS_IsKeyDown(KEY_B))//删除
      {
         if (rb_xp>=len && rb_xp) {exp[len-1]='\0';rb_xp--;}
         else if (rb_xp)
         {
            for (i=rb_xp-1;i<len;i++) exp[i]=exp[i+1];
            rb_xp--;
            len--;
         }
         else if (len)
         {
            for (i=0;i<len;i++) exp[i]=exp[i+1];
            rb_xp=0;
            len--;
         }
         cal_show(exp);
      }
      if (CS_IsKeyDown(KEY_L))
      {
         if (rb_xp)
         {
            sys_deamon=NULL;
            if (rb_yp) r_box(11+(rb_xp%31)*7,23+16*(rb_xp/31),18+(rb_xp%31)*7,33+16*(rb_xp/31),0,5);
            if (CS_IsKeyHold(KEY_DOWN))
            {
               if (rb_xp>10) rb_xp-=10;
               else rb_xp=0;
            }
            else rb_xp--;
            rb_yp=0;
            sys_deamon=cal_deamon;
         }
      }
      if (CS_IsKeyDown(KEY_R))
      {
         if (rb_xp<len)
         {
            sys_deamon=NULL;
            if (rb_yp) r_box(11+(rb_xp%31)*7,23+16*(rb_xp/31),18+(rb_xp%31)*7,33+16*(rb_xp/31),0,5);
            if (CS_IsKeyHold(KEY_DOWN))
            {
               if (rb_xp+10<len) rb_xp+=10;
               else rb_xp=len;
            }
            else rb_xp++;
            rb_yp=0;
            sys_deamon=cal_deamon;
         }
      }
      if (CS_IsKeyDown(KEY_SELECT)) return 2;//退出信号
      if (CS_IsKeyDown(KEY_START) && len) return 0;//确定信号
      if (CS_IsKeyHold(KEY_R)&&CS_IsKeyHold(KEY_L)) return 1;//帮助说明
      if (CS_IsKeyDown(KEY_LEFT))
      {
         num_sel_xp=(num_sel_xp+9)%10;
         done=1;
      }
      else if (CS_IsKeyDown(KEY_RIGHT))
      {
         num_sel_xp=(num_sel_xp+1)%10;
         done=1;
      }
      else if (CS_IsKeyDown(KEY_UP))
      {
         num_sel_yp=(num_sel_yp+3)%4;
         done=1;
      }
      else if (CS_IsKeyDown(KEY_DOWN))
      {
         num_sel_yp=(num_sel_yp+1)%4;
         done=1;
      }
      if (done)
      {
         if (xp<6)
         {
            Q_box(11+xp*15,81+yp*15,21+xp*15,91+yp*15,RGB(23,23,22));
            paint_en(13+xp*15,83+yp*15,font_color,num[xp+yp*6]);
         }
         else
         {
            i=yp;
            j=xp-6;
            Q_box(102+j*33,81+i*15,131+j*33,91+i*15,RGB(23,23,22));
            cwrite(103+j*33,80+i*15,font_color,fun[i*4+j]);
         }
         xp=num_sel_xp;
         yp=num_sel_yp;
         if (xp<6)
         {
            Q_box(11+xp*15,81+yp*15,21+xp*15,91+yp*15,RGB(30,30,0));
            paint_en(13+xp*15,83+yp*15,font_color,num[xp+yp*6]);
         }
         else
         {
            i=yp;
            j=xp-6;
            Q_box(102+j*33,81+i*15,131+j*33,91+i*15,RGB(30,30,0));
            cwrite(103+j*33,80+i*15,font_color,fun[i*4+j]);
         }
         done=0;
      }
   }
      
}

void calculator()
{
	double val[exp_max_len];
	u16 xp,yp;
	double R[10]={0,0,//用户
	299792458,//真空光速
	3.141592654,//PI
	2.718281828,//e
	6.0221367e23,//阿伏伽德罗常量
	1.60217733e-19,//电子电量
	6.67259e-11,//引力常量
	9.1093897e-31,//电子质量
	1.6726231e-27//质子质量
   };
	u8 type[exp_max_len];
   char str[exp_max_len+10]="\0";
   char exp[exp_max_len+30]="\0";
   int error=0;
   int end=0;
   calcu_get(R);
   num_sel_xp=0;
   num_sel_yp=0;
   rb_xp=0;
   rb_yp=0;
again:
   win_plate("科学计算器 V1.0","START:计算 R+L:退出 SELECT:帮助",RGB(27,27,26));
cal_aaa:
   end=cal_input_num(str,R);
   if (end==1) goto the_quit;
   else if (end==2)
   {
      xp=num_sel_xp;
      yp=num_sel_yp;
      sys_deamon=NULL;
      cal_say_help();
      num_sel_xp=xp;
      num_sel_yp=yp;
      goto again;
   }
   sys_deamon=NULL;
   strcpy(exp,str);
   str_replace(exp,"M","M1");
   str_replace(exp,"R","M0");
   str_replace(exp,"C","M");
   str_up(exp);
   Q_box(8,21,232,69,RGB(30,30,30));
   error=cal_exp_dns(exp,type,val);
   if (!error) {error=cal_check_exp(type,val);cal_exp_adj(type,val);}
   if (!error)
   {
      R[0]=calcu(type,val,R);
      if (log10(abs(R[0]))>390) error=6;
      if (error)
      cwrite(11,23+16*2,font_color,cal_errors[error-1]);
      else
      {
         num_to_str(R[0],exp);
         cwrite(11,23+16,font_color,"Result:");
         cwrite(11,23+16*2,font_color,exp);
      }
   }
   else cwrite(11,23+16*2,font_color,cal_errors[error-1]);
   while (1)
   {
      CS_ReadKey();
      if (CS_IsKeyDown(KEY_A)) break;
      if (CS_IsKeyDown(KEY_B))
      {
         rb_xp=0;
         str[0]='\0';
         break;
      }
      if (CS_IsAnyKeyDown(KEY_START)) {R[1]=R[0];calcu_set(R);}
   }
   rb_error=0;
   goto cal_aaa;
the_quit:
   rb_xp=0;
   rb_yp=0;
   sys_deamon=NULL;
   calcu_set(R);
   return;
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?