精华内容
下载资源
问答
  • c语言的图形库

    2013-11-27 16:54:25
    可以在vc++6.0中开发的图形库,方便,解决win7下不能用turbo c进行图形界面开发的问题,很好用
  • C语言图形库——EasyX基本贴图

    千次阅读 多人点赞 2019-09-08 17:50:49
    我们能不能用C语言做些好玩的东西,当然可以,我们可以做游戏,可以做动画,还有很多能装逼东西,在外行眼里看来,你逼格高就不是一点点了。做游戏、做动画一定要用到图片、音频等,怎么用C语言显示出来呢?...

    在C语言的学习过程中,接触最多的就是黑乎乎的DOS窗口,这也是在消磨学习者的兴趣,学到最后可能还不知道C语言到底能做什么,难道就是输入输出数据吗?当然不是,C的用处很广泛,这里不做讨论。我们能不能用C语言做些好玩的东西,当然可以,我们可以做游戏,可以做动画,还有很多能装逼的东西,在外行眼里看来,你的逼格高的就不是一点点了。做游戏、做动画一定要用到图片、音频等,怎么用C语言显示出来呢?这里我们就要用到EasyX库了,在文章末尾有百度网盘链接,下载后双击安装即可,但有编译器限制,VC、VS都可以安装,Dev C++目前不能安装EasyX库。文章的末尾给出了几个小项目。

    当我们安装好EasyX库后,该怎么用呢?我们首先来显示一张图片,首先我们要创立一个图形窗口(要建立.cpp文件才可以用EasyX,因为EasyX库是属于C++范畴的,但在编程风格上用的是C语言)。

    1、添加头文件:

     #include <graphics.h> 
    

    2、定义图像变量:

     IMAGE image1;
    

    IMAGE,通俗的说可视为图,型,和int,char一样,IMAGE image1就是说定义一个图片型变量image1。

    3、创立图形窗口:

    initgraph(800, 600); 
    

    这个函数就是说建立一个宽为800像素,高为600像素的图形窗口。

    4、加载图片:

    loadimage(&image1, L"bird.png", 200, 100); 
    

    选择一张图片,我这里的图片名为bird.jpg,将它放在和你源文件同一目录下。这个函数的意思就是说将这张名为bird.png的图片与image1绑定在一块,用image1代表bird.png,并将其宽和高拉伸为200和100像素点。

    5、显示图片:

    putimage(200,300,&image1);
    

    这个函数的意思就是说将image1显示在所创立的图形窗口的(200,300)处,这是一个坐标
    在这里插入图片描述

    最终的程序是这样的:
    在这里插入图片描述
    在有的时候,我们想要把一张图片的某一部分显示在另一张图片上,例如,把图1中的马显示在以图2为背景的图中。
    在这里插入图片描述
    图1
    在这里插入图片描述
    图2
    这个时候我们不能直接贴,否则无法去除图1中的背景,如图3结果。这很显然不是我们想要的。
    在这里插入图片描述
    图3
    而我们真正想要的是这样的,如图4。
    在这里插入图片描述
    图4

    这个时候我们需要用到图片编辑软件,只要能抠图就行,PS是最佳选择,此处就以PS为例(文章末尾有PS百度网盘连接,安装过程十分简单,不做赘述),选择图1用PS打开,W键用于抠图,把这个圆形光标调小一些,仔细把马选中,Ctrl+c复制,然后选择文件->新建一个黑底剪切板,Ctrl+v粘贴,便可得到图5,把它导出来,继续选择文件->新建一个白底剪切板,Ctrl+v粘贴,在用W键把这个马选择出来,鼠标右键填充,选择黑色,此时在右键选择取消选择便可得到图6,再把它导出来。

    在这里插入图片描述
    图5
    在这里插入图片描述
    图6

    将图2、图5、图6放在项目中,分别命名为bk.jpg、1.png、2.png。
    代码如下:

    #include<stdio.h>
    #include<graphics.h>
    #include<stdlib.h>
    
    int main()
    {
    	IMAGE bk, image1, image2;
    	initgraph(1000, 600);
    	loadimage(&bk,"bk.jpg",1000,600);
    	loadimage(&image1, "1.png");
    	loadimage(&image2, "2.png");
    	putimage(0, 0, &bk);
    	//先贴黑白图,即2.png
    	putimage(
    			50, 100, //显示的位置
    			286, 167,//图片的大小,也可自行设置大小
    			&image2, //选择需要贴的图
    			0, 0,	//从该图片的起始位置开始显示
    			SRCAND	//绘制出的像素颜色 = 屏幕颜色 & 图像颜色
    			);
    	//再贴彩黑图,即1.png
    	putimage(
    			50, 100, 286, 167,&image1, 0, 0,	//与上相同
    			SRCPAINT							//绘制出的像素颜色 = 屏幕颜色 | 图像颜色
    			);
    	system("pause");
    	return 0;
    }
    

    为什么这样可以把马显示在图2中呢?
    我们知道,三原色可以构成任何一种颜色,其中黑色的三原色构成为(0,0,0),白色为(255,255,255),其余的颜色在0—255之间。
    在与运算中,任何8位数与255 相与都等于该数,与0 相与都等于0 ,我们先拿黑白图(图6)按的形式贴在背景图(图2)上,因为白色的三原色数值是最大的,非白色白色等于非白色,又因为黑色的三原色数值最小,所以非黑色黑色等于黑色。示意图如下:
    在这里插入图片描述
    接着按或贴彩黑图(图5),一样的道理,在或运算中,任何一个8位数与0 相或 都等于该数,非黑色黑色等于非黑色。示意图如下:
    在这里插入图片描述

    EasyX链接:
    链接:https://pan.baidu.com/s/1CTWMbqaATgx663M01vRA5A
    提取码:2chn

    PS软件链接
    链接:https://pan.baidu.com/s/1PfaBDBnq07CnDzvwWIBZ2g
    提取码:m3sd

    小项目
    自定义一个屏保程序

    制作一个简易钟表

    EasyX常用函数请点此处查看

    展开全文
  • UNIX下c语言的图形编程--curses.h 函式 作者:不详 来源:supcode.com收集整理 发布时间:2005-7-22 19:39:36 减小字体 增大字体 <br /> 相信您在网路上一定过如 tin,elm 等...

    UNIX下c语言的图形编程--curses.h 函式库
    作者:不详  来源:supcode.com收集整理  发布时间:2005-7-22 19:39:36
    减小字体 增大字体

    相信您在网路上一定用过如  tin,elm 等工具, 这些软体有项共同的特色,
       即他们能利用上下左右等方向键来控制游标的位置.  除此之外, 这些程式
       的画面也较为美观. 对 Programming 有兴趣的朋友一定对此感到好奇, 也 8j
    b sJ5D5g

       许他能在 PC 上用 Turbo C 轻易地写出类似的程式, 然而, 但当他将相同 tech.techweb.com.cnECU L(H#/U*Kh(g
       的程式一字不变地移到工作站上来编译时, 却出现一堆抓也抓不完的错误. 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码
    Iq&D0Y]*zi;g

       其实, 原因很简单, 他使用的函式库可能在 UNIX 上是没有定义的.  有些
       在 Turbo-C 上被广泛使用的一些函式, 可能在 UNIX 上是不被定义的.
    TechWeb技术社区(h9lRF||j
    go2z"bJ

       为了因应网路上各式各样的终端机形态  (terminal), UNIX 上特别发展出
       一套函式库, 专门用来处理 UNIX 上游标移动及萤幕的显示.  这就是本篇
       文章要为您介绍的 - curses.h 函式库.  利用这个函式库, 您也可以写出 -f1f7^z0[?9x
       像 elm 般利用方向键来移动光棒位置的程式. (CCCA 近来所提供的线上选
       课程式, 及程式服务界面, 即是笔者利用 curses 发展而成的 )


    ■ curses 的历史与版本 ~lUhl-iXW
    t/~,X8m8FGXlG
       cureses 最早是由柏克莱大学的 Bill Joy 及 Ken Arnold 所发展出来的. 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码
    mh&CC)L
    o/d

       当时发展此一函式库主要原因是为了提高程式对不同终端机的相容性而设
       计的.  因此, 利用 curses  发展出来的程式将和您所使用的终端机无关.
       也就是说, 您不必担心您的程式因为换了一部终端机而无法使用.  这对程 'T(v%B8l/|
    Xya

       式设计师而言,    尤其是网路上程式的撰写,    是件相当重要的一件事. ~}E*^(E
       curses之所以能对上百种以上的终端机工作,  是因为它将所有终端机的资
       料, 存放在一个叫 termcap 的资料库, ( 而在第二版的 System V 系统中 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码O+cU2H$O
       , 新版的 curses 以 terminfo 取代原来的 termcap). 有了这些记录, 程 tech.techweb.com.cn
    E4b9o(t�@`

       式就能够知道遇到哪一种终端机时,   须送什麽字元才能移动游标的位置,
       送什麽字元才能清除整个萤幕清除. (* 注一)
    8g$ifHw)f j~'lT
       另外, 本文的介绍 以 System V 的 curses 版本为主. tech.techweb.com.cng"E        m%F1|


    ■ 如何在您的程式使用 curses ? 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码5K'r8FT([{P
    "nY0j
    ^GY0nd

       在您的 C 程式的档头将  <curses.h> include 进来.当您引进  curses.h
       这个函式库後, 系统会自动将 <stdio.h> 和 <unctl.h>一并  include 进
       来.另外,  在  System  V  版本中, <terminfo.h>  这个函式库也将一并 TechWeb技术社区0Te9f(hU
       include进来.
    /jx.P/z@J&aqe|)i
        #include <curses.h>
    i
    ~`%CUBTpS        c

        main()
        { -j6f5@ z+zHj_r
         :  : 8^j['yV9f6w*g
         :  : 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码7b^Nk@6?I!r
        }

       当然, 您的系统内必须放有 curses.h 这个函式库. tech.techweb.com.cn�Nqh3wX*F_
    _vo&`&gNZ+e5rP

    ■ 如何编译(compile)

       当您编辑好您的程式, 在 UNIX 提示符号下键入: tech.techweb.com.cn-/jD1VM/

         % /usr/5bin/cc [file.c] -lcurses
                                  ^^^^^^^
                                  引进 curses.h 这个 library

       或 % /usr/5bin/cc [file.c] -lcurses -ltermlib TechWeb技术社区�V        e[(tQi
    TechWeb技术社区'EO$/_](Fq
         (*注二)
    pQ,a9|PD&C

    ZQD8ELT~HO

    ■ 如何开始我的第一个 curses 程式?

       在开始使用 curses 的一切命令之前, 您必须先利用  initscr()这个函式 gk,Kwr,Y[] e9lC
       来开启 curses 模式.

       相对的, 在结束  curses  模式前  ( 通常在您结束程式前  )  也必须以 ]Q
    hT8[ e+|^

       endwin()来关闭 curses 模式. J/EU{`5J

        #include <curses.h> TechWeb技术社区/p
    I}2j


        main() e,?d(Sb+V0oo%{        l
        { E`$@'KEJ
          initscr();
          :  :
          :  : TechWeb技术社区!hq!F{4?!x7_'n"w
          :  : &}Q.L!V|^4DY$@m
          endwin(); tech.techweb.com.cn"M;G*P,`dN+~-K
        }

       这是一般 curses 程式标准的模式.

       此外, 您可以就您程式所须, 而做不同的设定. 当然, 您可以不做设定,而
       只是呼叫 initscr().
    0VD#Y;X2c
       您可以自己写一个函式来存放所有您所须要的设定.  平常使用时, 只要呼
       叫这个函式即可启动 curses 并完成一切设定.
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码7t        ])Nj1N
    Y4Q

       下面的例子, 即是笔者将平常较常用的一些设定放在一个叫 initial()的函 rn,I/TZ/RgV*E

       式内.
    TechWeb技术社区Z z}X        gh2R(a
         void initial()
        {
          initscr();
          cbreak();
          nonl();
          noecho(); 7d
    a.q)Y!J`Z8A0[

          intrflush(stdscr,FALSE);
          keypad(stdscr,TRUE); .Sr/vl]_6@Y9z
          refresh(); tech.techweb.com.cn]4~a
    Eq~

         }


      各函式分别介绍如下:
    F�Sl|+m"[-AQ3|.F
        □ initscr()

             initscr()  是一般 curses 程式必须先呼叫的函数, 一但这个函数
             被呼叫之後, 系统将根据终端机的形态并启动 curses 模式.
    Y
    i]z-{5^;r}&r8Gx7@

    ,t7j {$F0qC;L[iT
        □ endwin() 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码
    G:v;W/h%d)L

    z%rJ-/_
             curses 通常以呼叫 endwin() 来结束程式.  endwin() 可用来关闭
             curses 模式, 或是暂时的跳离  curses 模式.如果您在程式中须要 f!/,{T;pMr!n
             call shell ( 如呼叫 system() 函式 ) 或是需要做 system call,
             就必须先以   endwin()   暂时跳离   curses  模式.   最後再以 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码M)[ C9S._m.z
             wrefresh() doupdate() 来重返 curses 模式. TechWeb技术社区)j(K(fL0_M7u
    `S{!?


    tech.techweb.com.cnzx�m8A}uD(j
        □ cbreak()
           nocbreak()

             当 cbreak  模式被开启後, 除了 DELETE 或 CTRL 等仍被视为特殊
             控制字元外一切输入的字元将立刻被一一读取.当处於 nocbreak 模 TechWeb技术社区%O?M O:qe2t?m
             式时, 从键盘输入的字元将被储存在  buffer 里直到输入  RETURN tech.techweb.com.cn^w1A(zc@(Ap        |�S
             或 NEWLINE.在较旧版的 curses 须呼叫 crmode(),nocrmode() 来 tech.techweb.com.cn5M'[�e#RU:w)Y        E.Qh
             取代 cbreak(),nocbreak()
    TechWeb技术社区js(^e
    c/lv


        □ nl() #G/aHGl+xW1x3O8~
           nonl() i2||Wc(y�dL:e
    u'W0R/(d!T+L6t
             用来决定当输入资料时, 按下 RETURN 键是否被对应为 NEWLINE 字
             元 ( 如 /n ).
             而输出资料时, NEWLINE  字元是否被对应为  RETURN 和 LINDFEED
             系统预设是开启的.

    9/-rI,l"CD8E

        □ echo() tech.techweb.com.cnV2y/J${N
           noecho()

             此函式用来控制从键盘输入字元时是否将字元显示在终端机上.系统         B1R0{m*Z5e
             预设是开启的. tech.techweb.com.cnz4Z#H
    }oG+{'B4/

    @6s,B6o*B5f[{,aX

        □ intrflush(win,bf)

             呼叫 intrflush 时须传入两个值: P
    g"oeA

             win 为一 WINDOW 型态指标, 通常传入标准输出入萤幕 stdscr @H%ic-Y!y-j,C
             bf 为 TRUE 或 FALSE
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码:a4X9w$V7uT9X w
             当 bf 为 true 时, 当输入中断字元 ( 如 break) 时, 中断的反应 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码0iEKB/M2V*W!lW
             将较为快速.但可能会造成萤幕的错乱. tech.techweb.com.cnru5@"/)zq3amE
    J3{;|9Kh7w:A


         □ keypad(win,bf)

             呼叫 keypad 时须传入两个值:
             win 为一 WINDOW 型态指标, 通常传入标准输出入萤幕 stdscr tech.techweb.com.cn0A^GU4j(w_g
             bf 为 TRUE 或 FALSE 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码~4a'K?,Y(B3@9[
    tech.techweb.com.cn!ws qG&j
             当开启  keypad 後, 可以使用键盘上的一些特殊字元, 如上下左右 ;Bje6eb$Y
             等方向键, curses 会将这些特殊字元转换成 curses.h 内定义的一 a4WfD.rJw
             些特殊键. 这些定义的特殊键通常以 KEY_ 开头.


    tech.techweb.com.cn:b^4k2H"ai
         □ refresh() 0[:[        yb        d4N@
    tech.techweb.com.cn/s
    rR�YEf        y

             refresh() 为 curses 最常呼叫的一个函式. tech.techweb.com.cn+Y+DSobwW8@q

             curses 为了使萤幕输出入达最佳化, 当您呼叫萤幕输出函式企图改 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码HI.{9D#Mz
             变萤幕上的画面时, curses  并不会立刻对萤幕做改变,  而是等到 tsmUCoY
             refresh() 呼叫後, 才将刚才所做的变动一次完成.  其馀的资料将 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码!oK#{M6Rb[
             维持不变. 以尽可能送最少的字元至萤幕上. 减少萤幕重绘的时间.
             如果是 initscr() 後第一次呼叫  refresh(), curses 将做清除萤
             幕的工作. ;{-M#O
    [9UU#j




    4nQ1V&HE
    ]%h.C rGg

    ■ 游标的控制 6R5gG8@7J"Q!eV

          move(y,x)       将游标移动至 x,y 的位置
          getyx(win,y,x)  得到目前游标的位置 tech.techweb.com.cn8vgB@
    B        QF&Ry

                          (请注意! 是 y,x 而不是 &y,&x ) I*YY
    ILwgY]



    ■ 有关清除萤幕的函式

              clear() %g~&d5_ h k?S
              erase()   将整个萤幕清除 :sfN9rL-P?
                        (请注意配合refresh() 使用)
    J"Z3HW6Ju*c3S(a

    ■ 如何在萤幕上显示字元 i3O3sDvs;E
    tech.techweb.com.cntR_-FK%b+k
        echochar(ch)              显示某个字元
    MkX
    whak4M;a!y        g

        addch(ch)                 显示某个字元
        mvaddch(y,x,ch)           在(x,y) 上显示某个字元 bC        v
    O�h

                                  相当於呼叫 move(y,x);addch(ch);
    u,VIc"MN@r!W0Q
        addstr(str)               显示一串字串
        mvaddstr(y,x,str)         在(x,y) 上显示一串字串 TechWeb技术社区$^L9v(Gz:yh
                                  相当於呼叫 move(y,x);addstr(str);

        printw(format,str)        类似 printf() , 以一定的格式输出至萤幕
        mvprintw(y,x,format,str)  在(x,y) 位置上做 printw 的工作.
                                  相当於呼叫 move(y,x);printw(format,str);
    -sF@g!K
    R.sl

    z!T/jka LKm

    ■ 如何从键盘上读取字元
    0I#VUa9f
         getch()                        从键盘读取一个字元 (注意! 传回的是
    整数值)
         getstr()                       从键盘读取一串字元 TechWeb技术社区&Q,EUig
         scanw(format,&arg1,&arg2...)   如同 scanf, 从键盘读取一串字元
    TechWeb技术社区�oZ:`ii$r? v#H
         □例: $[hDM@q-D.P
    tech.techweb.com.cn*vW!H
    wW:?h

         int ch; d8x
    v
    M
    {8AU

         char string1[80];   /* 请注意! 不可宣告为 char *string1; */
         char string2[80]; tech.techweb.com.cn2_mo}5HD4k
    8f6HH9V)Hl.Y
         echo();            /* 开启 echo 模式, 使输入立刻显示在萤幕上 */
         ch=getch();
         string1=getstr();
         scanw("%s",string2);
         mvprintw(10,10,"String1=%s",string1); 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码&t-B`$p0I'BG+e(d
         mvprintw(11,10,"String2=%s",string2);
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码k?+U+XR3~
    ■ 如何利用方向键
    O/_,o6^(it�F,]
       curses 将一些如方向键等特殊控制字元, 以 KEY_ 为开头定义在 curses.h

       这个档案里头, 如 KEY_UP  即代表方向键的  " ↑ ".  但, 如果您想使用 )[ Q5o#/o2H8joa
    tech.techweb.com.cn$C2zN_Z`
       curses.h  所为您定义的这些特殊键的话,  您就必须将   keypad  设定为
    Qna1iD
       TRUE. 否则, 您就必须自己为所有的特殊键定义了.

      curses.h 为一些特殊键的定义如下:

        KEY_UP          0403           ↑
        KEY_DOWN        0402           ↓ tech.techweb.com.cn? b0pJ#J
        KEY_LEFT        0404           ← 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码_)AoYAeE
        KEY_RIGHT       0405           → TechWeb技术社区K/
    ^`
    JN:@d+mz

        KEY_HOME        0406           Home key (upward+left arrow) TechWeb技术社区;p6x
    D_e7U        X.QA

        KEY_BACKSPACE   0407           backspace (unreliable)
        KEY_F0          0410           Function keys.
        KEY_F(n)        (KEY_F0+(n))   formula for f . tech.techweb.com.cn-K        S?p'jp4Z8]?
    Vq0{

        KEY_NPAGE       0522           Next page
        KEY_PPAGE       0523           Previous page

       以上仅列出笔者较常使用的一些控制键, 至於其他控制键的定义, 请自行参
    ;Q,S7C4Z0P2^s
    w

       阅 man curses (* 注三) ?
    RSj
    YxQf)Z


       一并为您列出其他常用的一些特殊字元 ]d
    G+l5^
    f'lx&?


        [TAB]                 /t
        [ENTER]               /r tech.techweb.com.cn!K0TM7O/J0U
        [ESC]                 27
        [BACKSPACE]           127 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码/UkA.LO%n


    ■ 如何改变萤幕显示字元的属性 TechWeb技术社区0[�tLE"uO2[

       为了使输出的萤幕画面更为生动美丽,  我们常须要在萤幕上做一些如反白, TechWeb技术社区1K$E+GwYQ5f6]2o ]

       闪烁等变化.  curses 定义了一些特殊的属性, 透过这些定义, 我们也可以 7~Pl5o!ID-J"`&Ew
    emi+Zy+J
       在 curses 程式□控制萤幕的输出变化. k,L8Kwo+fy7q!y"H
    d;w/u2S_O#DJ3?A
        attron(mod)    开启属性 p4va+Tx_
    PI

        attroff(mod)   关闭属性

       curses.h 里头定义了一些属性, 如:

        A_UNDERLINE    加底线
        A_REVERSE      反白
        A_BLINK        闪烁
        A_BOLD         高亮度 9FCM5D/mN5Z
        A_NORMAL       标准模式 (只能配合 attrset() 使用)
    vZ
    vv
    Q"RI^

    !iY5b S']?
       当使用 attron() 开启某一种特殊属性模式後, 接下来在萤幕的输出都会以 J8QEC9a+XG

       该种属性出现. 直到您呼叫 attroff() 将此模式关闭.
    tech.techweb.com.cn        d9Y,S/,n{X
       请注意, 当您欲 attron() 开启另一种属性时, 请记得利用 attroff()先关
    TechWeb技术社区x1^}2V+gncK"i        a
       闭原来的属性, 或直接以 attrset(A_NORMAL)  将所有特殊属性关闭.否则,

       curses 会将两种属性做重叠处理.
    TechWeb技术社区|2IZ{5k(Fy1y
        □例: 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码7b        sYhG]#Sfun

           attrset(A_NORMAL);            /* 先将属性设定为正常模式       */

           attron(A_UNDERLINE);          /* 加底线                       */
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码;`;~/abbI8[Z
           mvaddstr(9,10,"加底线");      /* 加底线输出一串字元           */ TechWeb技术社区8H{8CF0|5awt
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码Yw(a!ko@t^ g
           attroff(A_UNDERLINE);         /* 关闭加底线模式, 恢复正常模式 */ sh@W`t
    &Q'p C"sz*Zmf
           attron(A_REVERSE);            /* 开启反白模式                 */

           mvaddstr(10,10,"反白");       /* 输出一串反白字元             */ tech.techweb.com.cnW!N(@GM,q

           attroff(A_REVERSE);           /* 关闭反白模式, 恢复正常模式   */ Y:A1x/s9hi/zK.}
    tech.techweb.com.cnn2Zj#{j
    i
    i

           attron(A_BLINK);              /* 开启闪烁模式                 */
    q4w*usjXv!x/Y
    zi6zSF

           mvaddstr(11,10,"闪烁");       /* 输出一串闪烁字元             */ +Rhx2}sF        Y1w
    tech.techweb.com.cn4c@L4j
    JY-a X

           attroff(A_BLINK);             /* 关闭闪烁模式, 恢复正常模式   */ TechWeb技术社区!SPA,_n{.Dc

           attron(A_BOLD);               /* 开启高亮度模式               */ TechWeb技术社区!s        Abv["r]q

           mvaddstr(12,10,"高亮度");     /* 输出一串高亮度字元           */

           attroff(A_BOLD);              /* 关闭高亮度模式, 恢复正常模式 */ uQOUr;BQ

    tech.techweb.com.cng;_E7m}$s|

    ■ 其他常用的一些函式 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码6A4rf(s"jN G!sf_;q1NN
    ~r~Q
    c"D+j:U

          beep()              发出一声哔声
          box(win,ch1,ch2)    自动画方框  ch1: 画方框时垂直方向所用字元
                                          ch2: 画方框时水平方向所用字元
    TechWeb技术社区t}2])B2D-T_ABU
                                          example: box(stdscr,'|','-'); ga1_g%N G5e3d"E
                                          将以 | 及 - 围成一个方框

    ■ 应用完整□例
    T9C^ct)i
       下面所举的例子,  即完全利用刚刚所介绍的含式来完成.这个程式可将从键 zdh,W&/C7s
    #TzM
    kB W9Z@

       盘上读取的字元显示在萤幕上, 并且可以上下左右方向键来控制游标的位置
    tech.techweb.com.cnv~q
    xGc{�sF

       , 当按下 [ESC] 後, 程式即结束. )m^_#j"H#u.E�iL
    tech.techweb.com.cn S)oT)[8j
       您有没有发现, 这不就是一个简单全萤幕编辑器的雏形吗?

    `(kO.JJTU;HJ7pc
      #include <curses.h>                  /* 引进 curses.h , 并自动引进
    stdio.h */ TechWeb技术社区'pN?
    @M+}x



      #define StartX  1                    /* 决定游标初始位置 */
      #define StartY  1 TechWeb技术社区)r?E
    a"Ys


      void initial();

      main()
      {
         int x=StartX;                     /* 宣告 x,y 并设定其初值
         */
    tech.techweb.com.cn%N7VeI8[gCT
         int y=StartY; ke`&Tv(R
         int ch;                           /* 宣告 ch 为整数,配合 getch()
    使用   */ 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码`Z)A        z
    UF$~w

    tech.techweb.com.cn2[%/1C~g7EB9e C
    TechWeb技术社区-KGH(^S~5{;H_b
         initial();                        /* 呼叫 initial(), 启动 curses 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码*}zQrt
    模式,  */ 3_I5d;A9D]I;?:o

    B4`0`+j|'[
    At

                                           /* 并完成其它设定 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码k{E        DWT
         */


         box(stdscr,'|','-');              /* 画方框
         */ 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码,q8A{Il7}a2r
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码$O*e)`
    I&frp�S


         attron(A_REVERSE);                /* 开启反白模式
         */ tech.techweb.com.cn"c@VD+N`

         mvaddstr(0,20,"Curses Program");  /* 在 (20,0) 处输出反白字元
         */ tech.techweb.com.cn
    Ub
    O^:Y


         attroff(A_REVERSE);               /* 关闭反白模式 Z7l8ezn4c/+{jQO
         */ tech.techweb.com.cnXq8Ls7@
    LU)X2^9GkT}
    /k8Gm6i,G
         move(x,y);                        /* 将游标移至初始位置
         */

    i*|Gi+r4L/%Mm*E'V
         do {                              /* 以无限回圈不断等待输入
         */

          ch=getch();                      /* 等待自键盘输入字元
          switch(ch) {                     /* 判断输入字元为何
         */

    9i0y&wk(L
             case KEY_UP: --y;             /* 判断是否"↑"键被按下
         */ 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码#D)`'U
    _0J!a,JZ3p

    y4WB,gB
                          break; 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码S+K8/a/b3?6h
             case KEY_DOWN: ++y;           /* 判断是否"↓"键被按下 TechWeb技术社区.t/EPd1J e#w
         */
    *~3{%j+M1WE
                          break; QE+e.JSM-Y
    a+{

             case KEY_RIGHT: ++x;          /* 判断是否"→"键被按下 TechWeb技术社区^}uRR        y2SxU
         */
    G?�butR&?4a
                          break;
             case KEY_LEFT: --x;           /* 判断是否"←"键被按下
         */
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码        F9]|$[
    Zp(['O7X

                          break;
             case '/r':                    /* 判断是否 ENTER 键被按下 C~KS7v^
         */ tech.techweb.com.cnm9a2g?0s.M1|F

                       ++y; 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码[&cESf`6u+O7o(z
                       x=0; 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码^/J9y&tO
    Vl!bY

                       break; "Q6FvH(P0t;S8y
             case '/t':                    /* 判断是否 TAB 键被按下 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码mAJ0?U
         */
    TechWeb技术社区Ux|8kj
                       x+=7;
                       break;
             case 127:                     /* 判断是否 BACKSPACE 键被按下
         */ ra&/t"p6`O9~_
    #e#fY3T.U/p
                        mvaddch(y,--x,' ');/* delete 一个字元 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码P0cP#u~+H|y*~?`U
         */ tech.techweb.com.cn]$]hu        p6H;n

                        break; :u9E5sFC

             case 27: endwin();            /* 判断是否[ESC]键被按下
         */ 7c/Hb8gj*n
    ^3`_$a5s"d
                      exit(1);             /* 结束 curses 模式
         */
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码X]*c-Ax&z2tlW
                                           /* 结束此程式
         */

    tech.techweb.com.cnL}_y.S(@
             default: 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码oq1FNZ+@
                      addch(ch);           /* 如果不是特殊字元, 将此字元印
    出     */ TechWeb技术社区Z/3f        ?O;n7`#}

                      x++;
                      break; TechWeb技术社区6YPx!FsTlG!{
           } 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码
    h7B`+WP)}#b9F

           move(y,x);                      /* 移动游标至现在位置
         */
    Z-@K/jI]T
         } while (1); 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码$r�_&X%`6`%Sr2T5v
       }

    gCy%?J�E(FF

      void initial()                       /* 自定开启 curses 函式
         */ zb$mv%E#z7g�h
    dshb:_&V
      {
          initscr();
          cbreak();
          nonl();
          noecho();
          intrflush(stdscr,FALSE);
          keypad(stdscr,TRUE); 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码2~^'e2?4^-PX9W
          refresh(); 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码 UDL$o�}*p6^5}
       }
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码9l3L!n$v3m6Z6[


    ■ 後记
    WuOVml7r6{:D�?
       学完了上述的一些命令,  相不相信您已经可以写出一个漂亮的全萤幕编辑 N-h?LM/3s        /7G
       器了? 事实上, curses 提供的函式不下  200 个, 可是笔者认为, 一切再
       复杂的函式都可以用本文提到的一些组合变化而成,  学了太多的函式, 只
       是徒增自己困扰罢了.  当然,  如果您对其它函式有兴趣,  可以自行参阅 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码a:qyL.N.J
       curses 说明档.  ( 方法: % man curses ) 本文不过行抛砖引玉之效, 也
       希望未来能陆续出现更多同学自行创作的程式.
    tech.techweb.com.cn7{*ZGzu;g        [;@]
        * 任何疑问及建议, 欢迎 e-mail 至 ljh@CCCA.NCTU.edu.tw . 谢谢 ! *
    tech.techweb.com.cnTWz
    Uj-/1B]gs

    &A7? hf8n,_3N
    l


    注一:
        请参考 /usr/share/lib/termcup 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码K3sM-do
               /usr/share/lib/terminfo/s/sun
    bb@~3bG)y@
    注二: 2FD7_!BI�l/f+swd
        1.如果是 BSD 的版本, 需使用
          cc [file.c] -lcurses -ltermcap 来完成 compile. Qu/@$e'RdW
        2.计中工作站不知何故将原来的 /usr/5bin/cc 更改为 /usr/5bin/cc.org tech.techweb.com.cn h;PapwV9wJ

          因此, 您若想在计中工作站 compile curses 程式.需以 /usr/5bin/cc.
    org 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码|z-T        jOf
          取代 /usr/5bin/cc , 否则 compile 可能发生错误. 6oGB4_-p$zl.[S
        3.较旧版的 curses 需同时引进 curses 和 termlib 这两个 library, hd]l[
          因此, 您必须使用 /usr/5bin/cc [file.c] -lcurses -ltermlib 来 H/@*tn,K~
    compile.
    程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码th,}Az/o
    注三: TechWeb技术社区_
    D@9Fn!S`-[

         根据笔者的经验, 上下左右方向键应可正常使用而不会发生问题, 但其它 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码um?N0I1O/
    O$iI8d*M3D
         如 PgUp,PgDn,功能键,Home,End 等特殊键, 很容易因机器, 键盘不同而无 程序开发,操作系统,服务器,源码下载,Linux,Unix,BSD,PHP,Apach,asp,下载,源码,g        @-^/![Z
    Q


         法使用, 因此, 若您的程式须要在不同的机器上使用, 建议您只用方向键来 @vu1AIB'~h
    M5d@+iD+O-M
         控制, 其它的特殊键少用为妙. tech.techweb.com.cnX!r�R;qEQ+]B8[
         至於 PgUp,PgDn 一些特殊键的控制方法, 由於较为复杂, 有兴趣的同学可
    tech.techweb.com.cn�rz F#D
    E%}5N-eE-{.}

         考 tin 原始程式 curses.c 内所使用的一些方法.

    展开全文
  • 不要以为C语言就只能写那种只有字符控制台程序,别忘了,Linux系统有FrameBuffer(帧缓冲),只要显示器是彩色,并且是linux系统,就可以用C语言代码通过读写FrameBuffer里数据在屏幕上绘制图形图形嘛,有...

    在Linux系统下,不要以为C语言就只能写那种只有字符的控制台程序,别忘了,Linux系统有FrameBuffer(帧缓冲),只要显示器是彩色的,并且是linux系统的,就可以用C语言代码通过读写FrameBuffer里的数据在屏幕上绘制图形;

    图形嘛,有png库,用它的函数解码图片文件,得到图片数组,共有red、green、blue、alpha四种数组,alpha用于图片之间的组合,最终将RGB数组输出到FrameBuffer就能显示了;

    想要动态图形效果,自己用算法实现。

    目前,我正在为自己的嵌入式设备开发一个游戏,图形素材来源于互联网,游戏截图如下图所示:

    a48729cc2462d62094e76646fab57188.gif

    6a60416dbd2e1317a5b12314702f02e3.gif

    f194f75113abf41789a8f4e62398c307.gif

    902d74f9c971725273e97b96039c622f.gif

    如上图所示,主菜单中的红色光标有闪烁效果,游戏画面切换有淡入淡出效果。

    下面有源码,现在使用的按键控制方法的效果不理想。

    linux系统环境,按键判断,使用了getch()和kbhit()函数,函数是模拟实现的。

    为了判断按键是否为按住状态,我使用一个变量count来计数,每循环一次自增,也就是按键检测延迟的最大时间,超过了这段时间,如果getch()函数没有再次返回接受到同样的按键的键值,那么就判断为这个按键已经释放,否则,该按键处于按住状态,并继续显示之前的动作。

    还有图形显示,目前没掌握局部刷新的技术,游戏显示的每一帧图形都是全屏刷新的,效率低,每秒大概刷新4帧。

    源码只提供部分:

    [cpp]

    voidnext_frames(void)

    {//更新到下一帧

    frames[0] += speed[0];//玩家1的

    frames[1] += speed[1];//AI的

    }

    voidinit_player_data(void)

    //初始化各个玩家的数据

    {

    direction[0] = IS_RIGHT;//玩家朝向右边

    direction[1] = IS_LEFT;//AI角色朝向左边

    //各个角色的初始位置

    map_site_x[0] = 100;

    map_site_x[1] = 300;

    map_site_y[1] = map_hight - 20;

    map_site_y[0] = map_hight - 20;//在地图上的坐标

    speed[0] = 1;//每次循环帧frames自增的的值,之前是想做能设置游戏刷新速度的功能,现在已抛弃,这个变量貌似没用了。

    speed[1] = 1;

    need_move[0] = 0;//玩家是否需要移动

    need_move[1] = 0;//AI是否需要移动

    can_use_next[0] = 0;//可以使用下一个动作

    can_use_next[1] = 0;//AI可以使用下一个动作

    status[0] = STANCE;//玩家为站立状态

    status[1] = STANCE;//AI为站立状态

    shock_wave_num = 0;//冲击波的总数为0

    need_view_shock_wave = 0;//不需要显示冲击波

    }

    intplay_game(void)

    {

    unsignedchar**game_map;//游戏地图

    intmap_id,temp_key = 0,count = 0,key = 0,man_id;//人物代号

    //分配内存

    man_id = ICHIGO;//人物动画选择黑崎一护

    init_player_data();//初始化玩家数据

    map_id = 1;

    if(map_id == 1) {

    game_map = load_map_1();//载入地图数据

    }

    while(1){

    update_graph();//规定镜头,显示玩家所在的区域的图形

    view_map_area(game_map[0],game_map[1],game_map[2]);//根据主角的位置,显示地图中的某个区域

    if(kbhit()){//调用kbhit()函数检测是否有按键输入

    key = getch();//有按键输入就用getch()函数获取键值并赋给key,下面开始判断key的值

    if(key == KEY_BACK)break;

    if(key =='w'|| key =='W'|| key == KEY_UP) {

    temp_key = key;

    }

    elseif((key =='d'|| key =='D'|| key == KEY_RIGHT) && status[0] != JUMP_ATTACK){//如果按的是a键或者左键

    if((temp_key =='d'|| temp_key =='D'|| temp_key == KEY_RIGHT)&& count 

    next_action[0] = WALK;//下一个动作还是行走

    }

    elseif(can_use_next[0] == 0){//如果之前没有按过a键或者左键,并且,可以使用下一个动作

    if(temp_status[0] != JUMP) {//如果之前不是跳跃状态

    status[0] = WALK;

    if(temp_status[0] != WALK) frames[0] = 0;//如果之前不是行走状态

    elseif(temp_status[0] == WALK){//如果之前是行走状态

    next_action[0] = WALK;//下一个动作还是行走

    }

    }

    elseneed_move[0] = 1;//否则,需要移动

    }

    direction[0] = IS_RIGHT;

    need_move[0] = 1;

    temp_key = key;

    count = 0;//计数清零

    }

    elseif((key =='a'|| key =='A'|| key == KEY_LEFT) && status[0] != JUMP_ATTACK){//如果按的是a键或者左键

    if((temp_key =='a'|| temp_key =='A'|| temp_key == KEY_LEFT)&& count 

    next_action[0] = WALK;//下一个动作还是行走

    }

    elseif(can_use_next[0] == 0){//如果之前没有按过a键或者左键,并且,可以使用下一个动作

    if(temp_status[0] != JUMP) {//如果之前不是跳跃状态

    status[0] = WALK;

    if(temp_status[0] != WALK) frames[0] = 0;//如果之前不是行走状态

    elseif(temp_status[0] == WALK){//如果之前是行走状态

    next_action[0] = WALK;//下一个动作还是行走

    }

    }

    elseneed_move[0] = 1;//否则,需要移动

    }

    direction[0] = IS_LEFT;

    need_move[0] = 1;

    temp_key = key;

    count = 0;//计数清零

    }

    elseif(key =='s'|| key =='S'|| key == KEY_DOWN){//如果按的是s键或者是下键

    if(can_use_next[0] == 0){

    status[0] = BLOCK;

    if((temp_key =='s'|| temp_key =='S'|| temp_key == KEY_DOWN) && count <10){

    //如果之前按过s键或者是下键,并且在最大延迟时间内

    if(temp_status[0] == BLOCK && status[0] == BLOCK)//如果之前的动作是防御

    {

    frames[0] = 2;speed[0] = 0;

    }

    }

    else{

    frames[0] = 0;//帧数归零www.linuxidc.com

    speed[0] = 1;

    }

    }

    temp_key = key;//保存按键的键值

    count = 0;//计数归零

    }

    elseif(key =='j'|| key =='J'){//如果按的是j键

    if(temp_status[0] == JUMP || temp_status[0] == JUMP_ATTACK)//如果之前还处于跳跃状态

    {

    if(jump_attack_num == 0) {

    status[0] = JUMP_ATTACK;//跳跃攻击

    jump_attack_num = 1;

    }

    }

    elseif(status[0] == DOWN_ATTACK || status[0] == BLOCK || temp_key == KEY_DOWN || temp_key =='s'|| temp_key =='S'){

    status[0] = DOWN_ATTACK;

    if(temp_status[0] != DOWN_ATTACK) frames[0] = 0;//帧数归零

    }

    elseif(temp_key == KEY_UP || temp_key =='w'|| temp_key =='W'){

    if(can_use_next[0] == 0){//如果可以使用下一个动作

    status[0] = UP_ATTACK;

    frames[0] = 0;//帧数归零

    }

    }

    elseif((temp_key =='j'|| temp_key =='J') && count <5){//如果之前按过j键,并且在最大延迟时间内

    if(temp_status[0] == FIRST_ATTACK && status[0] == FIRST_ATTACK)//如果之前处于第一段攻击状态下

    {

    status[0] = FIRST_ATTACK;

    if(can_use_next[0] == 0 && first_attack_complete[0] == 0){//如果可以使用下一个动作

    status[0] = SECOND_ATTACK;//开始进行第二段攻击

    frames[0] = 0;//帧数归零www.linuxidc.com

    }

    else{

    next_action[0] = SECOND_ATTACK;//保存下一个动作,等待之前的动作完成

    }

    }

    elseif(temp_status[0] == SECOND_ATTACK || status[0] == SECOND_ATTACK)//如果之前处于第二段攻击状态下

    {

    status[0] = SECOND_ATTACK;

    if(can_use_next[0] == 0 && second_attack_complete[0] == 0){//如果可以使用下一个动作

    status[0] = THIRD_ATTACK;//开始进行第二段攻击

    frames[0] = 0;//帧数归零

    }

    else{

    next_action[0] = THIRD_ATTACK;//保存下一个动作,等待之前的动作完成

    }

    }

    elseif(temp_status[0] == THIRD_ATTACK || status[0] == THIRD_ATTACK)//如果之前处于第二段攻击状态下

    {

    status[0] = THIRD_ATTACK;

    if(can_use_next[0] == 0 && third_attack_complete[0] == 0){//如果可以使用下一个动作

    status[0] = FIRST_ATTACK;//开始进行第一段攻击

    frames[0] = 0;//帧数归零

    }

    else{

    //next_action = FIRST_ATTACK;//保存下一个动作,等待之前的动作完成

    }

    }

    else{

    status[0] = FIRST_ATTACK;

    frames[0] = 0;

    }

    }

    else{

    status[0] = FIRST_ATTACK;

    if(temp_status[0] != FIRST_ATTACK) frames[0] = 0;

    }

    speed[0] = 1;

    count = 0;

    temp_key = key;//保存按键的键值

    }

    elseif((key =='k'|| key =='K') && can_use_next[0] == 0){//如果按的是k键,并且能使用下一个动作

    status[0] = JUMP;

    count = 0;

    jump_attack_num = 0;

    frames[0] = 0;

    }

    elseif(key =='U'|| key =='u'){

    if(status[0] == DOWN_Y_ATTACK || status[0] == BLOCK || temp_key == KEY_DOWN || temp_key =='s'|| temp_key =='S'){

    speed[0] = 1;

    status[0] = DOWN_Y_ATTACK;

    if(temp_status[0] != DOWN_Y_ATTACK) frames[0] = 0;//帧数归零

    }

    elseif(can_use_next[0] == 0){//如果可以使用下一个动作

    status[0] = Y_ATTACK;//开始进行第二段攻击

    frames[0] = 0;//帧数归零

    }

    else{

    next_action[0] = Y_ATTACK;//保存下一个动作,等待之前的动作完成

    }

    count = 0;

    temp_key = key;

    }

    elseif(key =='L'|| key =='l'){

    if(can_use_next[0] == 0){//如果可以使用下一个动作

    status[0] = DASH;

    frames[0] = 0;//帧数归零

    }

    else{

    next_action[0] = DASH;//保存下一个动作,等待之前的动作完成

    }

    need_move[0] = 1;//需要移动

    }

    }

    elseif(count > 5 && can_use_next[0] == 0) {//如果在计数大于5时还没有接收到按键输入,并且可以使用下一个动作

    status[0] = STANCE;//状态改为站立

    speed[0] = 1;

    temp_key = 0;

    count = 0;//计数清零www.linuxidc.com

    }

    if_need_move(0,count);//判断是否需要移动

    if(man_id == ICHIGO) ichigo(0);//使用黑崎一护的动作图形

    ichigo(1);

    next_frames();//更新到下一个帧

    write_to_fb(screen[0],screen[1],screen[2]);//显示图形

    //usleep(10000);//之前用过usleep(30000),牺牲帧的刷新速度,获得按键响应效果的提升,我认为这不值

    count++;//计数自增

    }

    //释放背景图占用的内存

    free(game_map[0]);

    free(game_map[1]);

    free(game_map[2]);

    free(game_map);

    return0;

    }

    intmain()

    {

    init_game();//初始化游戏,获取屏幕尺寸,分配内存

    game_boot();//显示游戏启动画面

    main_menu();//显示游戏主菜单

    system("stty echo");

    return0;

    }0b1331709591d260c1c78e86d0c51c18.png

    展开全文
  • C语言实现2048(ege图形库版)

    万次阅读 热门讨论 2017-04-01 13:39:57
    现在和大家分享一下,也希望得到大神指点。 实现效果如图 先来讲一下我思路吧 首先肯定是要一个4X4二维数组来存放数字存放0、2、4…… 游戏开始与过程中需要随机出现2或者4,所以需要调用time.h这个 ...

    这几天看到我们班上一个大神写了一个2048出来,我自己也想尝试一下,经过几天自己尝试努力下,自己终于写出来了。现在和大家分享一下,也希望能得到大神的指点。

     实现的效果如图
    

    这里写图片描述


    先来讲一下我的思路吧

    1. 首先肯定是要一个4X4的二维数组来存放数字存放0、2、4……
    2. 游戏开始与过程中需要随机出现2或者4,所以需要调用time.h这个库
    3. 游戏开始时,假如当获取字符为‘w’则先用循环判定这个数字的下方有无和它相等的数字。如无则跳过,如有相加。然后在判定是否可以向上移动

    下面是我的代码
    (我本来是还要写一个撤回的函数 可惜写出来却不能运行。求大神指教)

    #include<stdio.h>
    //#include<conio.h>
    #include<graphics.h>
    #include<Windows.h>
    #include<time.h>
    int _back[4][4] = {};
    void draw();//绘图
    void play();
    void init();//初始化数字
    void _up();//向上移动
    void _down();//向下移动
    void _left();//像左移动
    void _right();//向右移动
    void add_number();//增加一个数字
    int a[4][4] = { 0 };
    int emtpy;
    //空格的数量
    void draw()
    {
        int i, j;
        for (i = 0; i < 4; i++)
        {
            for (j = 0; j < 4; j++)
            {
                _back[i][j] = a[i][j];
                PIMAGE img;
                img = newimage();
                switch (a[i][j])
                {
                case 0:
                {
                    getimage(img, "2048\\0.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 2:
                {
                    getimage(img, "2048\\2.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 4:
                {
                    getimage(img, "2048\\4.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 8:
                {
                    getimage(img, "2048\\8.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 16:
                {
                    getimage(img, "2048\\16.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 32:
                {
                    getimage(img, "2048\\32.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 64:
                {
                    getimage(img, "2048\\64.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 128:
                {
                    getimage(img, "2048\\128.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 256:
                {
                    getimage(img, "2048\\256.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 512:
                {
                    getimage(img, "2048\\512.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 1024:
                {
                    getimage(img, "2048\\1024.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                case 2048:
                {
                    getimage(img, "2048\\2048.png");
                    putimage(j * 180, i * 180, img);
                    break;
                }
                }
            }
        }
    
    }
    void init()
    {
        int x, y;
        srand(time(0));
        x = rand() % 4;
        y = rand() % 4;
        a[x][y] = 2;
        emtpy = 15;
    
    }
    void _up()
    {
        int x, y, i;
    
        for (y = 0; y < 4; ++y) {     // 从上向下合并相同的方块 
            for (x = 0; x < 4; ++x) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = x + 1; i < 4; ++i) {
                        if (a[i][y] == 0)
                            ;
                        else if (a[x][y] == a[i][y]) {
                            a[x][y] += a[i][y];
                            a[i][y] = 0;
                            ++emtpy;
                            x = i;
                            break;
    
                        }
                        else {
    
                            break;
                        }
                    }
                }
            }
        }
    
        for (y = 0; y < 4; ++y)    // 向上移动箱子
            for (x = 0; x < 4; ++x)
            {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = x; (i > 0) && (a[i - 1][y] == 0); --i) {
                        a[i - 1][y] = a[i][y];
                        a[i][y] = 0;
                    }
                }
            }
    }
    void _down() {
        int x, y, i;
    
        for (y = 0; y < 4; ++y)  // 向下合并相同的方格 
            for (x = 3; x >= 0; --x) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = x - 1; i >= 0; --i) {
                        if (a[i][y] == 0)
                            ;
                        else if (a[x][y] == a[i][y]) {
                            a[x][y] += a[i][y];
                            a[i][y] = 0;
                            ++emtpy;
                            x = i;
                            break;
                        }
                        else
                            break;
                    }
                }
            }
    
        for (y = 0; y < 4; ++y)  // 向下移动方格 
            for (x = 3; x >= 0; --x) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = x; (i < 3) && (a[i + 1][y] == 0); ++i) {
                        a[i + 1][y] = a[i][y];
                        a[i][y] = 0;
                    }
                }
            }
    }
    void _left()
    {
        int x, y, i;
    
        for (x = 0; x < 4; ++x)   // 向左合并相同的方格 
            for (y = 0; y < 4; ++y) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = y + 1; i < 4; ++i) {
                        if (a[x][i] == 0)
                            ;
                        else if (a[x][y] == a[x][i]) {
                            a[x][y] += a[x][i];
                            a[x][i] = 0;
                            emtpy++;
                            y = i;
                            break;
                        }
                        else
                            break;
                    }
                }
            }
    
        for (x = 0; x < 4; ++x)  // 向左移动方格 
            for (y = 0; y < 4; ++y) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = y; (i > 0) && (a[x][i - 1] == 0); --i) {
                        a[x][i - 1] = a[x][i];
                        a[x][i] = 0;
                    }
                }
            }
    }
    void _right() {
        int x, y, i;
    
        for (x = 0; x < 4; ++x)  // 向右合并相同的方格 
            for (y = 3; y >= 0; --y) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = y - 1; i >= 0; --i) {
                        if (a[x][i] == 0)
                            ;
                        else if (a[x][y] == a[x][i]) {
                            a[x][y] += a[x][i];
                            a[x][i] = 0;
                            ++emtpy;
                            y = i;
                            break;
                        }
                        else
                            break;
                    }
                }
            }
    
        for (x = 0; x < 4; ++x)   // 向右移动方格 
            for (y = 3; y >= 0; --y) {
                if (a[x][y] == 0)
                    ;
                else {
                    for (i = y; (i < 3) && (a[x][i + 1] == 0); ++i) {
                        a[x][i + 1] = a[x][i];
                        a[x][i] = 0;
                    }
                }
            }
    }
    void add_number()
    {
        srand(time(0));
        if (emtpy > 0)
        {
            int x, y, temp;
            do
            {
                x = rand() % 4;
                y = rand() % 4;
            } while (a[x][y] != 0);
            temp = rand();
            int i = temp % 2;
            if (i == 1)
            {
                a[x][y] = 2;
                emtpy--;
    
            }
            else
            {
                a[x][y] = 4;
                emtpy--;
            }
    
        }
    }
    void play()
    {
        char c = getch();
        switch (c)
        {
        case 'w':
        case'W':
        {
            _up();
            add_number();
            draw();
    
            break;
    
        }
        case 's':
        case'S':
        {
            _down();
            add_number();
            draw();
            break;
    
        }
        case 'a':
        case'A':
        {
            _left();
            add_number();
            draw();
            break;
    
    
    
        }case 'd':
        case'D':
        {
            _right();
            add_number();
            draw();
            break;
    
        }
        case 'q':
        case 'Q':
        {
            for (int i = 0; i < 4; i++)
            {
                for (int j = 0; j < 4; j++)
                {
                    a[i][j] = _back[i][j];
                    draw();
                }
            }
        }
        }
    
    }
    int  main()
    {
        init();
        int i, j;
        initgraph(724, 724);//初始化
        PIMAGE img;
        img = newimage();
        getimage(img, "2048/背景.jpg");
        putimage(0, 0, img);
        draw();
        for (; is_run(); delay_fps(30))
        {
            for (int i = 0; i < 4; i++)
            {
                for (int j = 0; j < 4; j++)
                {
                    _back[i][j] = a[i][j];
                }
            }
            play();
        }
    }
    展开全文
  • 一、工具首先我们需要两个工具,我自己用的vc2017,然后需要图形库软件。EasyX,百度搜去官网就可以去找到。二,源码用到了循环,枚举,图形库函数,时间函数,结构体,如果你都懂那么都看到了。//贪吃蛇项目#...
  • 3.游戏开始时,假如当获取字符为‘w’则先循环判定这个数字下方有无和它相等数字。如无则跳过,如有相加。然后在判定是否可以向上移动 下面是我代码 (我本来是还要写一个撤回函数 可惜写出来却不...
  • UNIX下C语言的图形编程curses.h函式相信您在网路上一定过如 tin,elm 等工具, 这些软体有项共同的特色,即他们利用上下左右等方向键来控制游标的位置. 除此之外, 这些程式的画面也较为美观. 对 Programming 有...
  • C语言 图形

    千次阅读 2018-09-03 17:42:50
    最开始我是用的Qt,但是Qt的入门和掌握太花时间了,最后万般无奈地情况下我选择了EGE图形库。 首先提一下,笔者使用Visual Studio 2017开发环境,至于ege图形库安装和生效大家可以去csdn里面搜。 ege实现一些...
  • UNIX下C语言的图形编程-curses.h函数

    千次阅读 2013-12-01 20:40:47
    相信您在网路上一定过如 tin,elm 等工具, 这些软体有项共同特色, 即他们利用上下左右等方向键来控制游标位置. 除此之外, 这些程式 画面也较为美观. 对 Programming 有兴趣朋友一定对此感到...
  • <br /> 相信您在网路上一定过如 tin,elm 等工具, 这些软体有项共同特色,即他们利用上下左右等方向键来控制游标位置。 除此之外, 这些程式画面也较为美观。 对 Programming 有兴趣朋友一定对此...
  • C语言与C++区别

    2017-07-15 12:42:15
    1、全新的程序设计思维,C语言是面向过程的,而C++是面向对象的。2、C语言有标准的函数,它们是松散的,只是把功能相同的函数放在一个头文件中;而C++对于大多数的函数都...C语言的图形处理函数基本上是不能用
  • 该楼层疑似违规已被系统折叠隐藏此楼查看此楼贴吧内经常有人问C语言是不是只能用于字符终端界面开发,不用于图形界面。大家也都有回答,需要其他的库。MFC,GTK,QT。本人近期刚GTK加上纯C写成了第一个LINUX...
  • Borland BGI图形库是一个经典的图形库,被广泛应用于编写DOS应用程序。Turbo C/C++/PASCAL都支持BGI图形库,大多数DOS游戏都使用这些平台开发并使用BGI图形库。目前多数大学仍使用Turbo C++作为C语言课程的开发环境...
  • 该楼层疑似违规已被系统折叠隐藏此楼查看此楼贴吧内经常有人问C语言是不是只能用于字符终端界面开发,不用于图形界面。大家也都有回答,需要其他的库。MFC,GTK,QT。本人近期刚GTK加上纯C写成了第一个LINUX...
  • 大家好,这里先祝大家月饼节快乐了!博主我呢,目前是名大二学生,学校在本学期开设了...不过老师是C语言完成,在我C++重写时,遇到了不少问题,也做了很多学习和思考,最后完成得也算是比较满意吧。希望这个
  • 一、填空题(每空1分,共33分) 1. 一个计算机系统包括 硬件系统 和 软件系统 两大部分。 2. 一台计算机中全部程序集合,称为这台计算机为这台... C语言常量可分为整型常量、实型常量、字符型常量及 四种。
  • c语言五子棋

    2012-05-07 20:12:14
    使用VS开发的c语言贪吃蛇,界面非常友好,首先需要下载EasyX_v20110101b.zip(直接百度搜索下载),解压后安装使用即可,此包里面包含vs里面能用的graphic图形库
  • C语言贪吃蛇

    2007-09-19 23:23:41
    本人自己写的C语言版贪吃蛇,是在Linux下利用SDL图形库设计,Windows下不能用
  • 直接上图啦~ DNS流程图 ...第二步,从左侧符号选择合适的图形,拖放到画布合适位置; 将鼠标放置在图形上方,图形四周就会出现“◀▲▶▼”的指示符号,点击即可实现快速连线; 符号拖放、快速
  • 你必须知道495个C语言问题

    千次下载 热门讨论 2015-05-08 11:09:25
    2.9 为什么不能用内建==和!=操作符比较结构? 2.10结构传递和返回是如何实现? 2.11 如何向接受结构参数函数传入常量值?怎样创建无名中间常量结构值? 2.12 怎样从/向数据文件读/写结构? 结构...
  • 该楼层疑似违规已被系统折叠隐藏此楼查看此楼贴吧内经常有人问C语言是不是只能用于字符终端界面开发,不用于图形界面。大家也都有回答,需要其他的库。MFC,GTK,QT。本人近期刚GTK加上纯C写成了第一个LINUX...
  • C语言编程要点

    2017-09-18 00:10:37
    9.8. 为什么const说明常量不用来定义一个数组初始大小? 145 9.9. 字符串和数组有什么不同? 145 第10章 位(bit)和字节(byte) 147 10.1. 什么方法存储标志(flag)效率最高? 147 10.2. 什么是“位屏蔽(bit ...
  • 该楼层疑似违规已被系统折叠隐藏此楼查看此楼贴吧内经常有人问C语言是不是只能用于字符终端界面开发,不用于图形界面。大家也都有回答,需要其他的库。MFC,GTK,QT。本人近期刚GTK加上纯C写成了第一个LINUX...
  • 该楼层疑似违规已被系统折叠隐藏此楼查看此楼贴吧内经常有人问C语言是不是只能用于字符终端界面开发,不用于图形界面。大家也都有回答,需要其他的库。MFC,GTK,QT。本人近期刚GTK加上纯C写成了第一个LINUX...
  • 《你必须知道495个C语言问题》

    热门讨论 2010-03-20 16:41:18
    2.9 为什么不能用内建==和!=操作符比较结构? 26 2.10 结构传递和返回是如何实现? 26 2.11 如何向接受结构参数函数传入常量值?怎样创建无名中间常量结构值? 26 2.12 怎样从/向数据文件读/写结构...
  • 2.9 为什么不能用内建==和!=操作符比较结构? 26 2.10 结构传递和返回是如何实现? 26 2.11 如何向接受结构参数函数传入常量值?怎样创建无名中间常量结构值? 26 2.12 怎样从/向数据文件读/写结构...

空空如也

空空如也

1 2 3 4 5 ... 7
收藏数 124
精华内容 49
关键字:

c语言能用的图形库

c语言 订阅