Added support for transformation matrix in meters.

This commit is contained in:
Kimmo Pekkola 2009-07-27 11:48:57 +00:00
parent bded6e6fc7
commit dd9ab1dc04
23 changed files with 124 additions and 53 deletions

View File

@ -243,6 +243,24 @@ double CConfigParser::ReadFloat(LPCTSTR section, LPCTSTR key, double defValue)
return wcstod(result.c_str(), NULL); return wcstod(result.c_str(), NULL);
} }
std::vector<Gdiplus::REAL> CConfigParser::ReadFloats(LPCTSTR section, LPCTSTR key)
{
std::vector<Gdiplus::REAL> result;
std::wstring tmp = ReadString(section, key, L"");
if (!tmp.empty() && tmp[tmp.length() - 1] != L';')
{
tmp += L";";
}
// Tokenize and parse the floats
std::vector<std::wstring> tokens = Tokenize(tmp, L";");
for (size_t i = 0; i < tokens.size(); i++)
{
result.push_back((Gdiplus::REAL)wcstod(tokens[i].c_str(), NULL));
}
return result;
}
int CConfigParser::ReadInt(LPCTSTR section, LPCTSTR key, int defValue) int CConfigParser::ReadInt(LPCTSTR section, LPCTSTR key, int defValue)
{ {
TCHAR buffer[256]; TCHAR buffer[256];
@ -263,6 +281,30 @@ Color CConfigParser::ReadColor(LPCTSTR section, LPCTSTR key, Color defValue)
return ParseColor(result.c_str()); return ParseColor(result.c_str());
} }
/*
** Tokenize
**
** Splits the string from the delimiters
**
** http://www.digitalpeer.com/id/simple
*/
std::vector<std::wstring> CConfigParser::Tokenize(const std::wstring& str, const std::wstring delimiters)
{
std::vector<std::wstring> tokens;
std::wstring::size_type lastPos = str.find_first_not_of(L";", 0); // skip delimiters at beginning.
std::wstring::size_type pos = str.find_first_of(delimiters, lastPos); // find first "non-delimiter".
while (std::wstring::npos != pos || std::wstring::npos != lastPos)
{
tokens.push_back(str.substr(lastPos, pos - lastPos)); // found a token, add it to the vector.
lastPos = str.find_first_not_of(delimiters, pos); // skip delimiters. Note the "not_of"
pos = str.find_first_of(delimiters, lastPos); // find next "non-delimiter"
}
return tokens;
}
/* /*
** ParseColor ** ParseColor
** **

View File

@ -22,6 +22,7 @@
#include <windows.h> #include <windows.h>
#include <map> #include <map>
#include <string> #include <string>
#include <vector>
#include <gdiplus.h> #include <gdiplus.h>
class CRainmeter; class CRainmeter;
@ -38,12 +39,14 @@ public:
double ReadFloat(LPCTSTR section, LPCTSTR key, double defValue); double ReadFloat(LPCTSTR section, LPCTSTR key, double defValue);
int ReadInt(LPCTSTR section, LPCTSTR key, int defValue); int ReadInt(LPCTSTR section, LPCTSTR key, int defValue);
Gdiplus::Color ReadColor(LPCTSTR section, LPCTSTR key, Gdiplus::Color defValue); Gdiplus::Color ReadColor(LPCTSTR section, LPCTSTR key, Gdiplus::Color defValue);
std::vector<Gdiplus::REAL> ReadFloats(LPCTSTR section, LPCTSTR key);
std::wstring& GetFilename() { return m_Filename; } std::wstring& GetFilename() { return m_Filename; }
private: private:
void ReadVariables(); void ReadVariables();
Gdiplus::Color ParseColor(LPCTSTR string); Gdiplus::Color ParseColor(LPCTSTR string);
std::vector<std::wstring> Tokenize(const std::wstring& str, const std::wstring delimiters);
std::map<std::wstring, std::wstring> m_Variables; std::map<std::wstring, std::wstring> m_Variables;
std::wstring m_Filename; std::wstring m_Filename;

View File

@ -258,6 +258,17 @@ void CMeter::ReadConfig(const WCHAR* section)
m_UpdateDivider = parser.ReadInt(section, L"UpdateDivider", 1); m_UpdateDivider = parser.ReadInt(section, L"UpdateDivider", 1);
m_UpdateCounter = m_UpdateDivider; m_UpdateCounter = m_UpdateDivider;
std::vector<Gdiplus::REAL> matrix = parser.ReadFloats(section, L"TransformationMatrix");
if (matrix.size() == 6)
{
m_Transformation.SetElements(matrix[0], matrix[1], matrix[2], matrix[3], matrix[4], matrix[5]);
}
else if (!matrix.empty())
{
DebugLog(L"The transformation matrix has incorrect number of values:", parser.ReadString(section, L"TransformationMatrix", L"").c_str());
}
if (m_W == 0 || m_H == 0) if (m_W == 0 || m_H == 0)
{ {
throw CError(std::wstring(L"The meter ") + section + L" has zero dimensions.", __LINE__, __FILE__); throw CError(std::wstring(L"The meter ") + section + L" has zero dimensions.", __LINE__, __FILE__);
@ -367,14 +378,12 @@ bool CMeter::Update()
** **
** Draws the solid background & bevel if such are defined ** Draws the solid background & bevel if such are defined
*/ */
bool CMeter::Draw() bool CMeter::Draw(Graphics& graphics)
{ {
if (IsHidden()) return false; if (IsHidden()) return false;
if (m_SolidColor.GetA() != 0 || m_SolidColor2.GetA() != 0) if (m_SolidColor.GetA() != 0 || m_SolidColor2.GetA() != 0)
{ {
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
int x = GetX(); int x = GetX();
int y = GetY(); int y = GetY();
@ -393,8 +402,6 @@ bool CMeter::Draw()
if (m_SolidBevel != BEVELTYPE_NONE) if (m_SolidBevel != BEVELTYPE_NONE)
{ {
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
int x = GetX(); int x = GetX();
int y = GetY(); int y = GetY();

View File

@ -36,7 +36,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
virtual bool HasActiveTransition() { return false; } virtual bool HasActiveTransition() { return false; }
@ -59,6 +59,8 @@ public:
void Show() { m_Hidden = false; }; void Show() { m_Hidden = false; };
bool IsHidden() { return m_Hidden; }; bool IsHidden() { return m_Hidden; };
const Gdiplus::Matrix& GetTransformationMatrix() { return m_Transformation; }
virtual bool HitTest(int x, int y); virtual bool HitTest(int x, int y);
void SetMouseOver(bool over) { m_MouseOver = over; } void SetMouseOver(bool over) { m_MouseOver = over; }
@ -88,6 +90,7 @@ protected:
POSITION_RELATIVE_BR POSITION_RELATIVE_BR
}; };
Gdiplus::Matrix m_Transformation; // The transformation matrix
std::wstring m_Name; // Name of the meter std::wstring m_Name; // Name of the meter
std::wstring m_MeasureName; // Name of the measure this is bound to std::wstring m_MeasureName; // Name of the measure this is bound to
CMeasure* m_Measure; // Pointer to the measure this meter is bound to CMeasure* m_Measure; // Pointer to the measure this meter is bound to

View File

@ -142,15 +142,13 @@ bool CMeterBar::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterBar::Draw() bool CMeterBar::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
int x = GetX(); int x = GetX();
int y = GetY(); int y = GetY();
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
if(m_Orientation == VERTICAL) if(m_Orientation == VERTICAL)
{ {
int size = (int)((m_H - 2 * m_Border) * m_Value); int size = (int)((m_H - 2 * m_Border) * m_Value);

View File

@ -31,7 +31,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
private: private:
enum ORIENTATION enum ORIENTATION

View File

@ -263,9 +263,9 @@ bool CMeterBitmap::HasActiveTransition()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterBitmap::Draw() bool CMeterBitmap::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
int newY, newX; int newY, newX;
@ -309,8 +309,6 @@ bool CMeterBitmap::Draw()
// Blit the images // Blit the images
int offset; int offset;
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
if (m_Align == ALIGN_RIGHT) if (m_Align == ALIGN_RIGHT)
{ {
offset = 0; offset = 0;
@ -435,7 +433,6 @@ bool CMeterBitmap::Draw()
} }
// Blit the image // Blit the image
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
Rect r(x, y, m_W, m_H); Rect r(x, y, m_W, m_H);
graphics.DrawImage(m_Bitmap, r, newX, newY, m_W, m_H, UnitPixel); graphics.DrawImage(m_Bitmap, r, newX, newY, m_W, m_H, UnitPixel);
} }

View File

@ -33,7 +33,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual bool HasActiveTransition(); virtual bool HasActiveTransition();
private: private:

View File

@ -158,9 +158,9 @@ bool CMeterButton::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterButton::Draw() bool CMeterButton::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
if (m_Bitmaps[m_State] == NULL) return false; // Unable to continue if (m_Bitmaps[m_State] == NULL) return false; // Unable to continue
@ -168,7 +168,6 @@ bool CMeterButton::Draw()
int y = GetY(); int y = GetY();
// Blit the image // Blit the image
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
graphics.DrawCachedBitmap(m_Bitmaps[m_State], x, y); graphics.DrawCachedBitmap(m_Bitmaps[m_State], x, y);
// TEST // TEST

View File

@ -33,7 +33,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
bool MouseMove(POINT pos); bool MouseMove(POINT pos);

View File

@ -237,11 +237,10 @@ bool CMeterHistogram::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterHistogram::Draw() bool CMeterHistogram::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
Pen primaryPen(m_PrimaryColor); Pen primaryPen(m_PrimaryColor);
Pen secondaryPen(m_SecondaryColor); Pen secondaryPen(m_SecondaryColor);
Pen bothPen(m_BothColor); Pen bothPen(m_BothColor);

View File

@ -31,7 +31,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
private: private:

View File

@ -231,14 +231,12 @@ bool CMeterImage::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterImage::Draw() bool CMeterImage::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
if (m_Bitmap != NULL) if (m_Bitmap != NULL)
{ {
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
// Copy the image over the doublebuffer // Copy the image over the doublebuffer
int x = GetX(); int x = GetX();
int y = GetY(); int y = GetY();

View File

@ -36,7 +36,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
private: private:

View File

@ -186,9 +186,9 @@ bool CMeterLine::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterLine::Draw() bool CMeterLine::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
double maxValue = 0.0; double maxValue = 0.0;
int counter = 0; int counter = 0;
@ -235,7 +235,7 @@ bool CMeterLine::Draw()
maxValue = 1.0; maxValue = 1.0;
} }
Graphics graphics(m_MeterWindow->GetDoubleBuffer()); //GDI+ SmoothingMode mode = graphics.GetSmoothingMode();
if (m_AntiAlias) if (m_AntiAlias)
{ {
graphics.SetSmoothingMode(SmoothingModeAntiAlias); graphics.SetSmoothingMode(SmoothingModeAntiAlias);
@ -321,6 +321,11 @@ bool CMeterLine::Draw()
counter++; counter++;
} }
if (m_AntiAlias)
{
graphics.SetSmoothingMode(mode);
}
return true; return true;
} }

View File

@ -31,7 +31,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
private: private:

View File

@ -132,9 +132,9 @@ bool CMeterRotator::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterRotator::Draw() bool CMeterRotator::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
// Calculate the center for rotation // Calculate the center for rotation
int x = GetX(); int x = GetX();
@ -146,8 +146,6 @@ bool CMeterRotator::Draw()
// Calculate the rotation // Calculate the rotation
REAL angle = (REAL)(m_RotationAngle * m_Value + m_StartAngle); REAL angle = (REAL)(m_RotationAngle * m_Value + m_StartAngle);
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
angle = angle * 180.0f / 3.14159265f; // Convert to degrees angle = angle * 180.0f / 3.14159265f; // Convert to degrees
graphics.TranslateTransform(cx, cy); graphics.TranslateTransform(cx, cy);
@ -162,6 +160,7 @@ bool CMeterRotator::Draw()
// Blit the image // Blit the image
graphics.DrawImage(m_Bitmap, 0, 0, width, height); graphics.DrawImage(m_Bitmap, 0, 0, width, height);
} }
graphics.ResetTransform();
return true; return true;
} }

