Home

Awesome

<h1>Furex</h1>

Furex is a minimal GUI framework built on top of Ebitengine, a 2D game engine for Go. It provides support for the Flex Layout Algorithm, a powerful tool for laying out items of different sizes and dimensions. Furex is not a component library, but rather a framework for positioning and stacking virtual widgets, handling button and touch events for mobile, and more. How these widgets are rendered is up to the user.

Go Reference

<p align="center"> <img width="480" src="./assets/example.gif"> </p>

Assets by Kenney. Fonts by 00ff.

Full source code of the example is here.

Contents

Motivation

Flexbox is a popular layout mechanism in web development, used for creating responsive and flexible user interfaces. With Furex, we can bring this same concept to game development using Go and Ebitengine. This library aims to make it easier for developers with experience in web or React projects to create dynamic, user-friendly game UI.

If you are not familiar with Flexbox Layout, you can learn about it at this website.

Features

Here are some of the key features of Furex:

These are just a few examples of the capabilities of Furex. For more information, be sure to check out the GoDoc documentation.

Getting Started

To get started with Furex, install Furex using the following command:

go get github.com/yohamta/furex/v2

Basic Usage

Here's a simple example of how to use Furex to create an UI in your game:

Full source code of the example

type Game struct {
  initOnce sync.Once
  screen   screen
  gameUI   *furex.View
}

func (g *Game) Update() error {
  g.initOnce.Do(func() {
    g.setupUI()
  })
  return nil
}

func (g *Game) Draw(screen *ebiten.Image) {
  g.gameUI.Draw(screen)
}

func (g *Game) setupUI() {
  screen.Fill(color.RGBA{0x3d, 0x55, 0x0c, 0xff})
  colors := []color.Color{
    color.RGBA{0x3d, 0x55, 0x0c, 0xff},
    color.RGBA{0x81, 0xb6, 0x22, 0xff},
    color.RGBA{0xec, 0xf8, 0x7f, 0xff},
  }

  g.gameUI = &furex.View{
    Width:        g.screen.Width,
    Height:       g.screen.Height,
    Direction:    furex.Row,
    Justify:      furex.JustifyCenter,
    AlignItems:   furex.AlignItemCenter,
    AlignContent: furex.AlignContentCenter,
    Wrap:         furex.Wrap,
  }

  for i := 0; i < 20; i++ {
    g.gameUI.AddChild(&furex.View{
      Width:  100,
      Height: 100,
      Handler: &Box{
        Color: colors[i%len(colors)],
      },
    })
  }
}

type Box struct {
  Color color.Color
}

var _ furex.Drawer = (*Box)(nil)

func (b *Box) Draw(screen *ebiten.Image, frame image.Rectangle, view *furex.View) {
  graphic.FillRect(screen, &graphic.FillRectOpts{
    Rect: frame, Color: b.Color,
  })
}
<p align="center"> <img width="592" src="./assets/greens.png"> </p>

Building UI with HTML

Sometimes making a complex UI tree in Go can be cumbersome. You can use HTML to construct the UI tree more easily.

Here's how to create a view tree from HTML:

This example is equivalent to the following Go code. By using HTML for styling the UI, the code becomes more maintainable.

view := (&furex.View{
  Width: 480,
  Height: 600,
  AlignItems: furex.AlignItemsCenter,
  Justify: furex.JustifyCenter,
}).AddChild(
  &furex.View{
    Width: 64,
    Height: 64,
    Handler: &widgets.Sprite{SpriteID: "mario.png"},
  },
)

For a more extensive example, check out the example here and the embedded HTML file.

CSS Properties

The following table lists the available CSS properties:

CSS PropertyTypeAvailable Values
leftintAny integer value
rightintAny integer value
topintAny integer value
bottomintAny integer value
widthintAny integer value or percentage
heightintAny integer value or percentage
margin-leftintAny integer value
margin-topintAny integer value
margin-rightintAny integer value
margin-bottomintAny integer value
positionPositionstatic, absolute
flex-directionDirectionrow, column
flex-wrapFlexWrapno-wrap, wrap, wrap-reverse
justify-contentJustifyflex-start, flex-end, center, space-between, space-around
align-itemsAlignItemstretch, flex-start, flex-end, center
align-contentAlignContentflex-start, flex-end, center, space-between, space-around, stretch
flex-growfloat64Any float64 value
flex-shrinkfloat64Any float64 value
displayDisplayflex, none

HTML Attributes

The following table lists the available HTML attributes:

HTML AttributeTypeAvailable Values
idstringAny string value
hiddenbooltrue, false

Component Types

There are three types of components you can create in Furex:

Global Components

To register a custom component globally, use the furex.RegisterComponents function. For example:

  func init() {
  	furex.RegisterComponents(furex.ComponentsMap{
  		"button":  &widgets.Button{},
  		"sprite": &widgets.Sprite{},
  	})
  }

Debugging

You can enable Debug Mode by setting the variable below.

furex.Debug = true
<p align="center"> <img width="592" src="./assets/debug.png"> </p>

Contributions

Contributions are welcome! If you find a bug or have an idea for a new feature, feel free to open an issue or submit a pull request.