zoukankan      html  css  js  c++  java
  • 【开源程序(C++)】获取bing图片并自动设置为电脑桌面背景

    众所周知,bing搜索网站首页每日会更新一张图片,张张漂亮(额,也有一些不合我口味的),特别适合用来做电脑壁纸。

    我们想要将bing网站背景图片设置为电脑桌面背景的通常做法是:

    • 上网,搜索bing
    • 找到图片的下载链接,并下载之
    • 将图片设置为桌面背景(也有部分浏览器支持直接在网页中右击图片设置为壁纸)
    • 可能你还会删除下载下来的图片

    作为一枚coder,你不会觉得麻烦嘛?至少需要三个步骤呢!

    So...我就用C++语言写了一个小程序,用于获取bing网站的图片,并将其设置为桌面背景。整个过程只需要点击.exe文件,一键完成!

    当然,你也可以通过本程序,窥见Windows API的些许用法,活学活用C++知识!

    当然网上也存在片片断断的程序,我的部分程序也借鉴了它们的思想,在此感谢互联网和辛勤的贡献者们。

    以下是程序设计的技术要点:

    --------------------------------------------------------------

    技术要点:

        1、获取网络地址   直接使用网络地址或下载 注意若下载下来后,要将转换为/,当然也可以用\
           网络地址可以从这里获取:http://cn.bing.com/HPImageArchive.aspx?format=xml&idx=0&n=1
           在返回的xml页面中(images->image->url)找到具体的图片地址(xml解析),拼接到bing域名后面构成完整地址
           注:xml解析用了TinyXml2
    
    
        2、转换图片格式(jpg->bmp),本程序中的SystemParametersInfoA函数只支持bmp
           在程序中自动转换(单单改后缀名是没有用的),转换用的程序是从网上下载的,用C语言编写而成
           考虑到需要改后缀名,那就直接下载图片好了,顺便存储之
    
    
        3、图片保存路径为C:/Users/Administrator/bingPicture/,格式为.jpg 方便以后浏览

    注意:部分用户电脑可能不存在路径C:/Users/Administrator/,造成程序无法执行,可以直接在C盘根目录下创建路径,如C:/bingPicture/
           注意不保存转换后的bmp格式图片(设置背景后即删除),因为体积较大
           判断文件夹是否存在,若不存在,则自动创建文件夹


    4、注意本程序获取的图片尺寸是1366x768,若你的屏幕分辨率为1920x1080,还需要对Xml解析出来的图片Url地址进行字符串替换(将1366x768换成1920x1080即可)

    前提:针对1920x1080尺寸的图片地址存在


    5、若此程序若在国际网络下运行,获取的就是国际版bing壁纸;若在国内网络下运行,获取的就是中国版bing壁纸。因此在同一天内,在不同网络环境下获取的图片可能不同

    
    
    *未实现的功能*:
        1、获取每日壁纸的故事(利用bing故事接口) ,更新壁纸后显示在执行框中
    
    
        2、开机自启动,并隐藏到托盘中(为减少CPU占用并增加趣味性,设置为开机自动启动,提示网络连接,并输入"go"才执行功能)
           电脑若未关机,则在24:00自动启动,更换背景
    
    
        3、软件自动更新版本功能

    --------------------------------------------------------------

    程序在文章后面提供,源码已注释很详细,不再赘述。

    注意,使用程序之前,务必看以下注意事项:

    --------------------------------------------------------------

    请注意:
        1、本软件使用Qt开发,您也可以将文件加入自己的工程,使用其他IDE开发
             需要注意的一点是,本软件需要加入URLMON.DLL(源码包中有)

        2、本软件开源(源码位于xiaoxi666的博客园以及github,不对其他地址给出的链接负责),仅用于学习交流,请勿用于商业用途

        3、为防止软件被加入恶意功能,不提供可执行文件,若需使用请重新编译,编译器需要支持c++11

        4、本软件程序中内含删除临时文件功能,请在更改前仔细确认,避免路径错误而删除其他重要文件

    --------------------------------------------------------------

    然而许多小伙伴要体验效果,我就一并把可执行文件放出来吧(请勿随意传播.exe文件防止有人添加恶意功能。当然源码开放可共享)

    下载区:

    但一定要注意核对文件校验码(以保证安全):

    •  可执行文件压缩包WallPaper校验码

        MD5: 48173BA7DCF2120F2822226A5D4A90CF
               SHA1: CEB0ED570AF613EC3829AC8FDE4F8C50DDEF4101

    •  可执行文件WallPaper_1366x768_Common校验码(此版本用于1366x768分辨率)

        MD5: ACDA8E5E4CF0B2916254B233D1243FD3
           SHA1: 6041C813DC8E2AE29EA8675EF279CFC0E7921D53

    • 可执行文件WallPaper_1920x1080_Common校验码(此版本用于1920x1080分辨率)

        MD5: 474570808A56EFDC7B589F605D08C5B6
            SHA1: B78921AD655B35F079076904A22F1A0E5122EB7F

    为方便浏览,贴出主要源程序:

     main.cpp文件

      1 //main.cpp
      2 /******************windows桌面背景更换C++程序***********************************************************
      3 功能:获取每日bing搜索主页图片,设置为当日桌面壁纸。并将其下载保存至本地文件夹方便以后浏览
      4 作者:xiaoxi666
      5 日期:2017/03/12
      6 
      7 技术要点:
      8     1、获取网络地址   直接使用网络地址或下载 注意若下载下来后,要将转换为/,当然也可以用\
      9        网络地址可以从这里获取:http://cn.bing.com/HPImageArchive.aspx?format=xml&idx=0&n=1
     10        在返回  的xml页面中(images->image->url)找到具体的图片地址(xml解析),拼接到bing域名后面,构成完整地址
     11        注:xml解析用了TinyXml2
     12 
     13     2、转换图片格式(jpg->bmp),本程序中的SystemParametersInfoA函数只支持bmp
     14        在程序中自动转换(单单改后缀名是没有用的),转换用的程序是从网上下载的,用C语言编写而成
     15        考虑到需要改后缀名,那就直接下载图片好了,顺便存储之
     16 
     17     3、图片保存路径为C:ingPicture\,格式为.jpg 方便以后浏览
     18        注意不保存转换后的bmp格式图片(设置背景后即删除),因为体积较大
     19        判断文件夹是否存在,若不存在,则自动创建文件夹
     20 
     21 *未实现的功能*:
     22     ***获取每日壁纸的故事(利用bing故事接口) ,更新壁纸后显示在执行框中
     23 
     24     ***开机自启动,并隐藏到托盘中(为减少CPU占用并增加趣味性,设置为开机自动启动,提示网络连接,并输入"go"才执行功能)
     25        电脑若未关机,则在24:00自动启动,更换背景
     26 
     27     ***软件自动更新版本功能
     28 
     29 ******************************************************************************************************/
     30 
     31 #include <iostream>    //输入输出
     32 #include <cstring>     //文件命名处理需要用字符串
     33 #include <windows.h>   //调用操作系统各种API
     34 #include <ctime>       //获取时间,各种文件命名
     35 #include <UrlMon.h>    //包含提供下载服务的API
     36 #include "tinyxml2.h"  //解析XML
     37 #include <io.h>        //判断文件夹是否存在
     38 #include <direct.h>    //创建文件夹
     39 extern "C"
     40 {
     41 #include "jpeg.h"    //转换图片格式jpg->bmp  转换格式的程序使用C语言写的
     42 }
     43 
     44 //创建本地bingPicture路径和Tmp路径
     45 void createDir()
     46 {
     47     //本地bingPicture路径
     48     std::string LocalFolder="C:/bingPicture/";
     49 
     50     if(0!=access(LocalFolder.c_str(),0))    //判断文件夹是否存在,若不存在则创建
     51         if(0!=mkdir(LocalFolder.c_str()))
     52             std::cout<<"创建文件夹bingPicture失败!"<<std::endl;
     53         else
     54             std::cout<<"创建文件夹bingPicture成功!"<<std::endl;
     55     else
     56         std::cout<<"文件夹bingPicture已存在!"<<std::endl;
     57 
     58     //本地Tmp路径
     59     std::string LocalXmlFolder="C:/bingPicture/Tmp/";
     60 
     61     if(0!=access(LocalXmlFolder.c_str(),0))    //判断文件夹是否存在,若不存在则创建
     62         if(0!=mkdir(LocalXmlFolder.c_str()))
     63             std::cout<<"创建临时文件夹Tmp失败!"<<std::endl;
     64         else
     65             std::cout<<"创建临时文件夹Tmp成功!"<<std::endl;
     66     else
     67         std::cout<<"临时文件夹Tmp已存在!"<<std::endl;
     68 
     69 }
     70 
     71 /**************************************************************************************
     72 首先明白一个概念,即string替换所有字符串,将"12212"这个字符串的所有"12"都替换成"21",结果是什么?
     73 可以是22211,也可以是21221,有时候应用的场景不同,就会希望得到不同的结果,所以这两种答案都做了实现。
     74 **************************************************************************************/
     75 //替换字符串方法1(完全轮询,替换一次后接着再次扫描,因为替换一次后可能又出现了满足替换条件的字符串)
     76 std::string & replace_all(std::string& str,const std::string& old_value,const std::string& new_value)
     77 {
     78     while(true)   {
     79         std::string::size_type pos(0);
     80         if((pos=str.find(old_value))!=std::string::npos)
     81             str.replace(pos,old_value.length(),new_value);
     82         else
     83             break;
     84     }
     85     return str;
     86 }
     87 
     88 //替换字符串方法2(只替换一次) 本项目中,只替换为/用方法2即可
     89 std::string & replace_all_distinct(std::string& str,const std::string& old_value,const std::string& new_value)
     90 {
     91     for(std::string::size_type pos(0);  pos!=std::string::npos; pos+=new_value.length())
     92     {
     93         if((pos=str.find(old_value,pos))!=std::string::npos)
     94             str.replace(pos,old_value.length(),new_value);
     95         else   break;
     96     }
     97     return str;
     98 }
     99 
    100 //获取年月日(命名用)
    101 std::string getYearMonthDay()
    102 {
    103     time_t timer;
    104     time(&timer);
    105     tm* t_tm = localtime(&timer);
    106 
    107     std::string Year=std::to_string(t_tm->tm_year+1900);
    108     std::string Month=std::to_string(t_tm->tm_mon+1);
    109     std::string Day=std::to_string(t_tm->tm_mday);
    110     std::string PictureName=Year+"_"+Month+"_"+Day;
    111 
    112     return PictureName;
    113 }
    114 
    115 //获取图片的Xml并解析图片的url路径
    116 std::string getPicTureXmlAndUrl()
    117 {
    118     //网络上的XML路径
    119     std::string WebXmlpath ="http://cn.bing.com/HPImageArchive.aspx?format=xml&idx=0&n=1";
    120     //本地Xml路径
    121     std::string LocalXmlFolder="C:/bingPicture/Tmp/";
    122     std::string LocalXmleach=getYearMonthDay();
    123     std::string LocalXmlFullpath=LocalXmlFolder+LocalXmleach+".xml";
    124 
    125     if(URLDownloadToFileA(NULL,
    126                          WebXmlpath.c_str(),
    127                          LocalXmlFullpath.c_str(),
    128                          0,
    129                          NULL)
    130             ==S_OK)
    131     {
    132         std::cout<<"Xml下载成功!即将解析今日壁纸Url!"<<std::endl;
    133 
    134         /***************下面开始解析xml中的url路径*******************/
    135         tinyxml2::XMLDocument doc;
    136         if(tinyxml2::XML_SUCCESS != doc.LoadFile(LocalXmlFullpath.c_str()))
    137             std::cout<<"读取Xml文件异常!"<<std::endl;
    138         tinyxml2::XMLElement *images=doc.RootElement();
    139         tinyxml2::XMLElement *image =images->FirstChildElement("image");
    140 
    141         //图片Url
    142         std::string WebPicturedomain="http://cn.bing.com";
    143         std::string WebPictureUrl="";
    144 
    145         if(image!=NULL)
    146             WebPictureUrl=image->FirstChildElement("url")->GetText();
    147 
    148         std::string WebPictureFullpath1366x768 =WebPicturedomain+WebPictureUrl;
    149         std::cout<<"今日壁纸Url解析成功!"<<std::endl;
    150         /*********************************************************/
    151         return WebPictureFullpath1366x768;
    152 //        //将1366x768换成1920x1080
    153 //        std::string WebPictureFullpath1920x1080 =replace_all_distinct(WebPictureFullpath1366x768,"1366x768","1920x1080");
    154 
    155 //        return WebPictureFullpath1920x1080;
    156     }
    157     else
    158     {
    159         std::cout<<"Xml下载失败!无法获取图片Url!请检查网络连接是否正常!"<<std::endl;
    160         return "error";
    161     }
    162 
    163 }
    164 
    165 //从网络上下载图片并存储到本地
    166 std::string getPicture(std::string WebFullpath)
    167 {
    168     //本地存储路径
    169     std::string LocalFolder="C:/bingPicture/";
    170     std::string Localeach=getYearMonthDay();
    171     std::string LocalFullpath=LocalFolder+Localeach+".jpg";
    172 
    173     if(URLDownloadToFileA(NULL,
    174                          WebFullpath.c_str(),
    175                          LocalFullpath.c_str(),
    176                          0,
    177                          NULL)
    178             ==S_OK)
    179     {
    180         std::cout<<"今日壁纸下载成功!"<<std::endl;
    181 
    182         /***************下面转换图片格式jpg->bmp******************/
    183         //临时文件夹Tmp路径
    184         std::string TmpFolder="C:/bingPicture/Tmp/";
    185         //.bmp图片路径
    186         std::string bmpFolder=TmpFolder+getYearMonthDay()+".bmp";
    187         LoadJpegFile(const_cast<char *>(LocalFullpath.c_str()),const_cast<char *>(bmpFolder.c_str()));
    188         /*******************************************************/
    189         return bmpFolder;
    190     }
    191     else
    192     {
    193         std::cout<<"壁纸下载失败!请检查网络连接是否正常!"<<std::endl;
    194         return "error";
    195     }
    196 }
    197 
    198 //改变桌面背景成功后,删除bmp文件和xml文件(只保留jpg文件),此步骤需要小心,避免删除错误路径下的内容
    199 void deleteBmpAndXml()
    200 {
    201     //临时文件夹Tmp路径
    202     std::string TmpFolder="C:/bingPicture/Tmp/";
    203     //.bmp图片路径
    204     std::string bmpFolder=TmpFolder+getYearMonthDay()+".bmp";
    205     //xml文件路径
    206     std::string xmlFolder=TmpFolder+getYearMonthDay()+".xml";
    207 
    208     if(0==access("C:/bingPicture/Tmp/",0))    //判断文件夹是否存在,若存在则删除
    209     {
    210         //删除bmp图片
    211         if(0==access(bmpFolder.c_str(),0))
    212         {
    213             if(0==remove(bmpFolder.c_str()))
    214                 std::cout<<"删除临时bmp格式图片成功!"<<std::endl;
    215             else
    216                 std::cout<<"删除临时bmp格式图片失败!"<<std::endl;
    217         }
    218         else
    219             std::cout<<"临时bmp格式图片不存在!"<<std::endl;
    220 
    221         //删除xml文件
    222         if(0==access(xmlFolder.c_str(),0))
    223         {
    224             if(0==remove(xmlFolder.c_str()))
    225                 std::cout<<"删除xml文件成功!"<<std::endl;
    226             else
    227                 std::cout<<"删除xml文件失败!"<<std::endl;
    228         }
    229         else
    230             std::cout<<"xml文件不存在!"<<std::endl;
    231 
    232         //删除Tmp文件夹(注意此函数只能删除空文件夹,因此要先删除文件夹中的文件)
    233         if(0==rmdir(TmpFolder.c_str()))
    234             std::cout<<"临时文件夹Tmp已删除!"<<std::endl;
    235         else
    236             std::cout<<"临时文件夹Tmp删除失败!"<<std::endl;
    237     }
    238     else
    239         std::cout<<"临时文件夹Tmp不存在!"<<std::endl;
    240 
    241 }
    242 
    243 //改变桌面背景(PictureFullpath:图片完整路径)
    244 void changePicture(std::string PictureFullpath)
    245 {
    246     bool result=false;
    247     result=SystemParametersInfoA(SPI_SETDESKWALLPAPER,
    248                           0,
    249                           (PVOID)PictureFullpath.c_str(),
    250                           0);
    251     if(result==false)
    252     {
    253         std::cout<<"今日壁纸更新失败!请联系开发人员!"<<std::endl;
    254     }
    255 
    256     else
    257     {
    258         SystemParametersInfoA(SPI_SETDESKWALLPAPER,
    259                                   0,
    260                                   (PVOID)PictureFullpath.c_str(),
    261                                   SPIF_SENDCHANGE);
    262         //deleteBmpAndXml();    //windows8及其以上会变成黑色,把这条语句放到main最后面就没问题,具体原因未知
    263         system("cls");
    264         std::cout<<"version:1.0.0 (Author:xiaoxi666)"<<std::endl<<std::endl;
    265         std::cout<<"今日壁纸更新成功!"<<std::endl<<std::endl;
    266         std::cout<<"美好的一天开始啦!用心享受吧!"<<std::endl<<std::endl;
    267     }
    268 }
    269 
    270 int main()
    271 {
    272     std::string startOrder="";
    273     std::cout<<"嗨!小伙伴!你的贴心壁纸小助手已启动!将为你设置今日壁纸哦!"<<std::endl<<std::endl;
    274     std::cout<<"请确保电脑网络连接状况良好,准备好后输入go"<<std::endl<<std::endl;
    275     std::cout<<"请输入指令: ";
    276     std::cin>>startOrder;
    277     while("go"!=startOrder)
    278     {
    279         std::cout<<"哎呀输错了呢,重新输入吧: ";
    280         std::cin>>startOrder;
    281     }
    282     if("go"==startOrder)
    283     {
    284         createDir();
    285         changePicture(getPicture(getPicTureXmlAndUrl()));
    286     }
    287 
    288     /*******************************以下为个性化字幕输出,与程序核心功能无关************************/
    289     std::string umua0="          **     **   ********   *******   *******   ***  ***     ";
    290     std::string umua1="          **     **   ********   *******   *******   ***  ***     ";
    291     std::string umua2="          **     **   **    **   **   **   ***  **   ***  ***     ";
    292     std::string umua3="          **     **   **    **   **   **   ***  **    **  **      ";
    293     std::string umua4="          *********   ********   *******   *******     *  *       ";
    294     std::string umua5="          *********   ********   *******   **           **        ";
    295     std::string umua6="          **     **   **    **   **        **           **        ";
    296     std::string umua7="          **     **   **    **   **        **           **        ";
    297     std::string umua8="          **     **   **    **   **        **           **        ";
    298     std::string umua9="          **     **   **    **   **        **           **        ";
    299 
    300     #define mua(n) std::cout<<umua##n<<std::endl;
    301     std::cout<<std::endl<<std::endl;
    302     mua(0);mua(1);mua(2);mua(3);mua(4);mua(5);mua(6);mua(7);mua(8);mua(9);
    303     std::cout<<std::endl<<std::endl<<std::endl;
    304     system("pause");
    305     /******************************************************************************************/
    306     deleteBmpAndXml();
    307     return 0;
    308 }
    View Code

    图片格式转换程序(这个是网上下载的C源码,我改了一下接口,在此感谢)

    jpeg.h

    //头文件jpeg.h,配合程序jpeg2bmp.c使用
    //若用于c++程序中,请用extern "C"包含此头文件
    //功能:用于将图片从jpg类型转换为bmp类型,调用函数LoadJpegFile即可,参数1:jpg文件路径;参数2:bmp文件路径
    
    #define M_SOF0  0xc0
    #define M_DHT   0xc4
    #define M_EOI   0xd9
    #define M_SOS   0xda
    #define M_DQT   0xdb
    #define M_DRI   0xdd
    #define M_APP0  0xe0
    
    static int Zig_Zag[8][8]={{0,1,5,6,14,15,27,28},
                              {2,4,7,13,16,26,29,42},
                              {3,8,12,17,25,30,41,43},
                              {9,11,18,24,37,40,44,53},
                              {10,19,23,32,39,45,52,54},
                              {20,22,33,38,46,51,55,60},
                              {21,34,37,47,50,56,59,61},
                              {35,36,48,49,57,58,62,63}
                             };
    
    #define W1 2841 /* 2048*sqrt(2)*cos(1*pi/16) */
    #define W2 2676 /* 2048*sqrt(2)*cos(2*pi/16) */
    #define W3 2408 /* 2048*sqrt(2)*cos(3*pi/16) */
    #define W5 1609 /* 2048*sqrt(2)*cos(5*pi/16) */
    #define W6 1108 /* 2048*sqrt(2)*cos(6*pi/16) */
    #define W7 565  /* 2048*sqrt(2)*cos(7*pi/16) */
    
    int LoadJpegFile (char *JpegFileName,char *bmpFileName);
    View Code

    jpeg2bmp.c

    //jpeg.c
    //本程序用C语言编写,若用于c++程序中,请用extern "C"包含头文件jpeg.h
    //功能:用于将图片从jpg类型转换为bmp类型,调用函数LoadJpegFile即可,参数1:jpg文件路径;参数2:bmp文件路径
    
    #include "jpeg.h"
    #include "memory.h"
    #include "math.h"
    #include "stdio.h"
    #include "windows.h"
    
    //macro definition
    #define WIDTHBYTES(i)    ((i+31)/32*4)
    #define PI 3.1415926535
    //define return value of function
    #define FUNC_OK 0
    #define FUNC_MEMORY_ERROR 1
    #define FUNC_FILE_ERROR 2
    #define FUNC_FORMAT_ERROR 3
    //////////////////////////////////////////////////
    //Jpeg functions
    //int LoadJpegFile (char *JpegFileName,char *bmpFileName);
    void showerror(int funcret);
    int  InitTag();
    void InitTable();
    int  Decode();
    int  DecodeMCUBlock();
    int  HufBlock(unsigned char dchufindex,unsigned char achufindex);
    int  DecodeElement();
    void IQtIZzMCUComponent(short flag);
    void IQtIZzBlock(short  *s ,int * d,short flag);
    void GetYUV(short flag);
    void StoreBuffer();
    BYTE ReadByte();
    void Initialize_Fast_IDCT();
    void Fast_IDCT(int * block);
    void idctrow(int * blk);
    void idctcol(int * blk);
    //////////////////////////////////////////////////
    //global variable declaration
    BITMAPFILEHEADER   bf;
    BITMAPINFOHEADER   bi;
    HBITMAP            hBitmap=NULL;
    HGLOBAL            hImgData=NULL;
    DWORD              NumColors;
    DWORD              LineBytes;
    DWORD              ImgWidth=0 , ImgHeight=0;
    unsigned int       PcxBytesPerLine;
    LPSTR              lpPtr;
    //////////////////////////////////////////////////
    //variables used in jpeg function
    short            SampRate_Y_H,SampRate_Y_V;
    short            SampRate_U_H,SampRate_U_V;
    short            SampRate_V_H,SampRate_V_V;
    short            H_YtoU,V_YtoU,H_YtoV,V_YtoV;
    short            Y_in_MCU,U_in_MCU,V_in_MCU;
    unsigned char   *lpJpegBuf;
    unsigned char   *lp;
    short            qt_table[3][64];
    short            comp_num;
    BYTE            comp_index[3];
    BYTE            YDcIndex,YAcIndex,UVDcIndex,UVAcIndex;
    BYTE            HufTabIndex;
    short            *YQtTable,*UQtTable,*VQtTable;
    BYTE            And[9]={0,1,3,7,0xf,0x1f,0x3f,0x7f,0xff};
    short            code_pos_table[4][16],code_len_table[4][16];
    unsigned short    code_value_table[4][256];
    unsigned short    huf_max_value[4][16],huf_min_value[4][16];
    short            BitPos,CurByte;
    short            rrun,vvalue;
    short            MCUBuffer[10*64];
    int                QtZzMCUBuffer[10*64];
    short            BlockBuffer[64];
    short            ycoef,ucoef,vcoef;
    BOOL            IntervalFlag;
    short            interval=0;
    int                Y[4*64],U[4*64],V[4*64];
    DWORD            sizei,sizej;
    short             restart;
    static  long    iclip[1024];
    static  long    *iclp;
    
    ////////////////////////////////////////////////////////////////
    int LoadJpegFile (char *JpegFileName,char *bmpFileName)
    {
        HFILE               hfjpg;
        DWORD                ImgSize;
        DWORD              JpegBufSize;
        HFILE              hfbmp;
        HGLOBAL               hJpegBuf;
        int                   funcret;
        LPBITMAPINFOHEADER lpImgData;
    
        if((hfjpg=_lopen(JpegFileName,OF_READ))==HFILE_ERROR)
        {
            showerror(FUNC_FILE_ERROR);
            return 0;
        }
        //get jpg file length
        JpegBufSize=_llseek(hfjpg,0L,SEEK_END);
        //rewind to the beginning of the file
        _llseek(hfjpg,0L,SEEK_SET);
    
        if((hJpegBuf=GlobalAlloc(GHND,JpegBufSize))==NULL)
        {
            _lclose(hfjpg);
            showerror(FUNC_MEMORY_ERROR);
            return 0;
        }
        lpJpegBuf=(unsigned char  *)GlobalLock(hJpegBuf);
        _hread(hfjpg,(unsigned char  *)lpJpegBuf,JpegBufSize);
        _lclose(hfjpg);
    
    
        InitTable();
    
        if((funcret=InitTag())!=FUNC_OK)
        {
            GlobalUnlock(hJpegBuf);
            GlobalFree(hJpegBuf);
            showerror(funcret);
            return 0;
        }
        //create new bitmapfileheader and bitmapinfoheader
        memset((char *)&bf,0,sizeof(BITMAPFILEHEADER));    
        memset((char *)&bi,0,sizeof(BITMAPINFOHEADER));
    
        bi.biSize=(DWORD)sizeof(BITMAPINFOHEADER);
        bi.biWidth=(LONG)(ImgWidth);
        bi.biHeight=(LONG)(ImgHeight);
        bi.biPlanes=1;
        bi.biBitCount=24;
        bi.biClrUsed=0;
        bi.biClrImportant=0;
        bi.biCompression=BI_RGB;
        NumColors=0;
        LineBytes=(DWORD)WIDTHBYTES(bi.biWidth*bi.biBitCount);
        ImgSize=(DWORD)LineBytes*bi.biHeight;
    
        bf.bfType=0x4d42;
        bf.bfSize=sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER)+NumColors*sizeof(RGBQUAD)+ImgSize;
        bf.bfOffBits=(DWORD)(NumColors*sizeof(RGBQUAD)+sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER));
     
        if((hImgData=GlobalAlloc(GHND,ImgSize))==NULL)
        {
            GlobalUnlock(hJpegBuf);
            GlobalFree(hJpegBuf);
            showerror(FUNC_MEMORY_ERROR);
            return FALSE;
        }
        lpImgData=(LPBITMAPINFOHEADER)GlobalLock(hImgData); 
        lpPtr=(char *)lpImgData;
    
        if((SampRate_Y_H==0)||(SampRate_Y_V==0))
        {
            GlobalUnlock(hJpegBuf);
            GlobalFree(hJpegBuf);
            GlobalUnlock(hImgData);
            GlobalFree(hImgData);
            hImgData=NULL;
            showerror(FUNC_FORMAT_ERROR);
            return FALSE ;
        }
    
        funcret=Decode();
        
        if(funcret==FUNC_OK)
        {
    
            hfbmp=_lcreat(bmpFileName,0);
            _lwrite(hfbmp,(LPSTR)&bf,sizeof(BITMAPFILEHEADER)); //写BMP文件头
            _lwrite(hfbmp,(LPSTR)&bi,sizeof(BITMAPINFOHEADER)); //写BMP文件信息
            _lwrite(hfbmp,(LPSTR)lpImgData,ImgSize);            //写BMP位图数据
            _lclose(hfbmp);
            GlobalUnlock(hJpegBuf);
            GlobalFree(hJpegBuf);
            GlobalUnlock(hImgData);
            return TRUE;
        }
        else
        {
            GlobalUnlock(hJpegBuf);
            GlobalFree(hJpegBuf);
            GlobalUnlock(hImgData);
            GlobalFree(hImgData);
            hImgData=NULL;
            showerror(funcret);
            return FALSE;
        }
    }
    /////////////////////////////////////////////////
    void showerror(int funcret)
    {
        switch(funcret)
        {
        case FUNC_MEMORY_ERROR:
            printf("Error alloc memory!
    ");   
            exit(1);
            break;
        case FUNC_FILE_ERROR:
            printf("File not found!!
    ");   
            exit(1);
            break;
        case FUNC_FORMAT_ERROR:
            printf("File format error!
    ");   
            exit(1);
            break;
        }
    }
    ////////////////////////////////////////////////////////////////////////////////
    int InitTag()
    {
        BOOL finish=FALSE;
        BYTE id;
        short  llength;
        short  i,j,k;
        short  huftab1,huftab2;
        short  huftabindex;
        BYTE hf_table_index;
        BYTE qt_table_index;
        BYTE comnum;
    
        unsigned char  *lptemp;
        short  ccount;
    
        lp=lpJpegBuf+2;
    
        while (!finish)
        {
            id=*(lp+1);
            lp+=2;
            switch (id)
            {
            case M_APP0:
                llength=MAKEWORD(*(lp+1),*lp);
                lp+=llength;
                break;
            case M_DQT:
                llength=MAKEWORD(*(lp+1),*lp);
                qt_table_index=(*(lp+2))&0x0f;
                lptemp=lp+3;
                if(llength<80)
                {
                    for(i=0;i<64;i++)
                        qt_table[qt_table_index][i]=(short)*(lptemp++);
                }
                else
                {
                    for(i=0;i<64;i++)
                        qt_table[qt_table_index][i]=(short)*(lptemp++);
                    qt_table_index=(*(lptemp++))&0x0f;
                      for(i=0;i<64;i++)
                        qt_table[qt_table_index][i]=(short)*(lptemp++);
                  }
                  lp+=llength;        
                break;
            case M_SOF0:
                 llength=MAKEWORD(*(lp+1),*lp);
                 ImgHeight=MAKEWORD(*(lp+4),*(lp+3));
                 ImgWidth=MAKEWORD(*(lp+6),*(lp+5));
                comp_num=*(lp+7);
                if((comp_num!=1)&&(comp_num!=3))
                      return FUNC_FORMAT_ERROR;
                if(comp_num==3)
                {
                    comp_index[0]=*(lp+8);
                      SampRate_Y_H=(*(lp+9))>>4;
                      SampRate_Y_V=(*(lp+9))&0x0f;
                      YQtTable=(short *)qt_table[*(lp+10)];
    
                    comp_index[1]=*(lp+11);
                    SampRate_U_H=(*(lp+12))>>4;
                      SampRate_U_V=(*(lp+12))&0x0f;
                      UQtTable=(short *)qt_table[*(lp+13)];
    
                      comp_index[2]=*(lp+14);
                      SampRate_V_H=(*(lp+15))>>4;
                      SampRate_V_V=(*(lp+15))&0x0f;
                    VQtTable=(short *)qt_table[*(lp+16)];
                  }
                else
                {
                      comp_index[0]=*(lp+8);
                    SampRate_Y_H=(*(lp+9))>>4;
                      SampRate_Y_V=(*(lp+9))&0x0f;
                      YQtTable=(short *)qt_table[*(lp+10)];
    
                    comp_index[1]=*(lp+8);
                      SampRate_U_H=1;
                      SampRate_U_V=1;
                      UQtTable=(short *)qt_table[*(lp+10)];
    
                    comp_index[2]=*(lp+8);
                    SampRate_V_H=1;
                      SampRate_V_V=1;
                      VQtTable=(short *)qt_table[*(lp+10)];
                }
                  lp+=llength;                            
                break;
            case M_DHT:             
                llength=MAKEWORD(*(lp+1),*lp);
                if (llength<0xd0)
                {
                    huftab1=(short)(*(lp+2))>>4;     //huftab1=0,1
                     huftab2=(short)(*(lp+2))&0x0f;   //huftab2=0,1
                    huftabindex=huftab1*2+huftab2;
                     lptemp=lp+3;
                    for (i=0; i<16; i++)
                        code_len_table[huftabindex][i]=(short)(*(lptemp++));
                    j=0;
                    for (i=0; i<16; i++)
                        if(code_len_table[huftabindex][i]!=0)
                        {
                            k=0;
                            while(k<code_len_table[huftabindex][i])
                            {
                                code_value_table[huftabindex][k+j]=(short)(*(lptemp++));
                                k++;
                            }
                            j+=k;    
                        }
                    i=0;
                    while (code_len_table[huftabindex][i]==0)
                         i++;
                    for (j=0;j<i;j++)
                    {
                        huf_min_value[huftabindex][j]=0;
                        huf_max_value[huftabindex][j]=0;
                    }
                    huf_min_value[huftabindex][i]=0;
                    huf_max_value[huftabindex][i]=code_len_table[huftabindex][i]-1;
                    for (j=i+1;j<16;j++)
                    {
                        huf_min_value[huftabindex][j]=(huf_max_value[huftabindex][j-1]+1)<<1;
                        huf_max_value[huftabindex][j]=huf_min_value[huftabindex][j]+code_len_table[huftabindex][j]-1;
                    }
                    code_pos_table[huftabindex][0]=0;
                    for (j=1;j<16;j++)
                          code_pos_table[huftabindex][j]=code_len_table[huftabindex][j-1]+code_pos_table[huftabindex][j-1];
                      lp+=llength;
                }  //if
                else
                {
                     hf_table_index=*(lp+2);
                    lp+=2;
                    while (hf_table_index!=0xff)
                    {
                        huftab1=(short)hf_table_index>>4;     //huftab1=0,1
                         huftab2=(short)hf_table_index&0x0f;   //huftab2=0,1
                        huftabindex=huftab1*2+huftab2;
                        lptemp=lp+1;
                        ccount=0;
                        for (i=0; i<16; i++)
                        {
                            code_len_table[huftabindex][i]=(short)(*(lptemp++));
                            ccount+=code_len_table[huftabindex][i];
                        }
                        ccount+=17;    
                        j=0;
                        for (i=0; i<16; i++)
                            if(code_len_table[huftabindex][i]!=0)
                            {
                                k=0;
                                while(k<code_len_table[huftabindex][i])
                                {
                                    code_value_table[huftabindex][k+j]=(short)(*(lptemp++));
                                    k++;
                                }
                                j+=k;
                            }
                        i=0;
                        while (code_len_table[huftabindex][i]==0)
                            i++;
                        for (j=0;j<i;j++)
                        {
                            huf_min_value[huftabindex][j]=0;
                            huf_max_value[huftabindex][j]=0;
                        }
                        huf_min_value[huftabindex][i]=0;
                        huf_max_value[huftabindex][i]=code_len_table[huftabindex][i]-1;
                        for (j=i+1;j<16;j++)
                        {
                            huf_min_value[huftabindex][j]=(huf_max_value[huftabindex][j-1]+1)<<1;
                            huf_max_value[huftabindex][j]=huf_min_value[huftabindex][j]+code_len_table[huftabindex][j]-1;
                        }
                        code_pos_table[huftabindex][0]=0;
                        for (j=1;j<16;j++)
                            code_pos_table[huftabindex][j]=code_len_table[huftabindex][j-1]+code_pos_table[huftabindex][j-1];
                        lp+=ccount;
                        hf_table_index=*lp;
                    }  //while
                }  //else
                break;
            case M_DRI:
                llength=MAKEWORD(*(lp+1),*lp);
                restart=MAKEWORD(*(lp+3),*(lp+2));
                lp+=llength;
                break;
            case M_SOS:
                llength=MAKEWORD(*(lp+1),*lp);
                comnum=*(lp+2);
                if(comnum!=comp_num)
                    return FUNC_FORMAT_ERROR;
                lptemp=lp+3;
                for (i=0;i<comp_num;i++)
                {
                    if(*lptemp==comp_index[0])
                    {
                        YDcIndex=(*(lptemp+1))>>4;   //Y
                        YAcIndex=((*(lptemp+1))&0x0f)+2;
                    }
                    else{
                        UVDcIndex=(*(lptemp+1))>>4;   //U,V
                        UVAcIndex=((*(lptemp+1))&0x0f)+2;
                    }
                    lptemp+=2;
                }
                lp+=llength;
                finish=TRUE;
                break;
            case M_EOI:    
                return FUNC_FORMAT_ERROR;
                break;
            default:
                 if ((id&0xf0)!=0xd0)
                {
                    llength=MAKEWORD(*(lp+1),*lp);
                     lp+=llength;
                }
                else lp+=2;
                break;
              }  //switch
        } //while
        return FUNC_OK;
    }
    /////////////////////////////////////////////////////////////////
    void InitTable()
    {
        short i,j;
        sizei=sizej=0;
        ImgWidth=ImgHeight=0;
        rrun=vvalue=0;
        BitPos=0;
        CurByte=0;
        IntervalFlag=FALSE;
        restart=0;
        for(i=0;i<3;i++)
            for(j=0;j<64;j++)
                qt_table[i][j]=0;
        comp_num=0;
        HufTabIndex=0;
        for(i=0;i<3;i++)
            comp_index[i]=0;
        for(i=0;i<4;i++)
            for(j=0;j<16;j++)
            {
                code_len_table[i][j]=0;
                code_pos_table[i][j]=0;
                huf_max_value[i][j]=0;
                huf_min_value[i][j]=0;
            }
        for(i=0;i<4;i++)
            for(j=0;j<256;j++)
                code_value_table[i][j]=0;
        
        for(i=0;i<10*64;i++)
        {
            MCUBuffer[i]=0;
            QtZzMCUBuffer[i]=0;
        }
        for(i=0;i<4*64;i++)
        {
            Y[i]=0;
            U[i]=0;
            V[i]=0;        
        }
        for(i=0;i<64;i++)
            BlockBuffer[i]=0;
        ycoef=ucoef=vcoef=0;
    }
    /////////////////////////////////////////////////////////////////////////
    int Decode()
    {
        int funcret;
    
        Y_in_MCU=SampRate_Y_H*SampRate_Y_V;
        U_in_MCU=SampRate_U_H*SampRate_U_V;
        V_in_MCU=SampRate_V_H*SampRate_V_V;
        H_YtoU=SampRate_Y_H/SampRate_U_H;
        V_YtoU=SampRate_Y_V/SampRate_U_V;
        H_YtoV=SampRate_Y_H/SampRate_V_H;
        V_YtoV=SampRate_Y_V/SampRate_V_V;
        Initialize_Fast_IDCT();
        while((funcret=DecodeMCUBlock())==FUNC_OK)
        {
            interval++;
            if((restart)&&(interval % restart==0))
                 IntervalFlag=TRUE;
            else
                IntervalFlag=FALSE;
            IQtIZzMCUComponent(0);
            IQtIZzMCUComponent(1);
            IQtIZzMCUComponent(2);
            GetYUV(0);
            GetYUV(1);
            GetYUV(2);
            StoreBuffer();
            sizej+=SampRate_Y_H*8;
            if(sizej>=ImgWidth)
            {
                sizej=0;
                sizei+=SampRate_Y_V*8;
            }
            if ((sizej==0)&&(sizei>=ImgHeight))
                break;
        }
        return funcret;
    }
    /////////////////////////////////////////////////////////////////////////////////////////
    void  GetYUV(short flag)
    {
        short    H,VV;
        short    i,j,k,h;
        int        *buf;
        int        *pQtZzMCU;
    
        switch(flag)
        {
        case 0:
            H=SampRate_Y_H;
            VV=SampRate_Y_V;
            buf=Y;
            pQtZzMCU=QtZzMCUBuffer;
            break;
        case 1:
            H=SampRate_U_H;
            VV=SampRate_U_V;
            buf=U;
            pQtZzMCU=QtZzMCUBuffer+Y_in_MCU*64;
            break;
        case 2:
            H=SampRate_V_H;
            VV=SampRate_V_V;
            buf=V;
            pQtZzMCU=QtZzMCUBuffer+(Y_in_MCU+U_in_MCU)*64;
            break;
        }
        for (i=0;i<VV;i++)
            for(j=0;j<H;j++)
                for(k=0;k<8;k++)
                    for(h=0;h<8;h++)
                        buf[(i*8+k)*SampRate_Y_H*8+j*8+h]=*pQtZzMCU++;
    }
    ///////////////////////////////////////////////////////////////////////////////
    void StoreBuffer()
    {
        short i,j;
        unsigned char  *lpbmp;
        unsigned char R,G,B;
        int y,u,v,rr,gg,bb;
    
        for(i=0;i<SampRate_Y_V*8;i++)
        {
            if((sizei+i)<ImgHeight)
            {
                lpbmp=((unsigned char *)lpPtr+(DWORD)(ImgHeight-sizei-i-1)*LineBytes+sizej*3);
                for(j=0;j<SampRate_Y_H*8;j++)
                {
                    if((sizej+j)<ImgWidth)
                    {
                        y=Y[i*8*SampRate_Y_H+j];
                        u=U[(i/V_YtoU)*8*SampRate_Y_H+j/H_YtoU];
                        v=V[(i/V_YtoV)*8*SampRate_Y_H+j/H_YtoV];
                        rr=((y<<8)+18*u+367*v)>>8;
                        gg=((y<<8)-159*u-220*v)>>8;
                        bb=((y<<8)+411*u-29*v)>>8;
                        R=(unsigned char)rr;
                        G=(unsigned char)gg;
                        B=(unsigned char)bb;
                        if (rr&0xffffff00) if (rr>255) R=255; else if (rr<0) R=0;
                        if (gg&0xffffff00) if (gg>255) G=255; else if (gg<0) G=0;
                        if (bb&0xffffff00) if (bb>255) B=255; else if (bb<0) B=0;
                        *lpbmp++=B;
                        *lpbmp++=G;
                        *lpbmp++=R;
                    }
                    else  break;
                }
            }
            else break;
        }
    }
    ///////////////////////////////////////////////////////////////////////////////
    int DecodeMCUBlock()
    {
        short *lpMCUBuffer;
        short i,j;
        int funcret;
    
        if (IntervalFlag)
        {
            lp+=2;
            ycoef=ucoef=vcoef=0;
            BitPos=0;
            CurByte=0;
        }
        switch(comp_num)
        {
        case 3:
            lpMCUBuffer=MCUBuffer;
            for (i=0;i<SampRate_Y_H*SampRate_Y_V;i++)  //Y
            {
                funcret=HufBlock(YDcIndex,YAcIndex);
                if (funcret!=FUNC_OK)
                    return funcret;
                BlockBuffer[0]=BlockBuffer[0]+ycoef;
                ycoef=BlockBuffer[0];
                for (j=0;j<64;j++)
                    *lpMCUBuffer++=BlockBuffer[j];
            }
            for (i=0;i<SampRate_U_H*SampRate_U_V;i++)  //U
            {
                funcret=HufBlock(UVDcIndex,UVAcIndex);
                if (funcret!=FUNC_OK)
                    return funcret;
                BlockBuffer[0]=BlockBuffer[0]+ucoef;
                ucoef=BlockBuffer[0];
                for (j=0;j<64;j++)
                    *lpMCUBuffer++=BlockBuffer[j];
            }
            for (i=0;i<SampRate_V_H*SampRate_V_V;i++)  //V
            {
                funcret=HufBlock(UVDcIndex,UVAcIndex);
                if (funcret!=FUNC_OK)
                    return funcret;
                BlockBuffer[0]=BlockBuffer[0]+vcoef;
                vcoef=BlockBuffer[0];
                for (j=0;j<64;j++)
                    *lpMCUBuffer++=BlockBuffer[j];
            }
            break;
        case 1:
            lpMCUBuffer=MCUBuffer;
            funcret=HufBlock(YDcIndex,YAcIndex);
            if (funcret!=FUNC_OK)
                return funcret;
            BlockBuffer[0]=BlockBuffer[0]+ycoef;
            ycoef=BlockBuffer[0];
            for (j=0;j<64;j++)
                *lpMCUBuffer++=BlockBuffer[j];
            for (i=0;i<128;i++)
                *lpMCUBuffer++=0;
            break;
        default:
            return FUNC_FORMAT_ERROR;
        }
        return FUNC_OK;
    }
    //////////////////////////////////////////////////////////////////
    int HufBlock(BYTE dchufindex,BYTE achufindex)
    {
        short count=0;
        short i;
        int funcret;
    
        //dc
        HufTabIndex=dchufindex;
        funcret=DecodeElement();
        if(funcret!=FUNC_OK)
            return funcret;
    
        BlockBuffer[count++]=vvalue;
        //ac
        HufTabIndex=achufindex;
        while (count<64)
        {
            funcret=DecodeElement();
            if(funcret!=FUNC_OK)
                return funcret;
            if ((rrun==0)&&(vvalue==0))
            {
                for (i=count;i<64;i++)
                    BlockBuffer[i]=0;
                count=64;
            }
            else
            {
                for (i=0;i<rrun;i++)
                    BlockBuffer[count++]=0;
                BlockBuffer[count++]=vvalue;
            }
        }
        return FUNC_OK;
    }
    //////////////////////////////////////////////////////////////////////////////
    int DecodeElement()
    {
        int thiscode,tempcode;
        unsigned short temp,valueex;
        short codelen;
        BYTE hufexbyte,runsize,tempsize,sign;
        BYTE newbyte,lastbyte;
    
        if(BitPos>=1)
        {
            BitPos--;
            thiscode=(BYTE)CurByte>>BitPos;
            CurByte=CurByte&And[BitPos];
        }
        else
        {
            lastbyte=ReadByte();
            BitPos--;
            newbyte=CurByte&And[BitPos];
            thiscode=lastbyte>>7;
            CurByte=newbyte;
        }
        codelen=1;
        while ((thiscode<huf_min_value[HufTabIndex][codelen-1])||
              (code_len_table[HufTabIndex][codelen-1]==0)||
              (thiscode>huf_max_value[HufTabIndex][codelen-1]))
        {
            if(BitPos>=1)
            {
                BitPos--;
                tempcode=(BYTE)CurByte>>BitPos;
                CurByte=CurByte&And[BitPos];
            }
            else
            {
                lastbyte=ReadByte();
                BitPos--;
                newbyte=CurByte&And[BitPos];
                tempcode=(BYTE)lastbyte>>7;
                CurByte=newbyte;
            }
            thiscode=(thiscode<<1)+tempcode;
            codelen++;
            if(codelen>16)
                return FUNC_FORMAT_ERROR;
        }  //while
        temp=thiscode-huf_min_value[HufTabIndex][codelen-1]+code_pos_table[HufTabIndex][codelen-1];
        hufexbyte=(BYTE)code_value_table[HufTabIndex][temp];
        rrun=(short)(hufexbyte>>4);
        runsize=hufexbyte&0x0f;
        if(runsize==0)
        {
            vvalue=0;
            return FUNC_OK;
        }
        tempsize=runsize;
        if(BitPos>=runsize)
        {
            BitPos-=runsize;
            valueex=(BYTE)CurByte>>BitPos;
            CurByte=CurByte&And[BitPos];
        }
        else
        {
            valueex=CurByte;
            tempsize-=BitPos;
            while(tempsize>8)
            {
                lastbyte=ReadByte();
                valueex=(valueex<<8)+(BYTE)lastbyte;
                tempsize-=8;
            }  //while
            lastbyte=ReadByte();
            BitPos-=tempsize;
            valueex=(valueex<<tempsize)+(lastbyte>>BitPos);
            CurByte=lastbyte&And[BitPos];
        }  //else
        sign=valueex>>(runsize-1);
        if(sign)
            vvalue=valueex;
        else
        {
            valueex=valueex^0xffff;
            temp=0xffff<<runsize;
            vvalue=-(short)(valueex^temp);
        }
        return FUNC_OK;
    }
    /////////////////////////////////////////////////////////////////////////////////////
    void IQtIZzMCUComponent(short flag)
    {
        short H,VV;
        short i,j;
        int *pQtZzMCUBuffer;
        short  *pMCUBuffer;
    
        switch(flag)
        {
        case 0:
            H=SampRate_Y_H;
            VV=SampRate_Y_V;
            pMCUBuffer=MCUBuffer;
            pQtZzMCUBuffer=QtZzMCUBuffer;
            break;
        case 1:
            H=SampRate_U_H;
            VV=SampRate_U_V;
            pMCUBuffer=MCUBuffer+Y_in_MCU*64;
            pQtZzMCUBuffer=QtZzMCUBuffer+Y_in_MCU*64;
            break;
        case 2:
            H=SampRate_V_H;
            VV=SampRate_V_V;
            pMCUBuffer=MCUBuffer+(Y_in_MCU+U_in_MCU)*64;
            pQtZzMCUBuffer=QtZzMCUBuffer+(Y_in_MCU+U_in_MCU)*64;
            break;
        }
        for(i=0;i<VV;i++)
            for (j=0;j<H;j++)
                IQtIZzBlock(pMCUBuffer+(i*H+j)*64,pQtZzMCUBuffer+(i*H+j)*64,flag);
    }
    //////////////////////////////////////////////////////////////////////////////////////////
    void IQtIZzBlock(short  *s ,int * d,short flag)
    {
        short i,j;
        short tag;
        short *pQt;
        int buffer2[8][8];
        int *buffer1;
        short offset;
    
        switch(flag)
        {
        case 0:
            pQt=YQtTable;
            offset=128;
            break;
        case 1:
            pQt=UQtTable;
            offset=0;
            break;
        case 2:
            pQt=VQtTable;
            offset=0;
            break;
        }
    
        for(i=0;i<8;i++)
            for(j=0;j<8;j++)
            {
                tag=Zig_Zag[i][j];
                buffer2[i][j]=(int)s[tag]*(int)pQt[tag];
            }
        buffer1=(int *)buffer2;
        Fast_IDCT(buffer1);
        for(i=0;i<8;i++)
            for(j=0;j<8;j++)
                d[i*8+j]=buffer2[i][j]+offset;
    }
    ///////////////////////////////////////////////////////////////////////////////
    void Fast_IDCT(int * block)
    {
        short i;
    
        for (i=0; i<8; i++)
            idctrow(block+8*i);
    
        for (i=0; i<8; i++)
            idctcol(block+i);
    }
    ///////////////////////////////////////////////////////////////////////////////
    BYTE  ReadByte()
    {
        BYTE  i;
    
        i=*(lp++);
        if(i==0xff)
            lp++;
        BitPos=8;
        CurByte=i;
        return i;
    }
    ///////////////////////////////////////////////////////////////////////
    void Initialize_Fast_IDCT()
    {
        short i;
    
        iclp = iclip+512;
        for (i= -512; i<512; i++)
            iclp[i] = (i<-256) ? -256 : ((i>255) ? 255 : i);
    }
    ////////////////////////////////////////////////////////////////////////
    void idctrow(int * blk)
    {
        int x0, x1, x2, x3, x4, x5, x6, x7, x8;
        //intcut
        if (!((x1 = blk[4]<<11) | (x2 = blk[6]) | (x3 = blk[2]) |
            (x4 = blk[1]) | (x5 = blk[7]) | (x6 = blk[5]) | (x7 = blk[3])))
        {
            blk[0]=blk[1]=blk[2]=blk[3]=blk[4]=blk[5]=blk[6]=blk[7]=blk[0]<<3;
            return;
        }
        x0 = (blk[0]<<11) + 128; // for proper rounding in the fourth stage 
        //first stage
        x8 = W7*(x4+x5);
        x4 = x8 + (W1-W7)*x4;
        x5 = x8 - (W1+W7)*x5;
        x8 = W3*(x6+x7);
        x6 = x8 - (W3-W5)*x6;
        x7 = x8 - (W3+W5)*x7;
        //second stage
        x8 = x0 + x1;
        x0 -= x1;
        x1 = W6*(x3+x2);
        x2 = x1 - (W2+W6)*x2;
        x3 = x1 + (W2-W6)*x3;
        x1 = x4 + x6;
        x4 -= x6;
        x6 = x5 + x7;
        x5 -= x7;
        //third stage
        x7 = x8 + x3;
        x8 -= x3;
        x3 = x0 + x2;
        x0 -= x2;
        x2 = (181*(x4+x5)+128)>>8;
        x4 = (181*(x4-x5)+128)>>8;
        //fourth stage
        blk[0] = (x7+x1)>>8;
        blk[1] = (x3+x2)>>8;
        blk[2] = (x0+x4)>>8;
        blk[3] = (x8+x6)>>8;
        blk[4] = (x8-x6)>>8;
        blk[5] = (x0-x4)>>8;
        blk[6] = (x3-x2)>>8;
        blk[7] = (x7-x1)>>8;
    }
    //////////////////////////////////////////////////////////////////////////////
    void idctcol(int * blk)
    {
        int x0, x1, x2, x3, x4, x5, x6, x7, x8;
        //intcut
        if (!((x1 = (blk[8*4]<<8)) | (x2 = blk[8*6]) | (x3 = blk[8*2]) |
            (x4 = blk[8*1]) | (x5 = blk[8*7]) | (x6 = blk[8*5]) | (x7 = blk[8*3])))
        {
            blk[8*0]=blk[8*1]=blk[8*2]=blk[8*3]=blk[8*4]=blk[8*5]
                =blk[8*6]=blk[8*7]=iclp[(blk[8*0]+32)>>6];
            return;
        }
        x0 = (blk[8*0]<<8) + 8192;
        //first stage
        x8 = W7*(x4+x5) + 4;
        x4 = (x8+(W1-W7)*x4)>>3;
        x5 = (x8-(W1+W7)*x5)>>3;
        x8 = W3*(x6+x7) + 4;
        x6 = (x8-(W3-W5)*x6)>>3;
        x7 = (x8-(W3+W5)*x7)>>3;
        //second stage
        x8 = x0 + x1;
        x0 -= x1;
        x1 = W6*(x3+x2) + 4;
        x2 = (x1-(W2+W6)*x2)>>3;
        x3 = (x1+(W2-W6)*x3)>>3;
        x1 = x4 + x6;
        x4 -= x6;
        x6 = x5 + x7;
        x5 -= x7;
        //third stage
        x7 = x8 + x3;
        x8 -= x3;
        x3 = x0 + x2;
        x0 -= x2;
        x2 = (181*(x4+x5)+128)>>8;
        x4 = (181*(x4-x5)+128)>>8;
        //fourth stage
        blk[8*0] = iclp[(x7+x1)>>14];
        blk[8*1] = iclp[(x3+x2)>>14];
        blk[8*2] = iclp[(x0+x4)>>14];
        blk[8*3] = iclp[(x8+x6)>>14];
        blk[8*4] = iclp[(x8-x6)>>14];
        blk[8*5] = iclp[(x0-x4)>>14];
        blk[8*6] = iclp[(x3-x2)>>14];
        blk[8*7] = iclp[(x7-x1)>>14];
    }
    
    //main(   )
    //{
    //        LoadJpegFile("test.jpg");
    //}
    View Code

    xml解析,我用的是TinyXml2开源库,这个就不贴源码了。

    关于Qt项目图标制作

    我用的Qt版本是4.8.5。

    步骤如下:

    1. 在Qt工程目录下新建一个文本文件,并将其名称改为 *.rc (名字任取)
    2. 将你的图标文件.ico添加到项目中
    3. 打开该 rc 文件,在该rc文件里面加入以下一行文本(将文本中的*换成你的图标的名字):

      IDI_ICON   ICON    DISCARDABLE     "*.ico" 
    4. 在项目文件.pro中加入以下文本(将*换成你的rc文件名字):

          RC_FILE =
                 *.rc

          5. 重新编译工程即可

       

    关于Qt项目的发布

    Qt项目发布最麻烦的就是动态依赖库,常用的工具是hap-depends,它可以查看软件的依赖库(*.dll),直接用它打开你的.exe文件,查看缺失哪些.dll文件,找到它们后和exe放在相同目录即可。

    当然,发布之前需要经过多个平台的测试。

    最后祝大家生活愉快!

    『注:本文来自博客园“小溪的博客”,若非声明均为原创内容,请勿用于商业用途,转载请注明出处http://www.cnblogs.com/xiaoxi666/』
  • 相关阅读:
    变量的创建和初始化
    HDU 1114 Piggy-Bank (dp)
    HDU 1421 搬寝室 (dp)
    HDU 2059 龟兔赛跑 (dp)
    HDU 2571 命运 (dp)
    HDU 1574 RP问题 (dp)
    HDU 2577 How to Type (字符串处理)
    HDU 1422 重温世界杯 (dp)
    HDU 2191 珍惜现在,感恩生活 (dp)
    HH实习 acm算法部 1689
  • 原文地址:https://www.cnblogs.com/xiaoxi666/p/6544478.html
Copyright © 2011-2022 走看看