mirror of https://github.com/adamdruppe/arsd.git
omg i forgot stuff
This commit is contained in:
parent
d29bf66764
commit
868323bac0
6
apng.d
6
apng.d
|
@ -266,6 +266,12 @@ enum APNG_BLEND_OP : byte {
|
|||
OVER = 1
|
||||
}
|
||||
|
||||
/++
|
||||
Loads an apng file.
|
||||
|
||||
If it is a normal png file without animation it will
|
||||
just load it as a single frame "animation" FIXME
|
||||
+/
|
||||
ApngAnimation readApng(in ubyte[] data) {
|
||||
auto png = readPng(data);
|
||||
auto header = PngHeader.fromChunk(png.chunks[0]);
|
||||
|
|
12
cgi.d
12
cgi.d
|
@ -2352,6 +2352,18 @@ class Cgi {
|
|||
// maybeAutoClose can be false though to avoid this (important if you call from inside close()!
|
||||
}
|
||||
|
||||
/++
|
||||
Convenience method to set content type to json and write the string as the complete response.
|
||||
|
||||
History:
|
||||
Added January 16, 2020
|
||||
+/
|
||||
void writeJson(string json) {
|
||||
this.setResponseContentType("application/json");
|
||||
this.write(json, true);
|
||||
}
|
||||
|
||||
/// Flushes the pending buffer, leaving the connection open so you can send more.
|
||||
void flush() {
|
||||
if(rawDataOutput is null)
|
||||
stdout.flush();
|
||||
|
|
4
dom.d
4
dom.d
|
@ -8919,11 +8919,11 @@ unittest {
|
|||
}
|
||||
|
||||
/*
|
||||
Copyright: Adam D. Ruppe, 2010 - 2020
|
||||
Copyright: Adam D. Ruppe, 2010 - 2021
|
||||
License: <a href="http://www.boost.org/LICENSE_1_0.txt">Boost License 1.0</a>.
|
||||
Authors: Adam D. Ruppe, with contributions by Nick Sabalausky, Trass3r, and ketmar among others
|
||||
|
||||
Copyright Adam D. Ruppe 2010-2020.
|
||||
Copyright Adam D. Ruppe 2010-2021.
|
||||
Distributed under the Boost Software License, Version 1.0.
|
||||
(See accompanying file LICENSE_1_0.txt or copy at
|
||||
http://www.boost.org/LICENSE_1_0.txt)
|
||||
|
|
7
email.d
7
email.d
|
@ -932,6 +932,7 @@ class IncomingEmailMessage {
|
|||
string gpgproto; ///
|
||||
MimePart gpgmime; ///
|
||||
|
||||
///
|
||||
string fromEmailAddress() {
|
||||
auto i = from.indexOf("<");
|
||||
if(i == -1)
|
||||
|
@ -940,6 +941,7 @@ class IncomingEmailMessage {
|
|||
return from[i + 1 .. e];
|
||||
}
|
||||
|
||||
///
|
||||
string toEmailAddress() {
|
||||
auto i = to.indexOf("<");
|
||||
if(i == -1)
|
||||
|
@ -949,9 +951,11 @@ class IncomingEmailMessage {
|
|||
}
|
||||
}
|
||||
|
||||
///
|
||||
struct MboxMessages {
|
||||
immutable(ubyte)[][] linesRemaining;
|
||||
|
||||
///
|
||||
this(immutable(ubyte)[] data) {
|
||||
linesRemaining = splitLinesWithoutDecoding(data);
|
||||
popFront();
|
||||
|
@ -959,14 +963,17 @@ struct MboxMessages {
|
|||
|
||||
IncomingEmailMessage currentFront;
|
||||
|
||||
///
|
||||
IncomingEmailMessage front() {
|
||||
return currentFront;
|
||||
}
|
||||
|
||||
///
|
||||
bool empty() {
|
||||
return currentFront is null;
|
||||
}
|
||||
|
||||
///
|
||||
void popFront() {
|
||||
if(linesRemaining.length)
|
||||
currentFront = new IncomingEmailMessage(linesRemaining);
|
||||
|
|
9
game.d
9
game.d
|
@ -76,6 +76,15 @@ module arsd.game;
|
|||
|
||||
+/
|
||||
|
||||
/+
|
||||
ADD ME:
|
||||
Animation helper like audio style. Your game object
|
||||
has a particular image attached as primary.
|
||||
|
||||
You can be like `animate once` or `animate indefinitely`
|
||||
and it takes care of it, then set new things and it does that too.
|
||||
+/
|
||||
|
||||
public import arsd.gamehelpers;
|
||||
public import arsd.color;
|
||||
public import arsd.simpledisplay;
|
||||
|
|
41
jsvar.d
41
jsvar.d
|
@ -75,6 +75,10 @@
|
|||
Wrapping D native objects is coming later, the current ways suck. I really needed
|
||||
properties to do them sanely at all, and now I have it. A native wrapped object will
|
||||
also need to be set with _object prolly.
|
||||
|
||||
Author: Adam D Ruppe
|
||||
|
||||
History: Started in July 2013.
|
||||
+/
|
||||
module arsd.jsvar;
|
||||
|
||||
|
@ -945,6 +949,19 @@ struct var {
|
|||
|
||||
I also wrote the first draft of this documentation at that time,
|
||||
even though the function has been public since the beginning.
|
||||
|
||||
On January 1, 2021, I changed `get!some_struct` to call properties
|
||||
on the var, if a member looks like a function or object, to try to
|
||||
get plain-old-data out. Since the functions are only ever put there
|
||||
by you or by you allowing script, I don't feel too bad about it, but
|
||||
it still might not be ideal for all circumstances, so idk if I'll leave
|
||||
it this way or not.
|
||||
|
||||
One thing it helps for though is taking scripted subclasses back into D
|
||||
structs, since the parent class thing is likely to be virtual properties.
|
||||
And having that just work in argument lists is really cool...
|
||||
|
||||
Search function for the comment "property getter support" to see the impl.
|
||||
+/
|
||||
public T get(T)() if(!is(T == void)) {
|
||||
static if(is(T == var)) {
|
||||
|
@ -1024,7 +1041,14 @@ struct var {
|
|||
|
||||
if(initialized)
|
||||
foreach(i, a; t.tupleof) {
|
||||
cast(Unqual!(typeof((a)))) t.tupleof[i] = this[t.tupleof[i].stringof[2..$]].get!(typeof(a));
|
||||
var possibility = this[t.tupleof[i].stringof[2..$]];
|
||||
// FIXME: so there is the possibility of getting some data getting all caught
|
||||
// up in a script function doing weird things. If I can prevent that, I'd like to...
|
||||
// but it is also really useful for this to work for some scenarios...
|
||||
static if(!is(typeof(a) == return)) // if it is callable, just assign the func ref
|
||||
if(possibility.payloadType == Type.Function || possibility.payloadType == Type.Object)
|
||||
possibility = possibility.apply(this, null); // crude approximation of property getter support
|
||||
cast(Unqual!(typeof((a)))) t.tupleof[i] = possibility.get!(typeof(a));
|
||||
}
|
||||
|
||||
return t;
|
||||
|
@ -2461,8 +2485,13 @@ int typeCompatibilityScore(var arg, var type) {
|
|||
} else {
|
||||
// exact type category match
|
||||
if(type.payloadType == var.Type.Array) {
|
||||
// arrays not supported here....
|
||||
thisScore = 0;
|
||||
// arrays not really supported here....
|
||||
// so just like if both are arrays i'll take
|
||||
// it as a bare minimum but i don't love it otherwise
|
||||
if(arg.payloadType == var.Type.Array)
|
||||
thisScore = 1;
|
||||
else
|
||||
thisScore = 0;
|
||||
return thisScore;
|
||||
} else if(type.payloadType == var.Type.Object) {
|
||||
// objects are the interesting one...
|
||||
|
@ -2625,7 +2654,7 @@ class OverloadSet : PrototypeObject {
|
|||
}
|
||||
|
||||
if(bestScore < 0)
|
||||
throw new Exception("no matching overload found");// " ~ to!string(arguments) ~ " " ~ to!string(overloads));
|
||||
throw new Exception("no matching overload found " ~ to!string(arguments) ~ " " ~ to!string(overloads));
|
||||
|
||||
|
||||
return bestMatch.func.apply(this_, arguments);
|
||||
|
@ -2746,8 +2775,8 @@ string static_foreach(size_t length, int t_start_idx, int t_end_idx, string[] t.
|
|||
private
|
||||
auto ParamDefault(alias T, size_t idx)() {
|
||||
static if(is(typeof(T) Params == __parameters)) {
|
||||
auto fn(Params[idx .. idx + 1] args) {
|
||||
return args[0];
|
||||
auto fn(Params[idx .. idx + 1] _args__) { // if i used plain `args` and one of the args in the list was also called `args`, this fails to compile and that error will be dropped by opDispatch. LOL.
|
||||
return _args__[0];
|
||||
}
|
||||
static if(__traits(compiles, fn())) {
|
||||
return fn();
|
||||
|
|
|
@ -7,6 +7,7 @@ im tempted to add some css kind of thing to minigui. i've not done in the past c
|
|||
the virtual functions remain as the default calculated values. then the reads go through some proxy object that can override it...
|
||||
*/
|
||||
|
||||
// FIXME: opt-in file picker widget with image support
|
||||
|
||||
// FIXME: slider widget.
|
||||
// FIXME: number widget
|
||||
|
|
1
script.d
1
script.d
|
@ -240,6 +240,7 @@ make sure superclass ctors are called
|
|||
varargs
|
||||
lambdas - maybe without function keyword and the x => foo syntax from D.
|
||||
|
||||
Author: Adam D Ruppe
|
||||
|
||||
History:
|
||||
September 1, 2020: added overloading for functions and type matching in `catch` blocks among other bug fixes
|
||||
|
|
|
@ -258,6 +258,8 @@ struct AudioOutputThread {
|
|||
|
||||
@disable new(size_t); // gdc9 requires the arg fyi
|
||||
|
||||
@disable void start() {} // you aren't supposed to control the thread yourself!
|
||||
|
||||
/++
|
||||
Pass `true` to enable the audio thread. Otherwise, it will
|
||||
just live as a dummy mock object that you should not actually
|
||||
|
@ -456,7 +458,7 @@ final class AudioPcmOutThreadImplementation : Thread {
|
|||
}
|
||||
}
|
||||
|
||||
///
|
||||
/// Stops the output thread. Using the object after it is stopped is not recommended, except to `join` the thread. This is meant to be called when you are all done with it.
|
||||
void stop() {
|
||||
if(ao) {
|
||||
ao.stop();
|
||||
|
@ -1326,8 +1328,12 @@ struct AudioInput {
|
|||
snd_pcm_sframes_t read;
|
||||
|
||||
read = snd_pcm_readi(handle, buffer.ptr, buffer.length / channels /* div number of channels apparently */);
|
||||
if(read < 0)
|
||||
throw new AlsaException("pcm read", cast(int)read);
|
||||
if(read < 0) {
|
||||
read = snd_pcm_recover(handle, cast(int) read, 0);
|
||||
if(read < 0)
|
||||
throw new AlsaException("pcm read", cast(int)read);
|
||||
return null;
|
||||
}
|
||||
|
||||
return buffer[0 .. read * channels];
|
||||
}
|
||||
|
|
|
@ -7039,6 +7039,9 @@ class OperatingSystemFont {
|
|||
|
||||
this.isXft = true;
|
||||
|
||||
if(xftFont !is null)
|
||||
isMonospace_ = stringWidth("x") == stringWidth("M");
|
||||
|
||||
return !isNull();
|
||||
}
|
||||
|
||||
|
@ -7097,6 +7100,9 @@ class OperatingSystemFont {
|
|||
char* lol3;
|
||||
fontset = XCreateFontSet(display, xfontstr.ptr, &lol, &lol2, &lol3);
|
||||
|
||||
if(font !is null)
|
||||
isMonospace_ = stringWidth("l") == stringWidth("M");
|
||||
|
||||
return !isNull();
|
||||
}
|
||||
|
||||
|
@ -7121,6 +7127,8 @@ class OperatingSystemFont {
|
|||
|
||||
width_ = tm.tmAveCharWidth;
|
||||
height_ = tm.tmHeight;
|
||||
// If this bit is set the font is a variable pitch font. If this bit is clear the font is a fixed pitch font. Note very carefully that those meanings are the opposite of what the constant name implies.
|
||||
isMonospace_ = (tm.tmPitchAndFamily & TMPF_FIXED_PITCH) == 0;
|
||||
|
||||
return !isNull();
|
||||
}
|
||||
|
@ -7207,15 +7215,47 @@ class OperatingSystemFont {
|
|||
} else static assert(0);
|
||||
}
|
||||
|
||||
// Assuming monospace!!!!!
|
||||
// added March 26, 2020
|
||||
private bool isMonospace_;
|
||||
|
||||
/++
|
||||
History:
|
||||
Added January 16, 2021
|
||||
+/
|
||||
bool isMonospace() {
|
||||
return isMonospace_;
|
||||
}
|
||||
|
||||
/++
|
||||
Returns the average width of the font, conventionally defined as the width of the lowercase 'x' character.
|
||||
|
||||
History:
|
||||
Added March 26, 2020
|
||||
Documented January 16, 2021
|
||||
+/
|
||||
int averageWidth() {
|
||||
version(X11) {
|
||||
return stringWidth("x");
|
||||
} else version(Windows)
|
||||
return width_;
|
||||
else assert(0);
|
||||
}
|
||||
|
||||
/++
|
||||
Returns the width of the string as drawn on the specified window, or the default screen if the window is null.
|
||||
|
||||
History:
|
||||
Added January 16, 2021
|
||||
+/
|
||||
int stringWidth(string s, SimpleWindow window = null) {
|
||||
if(isNull)
|
||||
return 0;
|
||||
|
||||
version(X11) {
|
||||
version(with_xft)
|
||||
if(isXft && xftFont !is null) {
|
||||
//return xftFont.max_advance_width;
|
||||
XGlyphInfo extents;
|
||||
XftTextExtentsUtf8(XDisplayConnection.get, xftFont, "M", 1, &extents);
|
||||
XftTextExtentsUtf8(XDisplayConnection.get, xftFont, s.ptr, cast(int) s.length, &extents);
|
||||
//import std.stdio; writeln(extents);
|
||||
return extents.xOff;
|
||||
}
|
||||
|
@ -7223,19 +7263,35 @@ class OperatingSystemFont {
|
|||
return 0;
|
||||
else if(fontset) {
|
||||
XRectangle rect;
|
||||
Xutf8TextExtents(fontset, "M", 1, null, &rect);
|
||||
Xutf8TextExtents(fontset, s.ptr, cast(int) s.length, null, &rect);
|
||||
|
||||
return rect.width;
|
||||
} else {
|
||||
return font.max_bounds.width;
|
||||
return XTextWidth(font, s.ptr, cast(int) s.length);
|
||||
}
|
||||
} else version(Windows)
|
||||
return width_;
|
||||
} else version(Windows) {
|
||||
WCharzBuffer buffer = WCharzBuffer(s);
|
||||
|
||||
SIZE size;
|
||||
|
||||
auto dc = GetDC(window is null ? null : window.impl.hwnd);
|
||||
SelectObject(dc, font);
|
||||
GetTextExtentPoint32W(dc, buffer.ptr, cast(int) buffer.length, &size);
|
||||
ReleaseDC(null, dc);
|
||||
|
||||
return size.cx;
|
||||
}
|
||||
else assert(0);
|
||||
|
||||
}
|
||||
|
||||
// Assuming monospace!!!!!
|
||||
// added March 26, 2020
|
||||
/++
|
||||
Returns the height of the font.
|
||||
|
||||
History:
|
||||
Added March 26, 2020
|
||||
Documented January 16, 2021
|
||||
+/
|
||||
int height() {
|
||||
version(X11) {
|
||||
version(with_xft)
|
||||
|
@ -13025,6 +13081,9 @@ extern(C) nothrow @nogc {
|
|||
void Xutf8DrawText(Display*, Drawable, GC, int, int, XmbTextItem*, int);
|
||||
|
||||
int Xutf8TextExtents(XFontSet font_set, const char *, int num_bytes, XRectangle *overall_ink_return, XRectangle *overall_logical_return);
|
||||
|
||||
|
||||
//Status Xutf8TextPerCharExtents(XFontSet font_set, char *string, int num_bytes, XRectangle *ink_array_return, XRectangle *logical_array_return, int array_size, int *num_chars_return, XRectangle *overall_ink_return, XRectangle *overall_logical_return);
|
||||
|
||||
void XDrawText(Display*, Drawable, GC, int, int, XTextItem*, int);
|
||||
int XSetFunction(Display*, GC, int);
|
||||
|
|
20
terminal.d
20
terminal.d
|
@ -7018,10 +7018,13 @@ version(TerminalDirectToEmulator) {
|
|||
+/
|
||||
enum IntegratedEmulator = true;
|
||||
|
||||
version(Windows)
|
||||
version(Windows) {
|
||||
private enum defaultFont = "Consolas";
|
||||
else
|
||||
private enum defaultSize = 14;
|
||||
} else {
|
||||
private enum defaultFont = "monospace";
|
||||
private enum defaultSize = 12; // it is measured differently with fontconfig than core x and windows...
|
||||
}
|
||||
|
||||
/++
|
||||
Allows customization of the integrated emulator window.
|
||||
|
@ -7055,18 +7058,22 @@ version(TerminalDirectToEmulator) {
|
|||
On January 16, 2021, I changed the default to be a fancier
|
||||
font than the underlying terminalemulator.d uses ("monospace"
|
||||
on Linux and "Consolas" on Windows, though I will note
|
||||
that I do *not* guarantee this won't change.)
|
||||
that I do *not* guarantee this won't change.) On January 18,
|
||||
I changed the default size.
|
||||
|
||||
If you want specific values for these things, you should set
|
||||
them in your own application.
|
||||
+/
|
||||
string fontName = defaultFont;
|
||||
/// ditto
|
||||
int fontSize = 14;
|
||||
int fontSize = defaultSize;
|
||||
|
||||
/++
|
||||
Requested initial terminal size in character cells. You may not actually get exactly this.
|
||||
+/
|
||||
int initialWidth = 80;
|
||||
/// ditto
|
||||
int initialHeight = 40;
|
||||
int initialHeight = 30;
|
||||
|
||||
/++
|
||||
If `true`, the window will close automatically when the main thread exits.
|
||||
|
@ -7876,6 +7883,8 @@ private version(Windows) {
|
|||
History:
|
||||
Added December 29, 2020.
|
||||
+/
|
||||
static if(__traits(compiles, mixin(`{ static foreach(i; 0 .. 1) {} }`)))
|
||||
mixin(q{
|
||||
auto SdpyIntegratedKeys(SimpleWindow)(SimpleWindow window) {
|
||||
struct impl {
|
||||
static import sdpy = arsd.simpledisplay;
|
||||
|
@ -7981,6 +7990,7 @@ auto SdpyIntegratedKeys(SimpleWindow)(SimpleWindow window) {
|
|||
}
|
||||
return impl(window);
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
/*
|
||||
|
|
|
@ -4243,6 +4243,8 @@ mixin template SdpyDraw() {
|
|||
}
|
||||
} else version(Windows) {
|
||||
this.font = new OperatingSystemFont("Courier New", size, FontWeight.medium);
|
||||
if(!this.font.isNull && !this.font.isMonospace)
|
||||
this.font.unload(); // non-monospace fonts are unusable here. This should never happen anyway though as Courier New comes with Windows
|
||||
}
|
||||
|
||||
if(font.isNull) {
|
||||
|
|
Loading…
Reference in New Issue