#include "uihelper.h"

static QFont g_font("微软雅黑", 10);

std::string UiStyle::BTN = 
"QPushButton{background-color:rgba(150,150,150,80);border-radius:5px;font:bold 16px;color:white;border:2px solid gray;}"
"QPushButton:hover{background-color:rgba(150,150,150,100);border:2px solid white;}"
"QPushButton:pressed{border-width:3px 0 0 3px;border-style:inset;color:white;}";

std::shared_ptr<QLabel> QUI::label(QWidget* parent, int x, int y, int w, int h, std::string text, std::string sty)
{
    auto lab = std::make_shared<QLabel>(parent);
    lab->setGeometry(x, y, w, h);
    lab->setText(text.c_str());
    lab->setFont(g_font);
    if (!sty.empty())
    {
        lab->setStyleSheet(sty.c_str());
    }
    else
    {
        lab->setStyleSheet("QLabel {color:white;}");
    }
    return lab;
}

void QUI::label(QLabel& lab, QWidget* parent, int x, int y, int w, int h, std::string text, std::string sty)
{
    lab.setParent(parent);
    lab.setGeometry(x, y, w, h);
    lab.setText(text.c_str());
    lab.setFont(g_font);
    if (!sty.empty())
    {
        lab.setStyleSheet(sty.c_str());
    }
    else
    {
        lab.setStyleSheet("QLabel {color:white;}");
    }
}

void QUI::labelImage(QLabel& lab, QWidget* parent, int x, int y, int w, int h, std::string img)
{
    lab.setParent(parent);
    lab.setGeometry(x, y, w, h);
    lab.setPixmap(QPixmap(img.c_str()));
}

std::shared_ptr<LabelPairH> QUI::labelPair(QWidget* parent, int x, int y, int w, int h, int w1, std::string k, std::string v)
{
    return std::make_shared<LabelPairH>(parent, QRect(x, y, w, h), w1, k, v);
}

std::shared_ptr<LabelPairV> QUI::labelPairV(QWidget* parent, int x, int y, int w, int h, int h1, std::string k, std::string v)
{
    auto labPair = std::make_shared<LabelPairV>(parent, QRect(x, y, w, h), h1, k, v);
    const std::string STY_VAL = "font:bold 18px;color:rgb(38,220,172);";
    labPair->setValStyle(STY_VAL);
    return labPair;
}

void QUI::button(QPushButton& btn, QWidget* parent, int x, int y, int w, int h, std::string text, std::string sty)
{
    btn.setParent(parent);
    btn.setGeometry(x, y, w, h);
    btn.setText(text.c_str());
    btn.setFont(g_font);
    if (!sty.empty())
    {
        btn.setStyleSheet(sty.c_str());
    }
}

QPushButton* QUI::button(QWidget* parent, int x, int y, int w, int h, std::string text, std::string sty/* = ""*/)
{
    QPushButton* btn = new QPushButton(parent);
    btn->setGeometry(x, y, w, h);
    btn->setText(text.c_str());
    btn->setFont(g_font);
    if (!sty.empty())
    {
        btn->setStyleSheet(sty.c_str());
    }
    return btn;
}

//std::shared_ptr<QComboBox> QUI::combox(QWidget* parent, int x, int y, int w, int h, std::vector<std::string>& items)
//{
//    std::shared_ptr<QComboBox> comb = std::make_shared<QComboBox>(parent);
//    comb->setGeometry(x, y, w, h);
//    QStringList strlist;
//    for (auto& s: items)
//    {
//        strlist << s.c_str();
//    }
//    comb->insertItems(0, strlist);
//    return comb;
//}

void QUI::combox(QComboBox& comb, QWidget* parent, int x, int y, int w, int h, std::vector<std::string> items, std::string v/* = ""*/)
{
    comb.setParent(parent);
    comb.setGeometry(x, y, w, h);
    QStringList strlist;
    for (auto& s: items)
    {
        strlist << s.c_str();
    }
    comb.insertItems(0, strlist);
    if (!v.empty())
    {
        comb.setCurrentText(v.c_str());
    }
}