View File

@ -31,7 +31,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
private: private:
Gdiplus::Bitmap* m_Bitmap; // The bar bitmap Gdiplus::Bitmap* m_Bitmap; // The bar bitmap

View File

@ -126,11 +126,11 @@ bool CMeterRoundLine::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterRoundLine::Draw() bool CMeterRoundLine::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
Graphics graphics(m_MeterWindow->GetDoubleBuffer()); //GDI+ SmoothingMode mode = graphics.GetSmoothingMode();
if (m_AntiAlias) if (m_AntiAlias)
{ {
graphics.SetSmoothingMode(SmoothingModeAntiAlias); graphics.SetSmoothingMode(SmoothingModeAntiAlias);
@ -213,5 +213,10 @@ bool CMeterRoundLine::Draw()
graphics.DrawLine(&pen, cx, cy, x, y); graphics.DrawLine(&pen, cx, cy, x, y);
} }
if (m_AntiAlias)
{
graphics.SetSmoothingMode(mode);
}
return true; return true;
} }

View File

@ -30,7 +30,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
private: private:
bool m_AntiAlias; // If true, the line is antialiased bool m_AntiAlias; // If true, the line is antialiased

View File

@ -331,7 +331,8 @@ bool CMeterString::Update()
{ {
// Calculate the text size // Calculate the text size
RectF rect; RectF rect;
DrawString(&rect); Graphics graphics(m_MeterWindow->GetDoubleBuffer());
DrawString(graphics, &rect);
m_W = (int)rect.Width; m_W = (int)rect.Width;
m_H = (int)rect.Height; m_H = (int)rect.Height;
} }
@ -347,11 +348,11 @@ bool CMeterString::Update()
** Draws the meter on the double buffer ** Draws the meter on the double buffer
** **
*/ */
bool CMeterString::Draw() bool CMeterString::Draw(Graphics& graphics)
{ {
if(!CMeter::Draw()) return false; if(!CMeter::Draw(graphics)) return false;
return DrawString(NULL); return DrawString(graphics, NULL);
} }
/* /*
@ -360,9 +361,8 @@ bool CMeterString::Draw()
** Draws the string or calculates it's size ** Draws the string or calculates it's size
** **
*/ */
bool CMeterString::DrawString(RectF* rect) bool CMeterString::DrawString(Graphics& graphics, RectF* rect)
{ {
Graphics graphics(m_MeterWindow->GetDoubleBuffer());
StringFormat stringFormat; StringFormat stringFormat;
if (m_AntiAlias) if (m_AntiAlias)
@ -418,6 +418,8 @@ bool CMeterString::DrawString(RectF* rect)
graphics.TranslateTransform(-(Gdiplus::REAL)CMeter::GetX(), -y); graphics.TranslateTransform(-(Gdiplus::REAL)CMeter::GetX(), -y);
graphics.DrawString(m_String.c_str(), -1, m_Font, rc, &stringFormat, &solidBrush); graphics.DrawString(m_String.c_str(), -1, m_Font, rc, &stringFormat, &solidBrush);
graphics.ResetTransform();
} }
return true; return true;

