• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 506
  • Last Modified:

CPropertySheet - Update CListCtrl on inactive page

Hi,

I have an application which has three tabs. Each tab has a CListCtrl and when the application is started, I want to insert some items into those listboxes.  The problem I am having is that I get debug assertion errors because if I try to insert an item into a listbox located on a sheet that is not active, the hwnd pointer is NULL.  

I can think of two ways of getting around this.  One is to set the page as active everytime an item is inserted into the listbox.  This is not the way I would like to do this because I do not want the application to switch pages by itself all the time.  The second way would be to check of the page is active and if not, store the item to insert into a list.  When the page gets activated, the list would be emptied into the list box.  

I was wondering if there is any other way I can do this.

Your help is greatly appreciated.

Cheers
0
StanChart
Asked:
StanChart
  • 3
  • 2
2 Solutions
 
nonubikCommented:
>I was wondering if there is any other way I can do this.

What you should do is to initialize your listboxes in the OnInitDialog method of each of your CPropertyPages. This method is called only once when the dialog is about to be shown for the first time.

> I try to insert an item into a listbox located on a sheet that is not active, the hwnd pointer is NULL.
This is because the property page (not sheet, the sheet is the object that holds the pages/tabs) was not created yet (i.e. OnInitDialog has not been called for that page). After that, your HWND will not be NULL even if the page is inactive.
0
 
rcarlanCommented:
The easiest way to initialise all pages when the property sheet is displayed is to derive your own class from CPropertySheet and override OnInitDialog. Call the base first, then cycle through all pages and set them active:


BOOL CMyPropertySheet::OnInitDialog()
{
    CPropertySheet::OnInitDialog();

    for (int i=0; i<GetPageCount(); ++i)
        SetActivePage(i);
    SetActivePage(0);

    return TRUE;
}

If you see any flicker (normally you shouldn't, but it depends what OnInitDialog does for each page), you can hide the property sheet just before you start cycling, and show it again after you're finished (i.e. just before returning).

Radu
0
 
StanChartAuthor Commented:
Hi,

Thanks for your reply.  

Here is what I am currently doing.  I derived my class from CPropertySheet and use AddPage(&myPages) to add three pages to the property sheet.  Page 1 and Page 2 have the list controls I want to update.  If I add items to the list boxes in the OnInit override, I do not get the null hwnd.  

The application I am writing is a server.  Everytime I receive a request, I want to update the list controls (might be on either page 1 or page 2 depending on the request received by the server).  The problem I have now is that I have my request handler in a separate class (created and stored inside the dialog) which has a pointer to the property sheet.  The property sheet has methods to return a pointer to each page.  Therefore when I want to update a list control after I process the request, I do something like this inside my request handler:  

m_pDialog->GetPage1()->AddRequestLog("User Logging In");
or
m_pDialog->GetPage2()->AddServerLog("Stored user login event");

The methods AddRequestLog and AddServerLog look something like this:

*****************************************
// Add the server log to the list box.
m_ctrlServerLog.InsertItem(0, logDateTime.Format("%d-%b-%y %H:%M:%S"));
m_ctrlServerLog.SetItemData(0, 0);
m_ctrlServerLog.SetItemText(0, SL_LOG_COLUMN, log);
UpdateData(FALSE);
return TRUE;
*****************************************

The only way this works is if I set the page active before I update the list box.  I do this when the GetPage1() or GetPage2() methods are called.

Is there something I am doing wrong here?

Thanks again for your help.

Cheers
0
What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

 
StanChartAuthor Commented:
>What you should do is to initialize your listboxes in the OnInitDialog method of each of your CPropertyPages. This method is called only once when the dialog is about to be shown for the first time.

This is how I initialize the list controls on my property page's OnInit method which works.

m_ctrlServerLog.InsertColumn(SL_LOGDATETIME_COLUMN, _T("Log Date/Time"), LVCFMT_LEFT, 105);
m_ctrlServerLog.InsertColumn(SL_LOG_COLUMN, _T("Log Details"), LVCFMT_LEFT, 600);
m_ctrlServerLog.SendMessage(LVM_SETEXTENDEDLISTVIEWSTYLE, 0, LVS_EX_FULLROWSELECT|LVS_EX_GRIDLINES);

Cheers
0
 
nonubikCommented:
If you want to do any operations on a child control (the listbox here) before OnInitDialog of its parent (the property page) has been called you'll fail because the children do not have a window.

So, in the AddRequestLog method you could check the listbox whether it has a valid handle. If yes, do as before. If not, store the data you want to insert in the list in some member variables and then you will fill the list with this data in OnInitDialog. Something like:

*****************************************
// Add the server log to the list box.
if(m_ctrlServerLog.m_hWnd)
{
  m_ctrlServerLog.InsertItem(0, logDateTime.Format("%d-%b-%y %H:%M:%S"));
  m_ctrlServerLog.SetItemData(0, 0);
  m_ctrlServerLog.SetItemText(0, SL_LOG_COLUMN, log);
  UpdateData(FALSE);
}
else
{
  m_strSomeData = logDateTime.Format("%d-%b-%y %H:%M:%S");
...
}
return TRUE;
*****************************************

OnInitDialog
{
...
  if(m_strSomeData != "")
  {
    m_ctrlServerLog.InsertItem(0, m_strSomeData);
    m_ctrlServerLog.SetItemData(0, 0);
    m_ctrlServerLog.SetItemText(0, SL_LOG_COLUMN, log);
  }
}
0
 
StanChartAuthor Commented:
Thanks much!
0

Featured Post

[Webinar] Cloud and Mobile-First Strategy

Maybe you’ve fully adopted the cloud since the beginning. Or maybe you started with on-prem resources but are pursuing a “cloud and mobile first” strategy. Getting to that end state has its challenges. Discover how to build out a 100% cloud and mobile IT strategy in this webinar.

  • 3
  • 2
Tackle projects and never again get stuck behind a technical roadblock.
Join Now