|
Hey people!
Here's the problem: i have some code that draws a whole bunch of lines, nothing special, just the usual CDC::MoveTo, CDC::LineTo and CDC::DrawBezierTo calls. This works fine. But now the need arose to have these lines alphablended so the background they are drawn onto is visible. So i re-created the drawing code using Gdi+'s Graphics::DrawLine, Graphics::DrawBeziers specifying a Color with an alpha value for the pen that is used to draw the lines. The lines are all of the same color and have the same alpha but they can be really thick. And here comes the catch, of course, everywhere where the lines overlap they "draw over" each other creating a darker area on the picture which is not good. Any ideas how to avoid this?
I could try creating a bitmap, drawing the lines onto it, trying to render an alpha channel somehow and then alphablend this onto the original image but i wouldn't like to do this because it sounds a lot like wasting resources and not even sure how to render the alpha. Alternatively could try to fill the bitmap with a color dedicated for transparency, draw lines normally onto it and then blend it with a constant alpha + transparency. Still sounds ugly.
My second tought was to use BeginPath/EndPath/WidenPath to generate a path or region from the lines and then fill this blended onto the background but WidenPath for some reason produces holes in the lines.
Any ideas? Thanks in advance.
> The problem with computers is that they do what you tell them to do and not what you want them to do. <
> If it doesn't matter, it's antimatter.<
|
|
|
|
|
Code-o-mat wrote: I could try creating a bitmap, drawing the lines onto it, trying to render an
alpha channel somehow and then alphablend this onto the original image but i
wouldn't like to do this because it sounds a lot like wasting resources and not
even sure how to render the alpha.
I would use the bitmap method. Render your lines onto a white background and use AlphaBlend()[^] to render it onto your DC. In the BLENDFUNCTION structure (the last parameter to AlphaBlend) set BlendOp to AC_SRC_OVER and play with SourceConstantAlpha.
Independent ACN Business Owner- Check out the possibilities for your future!
- Financial independance
- Full time or Part time
- In more than 20 countries through North America, Europe, Asia and the Pacific
- Featuring the ACN IRIS 5000 video phone. See the person you are talking to.
Within you lies the power for good - Use it!
|
|
|
|
|
Thanks for your reply. What i ended up with was to use Gdiplus' GraphicsPath and its WidenPath (at the time i wrote the question i didn't realize Gdiplus had this too, i only knew about the GDI one). This one seems to work much better then the "simple" GDI implementation.
Once again, thanks for the reply.
> The problem with computers is that they do what you tell them to do and not what you want them to do. <
> If it doesn't matter, it's antimatter.<
|
|
|
|
|
Hi Developers,
I want to map the short cut keys like F1-F12 with some functionality. I have made entry in accelerator table for those keys with the respective menu IDs( which in turn mapped with the desired functions).
The problem i am facing is, it works only if any view is currently open/active, otherwise not.
Can anyone help me out.
Thanks.
Amrit Agrawal
Software Developer.
|
|
|
|
|
Function keys (or any keys) are only delivered to the Window that has the focus, that is the active window.
|
|
|
|
|
Have a look at RegisterHotKey[^].
Independent ACN Business Owner- Check out the possibilities for your future!
- Financial independance
- Full time or Part time
- In more than 20 countries through North America, Europe, Asia and the Pacific
- Featuring the ACN IRIS 5000 video phone. See the person you are talking to.
Within you lies the power for good - Use it!
|
|
|
|
|
Dear all,
I am facing a weird problem and I need your help. I have an MFC MDI application, and I am trying to create a WPF Window as a child of the opened CView.
I was able to successfully do that by handling the OnCreate message in my CView, and creating the WPF window. I also set the CView to be the parent of the WPF window so it behaves as its child.
Here is what I did:
int CMyView::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CView::OnCreate(lpCreateStruct) == -1)
return -1;
m_windowWrapper.Create(this->GetSafeHwnd());
return 0;
}
void CMyWindowWrapper::Create(HWND hParent)
{
m_myWindow = gcnew MyWindow();
m_myWindow->Show();
IntPtr^ hChildWnd = m_myWindow->GetHwnd();
::SetParent((HWND)hChildWnd->ToPointer(), hParent);
}
public partial class MyWindow : Window
{
public MyWindow()
{
InitializeComponent();
MouseLeftButtonDown += (o, e) => DragMove();
}
public IntPtr GetHwnd()
{
return (new System.Windows.Interop.WindowInteropHelper(this)).Handle;
}
}ndows.Interop.WindowInteropHelper(this)).Handle;
}
}
The WPF window appear as expected. Now the problem happens when I try to resize the WPF window. Suddenly the controls inside the window are streched and re-positioned as if the new size of the WPF window is the size of the parent CView! I tried to handle the SizeChanged event, and found that the NewSize was much larger than the size of the WPF window and was most probably the size of the containing CView.
I tried to remove the SetParent call, and the resizing worked correctly. I wonder what is going wrong in resizing and WPF window whose parent is a CView.
I uploaded a sample application illustrating the problem:
http://cid-a059807de2e23c43.office.live.com/self.aspx/.Public/ResizeProblem.zip
Please help me.
Thank you.
modified 6-Oct-11 10:01am.
|
|
|
|
|
I think you need to implement something in the WPF window analogous to what is described here[^].
I'm not versed in WPF.
You also might need to add ON_WM_SIZE() to your message map in the view class and then the following code:
void CMFCApplicationView::OnSize(UINT nType, int cx, int cy)
{
m_windowWrapper.OnSize(nType, cx, cy);
CView::OnSize(nType, cx, cy);
}
and the following code in MyWindowWrapper:
void CMyWindowWrapper::OnSize(UINT nType, int cx, int cy)
{
IntPtr^ hChildWnd = m_pMembers->m_myWindow->GetHwnd();
::SetWindowPos((HWND)hChildWnd->ToPointer(), 0, 0, 0, cx, cy, SWP_NOMOVE | SWP_ASYNCWINDOWPOS | SWP_NOZORDER);
}
Good luck!
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
Thank you Ahmed for your reply
I think the way you described makes the WPF window always having the size of the CView whenever the view gets resized. This is not what I am trying to do. My problem is that whenever I try to resize the WPF window, its controls suddenly get expanded and repositioned as if the new size of the WPF window is the size of the view!
This is really a strange problem. You can just run the sample application to see this behavior.
Please advise.
Thank you
|
|
|
|
|
Yes, I understood that. I have already downloaded and run your code and already saw the behavior of the "child wpf" when you resize the WPF embedded window.
You are correct that the code I posted will "maximize" the WPF window.
Like I said I think the answer is that you have to do something in WPF to make it work. Hence my posting with a link to the resizing WPF code.
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
Thank you again Ahmed
I read the article you sent me, and it seems they are trying to intercept the window messages so they can handle the Resizing event and not just the SizeChanged (to catch the message before the size is changed). I was able to do as the sample described, I just cannot find a workaround to fix my problem. I hope anyone can give me a hint.
Thank you for your time
|
|
|
|
|
here some info that might help you
WPF and Win32 Interoperation[^].
It has a section titled "Hosting WPF Content in a Microsoft Win32 Window". MFC is just a "light" wrapper around Win32.
And here's someone's blog about MFC and WPF Interop[^]
I found these by googling for wpf interop[^]
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
For years I've written
const Blah& b = GetMyBlah();
I was taught to read these right to left - ie a reference to a Blah which is const.
A colleague has pointed out that this is in fact incorrect as the const key word is left associative but most compilers allow it (gcc, intel, clang and VC in my case). So it should be written
Blah const& b = GetMyBlah();
When read right to left it's a reference to a const Blah - same thing.
He pointed me to the parashift c++ faq http://www.parashift.com/c++-faq-lite/[^] which was changed recently to put the const between the type and the reference.
Obviously pointers are different as both the pointer and the object pointed to (or both) can be const while a reference is always const.
modified 10-Oct-11 5:18am.
|
|
|
|
|
You're correct, both variants mean exactly the same thing. Whether you write const before or after the type is meaningless and just a matter of style - the latter variant may be a little clearer with respect to the rule of reading types right to left though.
If you wanted to express that your reference is const, then you could place const to the right of the reference operator, like this:
Blah const& b const = GetMyBlah();
However, as Herb Sutter points out (see point 13), this extra const is meaningless since references are always const. Therefore the extra const is usually omitted.
|
|
|
|
|
Good answer Stefan.
So I was trying out some stuff and I was surprised that the VC++ 2010 compiler gave me an error on the second of these saying that void GetBlah2(const Blah*) already has a body.
void GetBlah2(Blah const * blah) { }
void GetBlah2(Blah const * const blah) { }
Yet I am able to declare these variables with the expected meaning:
const Blah* blah1 = new Blah();
Blah const * const blah2 = new Blah();
Is this a bug in the compiler or is such a method (#2 above) disallowed by the C++ standard?
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
In the first function you passed a pointer, not a reference, and you passed that pointer by value. Passing a parameter of type X by value is the same as passing the same parameter as type const X - at least from the point of view of the caller - therefore the declaration of your second function is syntactically the same as the first (again, from the point of view of the caller). The compiler cannot disambiguate any calls to this function into one of the two versions, therefore it does not allow you to overload like that. Follow the link to GOTW I've posted above, IIRC that this was also covered there. In short, if you pass a parameter by value, you cannot overload it only by adding const to that type.
If you meant to pass your pointer by reference, do it this way (using underscore to highlight the change):
void GetBlah2(Blah const *& blah) { } void GetBlah2(Blah const * const blah) { }
This should work.
|
|
|
|
|
I see. Your reply makes sense. It's like trying to declare a const reference (Blah & const). It's redundant.
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
Not quite. In case of a reference there really is no difference as there is no such thing as a non-const reference. In your example however there would be a difference, but it would only be visible within the code of your function: there, if you defined the parameter const , you could not modify it (locally), whereas if you didn't define it const you could. Of course, since you pass it by value the caller wouldn't notice the difference, basically you gain an additional local variable by not declaring it const .
const Blah* GetBlah1(const Blah*& const b) {
b = 0; return b;
}
const Blah* GetBlah2(const Blah*& b) {
b = 0; return b;
}
const Blah* GetBlah3(const Blah* const b) {
b = 0; return b;
}
const Blah* GetBlah4(const Blah* b) {
b = 0; return b;
}
int main() {
Blah* a = new Blah;
Blah* b = GetBlah4(a); assert(b==0);
assert(a!=0);
delete a;
return 0;
}
|
|
|
|
|
I copied your code into VC++ 2010 and the first two errors do not occur.
Stefan_Lang wrote:
const Blah* GetBlah1(const Blah*& const b) {
b = 0;
return b;
}
const Blah* GetBlah2(const Blah*& b) {
b = 0;
return b;
}
Also, this line gets an error because you can't assign a const value to a non-const value:
Stefan_Lang wrote:
Blah* b = GetBlah4(a);
Anyway, thanks for your help. I understand I think.
If your actions inspire others to dream more, learn more, do more and become more, you are a leader." - John Quincy Adams You must accept one of two basic premises: Either we are alone in the universe, or we are not alone in the universe. And either way, the implications are staggering” - Wernher von Braun
|
|
|
|
|
Ah, my bad, you are right in all three cases: in the first functions the assignments don't change the reference, only the value they reference. So these examples were not valid for the purpose I wanted to demonstrate. Also, when I tried to compile GetBlah1() I got the warning warning C4227: anachronism used : qualifiers on reference are ignored. This leads me to believe that it is not actually possible to pass a parameter by const reference, and the rightmost const in the signature is ignored, therefore b is not const and may be modified. I wasn't aware of that restriction before.
The function call to GetBlah4() doesn't work because it tries to assign the (const) return value to a non-const variable. Add a const at the start of the line and it should work.
|
|
|
|
|
In the case of pointers, the following 2 lines are the same, where the contents cannot be changed while the pointer can be made to point to another object.
const Blah* p = GetMyBlahPtr();
Blah const* p = GetMyBlahPtr();
Whereas in the following line, the contents can be changed, but the pointer itself cannot be pointed to another object.
Blah* const p = GetMyBlahPtr();
|
|
|
|
|
I can do this in my code
PostMessage(WM_KEYDOWN);
The message gets properly intercepted, no problem.
I need to detect right arrow so I add wParam like this
PostMessage(WM_KEYDOWN,VK_RIGHT,0);
The message is nowhere to be found.
WindowProc does not even detects WM_KEYDOWN.
All this in MFC.
What am I missing?
Thanks for your help.
|
|
|
|
|
You may need to add some detail in your LPARAM variable as described here[^]. Also check the status returned from your PostMessage() call.
|
|
|
|
|
|
I have changed to SendMessage and get expected results.
Also adding GetLastError processing AFTER the PostMessage I get expected results.
Can anybody explain why is this happening?
Especialy when it works when only WM_KEYDOWN is used without the wParam.
The lParam should specify number of repeats of the keyboard, right arrow in my case and should be 0.
I am not using any other language, only US English.
|
|
|
|
|