I have two ScrollViewer's in my layout of windows phone app. I'm trying to synchronize both. i'm using VisualTreeHelper.GetChild to find HorizontalScrollBar and then setting ValueChanged event.
It happens that this event is not called whenever scrollviewer is scrolling, so the other scrollviewer scrolling is not smooth.
I had tried many solutions found in internet but it seems nothing is working for me.
Is there any event that i can subscribe in order to achieve this effect?
NOTE: the content of the first ScrollViewer is much longer than the second one.
Try listening to "mouseMove" event on the scrollviewer that you need to base your adjustment on.
this.MyScrollViewer.MouseMove += MyScrollViewer_MouseMove;
Handle the event in a method like this:
public void MyScrollViewer_MouseMove(object sender, System.Windows.Input.MouseEventArgs e)
{
// Write your manipulation here
}
Related
BTW I'm using UWP in case it matters.
So I am using a ListView and all ListViews have a ScrollViewer attached to them (in default template) by default. The problem is that I cannot find an event (on the ListView itself or on its ScrollViewer) that triggers when the ListView finishes scrolling.
I used the scrollViewer.ChangeView() method to automatically scroll to the beginning of the ListView and it uses an animation to scroll to the top, so I think that has something to do with it because the ViewChanged event fires before the animation completes. If I am correct about that then there would have to be a way to determine if the animation is complete because I need to be alerted when the ListView is completely idle again, which is only when the scroll animation completes. Thanks.
You can wire up the scrollViewer's ViewChanged event, and check the IsIntermediate of the event argument.
private void ScrollViewer_ViewChanged(object sender, ScrollViewerViewChangedEventArgs e)
{
if (e.IsIntermediate)
{
System.Diagnostics.Debug.WriteLine("scroll ongoing");
}
else
{
System.Diagnostics.Debug.WriteLine("scroll finish");
}
}
This event is fired multiple times. When the scroll finishes, IsIntermediate is false.
This need to be Windows Forms (winforms) - not WPF. Problem is with single MouseDown event that didn't fire properly on touchscreen on windows 8. MouseDown fire either after touch and move finger or after click - it fire just after you get off your finger. I want to fire it like a normal MouseDown should - after i touch the screen. The solution to that would be that TouchDown event. But, i just cant to handle that event. What I do is that I create class Multitouch like that:
class Moultitouch : UIElement
{
public Moultitouch()
{
this.TouchDown += new EventHandler<System.Windows.Input.TouchEventArgs>(Moultitouch_TouchDown);
}
void Moultitouch_TouchDown(object sender, System.Windows.Input.TouchEventArgs e)
{
//it never goes in
}
protected override void OnTouchDown(System.Windows.Input.TouchEventArgs e)
{
base.OnTouchDown(e);
}
}
After that I'm declaring that class in my component which on Touch should handle that event. I did a lot of research on that and 've been trying to do that and nothing so far. I think that "Hosting a WPF Composite Control in Windows Forms" http://msdn.microsoft.com/en-us/library/ms742215.aspx could solve my problem but that solution could be really long and tough. Any help or ideas are really appreciated.
Your issue is that touchscreen fired events and mouse fired events are not the same thing. For example a Winform button can toggle its background colour by handling OnMouseEnter and OnMouseLeave. Code that up on a form and run the cursor in and out of the button and everything works fine. Use a touch screen and run your finger over it in the same way and nothing happens until you release contact with the screen, and then a click event is raised. Not the answer you are looking for, but I am having the same issue with an on-screen keyboard I'm developing for a disabled friend of mine. My research led me here https://blogs.windows.com/buildingapps/2017/05/25/uwp-evolution-touch-development/#02octDx0X3uBHXqm.97 and specifically to the links that provide detail on the ManipulationStarted and ManipulationEnded events. Hope that helps, it has for what I'm trying to achieve.
I have two FlowLayoutPanels on a form: PanelA and PanelB. Each will be populated at run-time with multiple controls, such that the panel will scroll (i.e AutoScroll is true).
Here's the issue: The controls that the panels are populated with each contain a ComboBox. Thus, MouseWheel events are consumed by the combo box instead of by the panel. I want MouseWheel events to be consumed by the panel.
If there's no scrollable control on the child controls, then the MouseWheel event skips the child control (which doesn't handle it) and hits the panel, which does handle it. How can I set my child control's combo box to ignore the MouseWheel event? Can I tell it to re-raise the event?
I tried just applying Focus to the Parent whenever one of the child controls ticks the 'MouseEnter' event; this fixed the scrolling issues, but also left the child controls completely un-editable.
Something else I've found from digging around involves fiddling with the Windows API directly, but I find it hard to believe that something like that is required for this.
I tested the following code and it seems like a solution to your issue. Basically you need to focus the 'FlowLayoutPanel' when you click on it, or your mouse enters it:
private void newCheckListQuestionPanel_Click(object sender, EventArgs e)
{
newCheckListQuestionPanel.Focus(); //allows the mouse wheel to work after the panel is clicked
}
private void newCheckListQuestionPanel_MouseEnter(object sender, EventArgs e)
{
newCheckListQuestionPanel.Focus(); //allows the mouse wheel to work after the panel has had the mouse move over it
}
Source
How to capture mouse wheel on panel in C#?
I'm using WinForms
EDIT:
I try to do it on PictureBox now.
My code:
this.pictureBox1.MouseClick += new System.Windows.Forms.MouseEventHandler(this.pictureBox1_MouseClick);
this.pictureBox1.MouseWheel += new System.Windows.Forms.MouseEventHandler(this.pictureBox1_MouseClick);
private void pictureBox1_MouseClick(object sender, MouseEventArgs e)
{
MessageBox.Show("Click");
}
Clicking works. Wheelling doesn't.
Why?
If you can't see the "MouseWheel" event on a component, then you need to create it manually. Also, we need to focus that component, otherwise the "MouseWheel" event will not work for that component. I will show you how to create a "MouseWheel" event for "pictureBox1" and how it works.
INSIDE THE CONSTRUCTOR, create a mousewheel event on that component.
InitializeComponent();
this.pictureBox1.MouseWheel += pictureBox1_MouseWheel;
CREATE THE FUNCTION manually. According to my example, call it "pictureBox1_MouseWheel"
private void pictureBox1_MouseWheel(object sender, MouseEventArgs e)
{
//you can do anything here
}
CREATE a MouseHover event on that component (Go to properties in PicureBox1, select event, locate "MouseHover" and double-click the "MouseHover" event).
CALL "Focus()"; method inside that MouseHover event.
pictureBox1.Focus();
Now run the program.
Windows sends the WM_MOUSEWHEEL message to the control that has the focus. That won't be Panel, it is not a control that can get the focus. As soon as you put a control on the panel, say a button, then the button gets the focus and the message.
The button however has no use for the message, it's got nothing to scroll. Windows notices this and sends the message to the parent. That's the panel, now it will scroll.
You'll find code for a custom panel that can get the focus in this answer.
UPDATE: note that this behavior has changed in Windows 10. The new "Scroll inactive windows when I hover over them" option is turned on by default. The makes the mouse wheel behavior more consistent with the way it works in a browser or, say, an Office program. In this specific case the picturebox now will get the event. Watch out for this.
To wire it up manually...
this.panel1.MouseWheel += new System.Windows.Forms.MouseEventHandler(this.panel1_MouseWheel);
private void panel1_MouseWheel(object sender, System.Windows.Forms.MouseEventArgs e)
{
///process mouse event
}
Easier method is in visual studio click on panel, goto properties viewpanel, select events, locate and double click the "mousewheel" event.
In Winforms, this is achieved using the Control.MouseWheel event
Getting mousewheel events is tricky. The easiest way is using
this.MouseWheel += new System.Windows.Forms.MouseEventHandler(this.panel1_MouseWheel);
instead of
this.panel1.MouseWheel += new System.Windows.Forms.MouseEventHandler(this.panel1_MouseWheel);
This way the form gets the event instead of control. This way is easy but has one problem: you can use only one mousewheel event in your form.
If you have more than one control to get mousewheel event the best way is This answer by "Shehan Silva - weltZ"
I'm making a custom control with a panel. I want to be able to drag and drop it so I've implemented that in the MouseDown event of my control. But I want the thing to react when you start drag to give a little feedback to the user. So in the MouseDown even I change the color. Then I want to change it back in the MouseUp event.
My control is not installed into VS2008 but just a class I've written that I instanciate at run time (I don't know in advance how many I need and so on). Now, my control exposes a MouseDown event so as to be able to be dragged. When I subscribe to this event from the parent application to actually perform the drag and drop my control is not repainted on its MouseUp event! In fact, the MouseUp is never invoked. If, on the other hand, I don't subscribe to the event in the parent app it works as intended.
What's going on? Is the parent interrupting the flow so that the MouseUp event never fires in my control? How do I get around this?
I'm not sure if you are using Windows Forms or WPF, but in Windows forms here is what I mean:
public class DerivedPanel : Panel
{
protected override void OnMouseDown(MouseEventArgs e)
{
base.OnMouseDown(e);
Capture = true;
}
protected override void OnMouseUp(MouseEventArgs e)
{
base.OnMouseUp(e);
Capture = false;
// Change your color or whatever here
}
}
In WPF there are two methods, CaptureMouse() and ReleaseMouseCapture() to do the same thing. When the control captures the mouse, it will received mouse events even if the cursor isn't over the control. This could be causing your problem. See MSDN Article
Do you capture the mouse in the custom control on the mousedown event? Try capturing on the mousedown and releasing the capture on the mouseup.