wxWidgets/samples/docvwmdi/view.cpp
Julian Smart b9f933ab5d Applied patch [ 597398 ] Generic MDI, wxNotebook based.
By Hans Van Leemputten (hansvl)

- This patch implements a generic notebook based mdi,
due to that wxMDIChildFrame could not derive from
wxFrame some things in the samples and in the docmdi
classes needed to be adjusted... basically this comes
down to not do (wxFrame *) but instead do
(wxMDIChildFrame *), or store a pointer to the frame in a
wxWindow* instead of a wxFrame variable...

- The main reason wxMDIChildFrame cannot derive from
wxFrame is that it would take to much platform specific
functions to be overwritten (= lot of ifdef's). This then
couldn't be called generic anymore, so that's why we
need to derive from wxPanel...

- Tested on/with:
1. wxMSW (I disabled the MSW MDI implementation to
be able to test it), tested it with the MDI sample,
docvwmdi sample and docview sample and also tested it
with wxWorkshop. (test = compile and run)
2. wxX11, tested with the same set wxWin samples as
the wxMSW test. I also compiled wxWorkshop with it,
but could not run wxWorkshop due to some issue not
related to the MDI implementation.

- How to apply:
* Apply the patch
* move mdig.cpp into wxWindows/src/generic/
* move mdig.h into wxWindows/include/wx/generic/

- Some extra things that still need to be done:
* File lists, project files should be updated to include
mdig.cpp (the patch only change this on wxX11)
* The configuration script should be updated.
* Maybe wxUSE_GENERIC_MDI_ARCHITECTURE also
should be added so it is only included when wanted...




git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@16610 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
2002-08-20 09:09:55 +00:00

266 lines
5.8 KiB
C++

/////////////////////////////////////////////////////////////////////////////
// Name: view.cpp
// Purpose: View classes
// Author: Julian Smart
// Modified by:
// Created: 04/01/98
// RCS-ID: $Id$
// Copyright: (c) Julian Smart and Markus Holzem
// Licence: wxWindows license
/////////////////////////////////////////////////////////////////////////////
#ifdef __GNUG__
// #pragma implementation
#endif
// For compilers that support precompilation, includes "wx/wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/wx.h"
#endif
#if !wxUSE_DOC_VIEW_ARCHITECTURE
#error You must set wxUSE_DOC_VIEW_ARCHITECTURE to 1 in setup.h!
#endif
#include "docview.h"
#include "doc.h"
#include "view.h"
IMPLEMENT_DYNAMIC_CLASS(DrawingView, wxView)
// For drawing lines in a canvas
float xpos = -1;
float ypos = -1;
BEGIN_EVENT_TABLE(DrawingView, wxView)
EVT_MENU(DOODLE_CUT, DrawingView::OnCut)
END_EVENT_TABLE()
// What to do when a view is created. Creates actual
// windows for displaying the view.
bool DrawingView::OnCreate(wxDocument *doc, long WXUNUSED(flags) )
{
frame = wxGetApp().CreateChildFrame(doc, this, TRUE);
frame->SetTitle("DrawingView");
canvas = GetMainFrame()->CreateCanvas(this, frame);
#ifdef __X__
// X seems to require a forced resize
int x, y;
frame->GetSize(&x, &y);
frame->SetSize(-1, -1, x, y);
#endif
frame->Show(TRUE);
Activate(TRUE);
return TRUE;
}
// Sneakily gets used for default print/preview
// as well as drawing on the screen.
void DrawingView::OnDraw(wxDC *dc)
{
dc->SetFont(*wxNORMAL_FONT);
dc->SetPen(*wxBLACK_PEN);
wxNode *node = ((DrawingDocument *)GetDocument())->GetDoodleSegments().First();
while (node)
{
DoodleSegment *seg = (DoodleSegment *)node->Data();
seg->Draw(dc);
node = node->Next();
}
}
void DrawingView::OnUpdate(wxView *WXUNUSED(sender), wxObject *WXUNUSED(hint))
{
if (canvas)
canvas->Refresh();
/* Is the following necessary?
#ifdef __WXMSW__
if (canvas)
canvas->Refresh();
#else
if (canvas)
{
wxClientDC dc(canvas);
dc.Clear();
OnDraw(& dc);
}
#endif
*/
}
// Clean up windows used for displaying the view.
bool DrawingView::OnClose(bool deleteWindow)
{
if (!GetDocument()->Close())
return FALSE;
// Clear the canvas in case we're in single-window mode,
// and the canvas stays.
canvas->Clear();
canvas->view = (wxView *) NULL;
canvas = (MyCanvas *) NULL;
wxString s(wxTheApp->GetAppName());
if (frame)
frame->SetTitle(s);
SetFrame((wxFrame*)NULL);
Activate(FALSE);
if (deleteWindow)
{
delete frame;
return TRUE;
}
return TRUE;
}
void DrawingView::OnCut(wxCommandEvent& WXUNUSED(event) )
{
DrawingDocument *doc = (DrawingDocument *)GetDocument();
doc->GetCommandProcessor()->Submit(new DrawingCommand((const wxString) "Cut Last Segment", DOODLE_CUT, doc, (DoodleSegment *) NULL));
}
IMPLEMENT_DYNAMIC_CLASS(TextEditView, wxView)
bool TextEditView::OnCreate(wxDocument *doc, long WXUNUSED(flags) )
{
frame = wxGetApp().CreateChildFrame(doc, this, FALSE);
int width, height;
frame->GetClientSize(&width, &height);
textsw = new MyTextWindow(this, frame, wxPoint(0, 0), wxSize(width, height), wxTE_MULTILINE);
frame->SetTitle("TextEditView");
#ifdef __X__
// X seems to require a forced resize
int x, y;
frame->GetSize(&x, &y);
frame->SetSize(-1, -1, x, y);
#endif
frame->Show(TRUE);
Activate(TRUE);
return TRUE;
}
// Handled by wxTextWindow
void TextEditView::OnDraw(wxDC *WXUNUSED(dc) )
{
}
void TextEditView::OnUpdate(wxView *WXUNUSED(sender), wxObject *WXUNUSED(hint) )
{
}
bool TextEditView::OnClose(bool deleteWindow)
{
if (!GetDocument()->Close())
return FALSE;
Activate(FALSE);
if (deleteWindow)
{
delete frame;
return TRUE;
}
return TRUE;
}
/*
* Window implementations
*/
BEGIN_EVENT_TABLE(MyCanvas, wxScrolledWindow)
EVT_MOUSE_EVENTS(MyCanvas::OnMouseEvent)
END_EVENT_TABLE()
// Define a constructor for my canvas
MyCanvas::MyCanvas(wxView *v, wxMDIChildFrame *frame, const wxPoint& pos, const wxSize& size, long style):
wxScrolledWindow(frame, -1, pos, size, style)
{
view = v;
}
// Define the repainting behaviour
void MyCanvas::OnDraw(wxDC& dc)
{
if (view)
view->OnDraw(& dc);
}
// This implements a tiny doodling program. Drag the mouse using
// the left button.
void MyCanvas::OnMouseEvent(wxMouseEvent& event)
{
if (!view)
return;
static DoodleSegment *currentSegment = (DoodleSegment *) NULL;
wxClientDC dc(this);
PrepareDC(dc);
dc.SetPen(*wxBLACK_PEN);
wxPoint pt(event.GetLogicalPosition(dc));
if (currentSegment && event.LeftUp())
{
if (currentSegment->lines.Number() == 0)
{
delete currentSegment;
currentSegment = (DoodleSegment *) NULL;
}
else
{
// We've got a valid segment on mouse left up, so store it.
DrawingDocument *doc = (DrawingDocument *)view->GetDocument();
doc->GetCommandProcessor()->Submit(new DrawingCommand("Add Segment", DOODLE_ADD, doc, currentSegment));
view->GetDocument()->Modify(TRUE);
currentSegment = (DoodleSegment *) NULL;
}
}
if (xpos > -1 && ypos > -1 && event.Dragging())
{
if (!currentSegment)
currentSegment = new DoodleSegment;
DoodleLine *newLine = new DoodleLine;
newLine->x1 = (long)xpos;
newLine->y1 = (long)ypos;
newLine->x2 = pt.x;
newLine->y2 = pt.y;
currentSegment->lines.Append(newLine);
dc.DrawLine( (long)xpos, (long)ypos, pt.x, pt.y);
}
xpos = pt.x;
ypos = pt.y;
}
// Define a constructor for my text subwindow
MyTextWindow::MyTextWindow(wxView *v, wxMDIChildFrame *frame, const wxPoint& pos, const wxSize& size, long style):
wxTextCtrl(frame, -1, "", pos, size, style)
{
view = v;
}