void QUI::lineedit(QLineEdit& edit, QWidget* parent, int x, int y, int w, int h)
{
    edit.setParent(parent);
    edit.setGeometry(x, y, w, h);
}

void QUI::setBackground(QWidget* w, std::string name, QColor color, std::string border)
{
    if (!w) { return; }
    w->setObjectName(name.c_str());
    std::string sty =  "#" + name + "{background-color:rgba(" 
        + std::to_string(color.red())
        + "," + std::to_string(color.green()) 
        + "," + std::to_string(color.blue())
        + "," + std::to_string(color.alpha())
        + ");" + border + "}";
    w->setAutoFillBackground(true);
    w->setStyleSheet(sty.c_str());
}

Panel::Panel(QWidget* parent, QRect rt, std::string title) : QWidget(parent)
{
    this->setGeometry(rt);

    // 设置背景色：方法一
    //QPalette palette(this->palette());
    //palette.setColor(QPalette::Background, QColor(29, 54, 102)); // 设置背景色
    //this->setAutoFillBackground(true);
    //this->setPalette(palette);

    // 设置背景色：方法二
    //this->setObjectName("PanelBase");
    //this->setStyleSheet("#PanelBase{background-color:rgb(30,50,100);border-radius:5px;}");

    // 设置背景色
    QUI::setBackground(this, "PanelBase", QColor(29, 54, 102, 50));
    setMouseTracking(true);
    if (!title.empty())
    {
        // 渐变
        std::string styBkg = "background-color:qlineargradient(x1:0,y1:0, x2:1,y2:0,stop:0 rgb(3,208,242),stop:0.9 rgba(3,208,242,0));";
        // background-color:rgba(3, 208, 242, 200);
        QUI::label(labBkg_, this, 10, 30, this->width()-20, 2, "", styBkg);
        QUI::label(labIcon_, this, 10, 7, 6, 16, "", "background-color:rgb(33, 255, 210);");
        QUI::label(labTitle_, this, 20, 5, this->width(), 20, title.c_str(), "color:rgb(99, 196, 216);font:bold 16px;");
    }

    this->show();
}

void Panel::setBackground(QColor color, std::string border)
{
    QUI::setBackground(this, "PanelBase", color, border);
}

