summaryrefslogtreecommitdiff
path: root/irc/typing.go
diff options
context:
space:
mode:
authorHubert Hirtz <hubert@hirtzfr.eu>2020-09-02 00:06:37 +0200
committerHubert Hirtz <hubert@hirtzfr.eu>2020-09-02 16:00:57 +0200
commit3ea19ff21e5cda8afca7f8114e18466e9cf7663e (patch)
tree833a97485ebd98a2d1fd805db6f3eeacaf30127a /irc/typing.go
parentirc: Reset typing ratelimiter after sent message (diff)
Typing indicator timeout
Diffstat (limited to 'irc/typing.go')
-rw-r--r--irc/typing.go64
1 files changed, 64 insertions, 0 deletions
diff --git a/irc/typing.go b/irc/typing.go
new file mode 100644
index 0000000..a62a420
--- /dev/null
+++ b/irc/typing.go
@@ -0,0 +1,64 @@
+package irc
+
+import (
+ "sync"
+ "time"
+)
+
+type Typing struct {
+ Target string
+ Name string
+}
+
+type Typings struct {
+ l sync.Mutex
+ targets map[Typing]time.Time
+ timeouts chan Typing
+ stops chan Typing
+}
+
+func NewTypings() *Typings {
+ ts := &Typings{
+ targets: map[Typing]time.Time{},
+ timeouts: make(chan Typing, 16),
+ stops: make(chan Typing, 16),
+ }
+ go func() {
+ for {
+ t := <-ts.timeouts
+ now := time.Now()
+ ts.l.Lock()
+ oldT, ok := ts.targets[t]
+ if ok && 6.0 < now.Sub(oldT).Seconds() {
+ delete(ts.targets, t)
+ ts.l.Unlock()
+ ts.stops <- t
+ } else {
+ ts.l.Unlock()
+ }
+ }
+ }()
+ return ts
+}
+
+func (ts *Typings) Stops() <-chan Typing {
+ return ts.stops
+}
+
+func (ts *Typings) Active(target, name string) {
+ t := Typing{target, name}
+ ts.l.Lock()
+ ts.targets[t] = time.Now()
+ ts.l.Unlock()
+
+ go func() {
+ time.Sleep(6 * time.Second)
+ ts.timeouts <- t
+ }()
+}
+
+func (ts *Typings) Done(target, name string) {
+ ts.l.Lock()
+ delete(ts.targets, Typing{target, name})
+ ts.l.Unlock()
+}