Skip to content
Draft
Show file tree
Hide file tree
Changes from all 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
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,4 @@ package-lock.json
*.flippy
wasm
*.html
nimbledeps
23 changes: 23 additions & 0 deletions examples/minimal_scroll/minimal_scroll.nim
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
## This minimal example shows 5 blue squares in a scroll box

import fidget

proc drawMain() =
frame "main":
box 0, 0, 620, 140
frame "scrollBox":
box 5, 5, 610, 130
stroke "#000"
strokeWeight 1
clipContent true
scrollable true, true
fill "#FFF"
for i in 0 .. 4:
group "blockA" & $i:
scrollSpeed (i + 1) * 2 - 6
box 15 + (float i) * 120, 15, 100, 100
fill "#2B9FEA"
stroke "#000"
strokeWeight 1

startFidget(drawMain, w = 620, h = 140)
2 changes: 1 addition & 1 deletion fidget.nimble
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ srcDir = "src"

requires "nim >= 1.0.0"
requires "chroma >= 0.1.3"
requires "typography >= 0.4.0"
requires "typography >= 0.6.0"
requires "pixie >= 0.0.2"
requires "vmath >= 0.3.1"
requires "print >= 0.1.0"
Expand Down
38 changes: 37 additions & 1 deletion src/fidget.nim
Original file line number Diff line number Diff line change
Expand Up @@ -266,7 +266,7 @@ proc image*(imageName: string) =
## Sets image fill.
current.imageName = imageName

proc orgBox*(x, y, w, h: int|float32|float32) =
proc orgBox*(x, y, w, h: int|float32|float64) =
## Sets the box dimensions of the original element for constraints.
current.orgBox.x = float32 x
current.orgBox.y = float32 y
Expand All @@ -280,6 +280,13 @@ proc box*(x, y, w, h: float32) =
current.box.w = w
current.box.h = h

## Apply scroll
if not parent.isNil:
if parent.scrollable.x:
current.box.x += parent.scroll.x * current.scrollSpeed.x
if parent.scrollable.y:
current.box.y += parent.scroll.y * current.scrollSpeed.y

proc box*(
x: int|float32|float64,
y: int|float32|float64,
Expand Down Expand Up @@ -358,6 +365,35 @@ proc scrollBars*(scrollBars: bool) =
## Causes the parent to clip the children and draw scroll bars.
current.scrollBars = scrollBars

proc scrollable*(value: tuple[x: bool, y:bool]) =
## Causes the parent to let scroll its children.
current.scrollable = value

## Accumulate scroll value
if current.scrollable.x or current.scrollable.y:
onHover:
current.scroll += mouse.wheelDelta

proc scrollable*(xValue: bool, yValue: bool) =
## Causes the parent to let scroll its children.
scrollable((x: xValue, y: yValue))

proc scrollable*(yValue: bool) =
## Causes the parent to let scroll its children.
scrollable((x: false, y: yValue))

proc scrollSpeed*(value: Vec2) =
## Sets the speed at which a child is scrolled inside its parent's box
current.scrollSpeed = value

proc scrollSpeed*(value: int|float32|float64) =
## Sets the speed at which a child is scrolled inside its parent's box
scrollSpeed(vec2(float32 value, float32 value))

proc scrollSpeed*(xValue, yValue: int|float32|float64) =
## Sets the speed at which a child is scrolled inside its parent's box
scrollSpeed(vec2(float32 xValue, float32 yValue))

proc cursorColor*(color: Color) =
## Sets the color of the text cursor.
current.cursorColor = color
Expand Down
8 changes: 6 additions & 2 deletions src/fidget/common.nim
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,9 @@ type
textLayoutWidth*: float32
## Can the text be selected.
selectable*: bool
scrollable*: tuple[x: bool, y: bool]
scroll*: Vec2
scrollSpeed*: Vec2
scrollBars*: bool ## Should it have scroll bars if children are clipped.

KeyState* = enum
Expand All @@ -160,7 +163,7 @@ type
Mouse* = ref object
pos*, delta*, prevPos*: Vec2
pixelScale*: float32
wheelDelta*: float32
wheelDelta*: Vec2
cursorStyle*: MouseCursorStyle ## Sets the mouse cursor icon
prevCursorStyle*: MouseCursorStyle

Expand Down Expand Up @@ -320,6 +323,7 @@ proc resetToDefault*(node: Node)=
node.clipContent = false
node.diffIndex = 0
node.selectable = false
node.scrollSpeed = vec2(1, 1)

proc setupRoot*() =
if root == nil:
Expand All @@ -335,7 +339,7 @@ proc setupRoot*() =

proc clearInputs*() =

mouse.wheelDelta = 0
mouse.wheelDelta = vec2(0, 0)

# Reset key and mouse press to default state
for i in 0 ..< buttonPress.len:
Expand Down
7 changes: 7 additions & 0 deletions src/fidget/dom2.nim
Original file line number Diff line number Diff line change
Expand Up @@ -1154,6 +1154,13 @@ type
screenX*, screenY*: int
x*, y*: int

WheelEvent* = ref WheelEventObj ## see `docs<https://developer.mozilla.org/en-US/docs/Web/API/WheelEvent>`
WheelEventObj {.importc.} = object of MouseEvent
deltaX*: float64
deltaY*: float64
deltaZ*: float64
deltaMode*: uint32

DataTransferItemKind* {.pure.} = enum
File = "file",
String = "string"
Expand Down
6 changes: 6 additions & 0 deletions src/fidget/htmlbackend.nim
Original file line number Diff line number Diff line change
Expand Up @@ -519,6 +519,12 @@ proc startFidget*(draw: proc(), load: proc() = nil, w = 0, h = 0) =
## Scroll does not need to do anything special in HTML mode
refresh()

dom.window.addEventListener "wheel", proc(event: Event) =
## When wheel is used
let event = cast[WheelEvent](event)
mouse.wheelDelta += vec2(event.deltaX, event.deltaY)
refresh()

dom.window.addEventListener "mousedown", proc(event: Event) =
## When mouse button is pressed
let event = cast[MouseEvent](event)
Expand Down
2 changes: 1 addition & 1 deletion src/fidget/opengl/base.nim
Original file line number Diff line number Diff line change
Expand Up @@ -274,7 +274,7 @@ proc onScroll(window: staticglfw.Window, xoffset, yoffset: float64) {.cdecl.} =
if keyboard.focusNode != nil:
textBox.scrollBy(-yoffset * 50)
else:
mouse.wheelDelta += yoffset
mouse.wheelDelta += vec2(xoffset, yoffset)

proc onMouseButton(
window: staticglfw.Window, button, action, modifiers: cint
Expand Down