ChartBarView::ChartBarView(QWidget* parent, QRect rt, int xfrag)
    : QChartView(parent)
    , xfrag_(xfrag)
{
    QFont font("微软雅黑", 9);
    this->setGeometry(rt);
    QColor labColor(255, 255, 255);

    QUI::label(labTitle_, this, 0, 0, this->width(), 24, "");
    labTitle_.setAlignment(Qt::AlignHCenter);
    labTitle_.setFont(QFont("微软雅黑", 12, 100));

    this->setFont(QFont("微软雅黑", 8));
    chart_ = std::make_shared<QChart>();
    chart_->setTitleFont(font);
    chart_->setMargins(QMargins(0,0,0,0));
    //chart_->setAnimationOptions(QChart::SeriesAnimations);  // 动画方式
    setChart(chart_.get());

    // === 初始化序列 ==============================================================
    series_ = std::make_shared<QBarSeries>();
    series_->setBarWidth(0.8);
    chart_->addSeries(series_.get());

    // === 初始化X轴 ==============================================================
    // 创建 X 轴并设置其分类标签
    QStringList ticksX;
    for (int i = 1; i <= xfrag; ++i) {
        ticksX << QString::number(i);
    }
    axisX_ = std::make_shared<QBarCategoryAxis>();
    axisX_->setLabelsColor(labColor);                   // 设置X轴的颜色
    axisX_->setGridLineVisible(false);
    axisX_->append(ticksX);                             // 将分类标签添加到 X 轴
    chart_->addAxis(axisX_.get(), Qt::AlignBottom);     // 将 X 轴添加到图表底部
    series_->attachAxis(axisX_.get());                  // 将柱状图系列与 X 轴关联

    // === 初始化Y轴 ==============================================================
    axisYLeft_ = std::make_shared<QValueAxis>();
    axisYLeft_->setGridLineColor(QColor(200, 200, 200, 100));
    axisYLeft_->setTickCount(6);
    axisYLeft_->setRange(0, 10);                             // 设置 Y 轴的范围为 0 到 100
    chart_->addAxis(axisYLeft_.get(), Qt::AlignLeft);        // 将 Y 轴添加到图表左侧
    series_->attachAxis(axisYLeft_.get());                   // 将柱状图系列与 Y 轴关联
    axisYLeft_->setLabelsColor(labColor);

    // 设置背景色
    this->setBackground(QColor(30, 50, 100, 50));

    // === 初始化柱体 ==============================================================
    //QBarSet* set1 = new QBarSet("10/01");
    //for (int i = 1; i <= xfrag; ++i) { *set1 << i; }
    //series_->append(set1);
    //this->addBar("日换电次数1");
    //this->addBar("日换电次数2");  
    //this->addBar("日换电次数3");
    //this->addBar("日换电次数4");

    //// === 示例：更新bar的数据
    //set1->replace(0, 8);

    //// === 示例：更新X轴
    //QStringList ticksX2;
    //for (int i = 1; i <= xfrag; ++i) {
    //    ticksX2 << QString::number(100+i);
    //}
    //axisX_->setCategories(ticksX2);

    chart_->axisX()->setLabelsFont(font);
    chart_->axisY()->setLabelsFont(font);
    chart_->axisX()->setTitleFont(font);
    chart_->axisY()->setTitleFont(font);
    
    // 设置图例在图表中的位置
    // 参数1: 水平位置
    // 参数2: 垂直位置
    // 参数3: 对齐方式
    // , Qt::HorizontalAlignment::Right, Qt::VerticalAlignment::Top
    
    // 附着图表
    //chart_->legend()->attachToChart();
    //// 位于图表上方
    //chart_->legend()->setAlignment(Qt::AlignTop);
    //// 位于图表下方 
    //chart_->legend()->setAlignment(Qt::AlignBottom);
    //// 位于图表左侧 
    //chart_->legend()->setAlignment(Qt::AlignLeft);
    //// 位于图表右侧 
    //chart_->legend()->setAlignment(Qt::AlignRight);
    //// 不附着图表 
    //chart_->legend()->detachFromChart();
    chart_->legend()->setFont(g_font);
    chart_->legend()->setLabelColor(labColor);
    chart_->legend()->setAlignment(Qt::AlignTop);
    //chart_->legend()->setGeometry(QRectF(50, 0, this->width(), 24));
    //chart_->legend()->update();
}

void ChartBarView::setStatus(std::string title)
{
    //chart_->setTitle(title.c_str());
    labTitle_.setText(title.c_str());
    labTitle_.setGeometry(0, 10, this->width(), 24);

    QMargins margin;
    margin.setTop(40);
    chart_->setMargins(margin);
    chart_->legend()->setGeometry(QRectF(50, 20, this->width(), 24));
}

std::shared_ptr<QChart> ChartBarView::chart()
{
    return chart_;
}

QBarSet& ChartBarView::addItem(std::string name)
{
    int index = series_->barSets().size();
    QBarSet* barSet = new QBarSet(name.c_str());
    //bar初始化数据
    for (int i = 1; i <= xfrag_; ++i) { *barSet << 0; }
    //// === 示例：更新bar的数据
    //barSet->replace(0, 8);
    series_->append(barSet);
    chart_->legend()->setGeometry(QRectF(50, 0, this->width(), 24));    
    return *barSet;
}

void ChartBarView::updateItem(int index, std::vector<double>& vd)
{
    QBarSet* barSet = this->getBar(index);
    if (barSet)
    {
        for (int i = 0; i < xfrag_ && i< vd.size(); ++i)
        {
            barSet->replace(i, vd[i]);
        }
    }
}

