Use a backgroud image for a dialog

If you are using the main C++ distribution of wxWidgets, Feel free to ask any question related to wxWidgets development here. This means questions regarding to C++ and wxWidgets, not compile problems.
Post Reply
voyage
In need of some credit
In need of some credit
Posts: 8
Joined: Fri Aug 31, 2018 1:58 pm

Use a backgroud image for a dialog

Post by voyage » Mon Mar 25, 2019 10:33 am

I want to add a background image on a dialog and then put buttons on the image. I have followed the example at this link https://wiki.wxwidgets.org/An_image_panel
and I have written the following code:

Code: Select all

class wxImagePanel : public wxPanel
{
    wxImage image;
    wxBitmap resized;

public:
    wxImagePanel(wxDialog* parent, wxString file, wxBitmapType format);

    void paintEvent(wxPaintEvent & evt);

    DECLARE_EVENT_TABLE()
};


class Prova_wxwidgetsDialog: public wxDialog
{
    public:

        Prova_wxwidgetsDialog(wxWindow* parent,wxWindowID id = -1);
        virtual ~Prova_wxwidgetsDialog();
        wxImagePanel *ImagePanel;

    private:

        DECLARE_EVENT_TABLE()
};

BEGIN_EVENT_TABLE(wxImagePanel, wxPanel)
// catch paint events
EVT_PAINT(wxImagePanel::paintEvent)
END_EVENT_TABLE()


wxImagePanel::wxImagePanel(wxDialog* parent, wxString file, wxBitmapType format) : wxPanel(parent)
{
    image.LoadFile(file, format);
   resized = wxBitmap( image.Scale(352,544, wxIMAGE_QUALITY_HIGH ) );
}

void wxImagePanel::paintEvent(wxPaintEvent & evt)
{
    wxPaintDC dc(this);
    dc.DrawBitmap( resized, 100, 100, false );
}

BEGIN_EVENT_TABLE(Prova_wxwidgetsDialog,wxDialog)
END_EVENT_TABLE()

Prova_wxwidgetsDialog::Prova_wxwidgetsDialog(wxWindow* parent,wxWindowID id)
{
    Create(parent, wxID_ANY, _("wxWidgets app"), wxDefaultPosition, wxDefaultSize, wxRESIZE_BORDER|wxCLOSE_BOX|wxMAXIMIZE_BOX|wxMINIMIZE_BOX, _T("wxID_ANY"));
    SetClientSize(wxSize(488,432));
    ImagePanel = new wxImagePanel( this, wxT("campoverticale.jpg"), wxBITMAP_TYPE_JPEG);
}

Every time that I add a button on the dialog the background image disappears.
Is this the correct way to use a backgroud image for the dialog? What have I missed?
Thank you

Kvaz1r
Filthy Rich wx Solver
Filthy Rich wx Solver
Posts: 216
Joined: Tue Jun 07, 2016 1:07 pm

Re: Use a backgroud image for a dialog

Post by Kvaz1r » Mon Mar 25, 2019 11:15 am

You need to handle wxPaintEvent for your dialog. If I missed something in your question it would be better provide MCVE for reproducing the behaviour.

voyage
In need of some credit
In need of some credit
Posts: 8
Joined: Fri Aug 31, 2018 1:58 pm

Re: Use a backgroud image for a dialog

Post by voyage » Mon Mar 25, 2019 12:45 pm

I'm not sure to have undestood correctly.

This is the code with a button added but the image disappeared:

Code: Select all

//(*Headers(Prova_wxwidgetsDialog)
#include <wx/button.h>
#include <wx/dialog.h>
//*)

#include <wx/wx.h>
#include <wx/sizer.h>

class wxImagePanel : public wxPanel
    {
    wxImage image;
    wxBitmap resized;
    public:
        wxImagePanel(wxDialog* parent, wxString file, wxBitmapType format);

        void paintEvent(wxPaintEvent & evt);

        DECLARE_EVENT_TABLE()
    };


class Prova_wxwidgetsDialog: public wxDialog
{
    public:

        Prova_wxwidgetsDialog(wxWindow* parent,wxWindowID id = -1);
        virtual ~Prova_wxwidgetsDialog();
         wxImagePanel *ImagePanel;
    private:

        //(*Handlers(Prova_wxwidgetsDialog)
        void OnPaint(wxPaintEvent& event);
        //*)

        //(*Identifiers(Prova_wxwidgetsDialog)
        static const long ID_BUTTON1;
        //*)

        //(*Declarations(Prova_wxwidgetsDialog)
        wxButton* Button1;
        //*)

        DECLARE_EVENT_TABLE()
};

#include <wx/msgdlg.h>
#include <wx/textdlg.h>
#include <wx/numdlg.h>
//(*InternalHeaders(Prova_wxwidgetsDialog)
#include <wx/intl.h>
#include <wx/string.h>
//*)

