arsd.simpledisplay
simpledisplay
.d provides basic cross-platform GUI-related functionality,
including creating windows, drawing on them, working with the clipboard,
timers, OpenGL, and more. However, it does NOT provide high level GUI
widgets. See my minigui.d, an extension to this module, for that
functionality.
Discussion
simpledisplay
provides cross-platform wrapping for Windows and Linux
(and perhaps other OSes that use X11), but also does not prevent you
from using the underlying facilities if you need them. It has a goal
of working efficiently over a remote X link (at least as far as Xlib
reasonably allows.)
simpledisplay
depends on [arsd.color|color.d], which should be available from the
same place where you got this file. Other than that, however, it has
very few dependencies and ones that don't come with the OS and/or the
compiler are all opt-in.
simpledisplay
.d's home base is on my arsd repo on Github. The file is:
https:
//github.com/adamdruppe/arsd/blob/master/simpledisplay
.d
simpledisplay
is basically stable. I plan to refactor the internals,
and may add new features and fix bugs, but It do not expect to
significantly change the API. It has been stable a few years already now.
Jump list:
Don't worry, you don't have to read this whole documentation file!
Check out the [#Event-example] and [#Pong-example] to get started quickly.
The main classes you may want to create are [SimpleWindow], [Timer],
[Image], and [Sprite].
The main functions you'll want are [setClipboardText] and [getClipboardText].
There are also platform-specific functions available such as [XDisplayConnection]
and [GetAtom] for X11, among others.
See the examples and topics list below to learn more.
The goal here is to give some complete programs as overview examples first, then a look at each major feature with working examples first, then, finally, the inline class and method list will follow.
Scan for headers for a topic - they will visually stand out - you're interested in to get started quickly and feel free to copy and paste any example as a starting point for your program. I encourage you to learn the library by experimenting with the examples!
All examples are provided with no copyright restrictions whatsoever. You do not need to credit me or carry any kind of notice with the source if you copy and paste from them.
To get started, download
and simpledisplay
.dcolor.d
to a working directory. Copy an example info a file called example.d
and compile using the command given at the top of each example.
If you need help, email me: destructionator@gmail.com or IRC us, #d on Freenode (I am destructionator or adam_d_ruppe there). If you learn something that isn't documented, I appreciate pull requests on github to this file.
At points, I will talk about implementation details in the documentation. These are sometimes
subject to change, but nevertheless useful to understand what is really going on. You can learn
more about some of the referenced things by searching the web for info about using them from C.
You can always look at the source of simpledisplay
.d too for the most authoritative source on
its specific implementation. If you disagree with how I did something, please contact me so we
can discuss it!
Examples
This program creates a window and draws events inside them as they
happen, scrolling the text in the window as needed. Run this program
and experiment to get a feel for where basic input events take place
in the library.
// dmd example.d simpledisplay.d color.d
import arsd.simpledisplay;
import std.conv;
void main() {
auto window = new SimpleWindow(Size(500, 500), "My D App");
int y = 0;
void addLine(string text) {
auto painter = window.draw();
if(y + painter.fontHeight >= window.height) {
painter.scrollArea(Point(0, 0), window.width, window.height, 0, painter.fontHeight);
y -= painter.fontHeight;
}
painter.outlineColor = Color.red;
painter.fillColor = Color.black;
painter.drawRectangle(Point(0, y), window.width, painter.fontHeight);
painter.outlineColor = Color.white;
painter.drawText(Point(10, y), text);
y += painter.fontHeight;
}
window.eventLoop(1000,
() {
addLine("Timer went off!");
},
(KeyEvent event) {
addLine(to!string(event));
},
(MouseEvent event) {
addLine(to!string(event));
},
(dchar ch) {
addLine(to!string(ch));
}
);
}
// dmd example.d simpledisplay.d color.d
import arsd.simpledisplay;
enum paddleMovementSpeed = 8;
enum paddleHeight = 48;
void main() {
auto window = new SimpleWindow(600, 400, "Pong game!");
int playerOnePosition, playerTwoPosition;
int playerOneMovement, playerTwoMovement;
int playerOneScore, playerTwoScore;
int ballX, ballY;
int ballDx, ballDy;
void serve() {
import std.random;
ballX = window.width / 2;
ballY = window.height / 2;
ballDx = uniform(-4, 4) * 3;
ballDy = uniform(-4, 4) * 3;
if(ballDx == 0)
ballDx = uniform(0, 2) == 0 ? 3 : -3;
}
serve();
window.eventLoop(50, // set a 50 ms timer pulls
// This runs once per timer pulse
delegate () {
auto painter = window.draw();
painter.clear();
// Update everyone's motion
playerOnePosition += playerOneMovement;
playerTwoPosition += playerTwoMovement;
ballX += ballDx;
ballY += ballDy;
// Bounce off the top and bottom edges of the window
if(ballY + 7 >= window.height)
ballDy = -ballDy;
if(ballY - 8 <= 0)
ballDy = -ballDy;
// Bounce off the paddle, if it is in position
if(ballX - 8 <= 16) {
if(ballY + 7 > playerOnePosition && ballY - 8 < playerOnePosition + paddleHeight) {
ballDx = -ballDx + 1; // add some speed to keep it interesting
ballDy += playerOneMovement; // and y movement based on your controls too
ballX = 24; // move it past the paddle so it doesn't wiggle inside
} else {
// Missed it
playerTwoScore ++;
serve();
}
}
if(ballX + 7 >= window.width - 16) { // do the same thing but for player 1
if(ballY + 7 > playerTwoPosition && ballY - 8 < playerTwoPosition + paddleHeight) {
ballDx = -ballDx - 1;
ballDy += playerTwoMovement;
ballX = window.width - 24;
} else {
// Missed it
playerOneScore ++;
serve();
}
}
// Draw the paddles
painter.outlineColor = Color.black;
painter.drawLine(Point(16, playerOnePosition), Point(16, playerOnePosition + paddleHeight));
painter.drawLine(Point(window.width - 16, playerTwoPosition), Point(window.width - 16, playerTwoPosition + paddleHeight));
// Draw the ball
painter.fillColor = Color.red;
painter.outlineColor = Color.yellow;
painter.drawEllipse(Point(ballX - 8, ballY - 8), Point(ballX + 7, ballY + 7));
// Draw the score
painter.outlineColor = Color.blue;
import std.conv;
painter.drawText(Point(64, 4), to!string(playerOneScore));
painter.drawText(Point(window.width - 64, 4), to!string(playerTwoScore));
},
delegate (KeyEvent event) {
// Player 1's controls are the arrow keys on the keyboard
if(event.key == Key.Down)
playerOneMovement = event.pressed ? paddleMovementSpeed : 0;
if(event.key == Key.Up)
playerOneMovement = event.pressed ? -paddleMovementSpeed : 0;
},
delegate (MouseEvent event) {
// Player 2's controls are mouse movement while the left button is held down
if(event.type == MouseEventType.motion && (event.modifierState & ModifierState.leftButtonDown)) {
if(event.dy > 0)
playerTwoMovement = paddleMovementSpeed;
else if(event.dy < 0)
playerTwoMovement = -paddleMovementSpeed;
} else {
playerTwoMovement = 0;
}
}
);
}
simpledisplay
, and its other stand-alone support modules, simpleaudio.d and joystick.d, too.
This program displays a pie chart. Clicking on a color will increase its share of the pie.
simpledisplay
's flagship feature. It represents a single
window on the user's screen.
You may create multiple windows, if the underlying platform supports it. You may check
static if(multipleWindowsSupported)
at compile time, or catch exceptions thrown by
SimpleWindow's constructor at runtime to handle those cases.
A single running event loop will handle as many windows as needed.
setEventHandlers function
eventLoop function
draw function
title property
The simpledisplay
event loop is designed to handle common cases easily while being extensible for more advanced cases, or replaceable by other libraries.
The most common scenario is creating a window, then calling window.eventLoop
when setup is complete. You can pass several handlers to the eventLoop
method right there:
// dmd example.d simpledisplay.d color.d
import arsd.simpledisplay;
void main() {
auto window = new SimpleWindow(200, 200);
window.eventLoop(0,
delegate (dchar) { /* got a character key press */ }
);
}
epoll
system call for efficiency an extensibility to other files. On Windows, it runs a traditional GetMessage
+ DispatchMessage
loop, with a call to SleepEx
in each iteration to allow the thread to enter an alertable wait state regularly, primarily so Overlapped I/O callbacks will get a chance to run.
On Linux, simpledisplay
also supports my arsd.eventloop
module. Compile your program, including the eventloop.d file, with the -version=with_eventloop
switch.
It should be possible to integrate simpledisplay
with vibe.d as well, though I haven't tried.
Notification area icons are currently only implemented on X11 targets. Windows support will come when I need it (or if someone requests it and I have some time to spend on it).
There are event handlers for low-level keyboard and mouse events, and higher level handlers for character events.
To draw on your window, use the window.draw
method. It returns a [ScreenPainter] structure with drawing methods.
Important:
ScreenPainter
double-buffers and will not actually update the window until its destructor is run. Always ensure the painter instance goes out-of-scope before proceeding. You can do this by calling it inside an event handler, a timer callback, or an small scope inside main. For example:
// dmd example.d simpledisplay.d color.d
import arsd.simpledisplay;
void main() {
auto window = new SimpleWindow(200, 200);
{ // introduce sub-scope
auto painter = window.draw(); // begin drawing
/* draw here */
painter.outlineColor = Color.red;
painter.fillColor = Color.black;
painter.drawRectangle(Point(0, 0), 200, 200);
} // end scope, calling `painter`'s destructor, drawing to the screen.
window.eventLoop(0); // handle events
}
simpledisplay
can create OpenGL contexts on your window. It works quite differently than 2d drawing.
Note that it is still possible to draw 2d on top of an OpenGL window, using the draw
method, though I don't recommend it.
To start, you create a SimpleWindow
with OpenGL enabled by passing the argument OpenGlOptions.yes
to the constructor.
Next, you set redrawOpenGlScene
to a delegate which draws your frame.
To force a redraw of the scene, call window.redrawOpenGlSceneNow()
.
Please note that my experience with OpenGL is very out-of-date, and the bindings in simpledisplay
reflect that. If you want to use more modern functions, you may have to define the bindings yourself, or import them from another module. However, I believe the OpenGL context creation done in simpledisplay
will work for any version.
This example program will draw a rectangle on your window:
// dmd example.d simpledisplay.d color.d
import arsd.simpledisplay;
void main() {
}
png.d
.
// dmd example.d simpledisplay.d color.d png.d
import arsd.simpledisplay;
import arsd.png;
void main() {
auto image = Image.fromMemoryImage(readPng("image.png"));
displayImage(image);
}
dmd example.d
.
If you find an image file which is a valid png that simpledisplay
.d png.darsd.png
fails to load, please let me know. In the mean time of fixing the bug, you can probably convert the file into an easier-to-load format. Be sure to turn OFF png interlacing, as that isn't supported. Other things to try would be making the image smaller, or trying 24 bit truecolor mode with an alpha channel.
The [Sprite] class is used to make images on the display server for fast blitting to screen. This is especially important to use to support fast drawing of repeated images on a remote X11 link.
The free functions [getClipboardText] and [setClipboardText] consist of simpledisplay
's cross-platform clipboard support at this time.
It also has helpers for handling X-specific events.
There are two timers in simpledisplay
: one is the pulse timeout you can set on the call to window.eventLoop
, and the other is a customizable class, [Timer].
The pulse timeout is used by setting a non-zero interval as the first argument to eventLoop
function and adding a zero-argument delegate to handle the pulse.
import arsd.simpledisplay;
void main() {
auto window = new SimpleWindow(400, 400);
// every 100 ms, it will draw a random line
// on the window.
window.eventLoop(100, {
auto painter = window.draw();
import std.random;
// random color
painter.outlineColor = Color(uniform(0, 256), uniform(0, 256), uniform(0, 256));
// random line
painter.drawLine(
Point(uniform(0, window.width), uniform(0, window.height)),
Point(uniform(0, window.width), uniform(0, window.height)));
});
}
Timer
class works similarly, but is created separately from the event loop. (It still fires through the event loop, though.) You may make as many instances of Timer
as you wish.
The pulse timer and instances of the [Timer] class may be combined at will.
import arsd.simpledisplay;
void main() {
auto window = new SimpleWindow(400, 400);
auto timer = new Timer(1000, delegate {
auto painter = window.draw();
painter.clear();
});
window.eventLoop(0);
}
SetTimer
and Linux, using timerfd_create
. These deliver timeout messages through your application event loop.
simpledisplay
carries a lot of code to help implement itself without extra dependencies, and much of this code is available for you too, so you may extend the functionality yourself.
See also: xwindows.d
from my github.
handleNativeEvent
and handleNativeGlobalEvent
.
Integration with a third-party event loop is possible.
On Linux, you might want to support both terminal input and GUI input. You can do this by using simpledisplay
together with eventloop.d and terminal.d.
simpledisplay
does not provide GUI widgets such as text areas, buttons, checkboxes, etc. It only gives basic windows, the ability to draw on it, receive input from it, and access native information for extension. You may write your own gui widgets with these, but you don't have to because I already did for you!
Download minigui.d
from my github repository and add it to your project. minigui builds these things on top of simpledisplay
and offers its own Window class (and subclasses) to use that wrap SimpleWindow, adding a new event and drawing model that is hookable by subwidgets, represented by their own classes.
Migrating to minigui from simpledisplay
is often easy though, because they both use the same ScreenPainter API, and the same simpledisplay
events are available, if you want them. (Though you may like using the minigui model, especially if you are familiar with writing web apps in the browser with Javascript.)
minigui still needs a lot of work to be finished at this time, but it already offers a number of useful classes.
I don't have a Mac, so that code isn't maintained. I would like to have a Cocoa
implementation though.
The NativeSimpleWindowImplementation and NativeScreenPainterImplementation both
suck. If I was rewriting it, I wouldn't do it that way again.
This file must not have any more required dependencies. If you need bindings, add
them right to this file. Once it gets into druntime and is there for a while, remove
bindings from here to avoid conflicts (or put them in an appropriate version block
so it continues to just work on old dmd), but wait a couple releases before making the
transition so this module remains usable with older versions of dmd.
You may have optional dependencies if needed by putting them in version blocks or
template functions. You may also extend the module with other modules with UFCS without
actually editing this - that is nice to do if you can.
Try to make functions work the same way across operating systems. I typically make
it thinly wrap Windows, then emulate that on Linux.
A goal of this is to keep a gui hello world to less than 250 KB. This means avoiding
Phobos! So try to avoid it.
See more comments throughout the source.
I realize this file is fairly large, but over half that is just bindings at the bottom
or documentation at the top. Some of the classes are a bit big too, but hopefully easy
to understand. I suggest you jump around the source by looking for a particular
declaration you're interested in, like class SimpleWindow
using your editor's search
function, then look at one piece at a time.
License
Copyright Adam D. Ruppe, 2011-2016. Released under the Boost Software License.
Building documentation: You may wish to use the arsd.ddoc
file from my github with
building the documentation for simpledisplay
yourself. It will give it a bit more style.
Simply download the arsd.ddoc file and add it to your compile command when building docs.
dmd -c
simpledisplay
.d color.d -D arsd.ddoc
-
Declaration
enum bool
UsingSimpledisplayX11
;If you have to get down and dirty with implementation details, this helps figure out if X is available you can
static if(
more reliably thanUsingSimpledisplayX11
) ...version()
becauseversion
is module-local. -
Declaration
enum bool
multipleWindowsSupported
;Does this platform support multiple windows? If not, trying to create another will cause it to throw an exception.
-
Declaration
enum
WindowFlags
: int;After selecting a type from [WindowTypes], you may further customize its behavior by setting one or more of these flags.
Discussion
The different window types have different meanings of
normal
. If the window type already is a good match for what you want to do, you should just use [WindowFlags
.normal], the default, which will do the right thing for your users. -
Declaration
enum
WindowTypes
: int;When creating a window, you can pass a type to SimpleWindow's constructor, then further customize the window by changing
WindowFlags
.Discussion
This list is based on the EMWH spec for X11.
http: //standards.freedesktop.org/wm-spec/1.4/ar01s05.html#idm139704063786896
-
Declaration
normal
An ordinary application window.
-
Declaration
undecorated
A generic window without a title bar or border. You can draw on the entire area of the screen it takes up and use it as you wish. Remember that users don't really expect these though, so don't use it where a window of any other type is appropriate.
-
-
Declaration
void
setOpenGLContextVersion
()(ubytehi
, ubytelo
);Set OpenGL context version to use. This has no effect on non-OpenGL windows. You may want to change context version if you want to use advanced shaders or other modern OpenGL techinques. This setting doesn't affect already created windows. You may use version 2.1 as your default, which should be supported by any box since 2006, so seems to be a reasonable choice.
Discussion
Note that by default version is set to
0
, which forces SimpleDisplay to use old context creation code without any version specified. This is the safest way to init OpenGL, but it may not give you access to advanced features. See available OpenGL versions here: https://en.wikipedia.org/wiki/OpenGL -
Declaration
@property void
openGLContextCompatible
()(boolv
);Set OpenGL context mode. Modern (3.0+) OpenGL versions deprecated old fixed pipeline functions, and without "compatible" mode you won't be able to use your old non-shader-based code with such contexts. By default SimpleDisplay creates compatible context, so you can gradually upgrade your OpenGL code if you want to (or leave it as is, as it should "just work").
-
Declaration
@property void
openGLContextAllowFallback
()(boolv
);Set to
true
to allow creating OpenGL context with lower version than requested instead of throwing. If fallback was activated (or legacy OpenGL was requested),openGLContextFallbackActivated()
will returntrue
. -
Declaration
@property bool
openGLContextFallbackActivated
()();After creating OpenGL window, you can check this to see if you got only "legacy" OpenGL context.
-
Declaration
void
sdpyWindowClass
(const(char)[]v
);Set window class name for all following
new SimpleWindow()
calls.Discussion
WARNING! For Windows, you should set your class name before creating any window, and NEVER change it after that!
-
Declaration
string
sdpyWindowClass
();Get current window class name.
-
Declaration
class
SimpleWindow
: arsd.simpledisplay.CapableOfHandlingNativeEvent;The flagship window class.
Discussion
SimpleWindow
tries to make ordinary windows very easy to create and use without locking you out of more advanced or complex features of the underlying windowing system. For many applications, you can simply callnew
and get a suitable window to work with. From there, you can opt into additional features, like custom resizability and OpenGL support with the next two constructor arguments. Or, if you need even more, you can set a window type and customization flags with the final two constructor arguments. If none of that works for you, you can also create a window using native function calls, then wrap the window in aSimpleWindow
(some_width, some_height, "some title")SimpleWindow
instance by callingnew
. Remember, though, if you do this, managing the window is still your own responsibility! Notably, you will need to destroy it yourself.SimpleWindow
(native_handle)-
Declaration
this(int
width
= 640, intheight
= 480, stringtitle
= null, OpenGlOptionsopengl
= OpenGlOptions.no, Resizablityresizable
= Resizablity.automaticallyScaleIfPossible, WindowTypeswindowType
= WindowTypes.normal, intcustomizationFlags
= WindowFlags.normal, SimpleWindowparent
= null);This creates a window with the given options. The window will be visible and able to receive input as soon as you start your event loop. You may draw on it immediately after creating the window, without needing to wait for the event loop to start if you want.
Discussion
The constructor tries to have sane default arguments, so for many cases, you only need to provide a few of them.
Parameters
int
width
the
width
of the window's client area, in pixelsint
height
the
height
of the window's client area, in pixelsstring
title
the
title
of the window (seen in thetitle
bar, taskbar, etc.). You can change it after construction with the [SimpleWindow.title
\ property.OpenGlOptions
opengl
[OpenGlOptions] are yes and no. If yes, it creates an OpenGL context on the window.
Resizablity
resizable
[Resizablity] has three options:
allowResizing
, which allows the window to be resized by the user. ThewindowResized
delegate will be called when the size is changed.fixedSize
will not allow the user to resize the window.automaticallyScaleIfPossible
will allow the user to resize, but will still present the original size to the API user. The contents you draw will be scaled to the size the user chose. If this scaling is not efficient, the window will be fixed size. ThewindowResized
event handler will never be called. This is the default.WindowTypes
windowType
The type of window you want to make.
int
customizationFlags
A way to make a window without a border, always on top, skip taskbar, and more. Do not use this if one of the pre-defined [WindowTypes], given in the
argument, is a good match for what you need.windowType
SimpleWindow
parent
the
parent
window, if applicable -
Declaration
this(Size
size
, stringtitle
= null, OpenGlOptionsopengl
= OpenGlOptions.no, Resizablityresizable
= Resizablity.automaticallyScaleIfPossible);Same as above, except using the
Size
struct instead of separate width and height. -
Declaration
this(Image
image
, stringtitle
= null);Creates a window based on the given [Image]. It's client area width and height is equal to the
image
. (A window's client area is the drawable space inside; it excludes thetitle
bar, etc.)Discussion
Windows based on images will not be resizable and do not use OpenGL.
-
Declaration
this(NativeWindowHandle
nativeWindow
);Wraps a native window handle with very little additional processing - notably no destruction this is incomplete so don't use it for much right now. The purpose of this is to make native windows created through the low level API (so you can use platform-specific options and other details SimpleWindow does not expose) available to the event loop wrappers.
-
Declaration
void
requestAttention
();Requests attention from the user for this window.
Discussion
The typical result of this function is to change the color of the taskbar icon, though it may be tweaked on specific platforms. It is meant to unobtrusively tell the user that something relevant to them happened in the background and they should check the window when they get a chance. Upon receiving the keyboard focus, the window will automatically return to its natural state. If the window already has the keyboard focus, this function may do nothing, because the user is presumed to already be giving the window attention.
Implementation note:
uses the NET_WM_STATE_DEMANDS_ATTENTION atom on X11 and the FlashWindow function on Windows.requestAttention
-
Declaration
void delegate()
closeQuery
;This will be called when WM wants to close your window (i.e. user clicked "close" icon, for example).
Discussion
You'll have to call
close()
manually if you set this delegate. -
Declaration
void delegate(bool becomesVisible)
visibilityChanged
;This will be called when window visibility was changed.
-
Declaration
final @property bool
closed
();Returns
true
if the window has beenclosed
. -
Declaration
final @property bool
visible
();Returns
true
if the window isvisible
(mapped). -
Declaration
void
close
();Closes the window. If there are no more open windows, the event loop will terminate.
-
Declaration
void
show
();Alias for
hidden = false
-
Declaration
void
hide
();Alias for
hidden = true
-
Declaration
void
hideCursor
();Hide cursor when it enters the window.
-
Declaration
void
showCursor
();Don't hide cursor when it enters the window.
-
Declaration
bool
warpMouse
(intx
, inty
);"Warp" mouse pointer to coordinates relative to window top-left corner. Return "success" flag.
Discussion
Currently only supported on X11, so Windows implementation will return
false
.Note: "warping" pointer will not send any synthesised mouse events, so you probably doesn't want to use it to move mouse pointer to some active GUI area, for example, as your window won't receive "mouse moved here" event.
-
Declaration
void
sendDummyEvent
();Send dummy window event to ping event loop. Required to process NotificationIcon on X11, for example.
-
Declaration
void
setMinSize
(intminwidth
, intminheight
);Set window minimal size.
-
Declaration
void
setMaxSize
(intmaxwidth
, intmaxheight
);Set window maximal size.
-
Declaration
void
setResizeGranularity
(intgranx
, intgrany
);Set window resize step (window size will be changed with the given granularity on supported platforms).
Discussion
Currently only supported on X11.
-
Declaration
void
move
(intx
, inty
);Move window.
-
Declaration
void
resize
(intw
, inth
);Resize window.
-
Declaration
void
moveResize
(intx
, inty
, intw
, inth
);Move and resize window (this can be faster and more visually pleasant than doing it separately).
-
Declaration
final @property bool
hidden
();Returns
true
if the window ishidden
. -
Declaration
final @property void
hidden
(boolb
);Shows or hides the window based on the bool argument.
-
Declaration
void
setEventHandlers
(T...)(TeventHandlers
);Sets your event handlers, without entering the event loop. Useful if you have multiple windows - set the handlers on each window, then only do eventLoop on your main window.
-
Declaration
final int
eventLoop
(T...)(longpulseTimeout
, TeventHandlers
);The event loop automatically returns when the window is closed
Discussion
pulseTimeout
is given in milliseconds. IfpulseTimeout
== 0, no pulse timer is created. The event loop will block until an event arrives or the pulse timer goes off. -
Declaration
ScreenPainter
draw
();This lets you
draw
on the window (or its backing buffer) using basic 2D primitives.Discussion
Be sure to call this in a limited scope because your changes will not actually appear on the window until ScreenPainter's destructor runs.
Return Value
an instance of [ScreenPainter], which has the drawing methods on it to
draw
on this window. -
Declaration
final @property int
width
();Width of the window's drawable client area, in pixels.
-
Declaration
final @property int
height
();Height of the window's drawable client area, in pixels.
-
Declaration
void delegate()
redrawOpenGlScene
;Put your code in here that you want to be drawn automatically when your window is uncovered. Set a handler here *before* entering your event loop any time you pass
OpenGlOptions.yes
to the constructor. Ideally, you will set this delegate immediately after constructing theSimpleWindow
. -
Declaration
final @property void
vsync
(boolwait
);This will allow you to change OpenGL
vsync
state. -
Declaration
void
mtUnlock
();"Unlock" this window handle, to do multithreaded synchronization. You probably won't need
Discussion
to call this, as it's not recommended to share window between threads.
-
Declaration
void
beep
();Emit a
beep
to get user's attention. -
Declaration
bool
useGLFinish
;Set this to
false
if you don't need to doglFinish()
afterswapOpenGlBuffers()
.Discussion
Note that at least NVidia proprietary driver may segfault if you will modify texture fast enough without waiting 'em to finish their frame bussiness.
-
Declaration
void
redrawOpenGlSceneNow
();call this to invoke your delegate. It automatically sets up the context and flips the buffer. If you need to redraw the scene in response to an event, call this.
-
Declaration
void
setAsCurrentOpenGlContext
();Makes all gl* functions target this window until changed. This is only valid if you passed
OpenGlOptions.yes
to the constructor. -
Declaration
nothrow bool
setAsCurrentOpenGlContextNT
();Makes all gl* functions target this window until changed. This is only valid if you passed
OpenGlOptions.yes
to the constructor.Discussion
This doesn't throw, returning success flag instead.
-
Declaration
nothrow bool
releaseCurrentOpenGlContext
();Releases OpenGL context, so it can be reused in, for example, different thread. This is only valid if you passed
OpenGlOptions.yes
to the constructor.Discussion
This doesn't throw, returning success flag instead.
-
Declaration
void
swapOpenGlBuffers
();simpledisplay always uses double buffering, usually automatically. This manually swaps the OpenGL buffers.
Discussion
You should not need to call this yourself because simpledisplay will do it for you after calling your
redrawOpenGlScene
. Remember that this may throw an exception, which you can catch in a multithreaded application to keep your thread from dying from an unhandled exception. -
Declaration
@property void
title
(stringtitle
);Set the window
title
, which is visible on the window managertitle
bar, operating system taskbar, etc.Discussion
auto window = new SimpleWindow(100, 100, "First title"); window.title = "A new title";
-
Declaration
@property string
title
();Gets the
title
-
Declaration
@property void
icon
(MemoryImageicon
);Set the
icon
that is seen in the title bar or taskbar, etc., for the user. -
Declaration
@property void
image
(Imagei
);Draws an
image
on the window. This is meant to provide quick lookDiscussion
of a static
image
generated elsewhere. -
Declaration
void delegate(KeyEvent ke)
handleKeyEvent
;What follows are the event handlers. These are set automatically
Discussion
by the eventLoop function, but are still public so you can change them later. wasPressed ==
true
means key down.false
== key up. Handles a low-level keyboard event. Settable through setEventHandlers. -
Declaration
void delegate(dchar c)
handleCharEvent
;Handles a higher level keyboard event - c is the character just pressed. Settable through setEventHandlers.
-
Declaration
void delegate()
handlePulse
;Handles a timer pulse. Settable through setEventHandlers.
-
Declaration
void delegate(bool)
onFocusChange
;called when the focus changes, param is if we have it (
true
) or are losing it (false
) -
Declaration
void delegate(MouseEvent)
handleMouseEvent
;Mouse event handler. Settable through setEventHandlers.
-
Declaration
void delegate()
paintingFinished
;use to redraw child widgets if you use system apis to add stuff
-
Declaration
void delegate(int width, int height)
windowResized
;handle a resize, after it happens. You must construct the window with Resizablity.allowResizing
Discussion
for this to ever happen.
-
Declaration
NativeEventHandler
handleNativeEvent
;Platform specific - handle any native messages this window gets.
Note: this is called *in addition to* other event handlers, unless you return zero indicating that you handled it. On Windows, it takes the form of int delegate(HWND,UINT, WPARAM, LPARAM). On X11, it takes the form of int delegate(XEvent).
IMPORTANT: it used to be static in old versions of simpledisplay.d, but I always used it as if it wasn't static... so now I just fixed it so it isn't anymore.
-
Declaration
static NativeEventHandler
handleNativeGlobalEvent
;This is the same as handleNativeEvent, but static so it can hook ALL events in the loop.
Discussion
If you used to use handleNativeEvent depending on it being static, just change it to use this instead and it will work the same way.
-
Declaration
@property bool
eventQueueEmpty
()();Is our custom event queue empty? Can be used in simple cases to prevent "spamming" window with events it can't cope with. It is safe to call this from non-UI threads.
Discussion
This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.
-
Declaration
@property bool
eventQueued
(ET : Object)();Does our custom event queue contains at least one with the given type? Can be used in simple cases to prevent "spamming" window with events it can't cope with. It is safe to call this from non-UI threads.
Discussion
This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.
-
Declaration
uint
addEventListener
(ET : Object)(void delegate(ET)dg
);Add listener for custom event. Can be used like this:
Discussion
auto eid = win.addEventListener((MyStruct evt) { ... }); ... win.removeEventListener(eid);
Return Value
0 on failure (should never happen, so ignore it) This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.
-
Declaration
void
removeEventListener
()(uintid
);Remove event listener. It is safe to pass invalid event
id
here.Discussion
This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.
-
Declaration
bool
postTimeout
(ET : Object)(ETevt
, uinttimeoutmsecs
);Post event to queue. It is safe to call this from non-UI threads.
Discussion
If
is greater than zero, the event will be delayed for at leasttimeoutmsecs
milliseconds. This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.timeoutmsecs
-
Declaration
bool
postEvent
(ET : Object)(ETevt
);Post event to queue. It is safe to call this from non-UI threads.
Discussion
This is in-process one-way (from anything to window) event sending mechanics. It is thread-safe, so it can be used in multi-threaded applications to send, for example, "wake up and repaint" events when thread completed some operation. This will allow to avoid using timer pulse to check events with synchronization, 'cause event handler will be called in UI thread. You can stop guessing which pulse frequency will be enough for your app. Note that events handlers may be called in arbitrary order, i.e. last registered handler can be called first, and vice versa.
-
-
Declaration
class
Timer
;A timer that will trigger your function on a given interval.
Discussion
You create a timer with an interval and a callback. It will continue to fire on the interval until it is destroyed. There are currently no one-off timers (instead, just create one and destroy it when it is triggered) nor are there pause/resume functions - the timer must again be destroyed and recreated if you want to pause it. auto timer = new
Timer
(50, { it happened!; }); timer.destroy(); Timers can only be expected to fire when the event loop is running.-
Declaration
this(int
intervalInMilliseconds
, void delegate()onPulse
);Create a timer with a callback when it triggers.
-
Declaration
void
destroy
();Stop and
destroy
the timer object.
-
-
Declaration
void
getClipboardText
(SimpleWindowclipboardOwner
, void delegate(in char[])receiver
);this does a delegate because it is actually an async call on X...
Discussion
the
receiver
may never be called if the clipboard is empty or unavailable gets plain text from the clipboard -
Declaration
void
setClipboardText
(SimpleWindowclipboardOwner
, stringtext
);copies some
text
to the clipboard -
Declaration
@property Atom
GetAtom
(string name, bool create = false)(Display*display
);Platform specific for X11
-
Declaration
void
setPrimarySelection
(SimpleWindowwindow
, stringtext
);Asserts ownership of PRIMARY and copies the
text
into a buffer that clients can request later -
Declaration
void
setSecondarySelection
(SimpleWindowwindow
, stringtext
);Asserts ownership of SECONDARY and copies the
text
into a buffer that clients can request later -
Declaration
void
setX11Selection
(string atomName)(SimpleWindowwindow
, stringtext
); -
Declaration
void
getPrimarySelection
(SimpleWindowwindow
, void delegate(in char[])handler
); -
Declaration
void
getX11Selection
(string atomName)(SimpleWindowwindow
, void delegate(in char[])handler
); -
Declaration
void[]
getX11PropertyData
(Windowwindow
, Atomproperty
, Atomtype
= AnyPropertyType); -
Declaration
class
NotificationAreaIcon
: arsd.simpledisplay.CapableOfHandlingNativeEvent; -
Declaration
void
sendSyntheticInput
(wstrings
);Platform-specific for Windows. Sends a string as key press and release events to the actively focused window (not necessarily your application)
-
Declaration
int
registerHotKey
(SimpleWindowwindow
, uintmodifiers
, uintvk
, void delegate()handler
);Platform-specific for Windows. Registers a global hotkey. Returns a registration ID.
-
Declaration
void
unregisterHotKey
(SimpleWindowwindow
, intid
);Platform-specific for Windows. Unregisters a key. The
id
is the value returned by registerHotKey. -
Declaration
enum
RasterOp
: int; -
Declaration
enum
OpenGlOptions
: int;Determines if you want an OpenGL context created on the new window.
Discussion
See more: [#topics-3d|in the 3d topic].
import arsd.simpledisplay; void main() { auto window = new SimpleWindow(500, 500, "OpenGL Test", OpenGlOptions.yes); // Set up the matrix window.setAsCurrentOpenGlContext(); // make this window active // This is called on each frame, we will draw our scene window.redrawOpenGlScene = delegate() { }; window.eventLoop(0); }
-
Declaration
no
No OpenGL context is created
-
Declaration
yes
Yes, create an OpenGL context
-
Declaration
enum
Resizablity
: int;When you create a SimpleWindow, you can see its resizability to be one of these via the constructor...
-
Declaration
fixedSize
the window cannot be resized
-
Declaration
allowResizing
the window can be resized. The buffer (if there is one) will automatically adjust size, but not stretch the contents. the windowResized delegate will be called so you can respond to the new size yourself.
-
Declaration
automaticallyScaleIfPossible
if possible, your drawing buffer will remain the same size and simply be automatically scaled to the new window size. If this is impossible, it will not allow the user to resize the window at all. Note: window.width and window.height WILL be adjusted, which might throw you off if you draw based on them, so keep track of your expected width and height separately. That way, when it is scaled, things won't be thrown off.
-
-
Declaration
enum
TextAlignment
: uint;Alignment for . Left, Center, or Right may be combined with VerticalTop, VerticalCenter, or VerticalBottom via bitwise or.
-
Declaration
Left
-
Declaration
Center
-
Declaration
Right
-
Declaration
VerticalTop
-
Declaration
VerticalCenter
-
Declaration
VerticalBottom
-
-
Declaration
struct
KeyEvent
;Keyboard press and release events
-
Declaration
Key
key
;see table below. Always use the symbolic names, even for ASCII characters, since the actual numbers vary across platforms. See [Key]
-
Declaration
uint
hardwareCode
;A platform and hardware specific code for the key
-
Declaration
bool
pressed
;true
if the key was justpressed
,false
if it was just released. note: released events aren't always sent... -
Declaration
dchar
character
; -
Declaration
uint
modifierState
;see enum [ModifierState]. They are bitwise combined together.
-
Declaration
SimpleWindow
window
;associated Window
-
-
Declaration
enum
MouseEventType
: int;Type of a [MouseEvent]
-
Declaration
motion
The mouse moved inside the window
-
Declaration
buttonPressed
A mouse button was pressed or the wheel was spun
-
Declaration
buttonReleased
A mouse button was released
-
-
Declaration
struct
MouseEvent
;Listen for this on your event listeners if you are interested in mouse action.
-
Declaration
MouseEventType
type
;movement, press, release, double click. See [MouseEventType]
-
Declaration
int
x
;Current X position of the cursor when the event fired, relative to the upper-left corner of the window, reported in pixels. (0, 0) is the upper left, (window.width - 1, window.height - 1) is the lower right corner of the window.
-
Declaration
int
y
;Current Y position of the cursor when the event fired.
-
Declaration
int
dx
;Change in X position since last report
-
Declaration
int
dy
;Change in Y position since last report
-
Declaration
MouseButton
button
;See [MouseButton]
-
Declaration
int
modifierState
;See [ModifierState]
-
Declaration
SimpleWindow
window
;The
window
in which the event happened.
-
-
Declaration
struct
Pen
;This gives a few more options to drawing lines and such
-
Declaration
Color
color
;the foreground
color
-
Declaration
int
width
;width
of the line -
Declaration
Style
style
;See [Style] FIXME: not implemented
-
Declaration
enum
Style
: int;
-
-
Declaration
class
Image
;Represents an in-memory image in the format that the GUI expects, but with its raw data available to your program.
Discussion
On Windows, this means a device-independent bitmap. On X11, it is an XImage. Drawing an image to screen is not necessarily fast, but applying algorithms to draw to the image itself should be fast. An
is also the first step in loading and displaying images loaded from files. If you intend to draw an image to screen several times, you will want to convert it into a [Sprite]. Drawing pixels on the image may be simple, using theImage
opIndexAssign
function, but you can also often get a fair amount of speedup by getting the raw data format and writing some custom code. FIXME INSERT EXAMPLES HERE-
Declaration
this(int
width
, intheight
); -
Declaration
this(Size
size
); -
Declaration
const pure nothrow @system int
offsetForTopLeftPixel
();if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
const pure nothrow @system int
offsetForPixel
(intx
, inty
);if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
const pure nothrow @system int
adjustmentForNextLine
();if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
const pure nothrow @system int
redByteOffset
();once you have the position of a pixel, use these to get to the proper color
Discussion
if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
const pure nothrow @system int
greenByteOffset
();if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
const pure nothrow @system int
blueByteOffset
();if you do the math yourself you might be able to optimize it. Call these functions only once and cache the value.
-
Declaration
final void
putPixel
(intx
, inty
, Colorc
); -
Declaration
final Color
getPixel
(intx
, inty
); -
Declaration
final void
opIndexAssign
(Colorc
, intx
, inty
); -
Declaration
TrueColorImage
toTrueColorImage
(); -
Declaration
static Image
fromMemoryImage
(MemoryImagei
); -
Declaration
ubyte[]
getRgbaBytes
(ubyte[]where
= null);this is here for interop with arsd.image.
where
can be a TrueColorImage's data memberDiscussion
if you pass in a buffer, it will put it right there. length must be width*height*4 already if you pass
null
, it will allocate a new one. -
Declaration
void
setRgbaBytes
(in ubyte[]from
);this is here for interop with arsd.image.
from
can be a TrueColorImage's data member -
Declaration
ubyte*
getDataPointer
();warning: this is not portable across platforms because the data format can change
-
Declaration
final const pure nothrow @safe int
bytesPerLine
();for use with getDataPointer
-
Declaration
final const pure nothrow @safe int
bytesPerPixel
();for use with getDataPointer
-
Declaration
immutable int
width
; -
Declaration
immutable int
height
;
-
-
Declaration
void
displayImage
(Imageimage
, SimpleWindowwin
= null);A convenience function to pop up a window displaying the
image
.Discussion
If you pass a
win
, it will draw theimage
in it. Otherwise, it will create a window with the size of theimage
and run its event loop, closing when a key is pressed. -
Declaration
struct
ScreenPainter
;The 2D drawing proxy.
Discussion
Most functions use the outlineColor instead of taking a color themselves.
ScreenPainter
is reference counted and draws its buffer to the screen when its final reference goes out of scope.-
Declaration
int
fontHeight
(); -
Declaration
@property void
pen
(Penp
); -
Declaration
@property void
outlineColor
(Colorc
); -
Declaration
@property void
fillColor
(Colorc
); -
Declaration
@property void
rasterOp
(RasterOpop
); -
Declaration
void
scrollArea
(PointupperLeft
, intwidth
, intheight
, intdx
, intdy
);Scrolls the contents in the bounding rectangle by
dx
,dy
. Positivedx
means scroll left (make space available at the right), positivedy
means scroll up (make space available at the bottom) -
Declaration
void
clear
(); -
Declaration
void
drawPixmap
(Sprites
, PointupperLeft
); -
Declaration
void
drawImage
(PointupperLeft
, Imagei
, PointupperLeftOfImage
= Point(0, 0), intw
= 0, inth
= 0); -
Declaration
Size
textSize
(stringtext
); -
Declaration
void
drawText
(PointupperLeft
, in char[]text
, PointlowerRight
= Point(0, 0), uintalignment
= 0); -
Declaration
void
drawPixel
(Pointwhere
);Drawing an individual pixel is slow. Avoid it if possible.
-
Declaration
void
drawLine
(Pointstarting
, Pointending
);Draws a pen using the current pen / outlineColor
-
Declaration
void
drawRectangle
(PointupperLeft
, intwidth
, intheight
);Draws a rectangle using the current pen/outline color for the border and brush/fill color for the insides
Discussion
The outer lines, inclusive of x = 0, y = 0, x =
width
- 1, and y =height
- 1 are drawn with the outlineColor The rest of the pixels are drawn with the fillColor. If fillColor is transparent, those pixels are not drawn. -
Declaration
void
drawEllipse
(PointupperLeft
, PointlowerRight
);Arguments are the points of the bounding rectangle
-
Declaration
void
drawPolygon
(Point[]vertexes
);.
-
-
Declaration
class
Sprite
;Sprites are optimized for fast drawing on the screen, but slow for direct pixel access. They are best for drawing a relatively unchanging image repeatedly on the screen.
Discussion
On X11, this corresponds to an
XPixmap
. On Windows, it still uses a bitmap, though I'm not sure that's ideal and the implementation might change. You create one by giving a window and an image. It optimizes for that window, and copies the image into it to use as the initial picture. Creating a sprite can be quite slow (especially over a network connection) so you should do it as little as possible and just hold on to your sprite handles after making them. simpledisplay does try to do its best though, using the XSHM extension if available, but you should still write your code as if it will always be slow. Then you can usesprite.drawAt(painter, point);
to draw it, which should be a fast operation - much faster than drawing the Image itself every time.
represents a scarce resource which should be freed when you are done with it. Use theSprite
dispose
method to do this. Do not use a
after it has been disposed. If you are unsure about this, don't take chances, just let the garbage collector do it for you. But ideally, you can manage its lifetime more efficiently.Sprite
FIXME: you are supposed to be able to draw on these similarly to on windows. ScreenPainter needs to be refactored to allow that though. So until that is done, consider a
to have const contents.Sprite
-
Declaration
this(SimpleWindow
win
, Imagei
);Makes a sprite based on the image with the initial contents from the Image
-
Declaration
void
drawAt
(ScreenPainterpainter
, Pointwhere
);Draws the image on the specified
painter
at the specified point. The point is the upper-left pointwhere
the image will be drawn. -
Declaration
void
dispose
();Call this when you're ready to get rid of it
-
Declaration
final @property int
width
(); -
Declaration
final @property int
height
();
-
-
Declaration
void
flushGui
();Flushes any pending gui buffers. Necessary if you are using with_eventloop with X - flush after you create your windows but before you call loop()
-
Declaration
enum
ModifierState
: uint;State of keys on mouse events, especially motion.
Discussion
Do not trust the actual integer values in this, they are platform-specific. Always use the names.
-
Declaration
shift
-
Declaration
capsLock
-
Declaration
ctrl
-
Declaration
alt
-
Declaration
numLock
-
Declaration
windows
-
Declaration
leftButtonDown
-
Declaration
middleButtonDown
-
Declaration
rightButtonDown
-
-
Declaration
enum
MouseButton
: int; -
Declaration
enum
Key
: int;Do not trust the numeric values as they are platform-specific. Always use the symbolic name.
-
Declaration
Escape
-
Declaration
F1
-
Declaration
F2
-
Declaration
F3
-
Declaration
F4
-
Declaration
F5
-
Declaration
F6
-
Declaration
F7
-
Declaration
F8
-
Declaration
F9
-
Declaration
F10
-
Declaration
F11
-
Declaration
F12
-
Declaration
PrintScreen
-
Declaration
ScrollLock
-
Declaration
Pause
-
Declaration
Grave
The ` ~ key
-
Declaration
N1
Number key atop the keyboard
-
Declaration
N2
-
Declaration
N3
-
Declaration
N4
-
Declaration
N5
-
Declaration
N6
-
Declaration
N7
-
Declaration
N8
-
Declaration
N9
-
Declaration
N0
-
Declaration
Dash
-
Declaration
Equals
-
Declaration
Backslash
The \ | key
-
Declaration
Backspace
-
Declaration
Insert
-
Declaration
Home
-
Declaration
PageUp
-
Declaration
Delete
-
Declaration
End
-
Declaration
PageDown
-
Declaration
Up
-
Declaration
Down
-
Declaration
Left
-
Declaration
Right
-
Declaration
Tab
-
Declaration
Q
-
Declaration
W
-
Declaration
E
-
Declaration
R
-
Declaration
T
-
Declaration
Y
-
Declaration
U
-
Declaration
I
-
Declaration
O
-
Declaration
P
-
Declaration
LeftBracket
the [ { key
-
Declaration
RightBracket
the ] } key
-
Declaration
CapsLock
-
Declaration
A
-
Declaration
S
-
Declaration
D
-
Declaration
F
-
Declaration
G
-
Declaration
H
-
Declaration
J
-
Declaration
K
-
Declaration
L
-
Declaration
Semicolon
-
Declaration
Apostrophe
-
Declaration
Enter
-
Declaration
Shift
-
Declaration
Z
-
Declaration
X
-
Declaration
C
-
Declaration
V
-
Declaration
B
-
Declaration
N
-
Declaration
M
-
Declaration
Comma
-
Declaration
Period
-
Declaration
Slash
the / ? key
-
Declaration
Shift_r
Note: this isn't sent on all computers, sometimes it just sends Shift, so don't rely on it. If it is supported though, it is the right Shift key, as opposed to the left Shift key
-
Declaration
Ctrl
-
Declaration
Windows
-
Declaration
Alt
-
Declaration
Space
-
Declaration
Alt_r
ditto of shift_r
-
Declaration
Windows_r
-
Declaration
Menu
-
Declaration
Ctrl_r
-
Declaration
NumLock
-
Declaration
Divide
The / key on the number pad
-
Declaration
Multiply
The * key on the number pad
-
Declaration
Minus
The - key on the number pad
-
Declaration
Plus
The + key on the number pad
-
Declaration
PadEnter
Numberpad enter key
-
Declaration
Pad1
Numberpad keys
-
Declaration
Pad2
-
Declaration
Pad3
-
Declaration
Pad4
-
Declaration
Pad5
-
Declaration
Pad6
-
Declaration
Pad7
-
Declaration
Pad8
-
Declaration
Pad9
-
Declaration
Pad0
-
Declaration
PadDot
-
-
Declaration
string
xfontstr
;This is the default font used. You might change this before doing anything else with
Discussion
the library if you want to try something else. Surround that in
static if(UsingSimpledisplayX11)
for cross-platform compatibility. -
Declaration
class
XDisplayConnection
; -
Declaration
bool
doXNextEvent
(Display*display
);Platform-specific, you might use it when doing a custom event loop
-
Declaration
void
demandAttention
(SimpleWindowwindow
, boolneeds
= true);X-specific
-
Declaration
TrueColorImage
getWindowNetWmIcon
(Windowwindow
);X-specific