QBarSet* ChartBarView::getBar(int index)
{
   auto lstBarSet = series_->barSets();
   if (index < lstBarSet.size())
   {
       return lstBarSet[index];
   }
   return nullptr;
}

void ChartBarView::setBackground(QColor& color)
{
    //this->setAutoFillBackground(true);
    //QPalette palette;
    //palette.setColor(QPalette::Window, color); // 设置背景色
    //this->setPalette(palette);

    QUI::setBackground(this, "ChartBarView", color);
    //this->setObjectName("ChartBarView");
    //this->setStyleSheet("#ChartBarView{background-color:rgb(29,54,102);border-radius:5px;}");

    chart_->setBackgroundBrush(QBrush(QColor(100,100,100,0))); // 设置背景色
    chart_->setBackgroundVisible(true);
}

void ChartBarView::setAxisXTick(std::vector<std::string>& vecTick)
{    
    QStringList ticks;
    for (int i = 0; i < xfrag_ && i<vecTick.size(); ++i) {
        ticks << vecTick[i].c_str();
    }
    axisX_->setCategories(ticks);
}

ChartLineView::ChartLineView(QWidget* parent, QRect rt) : QChartView(parent)
{
    QColor labColor(255, 255, 255);
    QUI::setBackground(this, "ChartLineView1", QColor(30, 50, 100, 50));
    this->setGeometry(rt);
    // 图表视图
    //QChartView* chartView = new QChartView(chart, wParent);

    //this->setGeometry(10, 30, 900, 240);
    //this->setRenderHint(QPainter::Antialiasing);                   // 反锯齿绘制

    // 图表
    chart_ = std::make_shared<QChart>();
    chart_->setBackgroundBrush(QBrush(QColor(100, 100, 100, 0))); // 设置背景色
    chart_->setBackgroundVisible(true);
    //chart_->setAnimationOptions(QChart::SeriesAnimations);  // 动画方式
    //chart_->setTheme(QtCharts::QChart::ChartThemeBlueNcs);    // 设置主题
    //chart_->setTitle("方位角数据");                        // 设置标题
    chart_->setMargins(QMargins(0, 0, 0, 0));
    this->setChart(chart_.get());

    QDateTime curDateTIme = QDateTime::currentDateTime();
    qsrand(QTime(0, 0, 0).secsTo(QTime::currentTime()));

    // x轴(时间轴方式)
    axisX = std::make_shared<QDateTimeAxis>();
    axisX->setLabelsColor(labColor);
    //axisX->setTitleText("时间(分:秒)");   // x轴显示标题
    axisX->setGridLineVisible(false);   // 隐藏背景网格X轴框线
    axisX->setFormat("hh:mm");          // x轴格式
    axisX->setLabelsAngle(0);           // x轴显示的文字倾斜角度
    axisX->setTickCount(10);            // 轴上点的个数
    axisX->setRange(curDateTIme, curDateTIme.addSecs(10));  // 范围
    axisX->setLabelsFont(QFont("微软雅黑", 9));
    
    // y轴
    axisY = std::make_shared<QValueAxis>();
    axisY->setGridLineColor(QColor(200, 200, 200, 100));
    axisY->setLabelsColor(labColor);
    //AxisY->setTitleText("角度");        // y轴显示标题
    axisY->setRange(0, 20);             // 范围
    axisY->setTickCount(6);             // 轴上点的个数
    axisY->setGridLineVisible(true);    // 背景网格Y轴框线
    axisY->setLabelsFont(QFont("微软雅黑", 9));

    chart_->addAxis(axisX.get(), Qt::AlignBottom);  // 设置x轴位置
    chart_->addAxis(axisY.get(), Qt::AlignLeft);    // 设置y轴位置

    // 图例
    //chart_->legend()->detachFromChart();
    chart_->legend()->setFont(g_font);
    chart_->legend()->setLabelColor(labColor);
    chart_->legend()->setVisible(true);                 // 图例显示
    chart_->legend()->setAlignment(Qt::AlignTop);       // 图例向下居中
}

