📄 qlcdnumber.cpp
字号:
/*! Sets the display mode to \e m, which must be one of \c BIN, \c OCT, \c DEC and \c HEX. All four modes can display both integers, floating-point numbers and strings (subject to character set limitations). Example: \code myLcd.setMode( QLCDNumber::HEX ); \endcode \sa mode(), setHexMode(), setDecMode(), setOctMode(), setBinMode(), setSmallDecimalPoint(), display()*/void QLCDNumber::setMode( Mode m ){ base = m; display( val );}/*! \fn bool QLCDNumber::smallDecimalPoint() const Returns TRUE if the decimal point is currently drawn between two digit positions, and FALSE if it is drawn in a digit position. \sa setSmallDecimalPoint(), mode()*//*! If \e b is TRUE, the decimal point is drawn between two digits. If \e b is FALSE, the decimal point is drawn in a digit position. The inter-digit space is made slightly wider when the decimal point is drawn between the digits. \sa smallDecimalPoint(), setMode()*/void QLCDNumber::setSmallDecimalPoint( bool b ){ smallPoint = b;}/*! Draws the LCD number using painter \e p. This function is called from QFrame::paintEvent().*/void QLCDNumber::drawContents( QPainter *p ){ if ( smallPoint ) drawString( digitStr, *p, &points, FALSE ); else drawString( digitStr, *p, 0, FALSE );}/*! \internal*/void QLCDNumber::internalDisplay( const QString & ){ // Not used anymore}void QLCDNumber::internalSetString( const QString& s ){ QString buffer; int i; int len = s.length(); QBitArray newPoints(ndigits); if ( !smallPoint ) { if ( len == ndigits ) buffer = s; else buffer = s.right( ndigits ).rightJustify( ndigits, ' ' ); } else { int index = -1; bool lastWasPoint = TRUE; newPoints.clearBit(0); for ( i=0; i<len; i++ ) { if ( s[i] == '.' ) { if ( lastWasPoint ) { // point already set for digit? if ( index == ndigits - 1 ) // no more digits break; index++; buffer[index] = ' '; // 2 points in a row, add space } newPoints.setBit(index); // set decimal point lastWasPoint = TRUE; } else { if ( index == ndigits - 1 ) break; index++; buffer[index] = s[i]; newPoints.clearBit(index); // decimal point default off lastWasPoint = FALSE; } } if ( index < ((int) ndigits) - 1 ) { for( i=index; i>=0; i-- ) { buffer[ndigits - 1 - index + i] = buffer[i]; newPoints.setBit( ndigits - 1 - index + i, newPoints.testBit(i) ); } for( i=0; i<ndigits-index-1; i++ ) { buffer[i] = ' '; newPoints.clearBit(i); } } } if ( buffer == digitStr ) return; if ( backgroundMode() == FixedPixmap || colorGroup().brush( QColorGroup::Background ).pixmap() ) { digitStr = buffer; if ( smallPoint ) points = newPoints; repaint( contentsRect() ); } else { QPainter p( this ); if ( !smallPoint ) drawString( buffer, p ); else drawString( buffer, p, &newPoints ); }}/*! \internal*/void QLCDNumber::drawString( const QString &s, QPainter &p, QBitArray *newPoints, bool newString ){ if ( isVisible() ) { QPoint pos; int digitSpace = smallPoint ? 2 : 1; int xSegLen = width()*5/(ndigits*(5 + digitSpace) + digitSpace); int ySegLen = height()*5/12; int segLen = ySegLen > xSegLen ? xSegLen : ySegLen; int xAdvance = segLen*( 5 + digitSpace )/5; int xOffset = ( width() - ndigits*xAdvance + segLen/5 )/2; int yOffset = ( height() - segLen*2 )/2; for ( int i=0; i<ndigits; i++ ) { pos = QPoint( xOffset + xAdvance*i, yOffset ); if ( newString ) drawDigit( pos, p, segLen, s[i], digitStr[i].latin1() ); else drawDigit( pos, p, segLen, s[i]); if ( newPoints ) { char newPoint = newPoints->testBit(i) ? '.' : ' '; if ( newString ) { char oldPoint = points.testBit(i) ? '.' : ' '; drawDigit( pos, p, segLen, newPoint, oldPoint ); } else { drawDigit( pos, p, segLen, newPoint ); } } } } if ( newString ) { digitStr = s; if ( (int)digitStr.length() > ndigits ) digitStr.truncate( ndigits ); if ( newPoints ) points = *newPoints; }}/*! \internal*/void QLCDNumber::drawDigit( const QPoint &pos, QPainter &p, int segLen, char newCh, char oldCh ){// Draws and/or erases segments to change display of a single digit// from oldCh to newCh char updates[18][2]; // can hold 2 times number of segments, only // first 9 used if segment table is correct int nErases; int nUpdates; const char *segs; int i,j; const char erase = 0; const char draw = 1; const char leaveAlone = 2; segs = getSegments(oldCh); for ( nErases=0; segs[nErases] != 99; nErases++ ) { updates[nErases][0] = erase; // get segments to erase to updates[nErases][1] = segs[nErases]; // remove old char } nUpdates = nErases; segs = getSegments(newCh); for(i = 0 ; segs[i] != 99 ; i++) { for ( j=0; j<nErases; j++ ) if ( segs[i] == updates[j][1] ) { // same segment ? updates[j][0] = leaveAlone; // yes, already on screen break; } if ( j == nErases ) { // if not already on screen updates[nUpdates][0] = draw; updates[nUpdates][1] = segs[i]; nUpdates++; } } for ( i=0; i<nUpdates; i++ ) { if ( updates[i][0] == draw ) drawSegment( pos, updates[i][1], p, segLen ); if (updates[i][0] == erase) drawSegment( pos, updates[i][1], p, segLen, TRUE ); }}static void addPoint( QPointArray &a, const QPoint &p ){ uint n = a.size(); a.resize( n + 1 ); a.setPoint( n, p );}/*! \internal*/void QLCDNumber::drawSegment( const QPoint &pos, char segmentNo, QPainter &p, int segLen, bool erase ){ QPoint pt = pos; int width = segLen/5; const QColorGroup & g = colorGroup(); QColor lightColor,darkColor,fgColor; if ( erase ){ lightColor = backgroundColor(); darkColor = lightColor; fgColor = lightColor; } else { lightColor = g.light(); darkColor = g.dark(); fgColor = g.foreground(); }#define LINETO(X,Y) addPoint( a, QPoint(pt.x() + (X),pt.y() + (Y)))#define LIGHT#define DARK if ( fill ) { QPointArray a(0); //The following is an exact copy of the switch below. //don't make any changes here switch ( segmentNo ) { case 0 : p.moveTo(pt); LIGHT; LINETO(segLen - 1,0); DARK; LINETO(segLen - width - 1,width); LINETO(width,width); LINETO(0,0); break; case 1 : pt += QPoint(0 , 1); p.moveTo(pt); LIGHT; LINETO(width,width); DARK; LINETO(width,segLen - width/2 - 2); LINETO(0,segLen - 2); LIGHT; LINETO(0,0); break; case 2 : pt += QPoint(segLen - 1 , 1); p.moveTo(pt); DARK; LINETO(0,segLen - 2); LINETO(-width,segLen - width/2 - 2); LIGHT; LINETO(-width,width); LINETO(0,0); break; case 3 : pt += QPoint(0 , segLen); p.moveTo(pt); LIGHT; LINETO(width,-width/2); LINETO(segLen - width - 1,-width/2); LINETO(segLen - 1,0); DARK; if (width & 1) { // adjust for integer division error LINETO(segLen - width - 3,width/2 + 1); LINETO(width + 2,width/2 + 1); } else { LINETO(segLen - width - 1,width/2); LINETO(width,width/2); } LINETO(0,0); break; case 4 : pt += QPoint(0 , segLen + 1); p.moveTo(pt); LIGHT; LINETO(width,width/2); DARK; LINETO(width,segLen - width - 2); LINETO(0,segLen - 2); LIGHT; LINETO(0,0); break; case 5 : pt += QPoint(segLen - 1 , segLen + 1); p.moveTo(pt); DARK; LINETO(0,segLen - 2); LINETO(-width,segLen - width - 2); LIGHT; LINETO(-width,width/2); LINETO(0,0); break; case 6 : pt += QPoint(0 , segLen*2); p.moveTo(pt); LIGHT; LINETO(width,-width); LINETO(segLen - width - 1,-width); LINETO(segLen - 1,0); DARK; LINETO(0,0); break; case 7 : if ( smallPoint ) // if smallpoint place'.' between other digits pt += QPoint(segLen + width/2 , segLen*2); else pt += QPoint(segLen/2 , segLen*2); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break; case 8 : pt += QPoint(segLen/2 - width/2 + 1 , segLen/2 + width); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break; case 9 : pt += QPoint(segLen/2 - width/2 + 1 , 3*segLen/2 + width); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break;#if defined(CHECK_RANGE) default : qWarning( "QLCDNumber::drawSegment: (%s) Internal error." " Illegal segment id: %d\n", name( "unnamed" ), segmentNo );#endif } // End exact copy p.setPen( fgColor ); p.setBrush( fgColor ); p.drawPolygon( a ); p.setBrush( NoBrush ); pt = pos; }#undef LINETO#undef LIGHT#undef DARK#define LINETO(X,Y) p.lineTo(QPoint(pt.x() + (X),pt.y() + (Y)))#define LIGHT p.setPen(lightColor)#define DARK p.setPen(darkColor) if ( shadow ) switch ( segmentNo ) { case 0 : p.moveTo(pt); LIGHT; LINETO(segLen - 1,0); DARK; LINETO(segLen - width - 1,width); LINETO(width,width); LINETO(0,0); break; case 1 : pt += QPoint(0,1); p.moveTo(pt); LIGHT; LINETO(width,width); DARK; LINETO(width,segLen - width/2 - 2); LINETO(0,segLen - 2); LIGHT; LINETO(0,0); break; case 2 : pt += QPoint(segLen - 1 , 1); p.moveTo(pt); DARK; LINETO(0,segLen - 2); LINETO(-width,segLen - width/2 - 2); LIGHT; LINETO(-width,width); LINETO(0,0); break; case 3 : pt += QPoint(0 , segLen); p.moveTo(pt); LIGHT; LINETO(width,-width/2); LINETO(segLen - width - 1,-width/2); LINETO(segLen - 1,0); DARK; if (width & 1) { // adjust for integer division error LINETO(segLen - width - 3,width/2 + 1); LINETO(width + 2,width/2 + 1); } else { LINETO(segLen - width - 1,width/2); LINETO(width,width/2); } LINETO(0,0); break; case 4 : pt += QPoint(0 , segLen + 1); p.moveTo(pt); LIGHT; LINETO(width,width/2); DARK; LINETO(width,segLen - width - 2); LINETO(0,segLen - 2); LIGHT; LINETO(0,0); break; case 5 : pt += QPoint(segLen - 1 , segLen + 1); p.moveTo(pt); DARK; LINETO(0,segLen - 2); LINETO(-width,segLen - width - 2); LIGHT; LINETO(-width,width/2); LINETO(0,0); break; case 6 : pt += QPoint(0 , segLen*2); p.moveTo(pt); LIGHT; LINETO(width,-width); LINETO(segLen - width - 1,-width); LINETO(segLen - 1,0); DARK; LINETO(0,0); break; case 7 : if ( smallPoint ) // if smallpoint place'.' between other digits pt += QPoint(segLen + width/2 , segLen*2); else pt += QPoint(segLen/2 , segLen*2); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break; case 8 : pt += QPoint(segLen/2 - width/2 + 1 , segLen/2 + width); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break; case 9 : pt += QPoint(segLen/2 - width/2 + 1 , 3*segLen/2 + width); p.moveTo(pt); DARK; LINETO(width,0); LINETO(width,-width); LIGHT; LINETO(0,-width); LINETO(0,0); break;#if defined(CHECK_RANGE) default : qWarning( "QLCDNumber::drawSegment: (%s) Internal error." " Illegal segment id: %d\n", name( "unnamed" ), segmentNo );#endif }#undef LINETO#undef LIGHT#undef DARK}/*! Sets the style of the QLCDNumber to \a s. <ul> <li>\c Outline gives raised segments filled with the background color. <li>\c Filled gives raised segments filled with the foreground color. <li>\c Flat gives flat segments filled with the foreground color. </ul> \c Outline and \c Filled will additionally use QColorGroup::light() and QColorGroup::dark() for shadow effects. \sa segmentStyle() */void QLCDNumber::setSegmentStyle( SegmentStyle s ){ fill = ( s == Flat || s == Filled ); shadow = ( s == Outline || s == Filled ); update();}/*! Returns the style of the QLCDNumber. \sa setSegmentStyle()*/QLCDNumber::SegmentStyle QLCDNumber::segmentStyle() const{ ASSERT( fill || shadow ); if ( !fill && shadow ) return Outline; if ( fill && shadow ) return Filled; return Flat;}/*!\reimp*/QSize QLCDNumber::sizeHint() const{ return QSize( 10 + 9 * (numDigits() + (smallDecimalPoint() ? 0 : 1)), 23 );}/*!\reimp*/QSizePolicy QLCDNumber::sizePolicy() const{ //### removeme 3.0 return QWidget::sizePolicy();}#endif // QT_NO_LCDNUMBER
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -