Azul - Desktop GUI framework

Overview

Azul - Desktop GUI framework

Build Status Linux / macOS Build status Windows Coverage Status LICENSE Rust Compiler Version

Azul is a free, functional, reactive GUI framework for Rust and C++, built using the WebRender rendering engine and a CSS / HTML-like document object model for rapid development of beautiful, native desktop applications

Website | User guide | API documentation | Video demo | Matrix Chat

About

Azul is a library for creating graphical user interfaces in Rust and C. It mixes paradigms from functional, reactive and data-oriented programming with an API suitable for developing cross-platform desktop applications. The two core principles of Azul is to not render objects that aren't visible and to use composition of DOM trees over inheritance.

Azul separates the concerns of business logic / callbacks, data model and UI rendering / styling by not letting the UI / rendering logic have mutable access to the application data. In Azul, rendering the view is a pure function that maps your application data to a styled DOM. "Widgets" are just functions that render a certain state, more complex widgets use function composition.

Since recreating DOM objects is expensive (note: "expensive" = 3 milliseconds), Azul caches the DOM object and does NOT recreate it on every frame - only when callbacks request to recreate it.

The application and widget data is managed using a reference-counted boxed type (RefAny), which can be downcasted to a concrete type if necessary. Widget-local data that needs to be retained between frames is stored on the DOM nodes themselves, similar to how the HTML dataset property can be used to store widget data.

Current progress

The latest release for Windows can be found here.

Currenly I am using this framework to build cross-platform GUI applications: while the framework isn't finished yet, it is at least possible to build native, good-looking applications for Windows - for example, here is an Excel clone that I am working on:

image

Creating this demo took about two hours. As you can see, the layout system is already quite mature. To run this XML file, download the examples.zip folder and exchange the "ui.xml" file for the linked file and restart the xml.exe demo. The XML itself can be hot-reloaded and later be compiled into native Rust code - giving you both a fast design iteration time and native performance.

The application currently takes ~40MB to run and of course almost no CPU at all.

With the correct CSS styles, the window is indistinguishable from a native application:

image

image

Azul currently features:

  • Text input / text entry (see "widgets" demo)
  • Animations @ 60+ FPS (using webrender)
  • CSS support see list of supported CSS keys
  • De- / encoding images and fonts (TTF, WOFF, OTF).
  • Cross-platform text shaping (via allsorts)
  • Parsing and rendering SVG (via resvg)
  • Rendering / embedding OpenGL content (using OpenGL textures)
  • Tesselating shapes into triangles (via lyon)
  • Asynchronously managing running background threads for File I/O
  • Parsing XML (via xmlparser)
  • Stable API

Currently available widgets:

  • Button
  • TextInput (bug: has no cursor / text selection yet)
  • CheckBox
  • ColorInput
  • NumberInput
  • ProgressBar
  • NodeGraph
  • Frame
  • TabControl

Azul also allows for easy creation of custom widgets, for example a node graph widget

image

All widgets are stylable via CSS. Widgets in progress:

  • ListView
  • Spreadsheet
  • Slider
  • Dropdown
  • RadioSelect
  • RibbonBar

Additionally, Azul features cross-platform MsgBox and FileDialog dialogs.

Caveats:

  • Currently Azul only works on Windows because of rendering problems on X11 and Cocoa
  • Text shaping for non-Latin fonts as well as fallback fonts are rudimentary / non-existent
  • Scrolling, especially smooth scrolling is not yet implemented entirely
  • Scroll bars are not automatically inserted
  • Rich Text Layout has to be calculated manually, not done automatically
  • C++ API is a work in progress
  • Layout engine may have bugs (but those can usually be worked around)
  • Binary ABI is not entirely stable yet
  • Infinite scrolling / lazy loading of DOM content is not yet supported
  • Menus / context menus don't work yet (stub API)

Installation

Due to its relatively large size (and to provide C / C++ interop), azul is built as a dynamic library in the azul-dll package. You can download pre-built binaries from azul.rs/releases.

Using pre-built-binaries

  1. Download the library from azul.rs/releases
  2. Set your linker to link against the library
    • Rust: Set AZUL_LINK_PATH environment variable to the path of the library
    • C / C++: Copy the azul.h on the release page to your project headers and the azul.dll to your IDE project.

The API for Rust, C++ and other languages is exactly the same, since the API is auto-generated by the build.py script. If you want to generate language bindings for your language, you can generate them using the api.json file.

To run programs on Linux, you may also need to copy the libazul.so into /usr/lib. Eventually this will be solved by upstreaming the library into repositories once all major bugs are resolved.

Building from source (crates.io)

By default, you should be able to run

cargo install --version 1.0.0 azul-dll

to compile the DLL from crates.io. The library will be built and installed in the $AZUL_LINK_PATH directory, which defaults to $CARGO_HOME_DIR/lib/azul-dll-0.1.0/target/release/

Building from source (git)

Building the library from source requires clang as well as the prerequisites listed above.

git clone https://github.com/fschutt/azul
cd azul-dll
cargo build --release

This command should produce an azul.dll file in the /target/release folder, in order to use this, you will also need to set AZUL_LINK_PATH to $BUILD_DIR/target/release/.

If you are developing on the library, you may also need to re-generate the Rust / C API, in which case you should prefer to use the build.py script:

python3 ./build.py

Example

Note: The widgets are custom to each programming language. All callbacks have to use extern "C" in order to be compatible with the library. The binary layout of all API types is described in theapi.json file.

See the /examples folder for example code in different languages