void ChartLineView::addItem(std::string name)
{
    auto series = std::make_shared< QLineSeries>();
    chart_->addSeries(series.get());                             // 添加线段
    series->attachAxis(axisX.get());                       // 线段依附的x轴
    series->attachAxis(axisY.get());                       // 线段依附的y轴
    series->setName(name.c_str());                         // 线段名称，在图例会显示
    vecSeries_.push_back(series);
    //series->setPen(QPen(Qt::red, 0.6, Qt::SolidLine));   // 设置线段pen
}

//#include "common/TimeUtils.h"
void ChartLineView::updateItem(int index, std::vector<std::pair<double, double>>& vd)
{
    if (index >= vecSeries_.size()) { return; }

    auto& series = vecSeries_[index];
    series->clear();
    for (int i = 0; i < vd.size(); ++i)
    {
        series->append(vd[i].first, vd[i].second);
    }

    //int64_t t0 = TimeUtils::datetime2tms(TimeUtils::now_date() + " 00:00:00");
    //int64_t tx = t0;
    //for (int i = 0; i<=240; i++)
    //{
    //    tx = t0 + (i*360)*1000;
    //    series->append(tx, qrand()%18);
    //}
    //this->setAxisX(t0, tx, 13);
    //this->setAxisYLeft(0, 20, 6);
    
    //QDateTime t0 = QDateTime::fromString("2024-11-28 00:00:00", "yyyy-MM-dd hh:mm:ss");
    //QDateTime tx;
    //for (int i = 0; i<=240; i++)
    //{
    //    tx = t0.addSecs(i*360);
    //    series->append(tx.toMSecsSinceEpoch(), qrand()%18);
    //}
    //this->setAxisX(t0.toMSecsSinceEpoch(), tx.toMSecsSinceEpoch(), 13);
    //this->setAxisYLeft(0, 20, 6);
}
void ChartLineView::setAxisX(double min, double max, int tickCount, std::string fmt)
{
    axisX->setRange(QDateTime::fromMSecsSinceEpoch(min), QDateTime::fromMSecsSinceEpoch(max));         // 范围
    axisX->setTickCount(tickCount);        // 轴上点的个数
    axisX->setFormat(fmt.c_str());
}

void ChartLineView::setAxisYLeft(double min, double max, double tickCount, std::string fmt)
{
    axisY->setRange(min, max);
    axisY->setTickCount(tickCount);
    axisY->setLabelFormat(fmt.c_str());
}

ProgressView::ProgressView(QWidget* parent, int x, int y, int h, int w, int d, int n) 
    : QWidget(parent)
    , num_(n)
{
    this->setGeometry(x, y, (w+d)*num_+4+42, h);
    this->show();
    vecBar_.resize(num_);

    const std::string STY_LAB = "font:bold 14px;color:white;";

    QUI::label(labBarBkg_, this, 0, 0, width(), height(), "", "border-width:1px;border-style:solid;border-color:rgba(40,169,222,255);");
    for (int i = 0; i < num_; i++)
    {
        vecBar_[i] = QUI::label(this, 2+i*(w+d), 2, w, height() - 4, "", "background-color:rgba(255,255,255,30);");
    }
    QUI::label(labVal_, this, width()-42, 0, 40, height(), "100%", STY_LAB);
    //labVal_.setAlignment(Qt::AlignRight | Qt::AlignVCenter);
}

void ProgressView::setVal(int v)
{
    if (v<0) { v = 0; }
    if (v>100) { v = 100; }
    labVal_.setText(QString::number(v) + "%");
    float c = float(v)*0.01;
    int index = c*float(num_) - 1;
    for (int i = 0; i<num_; i++)
    {
        int r = 0 + 255.0f*float(i)/float(num_);
        int g = 255 - 255.0f*float(i)/float(num_);
        std::string strColor = "background-color:rgba(" + std::to_string(r) + "," + std::to_string(g) + ",0,255);";
        vecBar_[i]->setStyleSheet(index>=i ? strColor.c_str() : "background-color:rgba(255,255,255,30);");
    }
}

