2017-03-27 36 views
0

我開發與窗10 IOT芯覆盆子PI的脈衝計數器(遊戲幣計數器),並且我需要計數具有25毫秒這樣的間隔時間的脈衝:如何計算脈衝輸入間隔時間?

0,05€ - 1脈衝 0,10€ - 2脈衝 0,20€ - 4個脈衝 0,50€ - 10脈衝 1€ - 20個脈衝 2€ - 40個脈衝

像這樣的圖像:pulses

我當間隔時間爲dif時,需要打印脈衝數(以便插入值)不用25毫秒。

我有這樣的代碼:

public MainPage() 
    { 
     this.InitializeComponent(); 
     InitGPIO(); 
    } 

    private void InitGPIO() 
    { 
     var gpio = GpioController.GetDefault(); 

     if (gpio == null) 
     { 
      GpioStatus.Text = "There is no GPIO controller on this device."; 
     } 

     coinPin = gpio.OpenPin(coin_Pin); 

     if (coinPin.IsDriveModeSupported(GpioPinDriveMode.InputPullUp)) 
     { 
      coinPin.SetDriveMode(GpioPinDriveMode.InputPullUp); 
     } else 
     { 
      coinPin.SetDriveMode(GpioPinDriveMode.Input); 
     } 

     coinPin.DebounceTimeout = TimeSpan.FromMilliseconds(25); 

     coinPin.ValueChanged += coinPin_ValueChanged; 

     GpioStatus.Text = "GPIO pins initialized correctly."; 
    } 

    private void coinPin_ValueChanged(GpioPin sender, GpioPinValueChangedEventArgs e) 
    { 
     if (e.Edge == GpioPinEdge.FallingEdge) 
     { 
      counter++; 
     } 

     var task = Dispatcher.RunAsync(CoreDispatcherPriority.Normal,() => 
     { 
      if (e.Edge == GpioPinEdge.FallingEdge) 
      { 
       //counter++; 
       var time = PulseIn(coinPin, e.Edge); 
       value = (counter * 5); 
       value100 = value/100; 
       //money.Text = "Eur: " + (decimal)value100 + " €"; 

       if (time != 25) 
       { 
        money.Text = "Eur: " + (decimal)value100 + " €"; 
        GpioStatus.Text = "" + time; 
       } else 
       { 
        GpioStatus.IsEnabled = false; 
       } 
       //GpioStatus.Text = "" + time + ""; 
      } else 
      { 
       ///GpioStatus.Text = "" + coinPin.DebounceTimeout; 
      } 


     }); 
    } 

    private double PulseIn(GpioPin pin, GpioPinEdge edge) 
    { 
     var sw = new Stopwatch(); 

     while (edge.Equals(GpioPinEdge.RisingEdge)) 
     { 
      //sw.Start(); 
     } 

     sw.Start(); 

     if (!edge.Equals(GpioPinEdge.RisingEdge)) 
     { 
      //sw.Stop(); 
     } 

     sw.Stop(); 

     return sw.Elapsed.TotalMilliseconds; 
    } 


    private const int coin_Pin = 24; 
    private int counter = 0; 
    private double value = 0; 
    private double value100 = 0; 
    private GpioPin coinPin; 

你能幫助我嗎? 非常感謝。

回答

0

從您的代碼,

sw.Start(); 

    if (!edge.Equals(GpioPinEdge.RisingEdge)) 
    { 
     //sw.Stop(); 
    } 

    sw.Stop(); 

實際測量if語句的執行時間sw.Start()sw.Stop()之間。這根本不符合邏輯。當下降沿到達時記錄下watch.Elapsed.TotalMilliseconds,並重新啓動秒錶以測量脈衝間隔時間。爲此,我在counter++下添加以下兩條代碼行,刪除var time = PulseIn(coinPin, e.Edge),並在GpioStatus.Text = "" + timeinterval中使用timeinterval

  timeinterval = watch.Elapsed.TotalMilliseconds; 
      watch.Restart(); 

下面是完整的代碼塊:

private Stopwatch watch = new Stopwatch(); 
    private void coinPin_ValueChanged(GpioPin sender, GpioPinValueChangedEventArgs e) 
    { 
     double timeinterval = 0; 
     if (e.Edge == GpioPinEdge.FallingEdge) 
     { 
      counter++; 
      timeinterval = watch.Elapsed.TotalMilliseconds; 
      watch.Restart(); 
     } 

     var task = Dispatcher.RunAsync(CoreDispatcherPriority.Normal,() => 
     { 
      if (e.Edge == GpioPinEdge.FallingEdge) 
      { 
       //var time = PulseIn(coinPin, e.Edge); 
       value = (counter * 5); 
       value100 = value/100; 

       if (timeinterval != 25) 
       { 
        money.Text = "Eur: " + (decimal)value100 + " €"; 
        GpioStatus.Text = "" + timeinterval; 
       } 
       //... 
      } 
     }); 
    } 

你可以試試上面的代碼塊,看它是否符合您的精度要求。

注意:由於軟件抖動總是不可預測,所以不適合在軟件級別測量硬件脈衝間隔。

+0

我已經用2個硬幣的示例輸入(0,2€和0,05€)更新了這個問題,結果應該是0,20€和0,25€,現在顯示「0,05 0,1 0,15 0,20 0,25「...我只需要顯示總價值。 – rmntavares

+0

您如何輸入0,2€?它沒有四個脈衝嗎? –