1.第二阶段中的每周具体任务如下:
计划安排时间 | 计划完成内容 | 是否完成 |
2017.03.11~2017.04.14(4-8周) | 1.继续学习相关内容,并实际用到开发环境中去编写测试代码; 2.把核心代码写好; 3.并开始准备毕业论文; | 进行中 |
第四周 | 查阅相关获取系统信息状态的API,编写出一个基于控制台的简单查看系统各种状态信息的程序。 | 完成 |
第五周 | 扩展基本功能,不仅是局限于获取系统信息,比如有网的情况下通过调用API获取天气的信息数据等。 | 完成 |
第六周 | 研究图形化界面的编写,把相应功能用GUI界面显示。 | 待完成 |
第七周 | 继续上周的内容,研究图形化界面显示信息。(因为难度就在这里,动态实时显示数据信息之类的) | 待完成 |
第八周 | 1.继续编写代码 2.开始准备毕业论文 | 待完成 |
2.我的conky功能需求分析:
基本功能设计:
1.显示 CPU 占用情况、磁盘容量、OS 版本号、日历、网络情况等等各类系统的信息。
2.联网操作,获取web端返回的信息处理并显示。比如显示天气数据就需要进行联网。
3.最重要的是通过图形化界面展示(感觉此部分难度比较大,所以是我重点关注部分)。
系统功能模块图:
1.用户:
2.conky:
用例图和对应用例规约:
1.用户:
对应的用例规约:
简要说明 | 刷新显示信息 |
前置条件 | 1.打开程序 2.网络 |
基本事件流 | 1.用户动作:点击按钮刷新 2.系统响应:获取最新信息 |
异常事件流 | 1.用户动作:无 2.系统响应:提示网络错误 |
后置条件 | 刷新成功 |
2.conky:
对应的用例规约:
1.获取数据:
简要说明 | 获取数据 |
前置条件 | 1.操作系统正常 2.网络正常 |
基本事件流 | 1.用户动作:点击按钮刷新 2.系统响应:获取最新信息 |
异常事件流 | 1.用户动作:无 2.系统响应:提示网络错误 |
后置条件 | 获取成功 |
2.处理数据:
简要说明 | 处理数据 |
前置条件 | 获取数据正常 |
基本事件流 | 1.用户动作:无 2.系统响应:处理数据 |
异常事件流 | 1.用户动作:无 2.系统响应:提示网络错误 |
后置条件 | 处理成功 |
3.显示数据:
简要说明 | 显示数据 |
前置条件 | 处理数据正常 |
基本事件流 | 1.用户动作:无 2.系统响应:显示数据 |
异常事件流 | 1.用户动作:无 2.系统响应:提示网络错误 |
后置条件 | 显示成功 |
3.代码及效果展示:
本周主要针对conky的显示信息内容进行丰富和扩展,但是实际编写代码的过程中发现没有我想的那么简单。
之前在网上申请中国天气网的API一直都没回应,没办法只能换其它的API,之前粗心没注意看信息,其实google和雅虎提供的天气预报API早就已经停用而不能使用了。
后来在网上又花了好一段时间搜索免费的天气预报API接口,有的申请过程又太麻烦,我几乎快要放弃添加这个天气预报的功能了,但是我并没有放弃,经过不懈努力,后来还是在网上找到了一个感觉还挺好用的天气预报API( 和风天气,每天免费查询3000次),这个免费版的查询接口只能查当天的天气预报信息(但是对于我的conky显示天气信息已经是足够了)。
它是通过一个URL地址请求便可返回天气状况的json的数据:
https://free-api.heweather.com/v5/now?city=xiamen&key=4bbfae13718f43dfb66ec25b6b1df618
其中URL里面的参数它们官有详细说明:
返回的数据是json的数据:
{"HeWeather5":[{"basic":{"city":"厦门","cnty":"中国","id":"CN101230201","lat":"24.445000","lon":"118.070000","update":{"loc":"2017-03-24 09:51","utc":"2017-03-24 01:51"}},"now":{"cond":{"code":"104","txt":"阴"},"fl":"18","hum":"62","pcpn":"0","pres":"1019","tmp":"18","vis":"10","wind":{"deg":"70","dir":"东南风","sc":"3-4","spd":"17"}},"status":"ok"}]}
其中的关键字官网也有详细说明:
由于之前一直没接触过json,更是不用说处理json数据了,所以我在网上查了查相关c/c++解析json的资料和相关示例代码。
但是在这之前,我得先通过程序内部发送上面的URL请求,就是这个我弄了好久还是没成功,发现原因如下:
1.使用套接字进行URL请求很麻烦
2.我所请求的API接口是使用https而不是http,导致套接字进行URL请求的实现过程更复杂,因为还要下载安装编译相关的SSL资源,而且我去下载开源的OPENSSL来编译却一直出错,参考网上很多教程也还是同样的结果。
3.后来找教程的时候发现有人提到CURL工具(curl是利用url语法在命令行方式下工作的开源文件传输工具),curl官网()有支持C/C++版的相关库文件,用几行简单的代码便可进行URL请求,我一开始当然欣喜若狂,后来下载编译的时候却又发现也要保证之前有安装SSL才能编译成功。
后来我就放弃了用代码实现URL请求这样的想法。
但是呢:
CURL是一个开源的小工具,官网已经提供了SSL版本的可执行文件,我们直接在命令行界面下输入对应参数并运行就可以获取到请求返回来的数据信息。
于是我就有了这个想法(我现在平常都在公司实习,导师让我看linux程序设计这本书,书上有讲线程和管道):
想在主进程里面通过调用外部的程序,创建一个管道,并把外部程序的输出(CURL获取到的JSON数据)写到一个管道里面,然后主进程去读取管道里面的数据并显示。
以下便是我自己用来测试的代码:
#includeint main(){ FILE *fp; char buf[2048]={ 0}; int nread; //linux上的直接是popen 但是windows上面却是_popen加了下划线, //而且最后输出会有一些状态信息,我也不清楚是怎么回事,反正我能拿到数据就行了。 fp = _popen("curl -k \"https://free-api.heweather.com/v5/now?city=110.87.98.58&key=4bbfae13718f43dfb66ec25b6b1df618\"", "r"); if (fp) { nread=fread(buf, sizeof(char), sizeof(buf), fp); printf("\n\n\n\n"); if (nread > 0) { printf("%s", buf); printf("\n"); } _pclose(fp); return 0; } printf("error\n"); return 0;}
效果截图:
(截图上面显示的便是调用这个_popen而显示出来的状态信息,我也不清楚是怎么回事,反正我能拿到数据就行了,但是出现中文乱码的问题,这个我现在还没解决,因为返回的json数据是utf-8的格式)
拿到了JSON数据,接下来便是使用代码解析JSON了,参考了网上的示例代码,需要第三方库,我自己去官网下载编译的,最后自己写了符合解析本json数据的代码:
#include#include "json/json.h"#include #pragma comment(lib, "json.lib")using namespace Json;int main(){ FILE *fp; Reader reader; Value value; std::string out; char buf[2048] = { 0}; int nread; int i = 0; //curl参数-k 是允许不使用证书到SSL站点 不然请求失败 fp = _popen("curl -k \"https://free-api.heweather.com/v5/now?city=110.87.98.58&key=4bbfae13718f43dfb66ec25b6b1df618\"", "r"); if (!fp) { printf("error\n"); return 0; } nread=fread(buf, sizeof(char), sizeof(buf), fp); printf("\n\n\n\n"); if (nread > 0) { if (reader.parse(buf, value)) { //因为乱码问题 只显示部分信息 而且不是中文的信息 后面再看看能不能解决这个乱码问题 //有些用C的处理方式比较习惯和方便,C++的也是这样 //因为C++兼容C嘛,所以我编写的代码是C++混杂着C out = value["HeWeather5"][i]["basic"]["id"].asString(); printf("城市ID:%15s\n", out.c_str()); out = value["HeWeather5"][i]["now"]["tmp"].asString(); printf("温度:%15s ℃\n", out.c_str()); out = value["HeWeather5"][i]["now"]["cond"]["code"].asString(); printf("天气代码:%15s\n", out.c_str()); out = value["HeWeather5"][i]["basic"]["update"]["loc"].asString(); printf("更新时间:%15s\n", out.c_str()); } } _pclose(fp); return 0;}
效果截图:
暂时就先这样。
4.心得与体会:
通过这周的学习和代码的编写,我发现只是获取系统信息还是挺简单的,不过要图形化并显示出来那就比较难了,我现在心里也没啥底,我也尽量把我想到的想实现的功能都加上去,不过我相信我还是能完成我自己给自己定的需求的。
5.参考文献:
C/C++解析JSON数据示例:
windows的_popen,与linux的popen对应:
curl工具的使用方法: