/******************************************************************** glcommon GL code & font stuff Copyright (c)2011 Mark Watkins <jedimark@users.sourceforge.net> License: GPL *********************************************************************/ #include <QApplication> #include <QFontMetrics> #include <QMessageBox> #include <QDebug> #include <math.h> #include "glcommon.h" #include "SleepLib/profiles.h" #include <QFile> bool _graph_init=false; QFont * defaultfont=NULL; QFont * mediumfont=NULL; QFont * bigfont=NULL; GLshort *vertex_array[num_vert_arrays]={NULL}; bool evil_intel_graphics_chip=false; // Must be called from a thread inside the application. void InitGraphs() { if (!_graph_init) { defaultfont=new QFont("FreeSans",10); bigfont=new QFont("FreeSans",35); mediumfont=new QFont("FreeSans",18); for (int i=0;i<num_vert_arrays;i++) { vertex_array[i]=new GLshort[maxverts]; } _graph_init=true; } } void DoneGraphs() { if (_graph_init) { delete defaultfont; delete bigfont; delete mediumfont; for (int i=0;i<num_vert_arrays;i++) { delete [] vertex_array[i]; } _graph_init=false; } } void GetTextExtent(QString text, float & width, float & height, QFont *font) { QFontMetrics fm(*font); //QRect r=fm.tightBoundingRect(text); width=fm.width(text); //fm.width(text); height=fm.xHeight()+2; //fm.ascent(); } inline void RDrawText(QPainter & painter, QString text, int x, int y, float angle, QColor color,QFont *font) { //QFontMetrics fm(*font); float w,h; //GetTextExtent(text,w,h,font); //int a=fm.overlinePos(); //ascent(); //LinedRoundedRectangle(x,wid.GetScrY()-y,w,h,0,1,QColor("black")); if (!font) { QMessageBox::critical(NULL,"Critical Error","Font Problem. Forgot to call GraphInit()? Have to abort"); exit(-1); } // glEnable(GL_TEXTURE_2D); // glDisable(GL_DEPTH_TEST); painter.setFont(*font); //color=Qt::black; painter.setPen(color); painter.setBrush(QBrush(color)); painter.setOpacity(1); // painter.setCompositionMode(QPainter::CompositionMode_); if (angle==0) { painter.drawText(x,y,text); } else { GetTextExtent(text, w, h, font); painter.translate(floor(x),floor(y)); painter.rotate(-angle); painter.drawText(floor(-w/2.0),floor(-h/2.0),text); painter.rotate(+angle); painter.translate(floor(-x),floor(-y)); } } struct TextBuffer { QString text; int x,y; float angle; QColor color; QFont *font; TextBuffer() { x=0; y=0; } TextBuffer(QString _text, int _x, int _y, float _angle, QColor _color,QFont *_font) { text=_text; x=_x; y=_y; angle=_angle; color=_color; font=_font; } }; vector<TextBuffer> TextQue; vector<TextBuffer> TextQueRot; void DrawTextQueue(gGraphWindow & wid) { //glFlush(); for (unsigned i=0;i<TextQue.size();i++) { TextBuffer & t=TextQue[i]; wid.qglColor(t.color); wid.renderText(t.x,wid.GetScrY()-t.y,0,t.text,*t.font); //RDrawText(painter,t.text,t.x,t.y,t.angle,t.color,t.font); //delete TextQue[i]; } if (wid.parentWidget()!=0) { QPainter painter(&wid); // TODO.. Prerotate the 90degree stuff here and keep the matrix for all of these.. for (unsigned i=0;i<TextQueRot.size();i++) { TextBuffer & t=TextQueRot[i]; RDrawText(painter,t.text,t.x,t.y,t.angle,t.color,t.font); //delete TextQueRot[i]; } painter.end(); } TextQueRot.clear(); TextQue.clear(); glDisable(GL_TEXTURE_2D); glDisable(GL_DEPTH_TEST); } // I bet this slows things down craploads.. should probably skip the vector and use a preallocated textbuffer array. void DrawText(gGraphWindow &wid,QString text, int x, int y, float angle, QColor color,QFont *font) { if (angle!=0) { //TextBuffer *b=new TextBuffer(text,x,y,angle,color,font); TextQueRot.push_back(TextBuffer(text,x,y,angle,color,font)); } else { TextQue.push_back(TextBuffer(text,x,y,0,color,font)); //wid.qglColor(color); //wid.renderText(x,wid.GetScrY()-y,0,text,*font); //TextQue.push_back(b); } } void RoundedRectangle(int x,int y,int w,int h,int radius,const QColor color) { glEnable(GL_BLEND); glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA); glColor4ub(color.red(),color.green(),color.blue(),color.alpha()); glBegin(GL_POLYGON); glVertex2i(x+radius,y); glVertex2i(x+w-radius,y); for(float i=(float)M_PI*1.5f;i<M_PI*2;i+=0.1f) glVertex2f(x+w-radius+cos(i)*radius,y+radius+sin(i)*radius); glVertex2i(x+w,y+radius); glVertex2i(x+w,y+h-radius); for(float i=0;i<(float)M_PI*0.5f;i+=0.1f) glVertex2f(x+w-radius+cos(i)*radius,y+h-radius+sin(i)*radius); glVertex2i(x+w-radius,y+h); glVertex2i(x+radius,y+h); for(float i=(float)M_PI*0.5f;i<M_PI;i+=0.1f) glVertex2f(x+radius+cos(i)*radius,y+h-radius+sin(i)*radius); glVertex2i(x,y+h-radius); glVertex2i(x,y+radius); for(float i=(float)M_PI;i<M_PI*1.5f;i+=0.1f) glVertex2f(x+radius+cos(i)*radius,y+radius+sin(i)*radius); glEnd(); glDisable(GL_BLEND); } void LinedRoundedRectangle(int x,int y,int w,int h,int radius,int lw,QColor color) { glDisable(GL_TEXTURE_2D); glShadeModel(GL_SMOOTH); glEnable(GL_BLEND); glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA); glColor4ub(color.red(),color.green(),color.blue(),color.alpha()); glLineWidth((GLfloat)lw); glBegin(GL_LINE_STRIP); for(float i=(float)M_PI;i<=1.5f*M_PI;i+=0.1f) glVertex2f(radius*cos(i)+x+radius,radius*sin(i)+y+radius); for(float i=1.5f*(float)M_PI;i<=2*M_PI; i+=0.1f) glVertex2f(radius*cos(i)+x+w-radius,radius*sin(i)+y+radius); for(float i=0;i<=0.5f*M_PI; i+=0.1f) glVertex2f(radius*cos(i)+x+w-radius,radius*sin(i)+y+h-radius); for(float i=0.5f*(float)M_PI;i<=M_PI;i+=0.1f) glVertex2f(radius*cos(i)+x+radius,radius*sin(i)+y+h-radius); glVertex2i(x,y+radius); glEnd(); glEnable(GL_TEXTURE_2D); glDisable(GL_BLEND); }