add Tick() export and DialConnManual for JS-driven send loop in WASM
This commit is contained in:
@@ -83,6 +83,29 @@ func DialConn(conn Conn, ocb *OCB) (*Client, error) {
|
||||
return c, nil
|
||||
}
|
||||
|
||||
// DialConnManual creates a mosh client without an internal sendLoop.
|
||||
// The caller must call Tick() periodically (e.g., every 8-16ms) to flush
|
||||
// outgoing datagrams. Use this in WASM where Go timers are unreliable.
|
||||
func DialConnManual(conn Conn, ocb *OCB) (*Client, error) {
|
||||
c := &Client{
|
||||
conn: conn,
|
||||
transport: NewTransport(ocb, false),
|
||||
ocb: ocb,
|
||||
outputC: make(chan struct{}, 1),
|
||||
done: make(chan struct{}),
|
||||
sentActionCounts: make(map[uint64]int),
|
||||
}
|
||||
|
||||
c.wg.Add(1)
|
||||
go c.recvLoop()
|
||||
|
||||
// Send initial keepalive to associate with the server.
|
||||
c.transport.ForceNextSend()
|
||||
c.tick()
|
||||
|
||||
return c, nil
|
||||
}
|
||||
|
||||
// Send sends keystrokes to the server.
|
||||
func (c *Client) Send(keys []byte) {
|
||||
c.actionsMu.Lock()
|
||||
@@ -147,6 +170,13 @@ func (c *Client) Transport() *Transport {
|
||||
return c.transport
|
||||
}
|
||||
|
||||
// Tick flushes pending actions as mosh datagrams. Call this periodically
|
||||
// from an external timer (e.g., JS setInterval in WASM) when the internal
|
||||
// sendLoop is not used.
|
||||
func (c *Client) Tick() {
|
||||
c.tick()
|
||||
}
|
||||
|
||||
func (c *Client) tick() {
|
||||
// Batch: compute diff from accumulated actions.
|
||||
c.actionsMu.Lock()
|
||||
|
||||
+11
-1
@@ -72,7 +72,8 @@ func newSession(url, key string) (*session, error) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
client, err := mosh.DialConn(conn, ocb)
|
||||
// Use DialConnManual — no internal sendLoop. JS drives Tick() via setInterval.
|
||||
client, err := mosh.DialConnManual(conn, ocb)
|
||||
if err != nil {
|
||||
conn.Close()
|
||||
return nil, err
|
||||
@@ -90,6 +91,8 @@ func (s *session) jsObject() js.Value {
|
||||
}
|
||||
data := args[0].String()
|
||||
s.client.Send([]byte(data))
|
||||
// Tick immediately so keystrokes go out without waiting for the interval.
|
||||
s.client.Tick()
|
||||
return nil
|
||||
}))
|
||||
|
||||
@@ -100,6 +103,13 @@ func (s *session) jsObject() js.Value {
|
||||
cols := args[0].Int()
|
||||
rows := args[1].Int()
|
||||
s.client.Resize(uint16(cols), uint16(rows))
|
||||
s.client.Tick()
|
||||
return nil
|
||||
}))
|
||||
|
||||
// tick() — flush pending datagrams. Called by JS setInterval.
|
||||
obj.Set("tick", js.FuncOf(func(this js.Value, args []js.Value) interface{} {
|
||||
s.client.Tick()
|
||||
return nil
|
||||
}))
|
||||
|
||||
|
||||
Reference in New Issue
Block a user