LabelPairV::LabelPairV(QWidget* parent, QRect rt, int h, std::string k, std::string v)
{
    QUI::label(labV_, parent, rt.x(), rt.y(), rt.width(), h, v);
    QUI::label(labK_, parent, rt.x(), rt.y()+h, rt.width(), rt.height()-h, k);
    labV_.setAlignment(Qt::AlignCenter);
    labK_.setAlignment(Qt::AlignCenter);
}
void LabelPairV::setVal(std::string v, std::string sty/* = ""*/)
{
    labV_.setText(v.c_str());
    if (!sty.empty()) { labV_.setStyleSheet(sty.c_str()); }
}
void LabelPairV::setValStyle(std::string sty)
{
    labV_.setStyleSheet(sty.c_str());
}
void LabelPairV::setKeyStyle(std::string sty)
{
    labK_.setStyleSheet(sty.c_str());
}
void LabelPairV::setStyle(std::string styK, std::string styV /*= ""*/)
{
    this->setKeyStyle(styK);
    this->setValStyle(styV);
}

LabelPairH::LabelPairH(QWidget* parent, QRect rt, int w, std::string k, std::string v)
{
    QUI::label(labK_, parent, rt.x(), rt.y(), w, rt.height(), k);
    QUI::label(labV_, parent, rt.x()+w, rt.y(), rt.width()-w, rt.height(), v);
}

void LabelPairH::setVal(std::string v, std::string sty/* = ""*/)
{
    labV_.setText(v.c_str());
    if (!sty.empty()) { labV_.setStyleSheet(sty.c_str()); }
}

void LabelPairH::setValStyle(std::string sty)
{
    labV_.setStyleSheet(sty.c_str());
}

void LabelPairH::setKeyStyle(std::string sty)
{
    labK_.setStyleSheet(sty.c_str());
}
void LabelPairH::setStyle(std::string styK, std::string styV /*= ""*/)
{
    this->setKeyStyle(styK);
    this->setValStyle(styV);
}

static const std::string STY_TAB_BTN = R"(
QPushButton { background-color:rgb(240,120,0);border-radius:0px;font:bold 14px;color:white;border:1px solid #20a481; }
QPushButton:hover { background-color:rgba(32,164,128,255);color:white; }
QPushButton:pressed { border-width:3px 0 0 3px;border-style:inset;color:white;}
)";

static const std::string STY_TAB = R"(
QTableWidget
{
    background-color:rgb(37, 89, 120);
    alternate-background-color:rgb(57, 103, 130);
    color:white;
    font:bold 13px;
    selection-background-color:rgba(53, 125, 203, 100);
}
QTableWidget::item {padding-left:0px;text-align:center;color:rgba(255,255,255,200);}
QTableWidget::item:selected {color:#FFFFFF; background: rgba(53, 125, 203,100);}
)";


//QTableWidget::item:hover
//{
//    color:#FFFFFF;
//    background: #4B4B4D;
//}

