• TC字符界面菜单程序【原创】


    TC字符界面-菜单程序【原创】
    2008/03/06 22:58
    /*本程序代码属本人原创,未经允许不得转载,谢谢合作
    作者:HungryAnt
    发布时间:2008-3-6
    */

    /*快捷键功能没有提供,因为程序有各自的快捷键*/

    #include<stdio.h>
    #include<conio.h>
    #include<string.h>
    #include<bios.h>

    /*bios_key*/
    #define LEFT 0x4B00
    #define RIGHT 0x4D00
    #define UP    0x4800
    #define DOWN 0x5000
    #define ENTER 0x1c0d
    #define ALT   0x1100
    #define ESC   0x011B
    #define F1    0x3B00

    #define M 3
    #define MAX 20
    #define B0 4
    #define B1 5
    #define B2 6
    /*B0,B1等必须小于M*/

    char *mmenu[M];/*主菜单指针数组*/
    char *bmenu_0[B0];/*分菜单0指针数组*/
    char *bmenu_1[B1];/*分菜单1指针数组*/
    char *bmenu_2[B2];/*分菜单2指针数组*/

    void MenuItem(char *menu[],int max,char *pm,...){/*菜单项 可变参数*/
        int i=0;
        char **ppm=&pm;/*ppm为指向指针的指针*/
        while(i<max){/*将传进来的字符串地址全部存入指针数组中*/
            menu[i]=*ppm;
            /*ppm=sizeof(pm)/sizeof(ppm);*/
            ppm++;/*ppm和pm所占字节数都是2,这样就得到了pm后一个指向字符串的指针地址*/
            i++;
        }
    }

    void MainMenuPaint(int choose){/*主菜单绘制*/
        int i=0,x=1,len;
        int bg=LIGHTGRAY,text=BLACK,h=RED;/*灰底,黑字,红(表示ALT+快捷键)*/
        char t[2];

        window(1,1,80,1);/*主菜单栏*/
        textattr((bg<<4)+text);
        clrscr();
        while(i<M){/*显示各项名称*/
            cprintf(" %s ",mmenu[i]);/*主菜单各项左右各一个空格*/
            i++;
        }
        i=0;
        while(i<M){/*标上快捷键键位和当前选择项加黑*/
            if(i==choose){
                len=x+strlen(mmenu[i])+2;
                for(;x<len;x++){
                    gettext(x,1,x,1,t);
                    t[1]=(0<<4)+15;/*黑底白字*/
                    puttext(x,1,x,1,t);
                }
                i++;
            }
            else{
                x++;
                gettext(x,1,x,1,t);
                t[1]=(bg<<4)+RED;
                puttext(x,1,x,1,t);
                x+=strlen(mmenu[i]);
                x++;
                i++;
            }
        }
    }

    void BMenuPaint(char *menu[],int lx,int mx,int my,int bchoose){/*分菜单绘制*/
        int bg=LIGHTGRAY,text=BLACK;/*颜色设置*/
        int i,j;
        char t[2];


        window(lx,2,lx+mx-1,my+1+1);/*创建窗口*/
        textattr((bg<<4)+text);
        clrscr();

        gotoxy(1,1);/*相对于当前窗口*/
        for(j=0;j<mx;j++)putch(196);

        i=0;
        while(i<my){
            gotoxy(1,i+2);
            printf(" %s ",menu[i]);
            i++;
        }
        i=bchoose;
        for(j=0;j<mx;j++){
            gettext(lx+j,i+3,lx+j,i+3,t);
            t[1]=(BLACK<<4)+WHITE;
            puttext(lx+j,i+3,lx+j,i+3,t);
        }
    }



    int BMenuChoose(int choose){/*分菜单选择,并绘制*/
        char *menu[MAX];
        char *pt;/*储存被分菜单暂时覆盖部分的内容*/
        int my=0,lx,mx=0,bchoose=0,i,l,key;
        switch(choose){/*@@@@@@@@@@@@@@添加分菜单需要在此处添加相应代码*/
        case 0:/*分窗口0*/
            my=B0;/*此处用来设置分窗口共多少项,B0为预处理*/
            for(i=0;i<B0;i++)menu[i]=bmenu_0[i];/*将bmenu_0指针数组所有指向的地址传给menu指针数组*/

            lx=1;/*mx表示分菜单窗口左侧x坐标*/
            break;
        case 1:/*分窗口1*/
            my=B1;
            for(i=0;i<B1;i++)menu[i]=bmenu_1[i];
            lx=1+strlen(mmenu[0])+2;
            break;
        case 2:/*分窗口2*/
            my=B2;
            for(i=0;i<B2;i++)menu[i]=bmenu_2[i];
            lx=1+strlen(mmenu[0])+2;
            lx+=strlen(mmenu[1])+2;
            break;
        }
        i=0;

        while(i<my){/*使mx为大小为最长字符串的长度*/
            l=strlen(menu[i]);
            if(mx<l)mx=l;
            i++;
        }
        mx+=2;/*是项目左右各一个空格*/

        /*储存被分菜单暂时覆盖部分的内容*/
        pt=(char *)malloc(mx*(my+1)*2);/*my+1用意在于本菜单显示时会多一行横线*/
        gettext(lx,2,lx+mx-1,(my+1)+1,pt);

        BMenuPaint(menu,lx,mx,my,bchoose);

        while(1){
            if(bioskey(1)){
                key=bioskey(0);
                switch(key){
                case DOWN:
                    bchoose=(bchoose<my-1)?bchoose+1:0;
                    BMenuPaint(menu,lx,mx,my,bchoose);
                    break;
                case UP:
                    bchoose=(bchoose>0)?bchoose-1:my-1;
                    BMenuPaint(menu,lx,mx,my,bchoose);
                    break;
                case RIGHT:
                case LEFT:
                    free(pt);
                    puttext(lx,2,lx+mx-1,(my+1)+1,pt);/*覆盖区域复原*/
                    return key;/*返回kay值*/

                case ENTER:
                case ESC:
                    free(pt);
                    puttext(lx,2,lx+mx-1,(my+1)+1,pt);/*覆盖区域复原*/
                    return;
                }

            }
        }

    }



    void ChooseMainMenu(int choose){/*主菜单选择*/
        int key=0,at=0;
        MainMenuPaint(0);/*菜单项选择自动设为0*/
        key=BMenuChoose(0);
        if(key==RIGHT || key==LEFT)at=1;
        else at=0;
        while(1){
            if(bioskey(1) || at){/*at为自动,此用意是让切换分菜单切换加快*/
                if(at!=1)key=bioskey(0);
                switch(key){
                case RIGHT:
                    choose=(choose<M-1)?choose+1:0;
                    MainMenuPaint(choose);
                    key=BMenuChoose(choose);/*分菜单选择调用*/
                    /*返回值赋给key,是用来方便从*/
                    if(key==RIGHT || key==LEFT)at=1;
                    else at=0;
                    break;
                case LEFT:
                    choose=(choose>0)?choose-1:M-1;
                    MainMenuPaint(choose);
                    key=BMenuChoose(choose);/*分菜单选择调用*/
                    if(key==RIGHT || key==LEFT)at=1;
                    else at=0;
                    break;

                case ENTER:
                case ESC:return;
                }

            }
        }
    }


    int main(){
        int key,i;
        MenuItem(mmenu,M,"HungryAnt","Author","Help");/*主菜单*/
        /*用可变参数就是怎么爽,但字符串数量需要和M值相等,不能太多,仅支持一行显示*/

        MainMenuPaint(-1);/*菜单项选择*/

        MenuItem(bmenu_0,B0,"HungryAnt","I really","love you!!!","Good bye!");/*分菜单*/
        MenuItem(bmenu_1,B1,"HungryAnt","abcdffff","1223312","567","HHHH");
        MenuItem(bmenu_2,B2,"H","I","l","G","G","Good bye!");


        window(1,2,80,25);
        textattr((BLUE<<4)+WHITE);
        clrscr();
        /*for(i=0;i<B1;i++){
            printf(" %s /n",bmenu_1[i]);
        }
        getch(); */

        cprintf("Press F1 to the Main Menu...");

        while(1){
            if(bioskey(1)){
                key=bioskey(0);
                switch(key){
                case F1:
                    ChooseMainMenu(0);/*主菜单选择,先设为0*/
                    exit(1);
                }
            }
        }


        getch();

  • 相关阅读:
    Go语言环境配置 Sublime Text + GoSublime+ gocode + MarGo组合
    Java中string拼接,StringBuilder,StringBuffer和+
    java调优随记-java对象大小
    java调优随记-堆和栈
    java中一直说一个汉字使用两个字节,原来是不准确的
    kv存储对抗关系型数据库
    记一篇
    变态的静态资源缓存与更新
    git add shh public key
    hashmap 的最优访问
  • 原文地址:https://www.cnblogs.com/gods/p/3887673.html
Copyright © 2020-2023  润新知