第一句子网 - 唯美句子、句子迷、好句子大全
第一句子网 > qt实现颜色十六进制转换为rgb并且进行扩展

qt实现颜色十六进制转换为rgb并且进行扩展

时间:2020-05-26 14:28:35

相关推荐

qt实现颜色十六进制转换为rgb并且进行扩展

目录

一、转换为rgb

二、扩展rgb颜色

三、生成.txt文件储存rgb颜色点

四、补充代码

五、运行结果

六、补充(均匀采样)

最近需要使用qt来创建一个色板用于图像显示,而色板是十六进制的,网上的在线转换只能一个一个进行转换,比较麻烦(ˉ▽ˉ;)...,所以小写一个代码进行格式转换。由于色板只有30多种颜色,这里会进行扩展至256种颜色(这里采用两种颜色取中值的办法进行扩展),最终生成一个.txt文件用来存储这256个rgb颜色点。话不多说,直接上代码!

一、转换为rgb

void Widget::changeColor(){//数组清零memset(color_rgb_1, 0, sizeof(color_rgb_1));memset(color_rgb_2, 0, sizeof(color_rgb_2));int r, g, b;int color_count = 0;int loop_count = 0;int *p_rgb = color_rgb_1;//16进制颜色数据string color_hex[] = { "#EDB603","#EF9906","#FA7B06","#FE5A04","#E14B18","#E32E19","#D21C33","#B71048","#900956","#88","#61058F","#4D08B0","#361ABC","#1F29D9","#1A42D5","#0755FD","#076BDB","#018CF5","#0990F1","#10C0E5","#19BCBB","#33E4C8","#4BE7A6","#6CF990","#82F47B","#9FF95C","#BCEB4F","#CAE22C","#DACE18","#F2B50d","#F49F04"};//rgb转化for(int i = 0; i <= 30; i++){if (color_hex[i].at(0) == '#') {color_hex[i] = color_hex[i].erase(0, 1);}//提取rgb值istringstream(color_hex[i].substr(0, 2)) >> hex >> r;istringstream(color_hex[i].substr(2, 2)) >> hex >> g;istringstream(color_hex[i].substr(4, 2)) >> hex >> b;//把提取的rgb存储在数组里color_rgb_1[color_count] = r;color_rgb_1[color_count + 1] = g;color_rgb_1[color_count + 2] = b;if(i != 30){color_count += 3;}loop_count++;}createFile(extendColor(p_rgb, p_rgb, loop_count, recursion_count));}

二、扩展rgb颜色

/*功能说明:扩展rgb颜色点参数说明:p_rgb - 移位指针1p2_rgb - 移位指针2color_rgb_num - rgb颜色点的数量recursion_count - 递归的次数返回值 :一个指向数组的整型指针*/int *Widget::extendColor(int *p_rgb, int *p2_rgb, int color_rgb_num, int recursion_count){int r, g, b;int loop_count = 0;//循环次数int extend_num = color_rgb_num * 2 - 1;//扩展后的颜色点数//递归次数达到3次,也就是扩展到了241个颜色点if(recursion_count == 3){memset(color_rgb_1, 0, sizeof(color_rgb_1));//补充15个颜色点int lack_num = (256 - color_rgb_num) * 2;for(int i = 0; i < lack_num; i++){//正常赋值if(i % 2 == 0){for(int j = 0; j < 3; j++){color_rgb_1[i * 3 + j] = *p_rgb;p_rgb++;}}//取两个颜色点(r,g,b)的中值再赋值else{r = (*p2_rgb + *(p2_rgb + 3)) / 2;g = (*(p2_rgb + 1) + *(p2_rgb + 3 + 1)) / 2;b = (*(p2_rgb + 2) + *(p2_rgb + 3 + 2)) / 2;color_rgb_1[i * 3] = r;color_rgb_1[i * 3 + 1] = g;color_rgb_1[i * 3 + 2] = b;p2_rgb += 3;}}//补充剩下的颜色点,凑到256个for(int k = lack_num; k < 256; k++){for(int j = 0; j < 3; j++){color_rgb_1[k * 3 + j] = *p2_rgb;p2_rgb++;}}p2_rgb = color_rgb_1; //指针重新指向数组起始位置return p2_rgb;}//这里的功能实现就是使用指针,让两个数组互相赋值if(recursion_count % 2 == 0){memset(color_rgb_2, 0, sizeof(color_rgb_2));for(int i = 0; i < extend_num; i++){//正常赋值if(i % 2 == 0){for(int j = 0; j < 3; j++){color_rgb_2[i * 3 + j] = *p_rgb;p_rgb++;}}//取两个颜色点(r,g,b)的中值再赋值else{r = (*p2_rgb + *(p2_rgb + 3)) / 2;g = (*(p2_rgb + 1) + *(p2_rgb + 3 + 1)) / 2;b = (*(p2_rgb + 2) + *(p2_rgb + 3 + 2)) / 2;color_rgb_2[i * 3] = r;color_rgb_2[i * 3 + 1] = g;color_rgb_2[i * 3 + 2] = b;p2_rgb += 3;}loop_count++;}p_rgb = color_rgb_2; //指针重新指向数组起始位置}else{memset(color_rgb_1, 0, sizeof(color_rgb_1));for(int i = 0; i < extend_num; i++){//正常赋值if(i % 2 == 0){for(int j = 0; j < 3; j++){color_rgb_1[i * 3 + j] = *p_rgb;p_rgb++;}}//取两个颜色点(r,g,b)的中值再赋值else{r = (*p2_rgb + *(p2_rgb + 3)) / 2;g = (*(p2_rgb + 1) + *(p2_rgb + 3 + 1)) / 2;b = (*(p2_rgb + 2) + *(p2_rgb + 3 + 2)) / 2;color_rgb_1[i * 3] = r;color_rgb_1[i * 3 + 1] = g;color_rgb_1[i * 3 + 2] = b;p2_rgb += 3;}loop_count++;}p_rgb = color_rgb_1; //指针重新指向数组起始位置}recursion_count++;return extendColor(p_rgb, p_rgb, loop_count, recursion_count);//递归算法的实现}

三、生成.txt文件储存rgb颜色点

//创建文件(.txt)void Widget::createFile(int *p_rgb){char *Edit = 0;QString color_rgb;//字符串拼接for(int i = 1; i <= COLOR_NUM; i++){color_rgb += QString::number(*p_rgb);if(i == COLOR_NUM){// qDebug() << color_rgb;break;}color_rgb += ",";//每十个rgb颜色点就换行if(i % 30 == 0){color_rgb += "\n";}p_rgb++;}//.txt//类型转换QByteArray color_rgb_array = color_rgb.toLatin1();Edit = color_rgb_array.data();//数据长度qint64 length = color_rgb.length();// QString Filepath = QDir::currentPath();QString file_name = "color.txt";QFile file(file_name);if (file.open(QIODevice::WriteOnly | QIODevice::Text|QIODevice::Append)){file.write(Edit,length);file.close();QMessageBox::warning(this,tr("创建文件"),tr("文件创建成功!"));// 设置box大小// success.setStyleSheet("QLabel{"//"min-width: 200px;"//"min-height: 100px;"//"}");}else{QMessageBox::warning(this,tr("创建文件"),tr("文件创建失败!"));}}

四、补充代码

以上三个是widget.cpp的主要内容,下面把其他文件代码列出。

widget.h如下:

#ifndef WIDGET_H#define WIDGET_H#include <QWidget>#include <iostream>#include <sstream>#include <QDebug>#include <QString>#include <QMessageBox>#include <QTextStream>#include <QFileDialog>#include <QFile>#include <QColorDialog>#define COLOR_NUM 256 * 3using namespace std;class Widget : public QWidget{Q_OBJECTpublic:Widget(QWidget *parent = nullptr);~Widget();void changeColor();void createFile(int *p_rgb);int *extendColor(int *p_rgb, int *p2_rgb, int color_rgb_num, int recursion_count);private:int recursion_count = 0;int color_rgb_1[COLOR_NUM];int color_rgb_2[COLOR_NUM];};#endif // WIDGET_H

main.cpp如下:

#include "widget.h"#include <QApplication>int main(int argc, char *argv[]){QApplication a(argc, argv);Widget w;w.changeColor();return a.exec();}

五、运行结果

1.程序运行完后会有一个提示框

2.在build文件目录下会生成一个color.txt文件

3.color.txt文件内容如下:

提示:每三个数就是一种颜色,理论上是有256种颜色,但由于有些点的数值相近,所以算出来会有一样的点,也就是该扩展颜色的办法会有一定的误差。

六、补充(均匀采样)

当颜色点超过我们所需的颜色点数(这里是255个),就需要用到均匀采样,这样才能尽量缩小与原来色板的差别,以下方法和过程跟上面有所不同,可参考修改

int Widget::hexToInt(const QString &hexString){return hexString.toInt(nullptr, 16);}QString Widget::rgbToString(int red, int green, int blue){return QString("%1, %2, %3").arg(red).arg(green).arg(blue).replace(" ", "");}void Widget::changeColor(){//提取16进制颜色数据QString filePath = "./hex_color.txt"; // 指定文件路径QFile file(filePath);if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {qWarning() << "Failed to open file:" << file.errorString();return;}QStringList allColors; // 存储所有的十六进制数的QStringListQTextStream in(&file);while (!in.atEnd()) {QString line = in.readLine().simplified(); // 读取并去除行末尾的空格if (!line.isEmpty() && line.startsWith("#")) {allColors.append(line.mid(1)); // 去掉 '#' 符号并添加到列表中}}file.close();// 获取均匀采样的255个十六进制数int totalColors = allColors.size();double step = static_cast<double>(totalColors) / 255.0;QString rgbString;for (int i = 0; i < 255; ++i) {int index = qBound(0, static_cast<int>(i * step), totalColors - 1); // 确保 index 在有效范围内QString hexColor = allColors[index];int red = hexToInt(hexColor.mid(0, 2));int green = hexToInt(hexColor.mid(2, 2));int blue = hexToInt(hexColor.mid(4, 2));rgbString += rgbToString(red, green, blue);if(i != 254){rgbString += ",";}}QString filePath_rgb = "./rgb_color.txt"; // 指定要创建的.txt文件路径QFile file_rgb(filePath_rgb);if (!file_rgb.open(QIODevice::WriteOnly | QIODevice::Text)) {qWarning() << "无法创建文件:" << file_rgb.errorString();return;}QTextStream out(&file_rgb);out << rgbString;file_rgb.close();}

注意:需要先创建一个hex_color.txt文件,用来存放全部的16进制颜色点,采样后的rgb颜色点会保存在运行目录下的rgb_color.txt文件里。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。