//QHeaderView::section,QTableCornerButton:section
//{ 
//    text-align:center;
//    padding:3px; 
//    margin:0px; 
//    color:#DCDCDC; 
//    border:1px solid #242424; 
//    border-left-width:0px; 
//    border-right-width:1px; 
//    border-top-width:0px;
//    border-bottom-width:1px; 
//    background:qlineargradient(spread:pad,x1:0,y1:0,x2:0,y2:1,stop:0 #646464,stop:1 #525252);
// }
//QHeaderView::section:selected
//{ 
//    color:#FFFFFF; 
//    border:1px solid #242424; 
//}
//QScrollBar:vertical{ 
//    width:8px;  
//    border-style:flat;
//    border-radius: 4px;
//    border:0px;
//     background: #19191A;
//} 
//QScrollBar::handle:vertical{ 
//    background: rgba(255,255,255,0.50);
//    border-radius: 4px;
//    width:8px; 
//    min-height:91px; 
//    border-style:flat;
//}
//QScrollBar::handle:vertical::hover{ 
//    background: rgba(255,255,255,0.90);
//    border-radius: 4px;
//    width:8px; 
//}
//QScrollBar::handle:vertical::pressed{ 
//    background: rgba(255,255,255,0.90);
//    border-radius:4px;
//    width:8px; 
//}
//QScrollBar::sub-page:vertical {
//    background: #19191A;
//border-style:flat;
//}
//QScrollBar::add-page:vertical {
//   background: #19191A;
//border-style:flat;
//}
//QScrollBar::add-line:vertical{
//   background: #19191A;
//}
//QScrollBar::sub-line:vertical {
//   background: #19191A;
//}
//QScrollBar:horizontal{ 
//    height:8px;  
//    border-style:flat;
//    border-radius: 4px;
//    border:0px;
//background: #19191A;
//} 
//QScrollBar::handle:horizontal{ 
//    background: rgba(255,255,255,0.50);
//    border-radius: 4px;
//    height:8px; 
//    min-width:91px; 
//    border-style:flat;
//}
//QScrollBar::handle:horizontal::hover{ 
//    background: rgba(255,255,255,0.90);
//    border-radius: 4px;
//    height:8px; 
//}
//QScrollBar::handle:horizontal::pressed{ 
//    background: rgba(255,255,255,0.90);
//    border-radius:4px;
//    height:8px; 
//}
//QScrollBar::sub-page:horizontal {
//    background: #19191A;
//    border-style:flat;
//}
//QScrollBar::add-page:horizontal {
//   background: #19191A;
//   border-style:flat;
//}
//QScrollBar::sub-line:horizontal {
//   background: #19191A;
//}
//QScrollBar::add-line:horizontal{
//   background: #19191A;
//}

static const std::string STY_TAB_HEADER = R"(
QHeaderView {background:rgb(46,53,97); font:bold 15px;} 
QHeaderView::section {background:rgb(46,53,97);color:white;border:1px solid gray;}
)";

TableBase::TableBase(QWidget* parent, int rowMax, int colMax)
{
    widget_ = std::make_shared<QTableWidget>(rowMax, colMax, parent);
    //this->setItemDelegate(new MyTableItemDelegate(this));

    // "alternate-background-color:rgb(11,231,255);background-color:rgb(222,191,255);"
    widget_->setStyleSheet(STY_TAB.c_str());
    // 交替颜色
    widget_->setAlternatingRowColors(true);
    // 单元格编辑（）
    widget_->setEditTriggers(QAbstractItemView::NoEditTriggers);
    // 选中一行
    widget_->setSelectionBehavior(QAbstractItemView::SelectRows);

    // === 水平表头
    auto horiHeader = widget_->horizontalHeader();
    horiHeader->setFixedHeight(40);
    horiHeader->setStyleSheet(STY_TAB_HEADER.c_str());

    // === 垂直表头
    auto vertHeader = widget_->verticalHeader();
    // 隐藏垂直表头
    vertHeader->setVisible(false);
    // 设置默认行高
    vertHeader->setDefaultSectionSize(32);
}

TableBase::~TableBase()
{
    widget_->clearContents();
}

void TableBase::setGeometry(int x, int y, int w, int h)
{
    if (widget_)
    {
        widget_->setGeometry(x, y, w, h);
    }
}

void TableBase::setHeaderH(std::vector<std::string> vecHeader)
{
    widget_->setColumnCount(vecHeader.size());
    QStringList strList;
    for (int i = 0; i<vecHeader.size(); ++i) { strList << vecHeader[i].c_str(); }
    widget_->setHorizontalHeaderLabels(strList);
}

void TableBase::setHeaderWidth(std::vector<int> vecWidth)
{
    for (int i = 0; i<vecWidth.size(); ++i) 
    { 
        if (vecWidth[i] > 0)
        {
            widget_->setColumnWidth(i, vecWidth[i]);
        }
    }
}

