I'm developing a project in WPF using a Myo arm band which works so far in recognizing the device has connected and updates info to the textbox, but when I set up the event handler for recognizing if a pose is triggered the event never fires.
I debugged this by making poses with the device and holding them, also I set a break point on this line pose.Triggered += Pose_Triggered; and the start of the pose triggered event.
The break point triggers on the first line where the but it doesn't trigger the breakpoint on the actual event private void Pose_Triggered(object sender, PoseEventArgs e)
This is the C# wrapper I'm using for the project: https://github.com/tayfuzun/MyoSharp
Does anyone know why the event doesn't trigger although the poses are being made?
This is the method where pose_triggered is called and the event:
// listen for when the Myo connects
hub.MyoConnected += (sender, e) =>
{
this.Dispatcher.Invoke((Action)(() =>
{
statusTbx.Text = "Myo has connected! " + e.Myo.Handle;
e.Myo.Vibrate(VibrationType.Short);
// unlock the Myo so that it doesn't keep locking between our poses
e.Myo.Unlock(UnlockType.Hold);
// setup for the pose we want to watch for
var pose = HeldPose.Create(e.Myo, Pose.Fist);
pose.Triggered += Pose_Triggered;
e.Myo.OrientationDataAcquired += Myo_OrientationDataAcquired;
}));
};
Code for triggered event:
private void Pose_Triggered(object sender, PoseEventArgs e)
{
App.Current.Dispatcher.Invoke((Action)(() =>
{
//need to measure abduction of arm from 0 to 180 degrees.
poseStatusTbx.Text = "{0} arm Myo holding pose {1}" + e.Myo.Arm + e.Myo.Pose;
pitch = pitchCentre;
}));
}
Here is the complete code for the class: http://hastebin.com/xinirugufo.cs
I compare the sample code from GitHub and your. Did you forget to call pose.Start()?
var pose = HeldPose.Create(e.Myo, Pose.Fist);
pose.Interval = TimeSpan.FromSeconds(0.5);
pose.Start(); //this???
pose.Triggered += Pose_Triggered;
Related
Im trying to make a program that can scan for BLE advertisements. I have been looking at the Windows-universal-samples, more precisely the sample called BluetoothAdvertisement. I want to make a simple UWP application that can scan for BLE advertisements and show them in a listbox. But my application can't find anything at all and I'm totally lost.
namespace BleDiscAdv2
{
public sealed partial class MainPage : Page
{
// The Bluetooth LE advertisement watcher class is used to control and customize Bluetooth LE scanning.
private BluetoothLEAdvertisementWatcher watcher;
public MainPage()
{
this.InitializeComponent();
// Create and initialize a new watcher instance.
watcher = new BluetoothLEAdvertisementWatcher();
//Set the in-range threshold to -70dBm. This means advertisements with RSSI >= -70dBm
//will start to be considered "in-range"
watcher.SignalStrengthFilter.InRangeThresholdInDBm = -70;
// Set the out-of-range threshold to -75dBm (give some buffer). Used in conjunction with OutOfRangeTimeout
// to determine when an advertisement is no longer considered "in-range"
watcher.SignalStrengthFilter.OutOfRangeThresholdInDBm = -75;
// Set the out-of-range timeout to be 2 seconds. Used in conjunction with OutOfRangeThresholdInDBm
// to determine when an advertisement is no longer considered "in-range"
watcher.SignalStrengthFilter.OutOfRangeTimeout = TimeSpan.FromMilliseconds(2000);
}
protected override void OnNavigatedTo(NavigationEventArgs e)
{
// Attach a handler to process the received advertisement.
// The watcher cannot be started without a Received handler attached
watcher.Received += OnAdvertisementReceived;
}
private void btStart_Click(object sender, RoutedEventArgs e)
{
watcher.Start();
}
private async void OnAdvertisementReceived(BluetoothLEAdvertisementWatcher watcher, BluetoothLEAdvertisementReceivedEventArgs eventArgs)
{
DateTimeOffset timestamp = eventArgs.Timestamp;
string localName = eventArgs.Advertisement.LocalName;
await this.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
{
lbModtaget.Items.Add("Name of device: " + localName + "\t" + "Time for advertisement: " + timestamp.ToString("hh\\:mm\\:ss\\.fff"));
});
}
}
}
Can someone tell me what is wrong?
I'm new to BLE and I haven't been coding for a while.
Best regards
Christian
But my application can't find anything at all and I'm totally lost.
Please ensure that your app has enable Bluetooth capability in the Package.appxmanifest. See Basic Setup for details.
Please ensure the Bluetooth radio of running device was turn on and available.
There're devices are advertising and meet the filter. You can run the Scenario 2 of the Bluetooth advertisement official sample on another device to ensure that.
By testing on my side, your code snippet can scan the BLE advertisements well. In your code snippet, you didn't listen to the Stopped event handle of the watcher which is for notification to the app that the Bluetooth LE scanning for advertisements has been cancelled or aborted either by the app or due to an error. If the watcher is force stopped it will not get any advertisements.
You can add the Stopped event handle to check if there is a BluetoothError.
protected override void OnNavigatedTo(NavigationEventArgs e)
{
// Attach a handler to process the received advertisement.
// The watcher cannot be started without a Received handler attached
watcher.Received += OnAdvertisementReceived;
watcher.Stopped += OnAdvertisementWatcherStopped;
}
private async void OnAdvertisementWatcherStopped(BluetoothLEAdvertisementWatcher sender, BluetoothLEAdvertisementWatcherStoppedEventArgs args)
{
await this.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () =>
{
txtresult.Text = string.Format("Watcher stopped or aborted: {0}", args.Error.ToString());
});
}
For example, RadioNotAvailable may be caused by the running device is not enable the Bluetooth, OtherError may be caused by Bluetooth capability doesn't enabled. If the watcher is not stopped and there're advertisements, your app should work.
I'm in the early stages of writing a program to interface with an IP camera. A bit of code I wrote yesterday worked, but when I came back to it this morning it didn't. I know, I probably did something, but to the best of my memory it worked when I clicked debug before leaving and didn't when I clicked debug when I came in. I even left my computer on with VS running overnight (which I almost never do, and I have restarted since) so I could it and all my internet tabs as I left them. The computer was locked, so unless some very resourceful individual decided to mess with me, nothing changed overnight.
I'm using websocket-sharp, and when I connect to the websocket (which does seem to happen successfully), the OnOpen event isn't raised.
The bit where websocket-sharp raises the event is in the following lines.
private void open ()
{
_inMessage = true;
startReceiving ();
try {
OnOpen.Emit (this, EventArgs.Empty);
}
catch (Exception ex) {
_logger.Error (ex.ToString ());
error ("An error has occurred during the OnOpen event.", ex);
}
It reaches the OnOpen.Emit, and doesn't throw the exception, so it seems to think it's raising the event. Event is seen below
public event EventHandler OnOpen;
It does not seem to reach this line as when I put a breakpoint there it isn't paused. I've never used the .Emit way of raising events before, and not finding much in research, so maybe somethings is going wrong there?
My code is below.
public Form1()
{
InitializeComponent();
this.Shown += MainWindow_Loaded;
}
void MainWindow_Loaded(object sender, EventArgs e)
{
using (var ws = new WebSocket("ws://169.254.101.183"))
{
ws.OnMessage += (sender2, e2) =>
textBox1.Text = e2.Data.ToString();
ws.Connect();
ws.OnOpen += (sender2,e2) =>
textBox1.Text = "connected";
/*ws.OnError += (sender2, e2) =>
textBox1.Text = e2.Message;*/
//textBox1.Text = ".";
}
}
Is there any obvious reason that OnOpen.Emit should not actually raise the OnOpen event?
In your case the real reason is this line
using (var ws = new WebSocket("ws://169.254.101.183"))
When your block ends 'ws' object becomes disposed including your event handler. After some delay you have response from WebSocket, but handler already destroyed.
In the MainWindow_Loaded method are you calling Connect before you subscribe to the OnOpen event.
If you subscribe to the event before calling Connect then the textBox1.Text should be set to "connected" after a successful connection.
here's what I've done in my universal windows app:
public MainPage()
{
InitializeComponent();
private LockApplicationHost lol=LockApplicationHost.GetForCurrentView();
}
private async void Lol_Unlocking(LockApplicationHost sender, LockScreenUnlockingEventArgs args)
{
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
{
alarm.Pause();
Status.Text = "lolwtf";
});
}
I'm trying to know when the user unlocks his computer.
EDIT: also the error I keep getting is:
Delegate to an instance method cannot have null 'this'. and it highlights:
lol.Unlocking += Lol_Unlocking;
I'm trying to know when the user unlocks his computer.
You can hookup a SessionSwitchEventHandler. Obviously your application will need to be running. SessionSwitchEventHandler delegate, you identify the method that will handle the event. To associate the event with your event handler, add an instance of the delegate to the event.
Microsoft.Win32.SystemEvents.SessionSwitch += new Microsoft.Win32.SessionSwitchEventHandler(SystemEvents_SessionSwitch);
void SystemEvents_SessionSwitch(object sender, Microsoft.Win32.SessionSwitchEventArgs e)
{
if (e.Reason == SessionSwitchReason.SessionLock)
{
//I left my desk
}
else if (e.Reason == SessionSwitchReason.SessionUnlock)
{
//I returned to my desk
}
}
You can have a look on the SessionSwitchReason Enumeration to find more about the uses the SessionSwitchReason class to represent the type of a session switch event.
lol.Unlocking += Lol_Unlocking;
should be lol.Unlocking += Lol_Unlocking(EventHandler_Unlocking); and EventHandler_Unlocking has to be defined in the program.
my understanding for LockApplicationHost.Unlocking is that it helps to unlock and lock the device whereas to determine if the device is unlocked and unlocked SessionSwitchEventHandler will be better approach. For more understanding on the LockApplicationHost.Unlocking check this
I am developing a WinRT app. One of the requirements is that the app should have a "timed logout" feature.
What this means is that on any screen, if the app has been idle for 10 mins, the app should logout and navigate back to the home screen.
The brute force way of doing this obviously would be to hook up pointer pressed events on every grid of every page and resetting the timer if any of these events is fired but I was wondering if there was a more elegant and more reliable way of doing this.
Thanks,
Rajeev
With the use of DispatcherTimer & several events you can achieve that.
DispatcherTimer Timer;
private void InitializeTimer()
{
Dispatcher.AcceleratorKeyActivated += Dispatcher_AcceleratorKeyActivated;
Window.Current.CoreWindow.PointerMoved += CoreWindow_PointerMoved;
Window.Current.CoreWindow.PointerPressed += CoreWindow_PointerPressed;
Timer = new DispatcherTimer();
Timer.Interval = TimeSpan.FromMinutes(10);
Timer.Tick += Timer_Tick;
Timer.Start();
}
private void CoreWindow_PointerPressed(CoreWindow sender, PointerEventArgs args)
{
Timer.Start();
}
private void CoreWindow_PointerMoved(CoreWindow sender, PointerEventArgs args)
{
Timer.Start();
}
private void Dispatcher_AcceleratorKeyActivated(CoreDispatcher sender, AcceleratorKeyEventArgs args)
{
Timer.Start();
}
private void Timer_Tick(object sender, object e)
{
Timer.Stop();
//TODO: Do logout.
}
I'm not aware of anything built in, but rather than attaching to Grids and etc., I'd suggest you attach event handlers to the current CoreWindow (documentation) for the various types of events that you would need to track to determine idleness.
If you did attach to a Grid for example, you'd find controls that use Popup won't trigger the events. A ComboBox for example wouldn't be tracked by the event handlers.
For example, you might do this:
var core = CoreWindow.GetForCurrentThread();
core.KeyDown += (sender, kdArgs) => {
// reset timeout
};
core.PointerMoved = core.PointerMoved = (sender, pmArgs) {
// reset timeout (maybe with a bit of logic to prevent tiny mouse drift from
// causing false positives
};
// etc. (whatever else makes sense)
The code relies on the GetForCurrentThread call (documentation) which returns the instance of the CoreWindow that is the host for all content.
I'd like to use loop while left mousebutton is pressed:
private void Loop_MouseDown(object sender, MouseEventArgs e)
{
while (e.Button==MouseButtons.Left)
{
//Loop
}
}
I can't use solution from this thread:
C# how to loop while mouse button is held down
because I'm sending via RS232 data and using timer with it's own interval doesn't work. Also any solution from this topic doesn't work for me.
It can't also work one like here:
if (e.Button == MouseButtons.Left)
{
//loop
}
This solution also doesn't work:
bool isLooping = false;
//on mouse down
private void myControl_MouseUp(object sender, System.Windows.Forms.MouseEventArgs e) {
isLooping = true;
runLoop();
}
//on mouse up event
private void myControl_MouseUp(object sender, System.Windows.Forms.MouseEventArgs e) {
isLooping = false;
}
//This is the main loop you care about. Put this in your application
//This should go in its own thread
void runLoop() {
while (isLooping) {
//do stuff
}
}
because calling runLoop would block the thread, and so the MouseUp event would never fire.
So how to make it work correctly?
Use a BackGroundWorker. Perfect for your problem.
Put the loop function in the worker and start / stop the worker on mouse events.
If using a timer won't work, you'll need to send the data on a different thread, and signal that thread from the MouseUp handler.
The correct way to do this would be to put the rs-232 send function into a separate thread so the UI will remain responsive, then you can start and stop it when the mouse events change.
This page might be useful:
http://www.yoda.arachsys.com/csharp/threads/winforms.shtml
These scenarios are very complicated to implement - see your handlers and boolean variables for storing the state.
I would suggest to use Reactive Extensions.
Edit:
It will probably be slightly over-engineered (I don't know if this is the only scenario Elfoc wants to implement). In Rx you can create observable sequence of events
var mouseDown = Observable.FromEvent<MouseButtonEventArgs>(source, "MouseDown");
var mouseUp = Observable.FromEvent<MouseButtonEventArgs>(image, "MouseUp");
var mouseMove = from evt in Observable.FromEvent<MouseEventArgs>(image, "MouseMove")
select evt.EventArgs.GetPosition(this);
use LINQ-to-Rx to query and filter the events
var leftMouseDown = from evt in mouseDown
where evt.LeftButton == MouseButtonState.Pressed
select evt;
and compose it using Rx operators - until any mouse up event is raised take all the positions while left mouse is down
var q = from position in leftMouseDown
from pos in mouseMove.Until(mouseUp)
select new { X = pos.X - imageOffset.X, Y = pos.Y - imageOffset.Y };
Finally, subscribe to the observable sequence of positions and do your stuff
q.Subsribe(value => { ... });
Slightly modified from the code here.