Skip to content
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 6 additions & 3 deletions apa102/apa102.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ package apa102 // import "tinygo.org/x/drivers/apa102"

import (
"image/color"
"machine"

"tinygo.org/x/drivers"
"tinygo.org/x/drivers/internal/legacy"
)

const (
Expand Down Expand Up @@ -37,8 +37,11 @@ func New(b drivers.SPI) *Device {

// NewSoftwareSPI returns a new APA102 driver that will use a software based
// implementation of the SPI protocol.
func NewSoftwareSPI(sckPin, sdoPin machine.Pin, delay uint32) *Device {
return New(&bbSPI{SCK: sckPin, SDO: sdoPin, Delay: delay})
func NewSoftwareSPI(sckPin, sdoPin legacy.PinOutput, delay uint32) *Device {
return New(&bbSPI{SCK: sckPin.Set, SDO: sdoPin.Set, Delay: delay, config: func() {
legacy.ConfigurePinOut(sckPin)
legacy.ConfigurePinOut(sdoPin)
}})
}

// WriteColors writes the given RGBA color slice out using the APA102 protocol.
Expand Down
30 changes: 18 additions & 12 deletions apa102/softspi.go
Original file line number Diff line number Diff line change
@@ -1,24 +1,30 @@
package apa102

import "machine"
import (
"tinygo.org/x/drivers"
"tinygo.org/x/drivers/internal/legacy"
)

// bbSPI is a dumb bit-bang implementation of SPI protocol that is hardcoded
// to mode 0 and ignores trying to receive data. Just enough for the APA102.
// Note: making this unexported for now because it is probable not suitable
// most purposes other than the APA102 package. It might be desirable to make
// this more generic and include it in the TinyGo "machine" package instead.
type bbSPI struct {
SCK machine.Pin
SDO machine.Pin
Delay uint32
SCK drivers.PinOutput

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
SCK drivers.PinOutput
SetSCK drivers.PinOutput

picked this as a first example, but applies for all occurrences in this PR

reasoning:

  • in go it is best-practice that get-functions not start with "get"
  • the functions "Low()", "High()" are not named quite correct ("SetLow()", "SetHigh()" would be better), but are still understandable by its context e.g. "pin.Low()"
  • with this in mind, for "SCK(low)" I read it as "get-state-of-SCK-for-false" and was confused, why the return value is not used

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should also have in mind, that the "SCK" is not an attribute anymore, but a function now - maybe the name "drivers.PinOutput" does not make that clear enough?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm still not convinced of this change. In Go we typically avoid setters and getters. I understand where the confusion stems from and am open to the change though yet skeptical

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In Go we typically avoid setters and getters

this is not quite correct: https://go.dev/doc/effective_go#Getters

SDO drivers.PinOutput
Delay uint32
config func()
}

// Configure sets up the SCK and SDO pins as outputs and sets them low
func (s *bbSPI) Configure() {
s.SCK.Configure(machine.PinConfig{Mode: machine.PinOutput})
s.SDO.Configure(machine.PinConfig{Mode: machine.PinOutput})
s.SCK.Low()
s.SDO.Low()
if s.config == nil {
panic(legacy.ErrConfigBeforeInstantiated)
}
s.config()
s.SCK(false)
s.SDO(false)
if s.Delay == 0 {
s.Delay = 1
}
Expand Down Expand Up @@ -47,19 +53,19 @@ func (s *bbSPI) Transfer(b byte) (byte, error) {
for i := uint8(0); i < 8; i++ {

// half clock cycle high to start
s.SCK.High()
s.SCK(true)
s.delay()

// write the value to SDO (MSB first)
if b&(1<<(7-i)) == 0 {
s.SDO.Low()
s.SDO(false)
} else {
s.SDO.High()
s.SDO(true)
}
s.delay()

// half clock cycle low
s.SCK.Low()
s.SCK(false)
s.delay()

// for actual SPI would try to read the SDI value here
Expand Down
53 changes: 30 additions & 23 deletions bmi160/bmi160.go
Original file line number Diff line number Diff line change
@@ -1,40 +1,47 @@
package bmi160

import (
"machine"
"time"

"tinygo.org/x/drivers"
"tinygo.org/x/drivers/internal/legacy"
)

// DeviceSPI is the SPI interface to a BMI160 accelerometer/gyroscope. There is
// also an I2C interface, but it is not yet supported.
type DeviceSPI struct {
// Chip select pin
CSB machine.Pin
csb drivers.PinOutput

buf [7]byte

// SPI bus (requires chip select to be usable).
Bus drivers.SPI
bus drivers.SPI
config func()
}

// NewSPI returns a new device driver. The pin and SPI interface are not
// touched, provide a fully configured SPI object and call Configure to start
// using this device.
func NewSPI(csb machine.Pin, spi drivers.SPI) *DeviceSPI {
func NewSPI(csb legacy.PinOutput, spi drivers.SPI) *DeviceSPI {
return &DeviceSPI{
CSB: csb, // chip select
Bus: spi,
csb: csb.Set, // chip select
bus: spi,
config: func() {
legacy.ConfigurePinOut(csb)
},
}
}

// Configure configures the BMI160 for use. It configures the CSB pin and
// configures the BMI160, but it does not configure the SPI interface (it is
// assumed to be up and running).
func (d *DeviceSPI) Configure() error {
d.CSB.Configure(machine.PinConfig{Mode: machine.PinOutput})
d.CSB.High()
if d.config == nil {
return legacy.ErrConfigBeforeInstantiated
}
d.config()
d.csb(true)

// The datasheet recommends doing a register read from address 0x7F to get
// SPI communication going:
Expand Down Expand Up @@ -86,9 +93,9 @@ func (d *DeviceSPI) ReadTemperature() (temperature int32, err error) {
data[0] = 0x80 | reg_TEMPERATURE_0
data[1] = 0
data[2] = 0
d.CSB.Low()
err = d.Bus.Tx(data, data)
d.CSB.High()
d.csb(false)
err = d.bus.Tx(data, data)
d.csb(true)
if err != nil {
return
}
Expand Down Expand Up @@ -123,9 +130,9 @@ func (d *DeviceSPI) ReadAcceleration() (x int32, y int32, z int32, err error) {
for i := 1; i < len(data); i++ {
data[i] = 0
}
d.CSB.Low()
err = d.Bus.Tx(data, data)
d.CSB.High()
d.csb(false)
err = d.bus.Tx(data, data)
d.csb(true)
if err != nil {
return
}
Expand Down Expand Up @@ -153,9 +160,9 @@ func (d *DeviceSPI) ReadRotation() (x int32, y int32, z int32, err error) {
for i := 1; i < len(data); i++ {
data[i] = 0
}
d.CSB.Low()
err = d.Bus.Tx(data, data)
d.CSB.High()
d.csb(false)
err = d.bus.Tx(data, data)
d.csb(true)
if err != nil {
return
}
Expand Down Expand Up @@ -201,9 +208,9 @@ func (d *DeviceSPI) readRegister(address uint8) uint8 {
data := d.buf[:2]
data[0] = 0x80 | address
data[1] = 0
d.CSB.Low()
d.Bus.Tx(data, data)
d.CSB.High()
d.csb(false)
d.bus.Tx(data, data)
d.csb(true)
return data[1]
}

Expand All @@ -217,7 +224,7 @@ func (d *DeviceSPI) writeRegister(address, data uint8) {
buf[0] = address
buf[1] = data

d.CSB.Low()
d.Bus.Tx(buf, buf)
d.CSB.High()
d.csb(false)
d.bus.Tx(buf, buf)
d.csb(true)
}
15 changes: 8 additions & 7 deletions buzzer/buzzer.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,37 +2,38 @@
package buzzer // import "tinygo.org/x/drivers/buzzer"

import (
"machine"

"time"

"tinygo.org/x/drivers"
"tinygo.org/x/drivers/internal/legacy"
)

// Device wraps a GPIO connection to a buzzer.
type Device struct {
pin machine.Pin
pin drivers.PinOutput
High bool
BPM float64
}

// New returns a new buzzer driver given which pin to use
func New(pin machine.Pin) Device {
func New(pin legacy.PinOutput) Device {
return Device{
pin: pin,
pin: pin.Set,
High: false,
BPM: 96.0,
}
}

// On sets the buzzer to a high state.
func (l *Device) On() (err error) {
l.pin.Set(true)
l.pin(true)
l.High = true
return
}

// Off sets the buzzer to a low state.
func (l *Device) Off() (err error) {
l.pin.Set(false)
l.pin(false)
l.High = false
return
}
Expand Down
Loading