// headers
// ----------------------------------------------------------------------------
-#if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
- #pragma implementation "grid.h"
-#endif
-
// For compilers that support precompilatixon, includes "wx/wx.h".
#include "wx/wxprec.h"
#include "wx/combobox.h"
#include "wx/valtext.h"
#include "wx/intl.h"
+ #include "wx/math.h"
#endif
#include "wx/textfile.h"
class wxGridCellEditorEvtHandler : public wxEvtHandler
{
public:
- wxGridCellEditorEvtHandler()
- : m_grid(0), m_editor(0)
- { }
wxGridCellEditorEvtHandler(wxGrid* grid, wxGridCellEditor* editor)
- : m_grid(grid), m_editor(editor)
- { }
+ : m_grid(grid),
+ m_editor(editor),
+ m_inSetFocus(false)
+ {
+ }
+ void OnKillFocus(wxFocusEvent& event);
void OnKeyDown(wxKeyEvent& event);
void OnChar(wxKeyEvent& event);
+ void SetInSetFocus(bool inSetFocus) { m_inSetFocus = inSetFocus; }
+
private:
wxGrid* m_grid;
wxGridCellEditor* m_editor;
- DECLARE_DYNAMIC_CLASS(wxGridCellEditorEvtHandler)
+
+ // Work around the fact that a focus kill event can be sent to
+ // a combobox within a set focus event.
+ bool m_inSetFocus;
+
DECLARE_EVENT_TABLE()
+ DECLARE_DYNAMIC_CLASS(wxGridCellEditorEvtHandler)
DECLARE_NO_COPY_CLASS(wxGridCellEditorEvtHandler)
};
-IMPLEMENT_DYNAMIC_CLASS( wxGridCellEditorEvtHandler, wxEvtHandler )
+IMPLEMENT_ABSTRACT_CLASS(wxGridCellEditorEvtHandler, wxEvtHandler)
+
BEGIN_EVENT_TABLE( wxGridCellEditorEvtHandler, wxEvtHandler )
+ EVT_KILL_FOCUS( wxGridCellEditorEvtHandler::OnKillFocus )
EVT_KEY_DOWN( wxGridCellEditorEvtHandler::OnKeyDown )
EVT_CHAR( wxGridCellEditorEvtHandler::OnChar )
END_EVENT_TABLE()
// through in that case.
if ((ctrl || alt) && !(ctrl && alt))
return false;
-
+
#if wxUSE_UNICODE
int key = event.GetUnicodeKey();
bool keyOk = true;
return keyOk;
#else // !wxUSE_UNICODE
int key = event.GetKeyCode();
- if (key <= 255)
+ if (key <= 255)
return true;
return false;
#endif // wxUSE_UNICODE/!wxUSE_UNICODE
wxTextCtrl* tc = Text();
wxChar ch;
long pos;
-
+
#if wxUSE_UNICODE
ch = event.GetUnicodeKey();
if (ch <= 127)
void wxGridCellNumberEditor::StartingKey(wxKeyEvent& event)
{
+ int keycode = event.GetKeyCode();
if ( !HasRange() )
{
- int keycode = event.GetKeyCode();
if ( wxIsdigit(keycode) || keycode == '+' || keycode == '-')
{
wxGridCellTextEditor::StartingKey(event);
return;
}
}
-
+#if wxUSE_SPINCTRL
+ else
+ {
+ if ( wxIsdigit(keycode) )
+ {
+ wxSpinCtrl* spin = (wxSpinCtrl*)m_control;
+ spin->SetValue(keycode - '0');
+ spin->SetSelection(1,1);
+ return;
+ }
+ }
+#endif
event.Skip();
}
double value = 0.0;
wxString text(Text()->GetValue());
- if ( (text.empty() || text.ToDouble(&value)) && (value != m_valueOld) )
+ if ( (text.empty() || text.ToDouble(&value)) &&
+ !wxIsSameDouble(value, m_valueOld) )
{
if (grid->GetTable()->CanSetValueAs(row, col, wxGRID_VALUE_FLOAT))
grid->GetTable()->SetValueAsDouble(row, col, value);
tmpbuf[0] = (char) keycode;
tmpbuf[1] = '\0';
wxString strbuf(tmpbuf, *wxConvCurrent);
-#if wxUSE_INTL
+#if wxUSE_INTL
bool is_decimal_point = ( strbuf ==
wxLocale::GetInfo(wxLOCALE_DECIMAL_POINT, wxLOCALE_CAT_NUMBER) );
#else
tmpbuf[0] = (char) keycode;
tmpbuf[1] = '\0';
wxString strbuf(tmpbuf, *wxConvCurrent);
-#if wxUSE_INTL
+#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) &&
+ if ( (keycode < 128) &&
(wxIsdigit(keycode) || tolower(keycode) == 'e' ||
is_decimal_point || keycode == '+' || keycode == '-') )
return true;
case WXK_SPACE:
CBox()->SetValue(!CBox()->GetValue());
break;
-
+
case '+':
CBox()->SetValue(true);
break;
-
+
case '-':
CBox()->SetValue(false);
break;
wxASSERT_MSG(m_control,
wxT("The wxGridCellEditor must be Created first!"));
+ wxGridCellEditorEvtHandler* evtHandler = NULL;
+ if (m_control)
+ evtHandler = wxDynamicCast(m_control->GetEventHandler(), wxGridCellEditorEvtHandler);
+
+ // Don't immediately end if we get a kill focus event within BeginEdit
+ if (evtHandler)
+ evtHandler->SetInSetFocus(true);
+
m_startValue = grid->GetTable()->GetValue(row, col);
if (m_allowOthers)
{
// find the right position, or default to the first if not found
int pos = Combo()->FindString(m_startValue);
- if (pos == -1)
+ if (pos == wxNOT_FOUND)
pos = 0;
Combo()->SetSelection(pos);
}
Combo()->SetInsertionPointEnd();
Combo()->SetFocus();
+
+ if (evtHandler)
+ evtHandler->SetInSetFocus(false);
}
bool wxGridCellChoiceEditor::EndEdit(int row, int col,
// wxGridCellEditorEvtHandler
// ----------------------------------------------------------------------------
+void wxGridCellEditorEvtHandler::OnKillFocus(wxFocusEvent& event)
+{
+ // Don't disable the cell if we're just starting to edit it
+ if (m_inSetFocus)
+ return;
+
+ // accept changes
+ m_grid->DisableCellEditControl();
+
+ event.Skip();
+}
+
void wxGridCellEditorEvtHandler::OnKeyDown(wxKeyEvent& event)
{
switch ( event.GetKeyCode() )
// wxGridCellStringRenderer
// ----------------------------------------------------------------------------
-void wxGridCellStringRenderer::SetTextColoursAndFont(wxGrid& grid,
- wxGridCellAttr& attr,
+void wxGridCellStringRenderer::SetTextColoursAndFont(const wxGrid& grid,
+ const wxGridCellAttr& attr,
wxDC& dc,
bool isSelected)
{
dc.SetFont( attr.GetFont() );
}
-wxSize wxGridCellStringRenderer::DoGetBestSize(wxGridCellAttr& attr,
+wxSize wxGridCellStringRenderer::DoGetBestSize(const wxGridCellAttr& attr,
wxDC& dc,
const wxString& text)
{
// wxGridCellNumberRenderer
// ----------------------------------------------------------------------------
-wxString wxGridCellNumberRenderer::GetString(wxGrid& grid, int row, int col)
+wxString wxGridCellNumberRenderer::GetString(const wxGrid& grid, int row, int col)
{
wxGridTableBase *table = grid.GetTable();
wxString text;
return renderer;
}
-wxString wxGridCellFloatRenderer::GetString(wxGrid& grid, int row, int col)
+wxString wxGridCellFloatRenderer::GetString(const wxGrid& grid, int row, int col)
{
wxGridTableBase *table = grid.GetTable();
{
wxLogDebug(_T("Invalid wxGridCellFloatRenderer width parameter string '%s ignored"), params.c_str());
}
-
}
- tmp = params.AfterFirst(_T(','));
- if ( !tmp.empty() )
- {
- long precision;
+ tmp = params.AfterFirst(_T(','));
+ if ( !tmp.empty() )
+ {
+ long precision;
if ( tmp.ToLong(&precision) )
- {
+ {
SetPrecision((int)precision);
- }
- else
- {
+ }
+ else
+ {
wxLogDebug(_T("Invalid wxGridCellFloatRenderer precision parameter string '%s ignored"), params.c_str());
- }
-
+ }
}
}
}
mergefrom->GetAlignment( &hAlign, &vAlign);
SetAlignment(hAlign, vAlign);
}
-
- mergefrom->GetSize( &m_sizeRows, &m_sizeCols );
+ if ( !HasSize() && mergefrom->HasSize() )
+ mergefrom->GetSize( &m_sizeRows, &m_sizeCols );
// Directly access member functions as GetRender/Editor don't just return
// m_renderer/m_editor
return (wxGridCellAttr *)NULL;
}
+
void wxGridTableBase::SetAttr(wxGridCellAttr* attr, int row, int col)
{
if ( m_attrProvider )
int client_width = 0;
GetClientSize( &client_width, &client_height );
-#if __WXGTK__
+ // VZ: any reason for this ifdef? (FIXME)
+#ifdef __WXGTK__
wxRect rect;
rect.SetX( 1 );
rect.SetY( 1 );
rect.SetHeight( client_height - 2 );
wxRendererNative::Get().DrawHeaderButton( this, dc, rect, 0 );
-#else
+#else // !__WXGTK__
dc.SetPen( wxPen(wxSystemSettings::GetColour(wxSYS_COLOUR_3DDKSHADOW),1, wxSOLID) );
dc.DrawLine( client_width-1, client_height-1, client_width-1, 0 );
dc.DrawLine( client_width-1, client_height-1, 0, client_height-1 );
dc.SetPen( *wxWHITE_PEN );
dc.DrawLine( 1, 1, client_width-1, 1 );
dc.DrawLine( 1, 1, 1, client_height-1 );
-#endif
+#endif // __WXGTK__/!__WXGTK__
}
void wxGridWindow::OnMouseEvent( wxMouseEvent& event )
{
+ if (event.ButtonDown(wxMOUSE_BTN_LEFT) && FindFocus() != this)
+ SetFocus();
+
m_owner->ProcessGridCellMouseEvent( event );
}
break;
case WXGRID_CURSOR_SELECT_ROW:
+ {
if ( (row = YToRow( y )) >= 0 )
{
if ( m_selection )
event.MetaDown() );
}
}
+ }
+ break;
// default label to suppress warnings about "enumeration value
// 'xxx' not handled in switch
break;
case WXGRID_CURSOR_SELECT_COL:
+ {
if ( (col = XToCol( x )) >= 0 )
{
if ( m_selection )
event.MetaDown() );
}
}
+ }
+ break;
// default label to suppress warnings about "enumeration value
// 'xxx' not handled in switch
int topRow = internalYToRow(top);
int rightCol = internalXToCol(right);
int bottomRow = internalYToRow(bottom);
- wxRegion clippedcells(0, 0, cw, ch);
+#ifndef __WXMAC__
+ // CS: I don't know why suddenly unscrolled coordinates are used for clipping
+ wxRegion clippedcells(0, 0, cw, ch);
int i, j, cell_rows, cell_cols;
wxRect rect;
}
}
}
+#else
+ wxRegion clippedcells( left , top, right - left, bottom - top);
+
+ int i, j, cell_rows, cell_cols;
+ wxRect rect;
+
+ for (j=topRow; j<bottomRow; j++)
+ {
+ for (i=leftCol; i<rightCol; i++)
+ {
+ GetCellSize( j, i, &cell_rows, &cell_cols );
+ if ((cell_rows > 1) || (cell_cols > 1))
+ {
+ rect = CellToRect(j,i);
+ clippedcells.Subtract(rect);
+ }
+ else if ((cell_rows < 0) || (cell_cols < 0))
+ {
+ rect = CellToRect(j+cell_rows, i+cell_cols);
+ clippedcells.Subtract(rect);
+ }
+ }
+ }
+#endif
dc.SetClippingRegion( clippedcells );
dc.SetPen( wxPen(GetGridLineColour(), 1, wxSOLID) );
void wxGrid::DrawRowLabel( wxDC& dc, int row )
{
- if ( GetRowHeight(row) <= 0 )
+ if ( GetRowHeight(row) <= 0 || m_rowLabelWidth <= 0 )
return;
wxRect rect;
-#ifdef __WXGTK__
+#ifdef __WXGTK20__
rect.SetX( 1 );
rect.SetY( GetRowTop(row) + 1 );
rect.SetWidth( m_rowLabelWidth - 2 );
void wxGrid::DrawColLabel( wxDC& dc, int col )
{
- if ( GetColWidth(col) <= 0 )
+ if ( GetColWidth(col) <= 0 || m_colLabelHeight <= 0 )
return;
int colLeft = GetColLeft(col);
wxRect rect;
-#ifdef __WXGTK__
+#ifdef __WXGTK20__
rect.SetX( colLeft + 1 );
rect.SetY( 1 );
rect.SetWidth( GetColWidth(col) - 2 );
}
-void wxGrid::GetTextBoxSize( wxDC& dc,
+void wxGrid::GetTextBoxSize( const wxDC& dc,
const wxArrayString& lines,
long *width, long *height )
{
editor->Show( false );
editor->DecRef();
attr->DecRef();
+
m_gridWin->SetFocus();
+
// refresh whole row to the right
wxRect rect( CellToRect(row, col) );
CalcScrolledPosition(rect.x, rect.y, &rect.x, &rect.y );
if ( height<0 )
return;
m_minAcceptableRowHeight = height;
-};
+}
int wxGrid::GetColMinimalAcceptableWidth() const
{