Hello World Application

Rust

StyledDom { let mut result = StyledDom::default(); let data = match data.downcast_ref:: () { Some(s) => s, None => return result, }; let label = Label::new(format!("{}", data.counter)).dom(); let button = Button::with_label("Update counter") .onmouseup(update_counter, data.clone()) .dom(); result .append(label) .append(button) } // View updates model extern "C" fn update_counter(data: &mut RefAny, event: CallbackInfo) -> UpdateScreen { let mut data = match data.downcast_mut:: () { Some(s) => s, None => return UpdateScreen::DoNothing, }; data.counter += 1; UpdateScreen::RegenerateDomForCurrentWindow } fn main() { let app = App::new(RefAny::new(DataModel { counter: 0 }), AppConfig::default()); app.run(WindowCreateOptions::new(render_my_view)); }">
use azul::prelude::*;
use azul_widgets::{button::Button, label::Label};

struct DataModel {
    counter: usize,
}

// Model -> View
extern "C" fn render_my_view(data: &RefAny, _: LayoutInfo) -> StyledDom {

    let mut result = StyledDom::default();

    let data = match data.downcast_ref::
     () {
        
     Some(s) 
     => s,
        
     None 
     => 
     return result,
    };

    
     let label 
     = Label
     ::
     new(
     format!(
     "{}", data.counter)).
     dom();
    
     let button 
     = Button
     ::
     with_label(
     "Update counter")
        .
     onmouseup(update_counter, data.
     clone())
        .
     dom();

    result
    .
     append(label)
    .
     append(button)
}


     // View updates model

     extern 
     "C" 
     fn 
     update_counter(data: 
     &
     mut RefAny, event: CallbackInfo) -> UpdateScreen {
    
     let 
     mut data 
     = 
     match data.
     downcast_mut
     ::
     
      () {
        
      Some(s) 
      => s,
        
      None 
      => 
      return UpdateScreen
      ::DoNothing,
    };
    data.counter 
      += 
      1;
    UpdateScreen
      ::RegenerateDomForCurrentWindow
}


      fn 
      main() {
    
      let app 
      = App
      ::
      new(RefAny
      ::
      new(DataModel { counter: 
      0 }), AppConfig
      ::
      default());
    app.
      run(WindowCreateOptions
      ::
      new(render_my_view));
}
     
    

C++

View StyledDom render_my_view(const RefAny& data, LayoutInfo info) { auto result = StyledDom::default(); const DataModel* data = data.downcast_ref(); if !(data) { return result; } auto label = Label::new(String::format("{counter}", &[data.counter])).dom(); auto button = Button::with_label("Update counter") .onmouseup(update_counter, data.clone()) .dom(); result = result .append(label) .append(button); return result; } UpdateScreen update_counter(RefAny& data, CallbackInfo event) { DataModel data = data.downcast_mut().unwrap(); data.counter += 1; return UpdateScreen::RegenerateDomForCurrentWindow; } int main() { auto app = App::new(RefAny::new(DataModel { .counter = 0 }), AppConfig::default()); app.run(WindowCreateOptions::new(render_my_view)); }">
#include "azul.h"
#include "azul-widgets.h"

using namespace azul;
using namespace azul.widgets.button;
using namespace azul.widgets.label;

struct DataModel {
    counter: uint32_t
}

// Model -> View
StyledDom render_my_view(const RefAny& data, LayoutInfo info) {

    auto result = StyledDom::default();

    const DataModel* data = data.downcast_ref();
    if !(data) {
        return result;
    }

    auto label = Label::new(String::format("{counter}", &[data.counter])).dom();
    auto button = Button::with_label("Update counter")
       .onmouseup(update_counter, data.clone())
       .dom();

    result = result
        .append(label)
        .append(button);

    return result;
}

UpdateScreen update_counter(RefAny& data, CallbackInfo event) {
    DataModel data = data.downcast_mut().unwrap();
    data.counter += 1;
    return UpdateScreen::RegenerateDomForCurrentWindow;
}

int main() {
    auto app = App::new(RefAny::new(DataModel { .counter = 0 }), AppConfig::default());
    app.run(WindowCreateOptions::new(render_my_view));
}

C