View File

@ -37,7 +37,7 @@ public:
virtual void ReadConfig(const WCHAR* section); virtual void ReadConfig(const WCHAR* section);
virtual void Initialize(); virtual void Initialize();
virtual bool Update(); virtual bool Update();
virtual bool Draw(); virtual bool Draw(Gdiplus::Graphics& graphics);
virtual void BindMeasure(std::list<CMeasure*>& measures); virtual void BindMeasure(std::list<CMeasure*>& measures);
private: private:
@ -49,7 +49,7 @@ private:
BOLDITALIC BOLDITALIC
}; };
bool DrawString(Gdiplus::RectF* rect); bool DrawString(Gdiplus::Graphics& graphics, Gdiplus::RectF* rect);
Gdiplus::Color m_Color; // The color of the text Gdiplus::Color m_Color; // The color of the text
std::wstring m_Postfix; // The postfix of the text std::wstring m_Postfix; // The postfix of the text

View File

@ -1745,10 +1745,11 @@ void CMeterWindow::Redraw()
CreateRegion(true); CreateRegion(true);
} }
Graphics graphics(GetDoubleBuffer());
if (m_Background) if (m_Background)
{ {
// Copy the background over the doublebuffer // Copy the background over the doublebuffer
Graphics graphics(GetDoubleBuffer());
Rect r(0, 0, m_WindowW, m_WindowH); Rect r(0, 0, m_WindowW, m_WindowH);
graphics.DrawImage(m_Background, r, 0, 0, m_Background->GetWidth(), m_Background->GetHeight(), UnitPixel); graphics.DrawImage(m_Background, r, 0, 0, m_Background->GetWidth(), m_Background->GetHeight(), UnitPixel);
} }
@ -1759,7 +1760,20 @@ void CMeterWindow::Redraw()
{ {
try try
{ {
(*j)->Draw(); if (!(*j)->GetTransformationMatrix().IsIdentity())
{
// Change the world matrix
graphics.SetTransform(&((*j)->GetTransformationMatrix()));
(*j)->Draw(graphics);
// Set back to identity matrix
graphics.ResetTransform();
}
else
{
(*j)->Draw(graphics);
}
} }
catch (CError& error) catch (CError& error)
{ {