//
// $Source: /cvsroot/gambit/gambit/sources/gui/renratio.cc,v $
// $Date: 2006/08/20 17:02:14 $
// $Revision: 1.6 $
//
// DESCRIPTION:
// Implementation of wxSheet renderer for rational numbers
//
// This file is part of Gambit
// Copyright (c) 2005, The Gambit Project
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
//
#include <wx/wxprec.h>
#ifndef WX_PRECOMP
#include <wx/wx.h>
#endif // WX_PRECOMP
#include "renratio.h"
#include "wx/sheet/sheet.h" // the wxSheet widget
//----------------------------------------------------------------------------
// class gbtRationalRendererRefData
//----------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(gbtRationalRendererRefData, wxSheetCellRendererRefData)
void
gbtRationalRendererRefData::SetTextColoursAndFont(wxSheet& grid,
const wxSheetCellAttr& attr,
wxDC& dc,
bool isSelected)
{
dc.SetBackgroundMode(wxTRANSPARENT);
if (grid.IsEnabled()) {
if (isSelected) {
dc.SetTextBackground(grid.GetSelectionBackground());
dc.SetTextForeground(grid.GetSelectionForeground());
}
else {
dc.SetTextBackground(attr.GetBackgroundColour());
dc.SetTextForeground(attr.GetForegroundColour());
}
}
else {
dc.SetTextBackground(wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE));
dc.SetTextForeground(wxSystemSettings::GetColour(wxSYS_COLOUR_GRAYTEXT));
}
dc.SetFont(attr.GetFont());
}
static wxSize GetFractionExtent(wxDC &p_dc, const wxString &p_value)
{
p_dc.SetFont(wxFont(7, wxSWISS, wxNORMAL, wxBOLD));
wxString num;
int i = 0;
while (p_value[i] != '/') num += p_value[i++];
i++;
wxString den;
while (p_value[i] != '\0') den += p_value[i++];
int numWidth, numHeight;
p_dc.GetTextExtent(num, &numWidth, &numHeight);
int denWidth, denHeight;
p_dc.GetTextExtent(den, &denWidth, &denHeight);
int width = ((numWidth > denWidth) ? numWidth : denWidth);
return wxSize(width + 4, numHeight + denHeight);
}
wxSize gbtRationalRendererRefData::DoGetBestSize(wxSheet& grid,
const wxSheetCellAttr& attr,
wxDC& dc,
const wxString& text)
{
if (text.Find('/') != -1) {
return GetFractionExtent(dc, text);
}
wxArrayString lines;
long w=0, h=0;
if (grid.StringToLines(text, lines) > 0) {
dc.SetFont(attr.GetFont());
grid.GetTextBoxSize(dc, lines, &w, &h);
}
return wxSize(w, h);
}
wxSize
gbtRationalRendererRefData::GetBestSize(wxSheet& grid,
const wxSheetCellAttr& attr,
wxDC& dc,
const wxSheetCoords& coords)
{
return DoGetBestSize(grid, attr, dc, grid.GetCellValue(coords));
}
void gbtRationalRendererRefData::Draw(wxSheet& grid,
const wxSheetCellAttr& attr,
wxDC& dc,
const wxRect& rectCell,
const wxSheetCoords& coords,
bool isSelected)
{
wxRect rect = rectCell;
rect.Inflate(-1);
// erase only this cells background, overflow cells should have been erased
wxSheetCellRendererRefData::Draw(grid, attr, dc, rectCell, coords, isSelected);
DoDraw(grid, attr, dc, rectCell, coords, isSelected);
}
static void DrawFraction(wxDC &p_dc, wxRect p_rect, const wxString &p_value)
{
p_dc.SetFont(wxFont(7, wxSWISS, wxNORMAL, wxBOLD));
wxString num;
int i = 0;
while (p_value[i] != '/') num += p_value[i++];
i++;
wxString den;
while (p_value[i] != '\0') den += p_value[i++];
int numWidth, numHeight;
p_dc.GetTextExtent(num, &numWidth, &numHeight);
int denWidth, denHeight;
p_dc.GetTextExtent(den, &denWidth, &denHeight);
int width = ((numWidth > denWidth) ? numWidth : denWidth);
wxPoint point(p_rect.x, p_rect.y + p_rect.height/2);
p_dc.SetPen(wxPen(p_dc.GetTextForeground(), 1, wxSOLID));
p_dc.DrawText(num,
point.x + (p_rect.width-numWidth)/2,
point.y - numHeight);
p_dc.DrawText(den,
point.x + (p_rect.width-denWidth)/2,
point.y);
p_dc.DrawLine(point.x + (p_rect.width-width)/2 - 2, point.y,
point.x + (p_rect.width-width)/2 + width + 2, point.y);
}
void gbtRationalRendererRefData::DoDraw(wxSheet& grid,
const wxSheetCellAttr& attr,
wxDC& dc,
const wxRect& rectCell,
const wxSheetCoords& coords,
bool isSelected)
{
wxRect rect = rectCell;
rect.Inflate(-1);
int align = attr.GetAlignment();
wxString value = grid.GetCellValue(coords);
//int best_width = DoGetBestSize(grid, attr, dc, value).GetWidth();
wxSheetCoords cellSpan(grid.GetCellSpan(coords)); // shouldn't get here if <=0
//int cell_rows = cellSpan.m_row;
//int cell_cols = cellSpan.m_col;
//bool is_grid_cell = wxSheet::IsGridCell(coords);
// no overflow for row/col/corner labels
//int num_cols = grid.GetNumberCols();
// Draw the text
if (value.Find('/') != -1) {
SetTextColoursAndFont(grid, attr, dc, isSelected);
DrawFraction(dc, rect, value);
}
else {
SetTextColoursAndFont(grid, attr, dc, isSelected);
grid.DrawTextRectangle(dc, value, rect, align);
}
}
//----------------------------------------------------------------------------
// class gbtRationalEditorRefData
//----------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(gbtRationalEditorRefData, wxSheetCellTextEditorRefData)
#include "valnumber.h"
void gbtRationalEditorRefData::CreateEditor(wxWindow* parent,
wxWindowID id,
wxEvtHandler* evtHandler,
wxSheet* sheet)
{
wxSheetCellTextEditorRefData::CreateEditor(parent, id, evtHandler, sheet);
GetTextCtrl()->SetValidator(gbtNumberValidator(0));
}
bool gbtRationalEditorRefData::Copy(const gbtRationalEditorRefData &p_other)
{
return wxSheetCellTextEditorRefData::Copy(p_other);
}
void gbtRationalEditorRefData::StartingKey(wxKeyEvent &event)
{
int keycode = event.GetKeyCode();
char tmpbuf[2];
tmpbuf[0] = (char) keycode;
tmpbuf[1] = '\0';
wxString strbuf(tmpbuf, *wxConvCurrent);
#if wxUSE_INTL
bool is_decimal_point =
(strbuf == wxLocale::GetInfo(wxLOCALE_DECIMAL_POINT, wxLOCALE_CAT_NUMBER));
#else
bool is_decimal_point = ( strbuf == _T(".") );
#endif
if (wxIsdigit(keycode) || keycode == '-' || is_decimal_point) {
wxSheetCellTextEditorRefData::StartingKey(event);
return;
}
event.Skip();
}
bool gbtRationalEditorRefData::IsAcceptedKey(wxKeyEvent &p_event)
{
if (wxSheetCellEditorRefData::IsAcceptedKey(p_event)) {
int keycode = p_event.GetKeyCode();
char tmpbuf[2];
tmpbuf[0] = (char) keycode;
tmpbuf[1] = '\0';
wxString strbuf(tmpbuf, *wxConvCurrent);
#if wxUSE_INTL
bool is_decimal_point =
(strbuf == wxLocale::GetInfo(wxLOCALE_DECIMAL_POINT,
wxLOCALE_CAT_NUMBER));
#else
bool is_decimal_point = ( strbuf == _T(".") );
#endif
if ((keycode < 128) &&
(wxIsdigit(keycode) || is_decimal_point || keycode == '-') )
return true;
}
return false;
}
syntax highlighted by Code2HTML, v. 0.9.1