Skip to content

Commit

Permalink
Merge pull request #252 from andydotxyz/fix/virtualdeskslide
Browse files Browse the repository at this point in the history
Slide between virtual desktops (:chefkiss:)
  • Loading branch information
andydotxyz authored Jan 15, 2024
2 parents 75132c0 + 5f06c92 commit e74cff6
Show file tree
Hide file tree
Showing 8 changed files with 94 additions and 14 deletions.
1 change: 1 addition & 0 deletions desk.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ type Desktop interface {
RecentApps() []AppData
Settings() DeskSettings
ContentBoundsPixels(*Screen) (x, y, w, h uint32)
RootSizePixels() (w, h uint32)
Screens() ScreenList

IconProvider() ApplicationProvider
Expand Down
6 changes: 6 additions & 0 deletions internal/notify/desktop.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package notify

// DesktopNotify allows modules to be informed when user changes virtual desktop
type DesktopNotify interface {
DesktopChangeNotify(int)
}
51 changes: 46 additions & 5 deletions internal/ui/desk.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,10 @@ import (
"os/exec"
"strconv"

"fyshos.com/fynedesk/internal/notify"

"fyne.io/fyne/v2"
"fyne.io/fyne/v2/canvas"
"fyne.io/fyne/v2/container"
deskDriver "fyne.io/fyne/v2/driver/desktop"

Expand Down Expand Up @@ -46,13 +49,35 @@ func (l *desktop) Desktop() int {
}

func (l *desktop) SetDesktop(id int) {
diff := id - l.desk
l.desk = id

for _, item := range l.wm.Windows() {
if item.Desktop() == id {
item.Uniconify()
} else {
item.Iconify()
_, height := l.RootSizePixels()
offPix := float32(diff * -int(height))
wins := l.wm.Windows()

starts := make([]fyne.Position, len(wins))
deltas := make([]fyne.Delta, len(wins))
for i, win := range wins {
starts[i] = win.Position()

display := l.Screens().ScreenForWindow(win)
off := offPix / display.Scale
deltas[i] = fyne.NewDelta(0, off)
}

fyne.NewAnimation(canvas.DurationStandard, func(f float32) {
for i, item := range l.wm.Windows() {
newX := starts[i].X + deltas[i].DX*f
newY := starts[i].Y + deltas[i].DY*f

item.Move(fyne.NewPos(newX, newY))
}
}).Start()

for _, m := range l.Modules() {
if desk, ok := m.(notify.DesktopNotify); ok {
desk.DesktopChangeNotify(id)
}
}
}
Expand Down Expand Up @@ -171,6 +196,22 @@ func (l *desktop) ContentBoundsPixels(screen *fynedesk.Screen) (x, y, w, h uint3
return 0, 0, screenW, screenH
}

func (l *desktop) RootSizePixels() (w, h uint32) {
for _, screen := range l.Screens().Screens() {
right := uint32(screen.X + screen.Width)
bottom := uint32(screen.Y + screen.Height)

if right > w {
w = right
}
if bottom > h {
h = bottom
}
}

return w, h
}

func (l *desktop) IconProvider() fynedesk.ApplicationProvider {
return l.icons
}
Expand Down
31 changes: 24 additions & 7 deletions internal/x11/win/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,15 @@ package win
import (
"image"

"fyne.io/fyne/v2"

"github.com/BurntSushi/xgb/xproto"
"github.com/BurntSushi/xgbutil/ewmh"
"github.com/BurntSushi/xgbutil/icccm"
"github.com/BurntSushi/xgbutil/xevent"
"github.com/BurntSushi/xgbutil/xprop"

"fyne.io/fyne/v2"
"fyne.io/fyne/v2/canvas"

"fyshos.com/fynedesk"
"fyshos.com/fynedesk/internal/x11"
"fyshos.com/fynedesk/wm"
Expand Down Expand Up @@ -125,12 +126,20 @@ func (c *client) SetDesktop(id int) {
}

d := fynedesk.Instance()
diff := id - c.desk
c.desk = id
if id == d.Desktop() {
c.Uniconify()
} else {
c.Iconify()
}

_, height := d.RootSizePixels()
offPix := float32(diff * -int(height))
display := d.Screens().ScreenForWindow(c)
off := offPix / display.Scale

start := c.Position()
fyne.NewAnimation(canvas.DurationStandard, func(f float32) {
newY := start.Y + off*f

c.Move(fyne.NewPos(start.X, newY))
}).Start()
}

func (c *client) Expose() {
Expand Down Expand Up @@ -193,6 +202,14 @@ func (c *client) Maximized() bool {
return c.maximized
}

func (c *client) Move(pos fyne.Position) {
screen := fynedesk.Instance().Screens().ScreenForWindow(c)

targetX := int16(pos.X * screen.CanvasScale())
targetY := int16(pos.Y * screen.CanvasScale())
c.frame.updateGeometry(targetX, targetY, c.frame.width, c.frame.height, false)
}

func (c *client) NotifyBorderChange() {
c.props.refreshCache()
if c.Properties().Decorated() {
Expand Down
5 changes: 5 additions & 0 deletions modules/desktops/desktops.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,11 @@ type desktops struct {
gui *pager
}

func (d *desktops) DesktopChangeNotify(id int) {
d.current = id
d.gui.refresh()
}

func (d *desktops) Destroy() {
}

Expand Down
7 changes: 6 additions & 1 deletion test/desktop.go
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,12 @@ func (*Desktop) Capture() image.Image {

// ContentBoundsPixels returns a default value for how much space maximised apps should use
func (*Desktop) ContentBoundsPixels(_ *fynedesk.Screen) (x, y, w, h uint32) {
return 0, 0, uint32(320), uint32(240)
return 0, 0, 320, 240
}

// RootSizePixels returns the total number of pixels required to fit all the screens
func (*Desktop) RootSizePixels() (w, h uint32) {
return 320, 240
}

// Desktop returns the index of the current desktop (in test this is always 0)
Expand Down
6 changes: 5 additions & 1 deletion test/window.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,9 @@ package test
import (
"image"

"fyne.io/fyne/v2"
"fyshos.com/fynedesk"

"fyne.io/fyne/v2"
)

// Window is an in-memory virtual window for test purposes
Expand Down Expand Up @@ -80,6 +81,9 @@ func (w *Window) Maximized() bool {
return false
}

// Move the window, does nothing in test windows
func (w *Window) Move(fyne.Position) {}

// Parent returns a window that this should be positioned within, if set.
func (w *Window) Parent() fynedesk.Window {
return w.parent
Expand Down
1 change: 1 addition & 0 deletions window.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ type Window interface {
Parent() Window
Properties() WindowProperties // Request the properties set on this window
Position() fyne.Position
Move(position fyne.Position)

Desktop() int
SetDesktop(int)
Expand Down

0 comments on commit e74cff6

Please sign in to comment.