locked
Passing Data to a WorkItemHandler Delegate

    Question

  • Hi Everyone,

    I am implementing thread handling in my C++ Metro app and I am unable to pass data (say a void*) to WorkItemHandler delegate function. This is native C++ so I have the following:

    class CThreadWin8 : public CThreadBase
    {
    public:
    	CThreadWin8();
    	
    	void CreateThread(int _Priority = PRIORITY_NORMAL);
    	void WaitForExit();
    	bool IsAlive();
    	static void Sleep(int _ms);
    
    	IAsyncAction^ m_threadPoolWorkItem;    
    };


    And the implementation of CreateThread as :

    public delegate void ThreadItemDelegate(IAsyncAction^ _operation);
    
    void ThreadItemFunc(IAsyncAction^ _operation)
    {
    
    }
    CThreadWin8::CThreadWin8()
    {
    }
    
    void CThreadWin8::CreateThread(int _Priority)
    {
    	auto pri = WorkItemPriority::Normal;
    	auto workItemHandler = ref new Windows::System::Threading::WorkItemHandler(ThreadItemFunc);
       
    	if (_Priority == PRIORITY_LOW)
    	{
    		pri = WorkItemPriority::Low;
    	}
    	else if (_Priority == PRIORITY_HIGH)
    	{
    		pri = WorkItemPriority::High;
    	}
    }

    My problem is that I cannot pass any data to a delegate declared to be a WorkItemHandler. And, unlike the ThreadPool sample I cannot create a delegate inside the CreateThread function because an actual function name must be used.

    ThreadItemFunc needs to access CThreadWin8's public members so I would like to be able to pass 'this' through to the handler. Is there a way to do this without having to make this class and its parent managed (ie public ref class)?

    Thanks Much!

    Tuesday, May 29, 2012 11:13 PM

Answers

All replies

  •  

    Hello,

     

    I think you can use create_async with a lambda function to create the IAsyncAction. So that you can binding the data within the lambda function.

    Like [i, &j] { return i + j; };

    Or [] (int x, int y) { return x + y; }(5, 4);

     

    Please take a look at

    Creating Asynchronous Operations in C++ for Metro style Apps

    http://msdn.microsoft.com/en-us/library/windows/apps/hh750082.aspx

    Lambda Expressions in C++

    http://msdn.microsoft.com/en-us/library/dd293608.aspx

     

    Best regards,

    Jesse


    Jesse Jiang [MSFT]
    MSDN Community Support | Feedback to us

    • Marked as answer by TheMCP Wednesday, May 30, 2012 4:04 PM
    Wednesday, May 30, 2012 8:15 AM
  • Use


    void ThreadItemFunc( params)
    {
    // code here
    }

    void CThreadWin8::CreateThread(int _Priority) {
    ThreadPool::RunAsync( ref new WorkItemHandler( [this](Windows::Foundation::IAsyncAction^ operation)

    {
      ThreadItemFunc( params_you_need);
    });

    }


    Wednesday, May 30, 2012 3:40 PM
  • Thanks!

    The links and answers proved to be very useful. A big reason I posted was because Intellisense in VS 11 reported that using a local delegate is an error. For example:

    auto workItemDelegate = [this](IAsyncAction^ _workItem)
    {
      OnThread();
    };
    
    auto workItemHandler = ref new Windows::System::Threading::WorkItemHandler(workItemDelegate);
        

    This is the solution I went with and on the last line 'workItemDelegate' is underlined red with the mouse-over error: "Error: invalid delegate initializer -- must be a function."

    Just FYI and thanks again!

    Wednesday, May 30, 2012 4:03 PM