c++ 实现采集bing每日壁纸并设置成电脑壁纸

前提工作:

  • vcpkg工具
  • curl库
  • cJSON库
  • VS2022

1:功能分析

  既然是使用c++实现bing的壁纸,肯定得拿到bing壁纸的链接,我们需要先使用curl访问bing的图片api,拿到图片真是的地址:           https://cn.bing.com/HPImageArchive.aspx?format=js&idx=0&n=1&mkt=zh-CN

  这是官方的api,当我们访问时可以得到一个如图的json字符串:  

  

  可以看到图片的种种信息,我们需要拿到其中的url字段来获取到完整的图片url,这时候就需要通过curl库请求这个地址,然后再利用cJSON库对这个字符串进行解析,最后再得到其中得URL字段最后与bing.com/拼接起来就是图片得地址,例如:https://bing.com/th?id=OHR.HummingThistle_ZH-CN5057539905_1920x1080.jpg&rf=LaDigue_1920x1080.jpg&pid=hp

最后再请求图片的地址并把请求到的数据保存到图片文件中就ok了。

2:代码分析

  代码核心主要分为两块:获取真实的图片地址与保存图片

  下面我们来看看:

//第一次请求获取真实图地址的回调函数
size_t getUrlResponse(void* buffer, size_t size, size_t count, void* response)
{
    string* str = (string*)response;
    (*str).append((char*)buffer, size * count);
    return size * count;
}

//获取bing链接
string getImgURL() {
    const char* url = "https://cn.bing.com/HPImageArchive.aspx?format=js&idx=0&n=1&nc=1614319565639&pid=hp&FORM=BEHPTB&uhd=1&uhdwidth=3840&uhdheight=2160";
    CURL* curl = NULL;
    string response = "";
    string return_data = "";
    curl = curl_easy_init(); //初始化curl
    curl_easy_setopt(curl, CURLOPT_URL, url); //设置地址
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &getUrlResponse);
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response);

    // 执行请求
    curl_easy_perform(curl);
    // 释放
    curl_easy_cleanup(curl);
    curl_global_cleanup();
    string dateTime;
    string imgurl;
    cJSON* tmp = NULL;
    //开始获取真实链接
    cJSON* tmpData = cJSON_Parse(response.c_str());
    tmp = cJSON_GetObjectItem(tmpData, "images");
    tmp = cJSON_GetArrayItem(tmp, 0);
    return_data = "bing.com/"+ (string)(cJSON_GetObjectItem(tmp, "url")->valuestring);
    return return_data;
}

 

//获取图片数据的回调函数
size_t write_file(void* buffer, size_t size, size_t count, void* response) {
    FILE* file = (FILE*)response;
    fwrite(buffer, size, count, file);
    return size * count;
}

//请求图片并保存
int getImg(string url) {
    //读取数据
    FILE* fp = open_jpg();
    CURL* curl = NULL;
    curl = curl_easy_init(); //初始化curl
    curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); //设置地址
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_file);  //注册图片数据回调函数
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);
    curl_easy_perform(curl); //发起请求
    curl_easy_cleanup(curl);// 释放
    curl_global_cleanup();
    fclose(fp);
    cout << "图片下载成功,开始设置壁纸" << endl;
    return 1;
}

3:代码分享

 

#include <iostream>
#include <curl/curl.h>
#include <ctime>
#include <cJSON/cJSON.h>
#include <string>
#include <memory>
#include <Windows.h> 
#include<io.h>  
#include<direct.h> 
using namespace std;
size_t getUrlResponse(void* buffer, size_t size, size_t count, void* response)
{
    string* str = (string*)response;
    (*str).append((char*)buffer, size * count);
    return size * count;
}
//获取bing链接
string getImgURL() {
    const char* url = "https://cn.bing.com/HPImageArchive.aspx?format=js&idx=0&n=1&nc=1614319565639&pid=hp&FORM=BEHPTB&uhd=1&uhdwidth=3840&uhdheight=2160";
    CURL* curl = NULL;
    string response = "";
    string return_data = "";
    curl = curl_easy_init(); //初始化curl
    curl_easy_setopt(curl, CURLOPT_URL, url); //设置地址
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &getUrlResponse);
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response);

    // 执行请求
    curl_easy_perform(curl);
    // 释放
    curl_easy_cleanup(curl);
    curl_global_cleanup();
    string dateTime;
    string imgurl;
    cJSON* tmp = NULL;
    //开始获取真实链接
    cJSON* tmpData = cJSON_Parse(response.c_str());
    tmp = cJSON_GetObjectItem(tmpData, "images");
    tmp = cJSON_GetArrayItem(tmp, 0);
    return_data = "bing.com/"+ (string)(cJSON_GetObjectItem(tmp, "url")->valuestring);
    return return_data;
}
//获取日期
string getTime() {
    time_t* tmp_time= (time_t *)calloc(1,sizeof(time_t));
    time(tmp_time);
    tm* p = (tm*)calloc(1, sizeof(tm));
    localtime_s(p,tmp_time);
    string data= "bingImg/bing-"+to_string(p->tm_year+1900) + "-" + to_string(p->tm_mon + 1) + "-" + to_string(p->tm_mday)+".jpg";
    return data;
}
FILE* open_jpg() {
    string url = getTime();
    if (_access("bingImg", 0) == -1)//返回值为-1,表示不存在
    {
        int i = _mkdir("bingImg");
        cout << "bingImg文件创建成功" << endl;
    }
    else {
        cout << "bingImg文件已存在,正在打开图片文件" << endl;
    }
    FILE* fp;
    int statu = fopen_s(&fp, url.c_str(), "wb");
    if (statu) {
        cout << "文件打开失败" << endl;
        return NULL;
    }
    else {
        cout << "文件打开成功,开始下载壁纸" << endl;
    }
    return fp;
}
size_t write_file(void* buffer, size_t size, size_t count, void* response) {
    FILE* file = (FILE*)response;
    fwrite(buffer, size, count, file);
    return size * count;
}
//请求图片并保存
int getImg(string url) {
    //读取数据
    FILE* fp = open_jpg();
    CURL* curl = NULL;
    curl = curl_easy_init(); //初始化curl
    curl_easy_setopt(curl, CURLOPT_URL, url.c_str()); //设置地址
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_file);
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);
    curl_easy_perform(curl);
    curl_easy_cleanup(curl);// 释放
    curl_global_cleanup();
    fclose(fp);
    cout << "图片下载成功,开始设置壁纸" << endl;
    return 1;
}
//设置壁纸
void set_desktop() {
    char buffer[MAX_PATH];
    getcwd(buffer, MAX_PATH);
    string a = buffer;
    string b =a+ "\\" +getTime();
    const char* path = b.c_str();
    cout <<"图片路径:"<< path << endl;
    SystemParametersInfoA(SPI_SETDESKWALLPAPER, 0,(PVOID*)path, SPIF_SENDCHANGE | SPIF_UPDATEINIFILE);
    cout << "壁纸设置成功" << endl;
}
int main() {
    string url = getImgURL();
    getImg(url);
    set_desktop();
}

最后运行程序就可以了;

posted @ 2024-06-17 19:17  鬼灰也  阅读(28)  评论(0)    收藏  举报