summary refs log tree commit diff stats
path: root/tests/manyloc/keineschweine/lib/sg_gui.nim
diff options
context:
space:
mode:
authorAraq <rumpf_a@web.de>2013-04-13 21:55:02 +0200
committerAraq <rumpf_a@web.de>2013-04-13 21:55:02 +0200
commit75b508032b9da285f30d4ec7f2af4c63075b8611 (patch)
tree79476c0e8b7c70ee373bde21a2ea0a62d84520f8 /tests/manyloc/keineschweine/lib/sg_gui.nim
parent4f09794be9fb9b96728078712f01e990e0021929 (diff)
downloadNim-75b508032b9da285f30d4ec7f2af4c63075b8611.tar.gz
added manyloc test suite; --path now relative to project dir if not absolute
Diffstat (limited to 'tests/manyloc/keineschweine/lib/sg_gui.nim')
-rw-r--r--tests/manyloc/keineschweine/lib/sg_gui.nim281
1 files changed, 281 insertions, 0 deletions
diff --git a/tests/manyloc/keineschweine/lib/sg_gui.nim b/tests/manyloc/keineschweine/lib/sg_gui.nim
new file mode 100644
index 000000000..6741fe55e
--- /dev/null
+++ b/tests/manyloc/keineschweine/lib/sg_gui.nim
@@ -0,0 +1,281 @@
+import
+  sfml, sfml_colors, 
+  input_helpers, sg_packets
+from strutils import countlines
+{.deadCodeElim: on.}
+type
+  PGuiContainer* = ref TGuiContainer
+  TGuiContainer* = object of TObject
+    position: TVector2f
+    activeEntry: PTextEntry
+    widgets: seq[PGuiObject]
+    buttons: seq[PButton]
+  PGuiObject* = ref TGuiObject
+  TGuiObject* = object of TObject
+  PButton* = ref TButton
+  TButton* = object of TGuiObject
+    enabled: bool
+    bg*: sfml.PRectangleShape
+    text*: PText
+    onClick*: TButtonClicked
+    bounds: TFloatRect
+  PButtonCollection* = ref TButtonCollection
+  TButtonCollection* = object of TGuiContainer
+  PTextEntry* = ref TTextEntry
+  TTextEntry* = object of TButton
+    inputClient: input_helpers.PTextInput
+  PMessageArea* = ref TMessageArea
+  TMessageArea* = object of TGuiObject
+    pos: TVector2f
+    messages: seq[TMessage]
+    texts: seq[PText]
+    scrollBack*: int
+    sizeVisible*: int
+    direction*: int
+  TMessage = object
+    color: TColor
+    text: string
+    lines: int
+  TButtonClicked = proc(button: PButton)
+var
+  guiFont* = newFont("data/fnt/LiberationMono-Regular.ttf")
+  messageProto* = newText("", guiFont, 16)
+let
+  vectorZeroF* = vec2f(0.0, 0.0)
+
+proc newGuiContainer*(): PGuiContainer
+proc newGuiContainer*(pos: TVector2f): PGuiContainer {.inline.}
+proc free*(container: PGuiContainer)
+proc add*(container: PGuiContainer; widget: PGuiObject)
+proc clearButtons*(container: PGuiContainer)
+proc click*(container: PGuiContainer; position: TVector2f)
+proc setActive*(container: PGuiContainer; entry: PTextEntry)
+proc setPosition*(container: PGuiContainer; position: TVector2f)
+
+proc update*(container: PGuiContainer; dt: float)
+proc draw*(window: PRenderWindow; container: PGuiContainer) {.inline.}
+
+proc newMessageArea*(container: PGuiContainer; position: TVector2f): PMessageArea {.discardable.}
+proc add*(m: PMessageArea; msg: ScChat)
+
+proc draw*(window: PRenderWindow; b: PButton) {.inline.}
+proc click*(b: PButton; p: TVector2f)
+proc setPosition*(b: PButton; p: TVector2f)
+proc setString*(b: PButton; s: string) {.inline.}
+
+proc newButton*(container: PGuiContainer; text: string; position: TVector2f; 
+  onClick: TButtonClicked; startEnabled: bool = true): PButton {.discardable.}
+proc init(b: PButton; text: string; position: TVector2f; onClick: TButtonClicked)
+proc setEnabled*(b: PButton; enabled: bool)
+proc disable*(b: PButton) {.inline.}
+proc enable*(b: PButton) {.inline.}
+
+proc newTextEntry*(container: PGuiContainer; text: string;
+                    position: TVector2f; onEnter: TInputFinishedProc = nil): PTextEntry {.discardable.}
+proc init(t: PTextEntry; text: string; onEnter: TInputFinishedProc)
+proc draw*(window: PRenderWindow, t: PTextEntry) {.inline.}
+proc setActive*(t: PTextEntry) {.inline.}
+proc clearText*(t: PTextEntry) {.inline.}
+proc getText*(t: PTextEntry): string {.inline.}
+
+proc update*(m: PMessageArea)
+
+if guiFont == nil:
+  echo("Could not load font, crying softly to myself.")
+  quit(1)
+
+proc newGuiContainer*(): PGuiContainer =
+  new(result, free)
+  result.widgets = @[]
+  result.buttons = @[]
+proc newGuiContainer*(pos: TVector2f): PGuiContainer =
+  result = newGuiContainer()
+  result.setPosition pos
+proc free*(container: PGuiContainer) = 
+  container.widgets = nil
+  container.buttons = nil
+proc add*(container: PGuiContainer; widget: PGuiObject) =
+  container.widgets.add(widget)
+proc add*(container: PGuiContainer; button: PButton) =
+  if container.isNil: return
+  container.buttons.add(button)
+proc clearButtons*(container: PGuiContainer) =
+  container.buttons.setLen 0
+proc click*(container: PGuiContainer; position: TVector2f) =
+  for b in container.buttons:
+    click(b, position)
+proc setActive*(container: PGuiContainer; entry: PTextEntry) =
+  container.activeEntry = entry
+  setActive(entry)
+proc setPosition*(container: PGuiContainer; position: TVector2f) =
+  container.position = position
+
+
+proc update*(container: PGuiContainer; dt: float) =
+  if not container.activeEntry.isNil:
+    container.activeEntry.setString(container.activeEntry.getText())
+proc draw*(window: PRenderWindow; container: PGuiContainer) =
+  for b in container.buttons:
+    window.draw b
+
+proc free(c: PButton) =
+  c.bg.destroy()
+  c.text.destroy()
+  c.bg = nil
+  c.text = nil
+  c.onClick = nil
+proc newButton*(container: PGuiContainer; text: string;
+                 position: TVector2f; onClick: TButtonClicked;
+                 startEnabled: bool = true): PButton =
+  new(result, free)
+  init(result, 
+       text, 
+       if not container.isNil: position + container.position else: position, 
+       onClick)
+  container.add result
+  if not startEnabled: disable(result)
+
+proc init(b: PButton; text: string; position: TVector2f; onClick: TButtonClicked) =
+  b.bg = newRectangleShape()
+  b.bg.setSize(vec2f(80.0, 16.0))
+  b.bg.setFillColor(color(20, 30, 15))
+  b.text = newText(text, guiFont, 16)
+  b.onClick = onClick
+  b.setPosition(position)
+  b.enabled = true
+proc copy*(c: PButton): PButton =
+  new(result, free)
+  result.bg = c.bg.copy()
+  result.text = c.text.copy()
+  result.onClick = c.onClick
+  result.setPosition(result.bg.getPosition())
+
+proc setEnabled*(b: PButton; enabled: bool) =
+  b.enabled = enabled
+  if enabled:
+    b.text.setColor(White)
+  else:
+    b.text.setColor(Gray)
+proc enable*(b: PButton) = setEnabled(b, true)
+proc disable*(b: PButton) = setEnabled(b, false)
+
+proc draw*(window: PRenderWindow; b: PButton) =
+  window.draw b.bg
+  window.draw b.text
+proc setPosition*(b: PButton, p: TVector2f) =
+  b.bg.setPosition(p)
+  b.text.setPosition(p)
+  b.bounds = b.text.getGlobalBounds()
+proc setString*(b: PButton; s: string) =
+  b.text.setString(s)
+proc click*(b: PButton, p: TVector2f) = 
+  if b.enabled and (addr b.bounds).contains(p.x, p.y): 
+    b.onClick(b)
+
+proc free(obj: PTextEntry) =
+  free(PButton(obj))
+proc newTextEntry*(container: PGuiContainer; text: string; 
+                    position: TVector2F; onEnter: TInputFinishedProc = nil): PTextEntry =
+  new(result, free)
+  init(PButton(result), text, position + container.position, proc(b: PButton) =
+    setActive(container, PTextEntry(b)))
+  init(result, text, onEnter)
+  container.add result
+proc init(t: PTextEntry; text: string; onEnter: TInputFinishedProc) =
+  t.inputClient = newTextInput(text, text.len, onEnter)
+proc draw(window: PRenderWindow; t: PTextEntry) =
+  window.draw PButton(t)
+proc clearText*(t: PTextEntry) =
+  t.inputClient.clear()
+proc getText*(t: PTextEntry): string =
+  return t.inputClient.text
+proc setActive*(t: PTextEntry) =
+  if not t.isNil and not t.inputClient.isNil:
+    input_helpers.setActive(t.inputClient)
+
+
+discard """proc newMessageArea*(container: PGuiContainer; position: TVector2f): PMessageArea =
+  new(result)
+  result.messages = @[]
+  result.pos = position
+  container.add(result)
+proc add*(m: PMessageArea, text: string): PText =
+  result = messageProto.copy()
+  result.setString(text)
+  m.messages.add(result)
+  let nmsgs = len(m.messages)
+  var pos   = vec2f(m.pos.x, m.pos.y)
+  for i in countdown(nmsgs - 1, max(nmsgs - 30, 0)):
+    setPosition(m.messages[i], pos)
+    pos.y -= 16.0
+
+proc draw*(window: PRenderWindow; m: PMessageArea) =
+  let nmsgs = len(m.messages) 
+  if nmsgs == 0: return
+  for i in countdown(nmsgs - 1, max(nmsgs - 30, 0)):
+    window.draw(m.messages[i])
+"""
+proc newMessageArea*(container: PGuiContainer; position: TVector2f): PMessageArea =
+  new(result)
+  result.messages = @[]
+  result.texts = @[]
+  result.pos = position + container.position
+  result.sizeVisible = 10
+  result.scrollBack = 0
+  result.direction = -1 ## to push old messages up
+  container.add(result)
+  
+proc add*(m: PMessageArea, msg: ScChat) =
+  const prependName = {CPub, CPriv}
+  var mmm: TMessage
+  if msg.kind in prependName: 
+    mmm.text = "<"
+    mmm.text.add msg.fromPlayer
+    mmm.text.add "> "
+    mmm.text.add msg.text
+  else:
+    mmm.text = msg.text
+  case msg.kind
+  of CPub:  mmm.color = RoyalBlue
+  of CPriv, CSystem: mmm.color = Green
+  of CError: mmm.color = Red
+  
+  mmm.lines = countLines(mmm.text)+1
+  
+  m.messages.add mmm
+  update m
+proc add*(m: PMessageArea, msg: string) {.inline.} =
+  var chat = newScChat(kind = CSystem, text = msg)
+  add(m, chat)
+
+proc proctor*(m: PText; msg: ptr TMessage; pos: ptr TVector2f) =
+  m.setString msg.text 
+  m.setColor msg.color
+  m.setPosition pos[]
+proc update*(m: PMessageArea) =
+  if m.texts.len < m.sizeVisible:
+    echo "adding ", m.sizeVisible - m.texts.len, " fields"
+    for i in 1..m.sizeVisible - m.texts.len:
+      var t = messageProto.copy()
+      m.texts.add messageProto.copy()
+  elif m.texts.len > m.sizeVisible:
+    echo "cutting ", m.texts.len - m.sizeVisible, " fields"
+    for i in m.sizeVisible.. < m.texts.len:
+      m.texts.pop().destroy()
+  let nmsgs = m.messages.len()
+  if m.sizeVisible == 0 or nmsgs == 0: 
+    echo "no messages? ", m.sizeVisible, ", ", nmsgs
+    return
+  var pos = vec2f(m.pos.x, m.pos.y)
+  for i in 0.. min(m.sizeVisible, nmsgs)-1:
+    ##echo nmsgs - i - 1 - m.scrollBack
+    let msg = addr m.messages[nmsgs - i - 1 - m.scrollBack]
+    proctor(m.texts[i], msg, addr pos)
+    pos.y += (16 * m.direction * msg.lines).cfloat  
+
+proc draw*(window: PRenderWindow; m: PMessageArea) =
+  let nmsgs = len(m.texts)
+  if nmsgs == 0: return
+  for i in countdown(nmsgs - 1, max(nmsgs - m.sizeVisible, 0)):
+    window.draw m.texts[i]
+