BEGIN_EVENT_TABLE(wxImagePanel, wxPanel)
// catch paint events
EVT_PAINT(wxImagePanel::paintEvent)

END_EVENT_TABLE()


wxImagePanel::wxImagePanel(wxDialog* parent, wxString file, wxBitmapType format) :wxPanel(parent)
{
   image.LoadFile(file, format);
   resized = wxBitmap( image.Scale(352,544, wxIMAGE_QUALITY_HIGH) );
}

void wxImagePanel::paintEvent(wxPaintEvent & evt)
{
    wxPaintDC dc(this);
    dc.DrawBitmap(resized, 100, 100, false);
}


//(*IdInit(Prova_wxwidgetsDialog)
const long Prova_wxwidgetsDialog::ID_BUTTON1 = wxNewId();
//*)

BEGIN_EVENT_TABLE(Prova_wxwidgetsDialog,wxDialog)
    //(*EventTable(Prova_wxwidgetsDialog)
    //*)
END_EVENT_TABLE()

Prova_wxwidgetsDialog::Prova_wxwidgetsDialog(wxWindow* parent,wxWindowID id)
{
    //(*Initialize(Prova_wxwidgetsDialog)
    Create(parent, wxID_ANY, _("wxWidgets app"), wxDefaultPosition, wxDefaultSize, wxRESIZE_BORDER|wxCLOSE_BOX|wxMAXIMIZE_BOX|wxMINIMIZE_BOX, _T("wxID_ANY"));
    Button1 = new wxButton(this, ID_BUTTON1, _("Label"), wxPoint(72,64), wxSize(100,20), 0, wxDefaultValidator, _T("ID_BUTTON1"));

    Connect(wxEVT_PAINT,(wxObjectEventFunction)&Prova_wxwidgetsDialog::OnPaint);
    //*)
   ImagePanel = new wxImagePanel(this, wxT("campoverticale.jpg"), wxBITMAP_TYPE_JPEG);
}

Prova_wxwidgetsDialog::~Prova_wxwidgetsDialog()
{
    //(*Destroy(Prova_wxwidgetsDialog)
    //*)
}

void Prova_wxwidgetsDialog::OnPaint(wxPaintEvent& event)
{
   ImagePanel->paintEvent(event);
}

#include <wx/app.h>

class Prova_wxwidgetsApp : public wxApp
{
    public:
        virtual bool OnInit();
};

#include <wx/image.h>

IMPLEMENT_APP(Prova_wxwidgetsApp);

bool Prova_wxwidgetsApp::OnInit()
{
    //(*AppInitialize
    bool wxsOK = true;
    wxInitAllImageHandlers();
    if ( wxsOK )
    {
    	Prova_wxwidgetsDialog Dlg(0);
    	SetTopWindow(&Dlg);
    	Dlg.ShowModal();
    	wxsOK = false;
    }
    //*)
    return wxsOK;

}



Kvaz1r
Filthy Rich wx Solver
Filthy Rich wx Solver
Posts: 216
Joined: Tue Jun 07, 2016 1:07 pm

Re: Use a backgroud image for a dialog

Post by Kvaz1r » Mon Mar 25, 2019 4:24 pm

Remove wxImagePanel and move all painting to your dialog or use panel as dialog (I'm not sure about this, but guess it's also possible).

But, what exactly do you want to achieve? Maybe here XY problem.

voyage
In need of some credit
In need of some credit
Posts: 8
Joined: Fri Aug 31, 2018 1:58 pm

Re: Use a backgroud image for a dialog

Post by voyage » Mon Mar 25, 2019 7:13 pm

Thank you, I have solved putting all the code of the ImagePanel in the dialog. I thought there was some reasons to use a panel. I'm sorry for the newbie question

User avatar
doublemax
Moderator
Moderator
Posts: 14961
Joined: Fri Apr 21, 2006 8:03 pm
Location: $FCE2

Re: Use a backgroud image for a dialog

Post by doublemax » Mon Mar 25, 2019 9:02 pm

voyage wrote:
Mon Mar 25, 2019 7:13 pm
Thank you, I have solved putting all the code of the ImagePanel in the dialog. I thought there was some reasons to use a panel. I'm sorry for the newbie question
Using a wxPanel would have been better.

Code: Select all

void Prova_wxwidgetsDialog::OnPaint(wxPaintEvent& event)
{
   ImagePanel->paintEvent(event);
}
You can't do that. In a paint event handler, you can only draw onto the window that generated the event.

Another option would have been wxCustomBackgroundWindow:
https://docs.wxwidgets.org/trunk/classw ... indow.html
Use the source, Luke!

ONEEYEMAN
Part Of The Furniture
Part Of The Furniture
Posts: 4240
Joined: Sat Apr 16, 2005 7:22 am
Location: USA, Ukraine

Re: Use a backgroud image for a dialog

Post by ONEEYEMAN » Tue Mar 26, 2019 6:47 pm

Hi,
Using wxPanel gives you TAB handling for free.

Thank you.

Post Reply