Got it working!
This commit is contained in:
121
somewhat_working_dht22.go.inactive
Normal file
121
somewhat_working_dht22.go.inactive
Normal file
@@ -0,0 +1,121 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"github.com/warthog618/gpio"
|
||||
"math"
|
||||
"strconv"
|
||||
"time"
|
||||
)
|
||||
|
||||
const Timeout = math.MaxInt32
|
||||
const TimeoutErrInitial string = "timed out waiting for sensor's initial %s reading"
|
||||
|
||||
var oneSecondInCycles = (func() int {
|
||||
result := cyclesInAMillisecond()
|
||||
for i := 0; i < 100; i++ {
|
||||
result += cyclesInAMillisecond()
|
||||
}
|
||||
return result / 100
|
||||
})()
|
||||
|
||||
func cyclesInAMillisecond() int {
|
||||
count := 0
|
||||
start := time.Now().UnixNano()
|
||||
for {
|
||||
count++
|
||||
if time.Now().UnixNano() - start >= 1000000 {
|
||||
break
|
||||
}
|
||||
}
|
||||
return count
|
||||
}
|
||||
|
||||
func main() {
|
||||
err := gpio.Open()
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
defer gpio.Close()
|
||||
|
||||
pin := gpio.NewPin(gpio.GPIO4)
|
||||
dhtData, err := readDataFromDHT(pin)
|
||||
if err != nil {
|
||||
fmt.Println(fmt.Sprintf("Bad read! Reason: %s!", err.Error()))
|
||||
} else {
|
||||
fmt.Println(
|
||||
strconv.FormatInt(int64(dhtData[0]), 2),
|
||||
strconv.FormatInt(int64(dhtData[1]), 2),
|
||||
strconv.FormatInt(int64(dhtData[2]), 2),
|
||||
strconv.FormatInt(int64(dhtData[3]), 2),
|
||||
strconv.FormatInt(int64(dhtData[4]), 2))
|
||||
fmt.Println(convertToRhAndTemp(dhtData))
|
||||
}
|
||||
}
|
||||
|
||||
func sendStartSignal(pin *gpio.Pin) {
|
||||
pin.PullUp()
|
||||
time.Sleep(time.Millisecond)
|
||||
pin.Output()
|
||||
pin.Low()
|
||||
time.Sleep(1100 * time.Microsecond)
|
||||
pin.PullUp()
|
||||
pin.Input()
|
||||
time.Sleep(55 * time.Microsecond)
|
||||
}
|
||||
|
||||
func readDataFromDHT(pin *gpio.Pin) ([5]byte, error) {
|
||||
cycles := [80]int{}
|
||||
sendStartSignal(pin)
|
||||
if cyclesForReading(pin, gpio.Low) == Timeout {
|
||||
return [5]byte{}, errors.New(fmt.Sprintf(TimeoutErrInitial, "low"))
|
||||
}
|
||||
if cyclesForReading(pin, gpio.High) == Timeout {
|
||||
return [5]byte{}, errors.New(fmt.Sprintf(TimeoutErrInitial, "high"))
|
||||
}
|
||||
for i := 0; i < 80; i += 2 {
|
||||
cycles[i] = cyclesForReading(pin, gpio.Low)
|
||||
cycles[i + 1] = cyclesForReading(pin, gpio.High)
|
||||
}
|
||||
receivedInput, err := storeCycleCountsAsBinarySequence(&cycles)
|
||||
if err != nil {
|
||||
return [5]byte{}, err
|
||||
}
|
||||
return receivedInput, nil
|
||||
}
|
||||
|
||||
func cyclesForReading(pin *gpio.Pin, level gpio.Level) int {
|
||||
count := 0
|
||||
for pin.Read() == level {
|
||||
count++
|
||||
if count >= oneSecondInCycles {
|
||||
return Timeout
|
||||
}
|
||||
}
|
||||
return count
|
||||
}
|
||||
|
||||
func storeCycleCountsAsBinarySequence(cycles *[80]int) ([5]byte, error) {
|
||||
data := [5]byte{}
|
||||
for i := 0; i < 40; i++ {
|
||||
lowCycles := cycles[2 * i]
|
||||
highCycles := cycles[2 * i + 1]
|
||||
fmt.Println(lowCycles, highCycles)
|
||||
if (lowCycles == Timeout) || (highCycles == Timeout) {
|
||||
//return [5]byte{}, errors.New("timed out waiting for sensor pulse")
|
||||
}
|
||||
data[i / 8] <<= 1
|
||||
if highCycles > lowCycles {
|
||||
data[i / 8] |= 1
|
||||
}
|
||||
}
|
||||
return data, nil
|
||||
}
|
||||
|
||||
func convertToRhAndTemp(data [5]byte) (float32, float32) {
|
||||
rh := float32(int(data[0]) << 8) + float32(data[1])
|
||||
temp := float32(int(data[2]) << 8) + float32(data[3])
|
||||
return rh/10, temp/10
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user