void TableBase::setOperate(std::vector<std::string> vecOperate, std::function<void(int, std::string)> cb)
{
    cbOper_ = cb;
    vecOperate_ = vecOperate;
    //if (vecOperate_.size() > 0)
    {
        int colCount = widget_->columnCount();
        widget_->setColumnCount(colCount + 1);
        widget_->setHorizontalHeaderItem(colCount, new QTableWidgetItem("操作"));
        widget_->horizontalHeader()->setSectionResizeMode(colCount, QHeaderView::Stretch);
    }
}

void TableBase::setRow(int row, std::vector<std::string> vd)
{
    int rowCount = widget_->rowCount();
    if (row >= rowCount)
    {
        return;
    }

    int dataColCount = widget_->columnCount();
    if (vecOperate_.size() > 0)
    {
        dataColCount--;
        // 创建操作按钮
        if (vecWidgetOper_.size() != rowCount)
        {
            vecWidgetOper_.resize(rowCount, NULL);
        }
        std::shared_ptr<QWidget> wOpt = vecWidgetOper_[row];
        if (!wOpt)
        {
            wOpt = std::make_shared<QWidget>();
            wOpt->setMaximumSize(QSize(400, 40));
            vecWidgetOper_[row] = wOpt;

            for (int i = 0; i<vecOperate_.size(); i++)
            {
                std::string operText = vecOperate_[i];
                QPushButton* btn = QUI::button(wOpt.get(), 5+85*i, 5, 80, 24, operText, UiStyle::BTN);
                QObject::connect(btn, &QPushButton::clicked, widget_.get(), [=]() { this->onOperate(row, operText); });
            }
            widget_->setCellWidget(row, dataColCount, wOpt.get());
        }
    }
    for (int col = 0; col<dataColCount; col++)
    {
        if (col < vd.size())
        {
            QTableWidgetItem* item = widget_->item(row, col);
            if (!item)
            {
                item = new QTableWidgetItem();
                widget_->setItem(row, col, item);
            }
            item->setText(vd[col].c_str());
            item->setTextAlignment(Qt::AlignCenter);
        }
    }
}

void TableBase::clear()
{
    if (!widget_) { return; }
    widget_->clearContents();
    vecWidgetOper_.clear();
}

std::shared_ptr<QTableWidget> TableBase::widget()
{
    return widget_;
}

void TableBase::onOperate(int row, std::string oper)
{
    auto curItem = widget_->item(row, 0);
    widget_->setCurrentItem(curItem);

    if (cbOper_) { cbOper_(row, oper); }

    //curItem->setFlags(curItem->flags() | Qt::ItemIsEditable);
    //QPushButton* btn = qobject_cast<QPushButton*>(sender());
    //std::string text = btn->text().toStdString();
}

PageCtrl::PageCtrl(QWidget* parent, QRect rt, int pageSize) : QWidget(parent), pageSize_(pageSize)
{
    this->setGeometry(rt);
    QUI::setBackground(this, "PageCtrl", QColor(255, 0, 0, 30));

    int x = 10;
    QUI::label(labTotal_, this, x, 5, 100, 24, "共0条");
    QUI::button(btnFirst_, this, x += 110, 5, 60, 24, "首页");
    QUI::button(btnPrev_, this, x += 70, 5, 60, 24, "上一页");
    QUI::label(labPage_, this, x += 70, 5, 100, 25, "0/0");
    QUI::button(btnNext_, this, x += 110, 5, 60, 24, "下一页");
    QUI::button(btnLast_, this, x += 70, 5, 60, 24, "尾页");

    labPage_.setAlignment(Qt::AlignCenter);
}

void PageCtrl::setPage(int pageId, int total)
{
    curPage_ = pageId;
    int pageCount = total/pageSize_;
    if (total%pageSize_ > 0) { pageCount++; }

    std::string s = "共" + std::to_string(total) + "条";
    labTotal_.setText(s.c_str());

    s = std::to_string(curPage_) + "/" + std::to_string(pageCount);
    labPage_.setText(s.c_str());
}