counter) }}); counter_string = AzString_format(AzString_fromConstStr("{counter}"), fmt_args); } else { return AzStyledDom_empty(); } DataModelRef_delete(&d); AzDom const html = { .root = AzNodeData_new(AzNodeType_Body), .children = AzDomVec_fromConstArray({AzDom_new(AzNodeType_Label(counter_string))}), .total_children = 1, // len(children) }; AzCss const css = AzCss_fromString(AzString_fromConstStr("body { font-size: 50px; }")); return AzStyledDom_new(html, css); } UpdateScreen update_counter(RefAny& data, CallbackInfo event) { DataModelRefMut d = DataModelRefMut_create(data); if !(DataModel_downcastRef(data, &d)) { return UpdateScreen_DoNothing; } d->ptr.counter += 1; DataModelRefMut_delete(&d); return UpdateScreen_RegenerateDomForCurrentWindow; } int main() { DataModel model = { .counter = 5 }; AzApp app = AzApp_new(DataModel_upcast(model), AzAppConfig_default()); AzApp_run(app, AzWindowCreateOptions_new(render_my_view)); return 0; }">
#include "azul.h"

typedef struct {
    uint32_t counter;
} DataModel;

void DataModel_delete(DataModel* restrict A) { }
AZ_REFLECT(DataModel, DataModel_delete);

AzStyledDom render_my_view(AzRefAny* restrict data, AzLayoutInfo info) {

    AzString counter_string;

    DataModelRef d = DataModelRef_create(data);
    if (DataModel_downcastRef(data, &d)) {
        AzFmtArgVec fmt_args = AzFmtArgVec_fromConstArray({{
            .key = AzString_fromConstStr("counter"),
            .value = AzFmtValue_Uint(d.ptr->counter)
        }});
        counter_string = AzString_format(AzString_fromConstStr("{counter}"), fmt_args);
    } else {
        return AzStyledDom_empty();
    }
    DataModelRef_delete(&d);

    AzDom const html = {
        .root = AzNodeData_new(AzNodeType_Body),
        .children = AzDomVec_fromConstArray({AzDom_new(AzNodeType_Label(counter_string))}),
        .total_children = 1, // len(children)
    };
    AzCss const css = AzCss_fromString(AzString_fromConstStr("body { font-size: 50px; }"));
    return AzStyledDom_new(html, css);
}

UpdateScreen update_counter(RefAny& data, CallbackInfo event) {
    DataModelRefMut d = DataModelRefMut_create(data);
    if !(DataModel_downcastRef(data, &d)) {
        return UpdateScreen_DoNothing;
    }
    d->ptr.counter += 1;
    DataModelRefMut_delete(&d);
    return UpdateScreen_RegenerateDomForCurrentWindow;
}

int main() {
    DataModel model = { .counter = 5 };
    AzApp app = AzApp_new(DataModel_upcast(model), AzAppConfig_default());
    AzApp_run(app, AzWindowCreateOptions_new(render_my_view));
    return 0;
}

Documentation

The documentation is built using the build.py script, which will generate the entire azul.rs website in the /target/html directory:

python3 ./build.py

NOTE: The class documentation can also be printed as a PDF if you prefer that.

License

This library is licensed under the LGPL version 3.0 with an exception for static linking. Which means that similar to the FLTK and wxWidgets license, you can build proprietary applications without having to publish your source code: you only have to publish changes made to the azul library itself. The static linking exception allows you to statically link Azul without having to publish your code.

Copyright 2017 - current Felix Schütt

Comments
  • Azul doesn't work on macOS due to

    Azul doesn't work on macOS due to "not yet implemented" error (missing implementation of shared OpenGL contexts)

    Description

    Crash attempting to run the examples.

    An unexpected panic ocurred, the program has to exit.
    Please report this error and attach the log file found in the directory of the executable.
    
    The error ocurred in: $HOME/.cargo/git/checkouts/azul-dependencies-70bb1f94316762f9/c154897/tomaka.glutin#23b3b10/src/platform/macos/mod.rs at line 61 in thread main
    
    Error information:
    not yet implemented
    
    Backtrace:
    
    azul::logging::set_up_panic_hooks::panic_fn @ logging.rs:86
    core::ops::function::Fn::call @ function.rs:69
    std::panicking::rust_panic_with_hook @ panicking.rs:478
    std::panicking::begin_panic @ panicking.rs:408
    glutin::platform::platform::Context::new @ mod.rs:61
    glutin::combined::CombinedContext::new @ combined.rs:58
    azul::window::create_gl_window @ window.rs:851
    azul::window::Window<T>::new @ window.rs:539
    azul::app::App<T>::create_window @ app.rs:287
    calculator::main @ calculator.rs:403
    std::rt::lang_start::{{closure}} @ rt.rs:64
    std::panicking::try::do_call @ panicking.rs:293
     @ lib.rs:87
    std::rt::lang_start_internal @ rt.rs:48
    std::rt::lang_start @ rt.rs:64
    

    Version / OS

    • azul version: master
    • Operating system: macOS Mojave version 10.14.4

    Steps to Reproduce

    git clone https://github.com/maps4print/azul.git cargo build cargo run --example calculator

    Additional Information

    Issue seems in statement below from $HOME/.cargo/git/checkouts/azul-dependencies-70bb1f94316762f9/c154897/tomaka.glutin#23b3b10/src/platform/macos/mod.rs at line 61, which runs panic on any example from list.

    if gl_attr.sharing.is_some() {
        unimplemented!()
    }
    
    bug platform:macos 
    opened by andrew-ignatiev 33
  • Build failed with

    Build failed with "failed to resolve: could not find `IoReader` in `bincode`" error

    Description

    warning: build failed, waiting for other jobs to finish... error: build failed PS L:\R\Coding\Rust\my_first_azul_app> cargo run Compiling webrender_api v0.60.0 error[E0433]: failed to resolve: could not find 'IoReader' in 'bincode' --> C:\Users\Admin\.cargo\registry\src\github.com-1ecc6299db9ec823\webrender_api-0.60.0\src\display_list.rs:270:35 | 270 | let reader = bincode::IoReader::new(UnsafeReader::new(&mut self.data)); | ^^^^^^^^ could not find 'IoReader' in 'bincode' error: aborting due to previous error For more information about this error, try 'rustc --explain E0433. error: could not compile 'webrender_api.

    Version / OS

    • azul version: 0.1

    • Operating system: Windows 10

    • Windowing system (X11 or Wayland, Linux only):

    Steps to Reproduce

    cargo run

    Additional Information

    CMake installed, default toolchain is stable-x86_64-pc-windows-msvc, MSVC installed

    bug 
    opened by ThisIsRex 27
  • Empty window for Simple Counter example

    Empty window for Simple Counter example

    Hello,

    I'm very excited to give this a try and reading the guide ATM: https://github.com/maps4print/azul/wiki/A-simple-counter

    But using the example code above simply shows an empty window without the label and the button: screen shot 2018-11-10 at 00 52 21

    macOS 10.14.1 Azul version: d39fde59c375c7a3a684a7c90bc8623521351e7e rustc 1.32.0-nightly (653da4fd0 2018-11-08)

    bug platform:macos 
    opened by yay 24
  • Build fails with VS 2019

    Build fails with VS 2019

    I cannot build azul.

    Description

    When I run cargo build on powershell, my shell displays

    error: failed to run custom build command for `harfbuzz-sys v0.3.0 (https://github.com/maps4print/azul-dependencies?rev=380b7e7cba8b728a3fc89fe28952e3b07aa624e7#380b7e7c)`
    process didn't exit successfully: `C:\Users\Shogo\Projects\azul\target\debug\build\harfbuzz-sys-edd981c7a9cf27bd\build-script-build` (exit code: 101)
    --- stdout
    cargo:rerun-if-env-changed=HARFBUZZ_SYS_NO_PKG_CONFIG
    
    --- stderr
    thread 'main' panicked at '
    
    couldn't determine visual studio generator
    if VisualStudio is installed, however, consider running the appropriate vcvars script before building this crate
    ', C:\Users\Shogo\.cargo\git\checkouts\azul-dependencies-70bb1f94316762f9\380b7e7\cmake-0.1.35\src\lib.rs:687:25
    note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
    

    With VS 2019's vcvars64,

    error: failed to run custom build command for `harfbuzz-sys v0.3.0 (https://github.com/maps4print/azul-dependencies?rev=380b7e7cba8b728a3fc89fe28952e3b07aa624e7#380b7e7c)`
    process didn't exit successfully: `C:\Users\Shogo\Projects\azul\target\debug\build\harfbuzz-sys-edd981c7a9cf27bd\build-script-build` (exit code: 101)
    --- stdout
    cargo:rerun-if-env-changed=HARFBUZZ_SYS_NO_PKG_CONFIG
    
    --- stderr
    thread 'main' panicked at '
    
    unsupported or unknown VisualStudio version: 16.0
    if another version is installed consider running the appropriate vcvars script before building this crate
    ', C:\Users\Shogo\.cargo\git\checkouts\azul-dependencies-70bb1f94316762f9\380b7e7\cmake-0.1.35\src\lib.rs:687:25
    note: Run with `RUST_BACKTRACE=1` environment variable to display a backtrace.
    

    Version / OS

    • azul version: since 7add48d77f33e517d11df57d0a76366c3c51aa8e

    • Operating system: Windows 10 64bit

    bug platform:windows 
    opened by moshg 20
  • [Feature Request] Allow error-propagation

    [Feature Request] Allow error-propagation

    Description

    I tried to propagate errors instead of letting the program panic! with unwrap() calls:

    fn start() -> Result<(), /* What to put here? */> {
        // Instantiate the app with default values.
        let mut app = App::new(DataModel::default(), AppConfig::default());
    
        // Create a new window.
        app.create_window(WindowCreateOptions::default(), Css::native())?;
    
        // Run the app.
        app.run()?
    }
    

    The example above illustrates the issue:

    • app.create_window returns a Result<(), WindowCreateError>
    • app.run returns a Result<T, RuntimeError<T>>

    But they do not share an Into (or From) implementation. In other words: There is a lack of an Error-implementation higher in the hierarchy.

    This forces the API-consumer to either unwrap all errors which:

    • Causes visual clutter in the code
    • Panics: Exactly the thing that the Error type should prevent

    Proposed solutions

    Option 1: Implement std::error::Error for all the top-level error-types in Azul

    From looking at the code, that would be:

    • CssParseError
    • FontError
    • ImageError
    • ClipboardError
    • WindowCreateError

    I'm not sure, but I think that those are the only errors returned from functions in the library.

    Option 2: Create one top-level azul::Error

    The azul::Error should then be implemented by all the errors mentioned in option 1.

    Which all other azul Errors can convert into. (Also see rfc-356 about stuttering names)

    Option 3: Kind-of combination of option 1 and option 2

    Creating one top-level azul::Error which implements std::error::Error. This allows API-consumers to use the azul::Error together with other libraries and use the errors interchangeably.

    This one is my favourite :)

    Is this a breaking change

    I'm not sure, option 2 and 3 may be be a breaking change?


    I'm willing to help and write the code if you find one of the solutions a good idea.

    Great job by the way, I like the library and I think it has a big potential of becoming a widely used GUI library for Rust (which is something Rust really needs).

    feature-request 
    opened by Xoronic 19
  • Linux Wayland glitches

    Linux Wayland glitches

    Description

    Running the Calculator and Table example under Wayland looks "out of shape".

    Version / OS

    • azul version: master from this commit

    • Operating system: Arch Linux 4.18.16 Gnome 3.30.1

    • Windowing system (X11 or Wayland, Linux only): Wayland

    Steps to Reproduce

    clone from the listed commit and run cargo run --example calculator

    Expected Behavior

    accurate layout

    Actual Behavior

    glitched layout

    Additional Information

    bug platform:linux 
    opened by pythoneer 17
  • Harfbuzz fails to build due to wrong Visual Studio version

    Harfbuzz fails to build due to wrong Visual Studio version

    Description

    rustup 1.18.3 (435397f48 2019-05-22)

    Version / OS

    • azul version: azul = { git = "https://github.com/maps4print/azul" }

    Steps to Reproduce

    Trying to build

    Additional Information

    Getting this error: error: failed to run custom build command for harfbuzz-sys v0.3.0 (https://github.com/maps4print/azul-dependencies?rev=bf2933b9aac43a7003278862772250398e4fa457#bf2933b9)

    Caused by: process didn't exit successfully: D:\RustProjects\azul_test\azulapp\target\debug\build\harfbuzz-sys-94af335e9d1d05e2\build-script-build (exit code: 101) --- stdout cargo:rerun-if-env-changed=HARFBUZZ_SYS_NO_PKG_CONFIG

    --- stderr thread 'main' panicked at '

    couldn't determine visual studio generator if VisualStudio is installed, however, consider running the appropriate vcvars script before building this crate ', C:\Users\user.cargo\git\checkouts\azul-dependencies-70bb1f94316762f9\bf2933b\cmake-0.1.35\src\lib.rs:687:25 note: Run with RUST_BACKTRACE=1 environment variable to display a backtrace.

    warning: build failed, waiting for other jobs to finish... error: build failed

    bug platform:windows 
    opened by redagrandrei 15
  • Why are dependencies vendored?

    Why are dependencies vendored?

    Hey! I pulled down Azul today to give it a shot with hello world, it's pretty great!

    I did notice that there was a gigantic Git checkout at the part of my first build, so I dug around and found that all the dependencies are in one giant repo, azul-dependencies.

    Why are dependencies vendored like this?

    It's super strange and makes it so that there's two versions of every crate that I have in common with Azul in my executable! It also blocks the entire download/compilation step of my application with a single giant Git clone.

    opened by LPGhatguy 15
  • UI blank and renders only after resize/click

    UI blank and renders only after resize/click

    Description

    When trying out the examples on my machine, I noticed that reproducibly the UI only shows after I force a redraw by resizing the window or clicking somewhere inside it.

    Version / OS

    • azul version: version = "0.1.0" source = "git+https://github.com/maps4print/azul#2068541297c8345b622a8a05c5e0ac690d1c154e"

    • Operating system: Linux Ubuntu 16.04

    • Windowing system (X11 or Wayland, Linux only): X11

    • Rust: rustc 1.30.1 (1433507eb 2018-11-07)

    Steps to Reproduce

    • Create a new cargo project with azul as dependency.
    • paste one of the azul examples in main.rs
    • cargo run

    Expected Behavior

    The window opens and immediately shows the rendered example.

    Actual Behavior

    The window is empty and only redraws the example when resizing the window or clicking somewhere.

    screenshot from 2018-11-25 12-25-03

    After clicking: screenshot from 2018-11-25 12-25-23

    Additional Information

    bug area:fonts 
    opened by r-arias 14
  • Running the HelloWorld application on windows panics

    Running the HelloWorld application on windows panics

    Description

    $ cargo run
        Finished dev [unoptimized + debuginfo] target(s) in 0.46s
         Running `target\debug\guitests.exe`
    [ERROR][azul::logging] An unexpected panic ocurred, the program has to exit.
    Please report this error and attach the log file found in the directory of the executable.
    
    The error ocurred in: libcore\result.rs at line 945 in thread main
    
    Error information:
    called `Result::unwrap()` on an `Err` value: CreateError(NotSupported("required extension \"WGL_ARB_create_context_profile\" not found"))
    
    Backtrace:
    
    backtrace::backtrace @ mod.rs:42
    backtrace::capture::Backtrace @ capture.rs:88
    backtrace::capture::Backtrace @ capture.rs:64
    azul::logging::set_up_panic_hooks @ logging.rs:87
    core::ops::function::Fn::call<fn(core::panic::PanicInfo*),(core::panic @ function.rs:73
    std::panicking @ panicking.rs:482
    std::panicking @ panicking.rs:390
    std::panicking @ panicking.rs:325
    core::panicking @ panicking.rs:77
    core::result::unwrap_failed<azul::window @ macros.rs:26
    core::result::Result<azul::window::Window<guitests::DataModel>, azul::window::WindowCreateError>::unwrap<azul::window::Window<guitests::DataModel>,azul::window @ result.rs:782
    guitests @ main.rs:28
    std::rt::lang_start @ rt.rs:74
    std::panicking::try @ panicking.rs:310
    panic_unwind @ lib.rs:105
    std::rt @ rt.rs:58
    std::rt @ rt.rs:74
     @ exe_common.inl:253
    
    error: process didn't exit successfully: `target\debug\guitests.exe` (exit code: 101)
    

    Version / OS

    • azul version: master
    • Operating system: Windows 8
    opened by fbstj 14
  • Everything is too huge

    Everything is too huge

    Description

    When I start the demo app, it is about twice as large as my screen. The font appears to be about double what it's supposed to be.

    Version / OS

    • azul version: 0.1.0

    • Operating system: Debian linux, openbox window manager

    • Windowing system (X11 or Wayland, Linux only): X11

    Expected Behavior

    Draw from system info that doesn't lie about the dpi or the screen size, or do some sanity checking to notice when that info is lies and do something sensible instead

    Actual Behavior

    Similar to Servo, everything is too huge (the problem might be upstream, but I'm reluctant to report it to servo, because in servo's case the issue is confounded with many other problems happening at the same time.)

    Additional Information

    This issue may have something to do with the fact I'm using a tv as a monitor. Until recently, many other apps had similar issues, either rendering text and icons way too large (most qt apps), or, strangely, in the case of openbox and tint2, rendering text way too small. Most apps, though (chrome, firefox, terminals, other gtk apps), got along fine.

    While reporting this bug, though, I got around to creating a ~/.Xresources file, containing Xft.dpi: 75. This has corrected all of the offending programs I was aware of, but it has not corrected the azul demo.

    bug platform:linux 
    opened by makoConstruct 13
  • C header fails to parse with clang

    C header fails to parse with clang

    Description

    Upon attempting to parse the C header for azul with clang, it fails with various errors

    Version / OS

    • azul version: master commit a1f9c526d4a2dfb79770717f7a63539e22f18a40

    • Operating system: Windows 10 and Arch Linux

    • Windowing system (X11 or Wayland, Linux only): Wayland

    Steps to Reproduce

    clang azul.h

    Additional Information

    azul.h:4064:18: error: expected expression
        AzFloatValue[;20] matrix;
                     ^
    azul.h:4064:17: error: expected member name or ';' after declaration specifiers
        AzFloatValue[;20] matrix;
        ~~~~~~~~~~~~^
    azul.h:4064:19: error: type name requires a specifier or qualifier
        AzFloatValue[;20] matrix;
                      ^
    azul.h:4064:19: error: expected member name or ';' after declaration specifiers
    azul.h:4064:19: error: expected ';' at end of declaration list
        AzFloatValue[;20] matrix;
                      ^
                      ;
    azul.h:4064:21: error: type name requires a specifier or qualifier
        AzFloatValue[;20] matrix;
                        ^
    azul.h:4064:21: error: expected member name or ';' after declaration specifiers
    azul.h:4064:21: error: expected ';' at end of declaration list
        AzFloatValue[;20] matrix;
                        ^
                        ;
    azul.h:6436:13: error: expected expression
        uint8_t[; 10] panose;
                ^
    azul.h:6436:12: error: expected member name or ';' after declaration specifiers
        uint8_t[; 10] panose;
        ~~~~~~~^
    azul.h:6436:15: error: type name requires a specifier or qualifier
        uint8_t[; 10] panose;
                  ^
    azul.h:6436:15: error: expected member name or ';' after declaration specifiers
    azul.h:6436:14: error: expected ';' at end of declaration list
        uint8_t[; 10] panose;
                 ^
                 ;
    azul.h:6436:17: error: type name requires a specifier or qualifier
        uint8_t[; 10] panose;
                    ^
    azul.h:6436:17: error: expected member name or ';' after declaration specifiers
    azul.h:6436:17: error: expected ';' at end of declaration list
        uint8_t[; 10] panose;
                    ^
                    ;
    azul.h:9725:1: error: use of 'AzMenuItem' with tag type that does not match previous declaration
    union AzMenuItem {
    ^~~~~
    struct
    azul.h:6591:8: note: previous use is here
    struct AzMenuItem;
           ^
    azul.h:9730:9: error: use of 'AzMenuItem' with tag type that does not match previous declaration
    typedef union AzMenuItem AzMenuItem;
            ^~~~~
            struct
    azul.h:9725:7: note: previous use is here
    union AzMenuItem {
          ^
    azul.h:12376:46: error: 'void' must be the first and only parameter if specified
    extern DLLIMPORT AzRefAny AzRefAny_newC(void ptr, size_t len, uint64_t type_id, AzString  type_name, AzRefAnyDestructorType  destructor);
                                                 ^
    fatal error: too many errors emitted, stopping now [-ferror-limit=]
    20 errors generated.
    

    (this error log taken from linux, but happens the same on windows too)

    bug 
    opened by Beyley 0
  • Bump lyon from 0.17.10 to 1.0.1

    Bump lyon from 0.17.10 to 1.0.1

    Bumps lyon from 0.17.10 to 1.0.1.

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    dependencies 
    opened by dependabot[bot] 0
  • Bump usvg from 0.22.0 to 0.24.0

    Bump usvg from 0.22.0 to 0.24.0

    Bumps usvg from 0.22.0 to 0.24.0.

    Release notes

    Sourced from usvg's releases.

    v0.24.0

    • viewsvg is a simple application that showcases resvg capabilities
    • resvg-0.*.0.tar.xz is a sources archive with vendored Rust dependencies
    • resvg-explorer-extension.exe is an SVG thumbnailer for Windows Explorer

    v0.23.0

    • viewsvg is a simple application that showcases resvg capabilities
    • resvg-0.*.0.tar.xz is a sources archive with vendored Rust dependencies
    • resvg-explorer-extension.exe is an SVG thumbnailer for Windows Explorer
    Changelog

    Sourced from usvg's changelog.

    [0.24.0] - 2022-10-22

    Added

    • CSS3 writing-mode variants vertical-rl and vertical-lr. Thanks to yisibl.
    • (tiny-skia) AArch64 Neon SIMD support. Up to 3x faster on Apple M1.

    Changed

    • usvg::Tree stores only Group, Path and Image nodes now. Instead of emulating an SVG file structure, where gradients, patterns, filters, clips and masks are part of the nodes tree (usually inside the defs element), we reference them using Rc from now. This change makes usvg a bit simpler. Makes usvg API way easier, since instead of looking for a node via usvg::Tree::defs_by_id the caller can access the type directly via Rc. And makes creation of custom usvg::Trees way easier.
    • clip_path, mask and filters usvg::Group fields store Rc instead of String now.
    • usvg::NodeExt::units was moved to usvg::Paint::units.
    • usvg::filter::ImageKind::Use stores usvg::Node instead of String.
    • usvg::PathData stores commands and points separately now to reduce overall memory usage.
    • usvg::PathData segments should be accessed via segments() now.
    • Most numeric types have been moved to the strict-num crate.
    • Rename NormalizedValue into NormalizedF64.
    • Rename PositiveNumber into PositiveF64.
    • Raw number of numeric types should be accessed via get() method instead of value() now.
    • usvg::TextSpan::font_size is NonZeroPositiveF64 instead of f64 now.
    • Re-export usvg and tiny-skia dependencies in resvg.
    • Re-export roxmltree dependency in usvg.
    • (usvg) Output float precision is reduced from 11 to 8 digits.

    Removed

    • usvg::Tree::create. usvg::Tree is an open struct now.
    • usvg::Tree::root. It's a public field now.
    • usvg::Tree::svg_node. Replaced with usvg::Tree public fields.
    • defs, is_in_defs, append_to_defs and defs_by_id from usvg::Tree. We no longer emulate SVG structure. No alternative.
    • usvg::Tree::is_in_defs. There are no defs anymore.
    • usvg::Paint::Link. We store gradient and patterns directly in usvg::Paint now.
    • usvg::Svg. No longer needed. size and view_box are usvg::Tree fields now.
    • usvg::SubPathIter and usvg::PathData::subpaths. No longer used.

    Fixed

    • Path bbox calculation scales stroke width too. Thanks to growler.
    • (tiny-skia) Round caps roundness.
    • (xmlparser) Stack overflow on specific files.
    • (c-api) resvg_is_image_empty output was inverted.

    [0.23.0] - 2022-06-11

    Added

    • #RRGGBBAA and #RGBA color notation support. Thanks to demurgos.

    ... (truncated)

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    dependencies 
    opened by dependabot[bot] 0
  • Bump resvg from 0.22.0 to 0.24.0

    Bump resvg from 0.22.0 to 0.24.0

    Bumps resvg from 0.22.0 to 0.24.0.

    Release notes

    Sourced from resvg's releases.

    v0.24.0

    • viewsvg is a simple application that showcases resvg capabilities
    • resvg-0.*.0.tar.xz is a sources archive with vendored Rust dependencies
    • resvg-explorer-extension.exe is an SVG thumbnailer for Windows Explorer

    v0.23.0

    • viewsvg is a simple application that showcases resvg capabilities
    • resvg-0.*.0.tar.xz is a sources archive with vendored Rust dependencies
    • resvg-explorer-extension.exe is an SVG thumbnailer for Windows Explorer
    Changelog

    Sourced from resvg's changelog.

    [0.24.0] - 2022-10-22

    Added

    • CSS3 writing-mode variants vertical-rl and vertical-lr. Thanks to yisibl.
    • (tiny-skia) AArch64 Neon SIMD support. Up to 3x faster on Apple M1.

    Changed

    • usvg::Tree stores only Group, Path and Image nodes now. Instead of emulating an SVG file structure, where gradients, patterns, filters, clips and masks are part of the nodes tree (usually inside the defs element), we reference them using Rc from now. This change makes usvg a bit simpler. Makes usvg API way easier, since instead of looking for a node via usvg::Tree::defs_by_id the caller can access the type directly via Rc. And makes creation of custom usvg::Trees way easier.
    • clip_path, mask and filters usvg::Group fields store Rc instead of String now.
    • usvg::NodeExt::units was moved to usvg::Paint::units.
    • usvg::filter::ImageKind::Use stores usvg::Node instead of String.
    • usvg::PathData stores commands and points separately now to reduce overall memory usage.
    • usvg::PathData segments should be accessed via segments() now.
    • Most numeric types have been moved to the strict-num crate.
    • Rename NormalizedValue into NormalizedF64.
    • Rename PositiveNumber into PositiveF64.
    • Raw number of numeric types should be accessed via get() method instead of value() now.
    • usvg::TextSpan::font_size is NonZeroPositiveF64 instead of f64 now.
    • Re-export usvg and tiny-skia dependencies in resvg.
    • Re-export roxmltree dependency in usvg.
    • (usvg) Output float precision is reduced from 11 to 8 digits.

    Removed

    • usvg::Tree::create. usvg::Tree is an open struct now.
    • usvg::Tree::root. It's a public field now.
    • usvg::Tree::svg_node. Replaced with usvg::Tree public fields.
    • defs, is_in_defs, append_to_defs and defs_by_id from usvg::Tree. We no longer emulate SVG structure. No alternative.
    • usvg::Tree::is_in_defs. There are no defs anymore.
    • usvg::Paint::Link. We store gradient and patterns directly in usvg::Paint now.
    • usvg::Svg. No longer needed. size and view_box are usvg::Tree fields now.
    • usvg::SubPathIter and usvg::PathData::subpaths. No longer used.

    Fixed

    • Path bbox calculation scales stroke width too. Thanks to growler.
    • (tiny-skia) Round caps roundness.
    • (xmlparser) Stack overflow on specific files.
    • (c-api) resvg_is_image_empty output was inverted.

    [0.23.0] - 2022-06-11

    Added

    • #RRGGBBAA and #RGBA color notation support. Thanks to demurgos.

    ... (truncated)

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    dependencies 
    opened by dependabot[bot] 0
  • get rid of four year old xcb dependency

    get rid of four year old xcb dependency

    Description

    This project ships a Cargo.lock (which is good, considering that it also is meant to be build-able as binary to provide the azul-dll), which unfortunately contains a very old version of xcb. This very old version of xcb generates code into the cargo-vendor-dir, which makes it impossible to compile azul in the nix ecosystem, since the cargo-vendor-dir resides in the read-only nix store, causing any attempt to write a file to it to fail. Generally I think its also considered just wrong to write to the cargo vendor dir, there is an environment variable for where to generate artifacts (OUT I think?).

    Edit: This dependency is introduced via azul-desktop/clipboard2, which hasn't been touched in the last 4 years and pinpoints x11-clipboard to version 0.3.0-alpha.1, which again is 4 years old and has reached version 0.7.0 by now. I think it would be good to update some of the transitive dependencies of the stuff involved.

    bug 
    opened by wucke13 1
  • Bump strfmt from 0.1.6 to 0.2.2

    Bump strfmt from 0.1.6 to 0.2.2

    Bumps strfmt from 0.1.6 to 0.2.2.

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    dependencies 
    opened by dependabot[bot] 0
Releases(1.0.0-alpha1)
Owner
Felix Schütt
Felix Schütt
Simple and portable (but not inflexible) GUI library in C that uses the native GUI technologies of each platform it supports.

libui: a portable GUI library for C This README is being written. Status It has come to my attention that I have not been particularly clear about how

Pietro Gagliardi 10.4k Dec 31, 2022
A simple, cross-platform GUI automation module for Rust.

AutoPilot AutoPilot is a Rust port of the Python C extension AutoPy, a simple, cross-platform GUI automation library for Python. For more information,

null 271 Dec 27, 2022
An easy-to-use, 2D GUI library written entirely in Rust.

Conrod An easy-to-use, 2D GUI library written entirely in Rust. Guide What is Conrod? A Brief Summary Screenshots and Videos Feature Overview Availabl

PistonDevelopers 3.3k Jan 1, 2023
Rust bindings for the FLTK GUI library.

fltk-rs Rust bindings for the FLTK Graphical User Interface library. The FLTK crate is a crossplatform lightweight gui library which can be statically

Mohammed Alyousef 1.1k Jan 9, 2023
Idiomatic, GTK+-based, GUI library, inspired by Elm, written in Rust

Relm Asynchronous, GTK+-based, GUI library, inspired by Elm, written in Rust. This library is in beta stage: it has not been thoroughly tested and its

null 2.2k Dec 31, 2022
Clear Coat is a Rust wrapper for the IUP GUI library.

Clear Coat Clear Coat is a Rust wrapper for the IUP GUI library. IUP uses native controls and has Windows and GTK backends. A macOS backend has been o

Jordan Miner 18 Feb 13, 2021
A single-header ANSI C immediate mode cross-platform GUI library

Nuklear This is a minimal-state, immediate-mode graphical user interface toolkit written in ANSI C and licensed under public domain. It was designed a

Immediate Mode UIs, Nuklear, etc. 6.9k Jan 8, 2023
The bindings to the Nuklear 2D immediate GUI library.

nuklear-rust The bindings to the Nuklear 2D immediate GUI library. Currently beta. Drawing backends: gfx-pre-ll for GFX 3D drawing engine (examples: O

Serhii Plyhun 332 Dec 27, 2022
A cross-platform GUI library for Rust, inspired by Elm

Iced A cross-platform GUI library for Rust focused on simplicity and type-safety. Inspired by Elm. Features Simple, easy-to-use, batteries-included AP

Héctor Ramón 17.5k Jan 2, 2023
Truly cross platform, truly native. multiple backend GUI for rust

WIP: Sauron-native a rust UI library that conquers all platforms ranging from desktop to mobile devices. An attempt to create a truly native, truly cr

Jovansonlee Cesar 627 Jan 5, 2023
A GUI for Cargo

A GUI for Cargo This is a project to make a GUI for cargo, built using SixtyFPS: The idea cargo install cargo-ui cargo ui Prerequisites In addition to

SixtyFPS 128 Dec 28, 2022
A cross-platform GUI library for Rust focused on simplicity and type-safety

A cross-platform GUI library for Rust, inspired by Elm

Héctor Ramón 17.5k Jan 8, 2023
Automatically create GUI applications from clap3 apps

Automatically create GUI applications from clap3 apps

Michał Gniadek 340 Dec 20, 2022
A simple news reading GUI app built in Rust

Headlines [WIP] A native GUI app built with Rust using egui. Uses newsapi.org as the source to fetch news articles. This is a WIP and the current stat

creativcoder 89 Dec 29, 2022
Build GUI applications with minimal dependencies in Rust

winapi-app-windows A crate to build applications' windows in Windows using WinAPI. This would be less confusing if the operating system was called som

Lonami 5 Jul 26, 2022
A simple GUI version of the pH calibration tool written in egui, based on the eframe template.

caliphui A simple GUI version of the pH calibration tool written in egui, based on the eframe template. Usage Native binaries are provided under relea

Peter Dunne 0 Dec 29, 2021
GUI based tool to sort and categorize images written in Rust

ImageSieve GUI based tool to sort out images based on similarity, categorize them according to their creation date and archive them in a target folder

Florian Fetz 67 Dec 14, 2022
Simplify generating an fltk gui from a data structure

This crate aims to simplify generating gui from a data structure.

fltk-rs 3 Dec 19, 2021
An idiomatic GUI library inspired by Elm and based on gtk4-rs

An idiomatic GUI library inspired by Elm and based on gtk4-rs. Relm4 is a new version of relm that's built from scratch and is compatible with GTK4 an

Aaron Erhardt 722 Dec 31, 2022