From a91da272cb525a0dda1baa2aad2c8da2560405fe Mon Sep 17 00:00:00 2001 From: =?utf8?q?Jean-Philippe=20Bruy=C3=A8re?= Date: Tue, 2 Feb 2021 04:59:31 +0100 Subject: [PATCH] dont preload all cursors, use standard one if available --- Crow/src/Interface.cs | 44 ++++++++++++++++++++++++++-------- Crow/src/Widgets/OldLabel.cs | 1 + Crow/src/Widgets/OldTextBox.cs | 4 +++- Crow/src/XCursor.cs | 44 +++++++++++++--------------------- 4 files changed, 55 insertions(+), 38 deletions(-) diff --git a/Crow/src/Interface.cs b/Crow/src/Interface.cs index e1b9bc77..1e26824a 100644 --- a/Crow/src/Interface.cs +++ b/Crow/src/Interface.cs @@ -1,4 +1,4 @@ -// Copyright (c) 2013-2020 Bruyère Jean-Philippe +// Copyright (c) 2013-2021 Bruyère Jean-Philippe // // This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) @@ -95,10 +95,8 @@ namespace Crow } public Interface (int width = 800, int height = 600, bool startUIThread = true, bool createSurface = true) { - loadCursors (); - CultureInfo.DefaultThreadCurrentCulture = CultureInfo.InvariantCulture; - CurrentInterface = this; + //CurrentInterface = this; clientRectangle = new Rectangle (0, 0, width, height); if (createSurface) @@ -331,7 +329,7 @@ namespace Crow public static float WheelIncrement = 1; /// Tabulation size in Text controls public static int TAB_SIZE = 4; - public static string LineBreak = "\n"; + [Obsolete]public static string LineBreak = "\n"; /// Allow rendering of interface in development environment public static bool DesignerMode = false; /// Disable caching for a widget if this threshold is reached @@ -351,7 +349,7 @@ namespace Crow /// Each control need a ref to the root interface containing it, if not set in GraphicObject.currentInterface, /// the ref of this one will be stored in GraphicObject.currentInterface /// - protected static Interface CurrentInterface; + //protected static Interface CurrentInterface; #endregion #region Events @@ -881,12 +879,12 @@ namespace Crow } blinkingCursor.Restart (); forceTextCursor = false; - } else if (textCursor != null && blinkingCursor.ElapsedMilliseconds > blinkFrequency) { + } else if (textCursor != null && blinkingCursor.ElapsedMilliseconds > TEXT_CURSOR_BLINK_FREQUENCY) { RegisterClip (textCursor.Value); textCursor = null; blinkingCursor.Restart (); } else if (FocusedWidget is Label lab && lab.SelectionIsEmpty) { - if (blinkingCursor.ElapsedMilliseconds > blinkFrequency) { + if (blinkingCursor.ElapsedMilliseconds > TEXT_CURSOR_BLINK_FREQUENCY) { textCursor = lab.DrawCursor (ctx); surf.Flush (); blinkingCursor.Restart (); @@ -896,10 +894,14 @@ namespace Crow DbgLogger.EndEvent (DbgEvtType.Drawing, true); } #endregion - const long blinkFrequency = 300; + + #region Blinking text cursor + public static long TEXT_CURSOR_BLINK_FREQUENCY = 300; internal Rectangle? textCursor = null; internal bool forceTextCursor = true; Stopwatch blinkingCursor = Stopwatch.StartNew (); + #endregion + #region GraphicTree handling /// Add widget to the Graphic tree of this interface and register it for layouting public Widget AddWidget(Widget g) @@ -1125,6 +1127,10 @@ namespace Crow Cursor createCursor (MouseCursor mc) { + const int minimumSize = 24; + if (!XCursor.Cursors.ContainsKey (mc)) { + XCursor.Cursors[mc] = XCursorFile.Load (this, $"#Crow.Cursors.{mc}").Cursors.First (cu => cu.Width >= minimumSize); + } XCursor c = XCursor.Cursors [mc]; return new CustomCursor (c.Width, c.Height, c.data, c.Xhot, c.Yhot); } @@ -1139,7 +1145,25 @@ namespace Crow cursor = value; currentCursor?.Dispose (); - currentCursor = createCursor (cursor); + switch (cursor) { + case MouseCursor.arrow: + case MouseCursor.top_left_arrow: + currentCursor = new Cursor (CursorShape.Arrow); + break; + case MouseCursor.crosshair: + currentCursor = new Cursor (CursorShape.Crosshair); + break; + case MouseCursor.hand: + currentCursor = new Cursor (CursorShape.Hand); + break; + case MouseCursor.ibeam: + currentCursor = new Cursor (CursorShape.IBeam); + break; + default: + currentCursor = XCursor.Create (this, cursor); + break; + } + currentCursor.Set (hWin); //MouseCursorChanged.Raise (this,new MouseCursorChangedEventArgs(cursor)); } diff --git a/Crow/src/Widgets/OldLabel.cs b/Crow/src/Widgets/OldLabel.cs index ed87d712..b7d62c1f 100644 --- a/Crow/src/Widgets/OldLabel.cs +++ b/Crow/src/Widgets/OldLabel.cs @@ -10,6 +10,7 @@ using System.Text.RegularExpressions; using System.ComponentModel; namespace Crow { + [Obsolete] public class OldLabel : Widget { #region CTOR diff --git a/Crow/src/Widgets/OldTextBox.cs b/Crow/src/Widgets/OldTextBox.cs index f209746f..c236bf4b 100644 --- a/Crow/src/Widgets/OldTextBox.cs +++ b/Crow/src/Widgets/OldTextBox.cs @@ -1,12 +1,14 @@ -// Copyright (c) 2013-2020 Jean-Philippe Bruyère +// Copyright (c) 2013-2021 Jean-Philippe Bruyère // // This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) using Crow.Cairo; using Glfw; +using System; namespace Crow { + [Obsolete] public class OldTextBox : OldLabel { #region CTOR diff --git a/Crow/src/XCursor.cs b/Crow/src/XCursor.cs index a987b602..2fdfa5a0 100644 --- a/Crow/src/XCursor.cs +++ b/Crow/src/XCursor.cs @@ -6,6 +6,7 @@ using System; using System.IO; using System.Diagnostics; using System.Collections.Generic; +using System.Linq; namespace Crow { @@ -13,7 +14,7 @@ namespace Crow { const uint XC_TYPE_IMG = 0xfffd0002; - class toc + struct toc { public uint type; public uint subtype; @@ -32,13 +33,12 @@ namespace Crow static XCursorFile loadFromStream(Stream s) { - List tocList = new List (); + List tocList = new List (5); XCursorFile tmp = new XCursorFile (); using (BinaryReader sr = new BinaryReader (s)) { - byte[] data; - //magic: CARD32 ’Xcur’ (0x58, 0x63, 0x75, 0x72) - if (new string (sr.ReadChars (4)) != "Xcur") { + //magic: CARD32 ’Xcur’ (0x58, 0x63, 0x75, 0x72) + if (!sr.ReadChars (4).AsSpan ().SequenceEqual("Xcur".AsSpan())) { Debug.WriteLine ("XCursor Load error: Wrong magic"); return null; } @@ -56,7 +56,6 @@ namespace Crow foreach (toc t in tocList) { if (t.type != XC_TYPE_IMG) continue; - sr.BaseStream.Seek (t.pos, SeekOrigin.Begin); tmp.Cursors.Add(imageLoad (sr)); } @@ -91,21 +90,7 @@ namespace Crow // delay: CARD32 Delay between animation frames in milliseconds tmp.Delay = sr.ReadUInt32 (); // pixels: LISTofCARD32 Packed ARGB format pixels - tmp.data = new byte [tmp.Width * tmp.Height * 4]; - for (int i = 0; i < tmp.Width * tmp.Height; i++) { - //unchecked { tmp.data [i * 4 + 3] = (byte)(2 * (int)sr.ReadByte ()); } - tmp.data [i * 4 + 0] = sr.ReadByte (); - tmp.data [i * 4 + 1] = sr.ReadByte (); - tmp.data [i * 4 + 2] = sr.ReadByte (); - tmp.data [i * 4 + 3] = sr.ReadByte (); - - //System.Diagnostics.Debug.WriteLine ($"{tmp.data [i * 4 + 3],2:X} {tmp.data [i * 4 + 0],2:X} {tmp.data [i * 4 + 1],2:X} {tmp.data [i * 4 + 2],2:X}"); - } - //tmp.data = sr.ReadBytes((int)(tmp.Width * tmp.Height * 4)); - /*using(Stream fs = new FileStream($"/tmp/test.bin_{tmp.Width}", FileMode.Create)) - using (BinaryWriter sr2 = new BinaryWriter(fs)) { - sr2.Write (tmp.data, 0, tmp.data.Length); - }*/ + tmp.data = sr.ReadBytes ((int)(4 * tmp.Width * tmp.Height)); return tmp; } } @@ -119,13 +104,18 @@ namespace Crow public uint Delay; public byte[] data; - public XCursor () - { + public XCursor () { } + public static Glfw.CustomCursor Create (Interface iface, MouseCursor mc) { + const int minimumSize = 24; + if (!Cursors.ContainsKey (mc)) + XCursor.Cursors[mc] = XCursorFile.Load (iface, $"#Crow.Cursors.{mc}").Cursors.First (cu => cu.Width >= minimumSize); + XCursor c = XCursor.Cursors[mc]; + return new Glfw.CustomCursor (c.Width, c.Height, c.data, c.Xhot, c.Yhot); } -// public static implicit operator MouseCursor(XCursor xc) -// { -// return new MouseCursor((int)xc.Xhot, (int)xc.Yhot, (int)xc.Width, (int)xc.Height,xc.data); -// } + // public static implicit operator MouseCursor(XCursor xc) + // { + // return new MouseCursor((int)xc.Xhot, (int)xc.Yhot, (int)xc.Width, (int)xc.Height,xc.data); + // } } } -- 2.47.3