diff --git a/MetaBrush.cabal b/MetaBrush.cabal
index 0d9602e..622a6a1 100644
--- a/MetaBrush.cabal
+++ b/MetaBrush.cabal
@@ -10,6 +10,7 @@ data-dir:
assets
data-files:
theme.css
+ icon.png
description:
MetaBrush is a GUI for brush calligraphy based on Bézier curves.
@@ -84,6 +85,7 @@ executable MetaBrush
other-modules:
MetaBrush.Asset.Brush
, MetaBrush.Asset.Colours
+ , MetaBrush.Asset.Cursor
, MetaBrush.Asset.Logo
, MetaBrush.Asset.Magnifier
, MetaBrush.Asset.Meta
diff --git a/app/Main.hs b/app/Main.hs
index da06f6b..86eef31 100644
--- a/app/Main.hs
+++ b/app/Main.hs
@@ -39,10 +39,18 @@ import qualified Data.Text as Text
( pack )
-- MetaBrush
+import MetaBrush.Asset.Brush
+ ( drawBrush )
import MetaBrush.Asset.Colours
( ColourRecord(..), colours )
+import MetaBrush.Asset.Cursor
+ ( drawCursorIcon )
import MetaBrush.Asset.Logo
( drawLogo )
+import MetaBrush.Asset.Meta
+ ( drawMeta )
+import MetaBrush.Asset.WindowIcons
+ ( drawMinimise, drawRestoreDown, drawMaximise, drawClose )
import MetaBrush.Event
( handleKeyboardPressEvent, handleKeyboardReleaseEvent )
import MetaBrush.Render.Util
@@ -88,6 +96,9 @@ main = do
( Just windowGeometry )
[ GDK.WindowHintsMinSize ]
+ iconPath <- Directory.canonicalizePath =<< Cabal.getDataFileName "icon.png"
+ GTK.windowSetIconFromFile window iconPath
+
Colours { .. } <- colours windowWidgetPath
---------------------------------------------------------
@@ -106,9 +117,9 @@ main = do
panelGrid <- GTK.gridNew
GTK.gridAttach uiGrid logo 0 0 1 2
- GTK.gridAttach uiGrid titleBar 1 0 3 1
- GTK.gridAttach uiGrid toolBar 0 2 2 2
- GTK.gridAttach uiGrid mainPane 2 1 2 4
+ GTK.gridAttach uiGrid titleBar 1 0 2 1
+ GTK.gridAttach uiGrid toolBar 0 2 2 1
+ GTK.gridAttach uiGrid mainPane 2 2 1 1
mainView <- GTK.boxNew GTK.OrientationVertical 0
@@ -149,6 +160,20 @@ main = do
widgetAddClasses menuBar [ "menuBar", "text", "plain" ]
GTK.boxPackStart titleBar menuBar False False 0
+ -- TODO: this is a bit of a workaround to add hover highlight to top-level menu items.
+ -- Activating a menu somehow sets the "hover" setting,
+ -- so instead we use the "selected" setting for actual hover highlighting.
+ topLevelMenuItems <- GTK.containerGetChildren menuBar
+ for_ topLevelMenuItems \ topLevelMenuItem -> do
+ void $ GTK.onWidgetEnterNotifyEvent topLevelMenuItem \ _ -> do
+ flags <- GTK.widgetGetStateFlags topLevelMenuItem
+ GTK.widgetSetStateFlags topLevelMenuItem ( GTK.StateFlagsSelected : flags ) True
+ pure False
+ void $ GTK.onWidgetLeaveNotifyEvent topLevelMenuItem \ _ -> do
+ flags <- GTK.widgetGetStateFlags topLevelMenuItem
+ GTK.widgetSetStateFlags topLevelMenuItem ( filter ( /= GTK.StateFlagsSelected ) flags ) True
+ pure False
+
windowIcons <- GTK.boxNew GTK.OrientationHorizontal 0
widgetAddClasses windowIcons [ "windowIcon" ]
GTK.boxPackEnd titleBar windowIcons False False 0
@@ -157,11 +182,91 @@ main = do
widgetAddClasses title [ "text", "title", "plain" ]
GTK.boxSetCenterWidget titleBar ( Just title )
+ minimiseButton <- GTK.buttonNew
+ fullscreenButton <- GTK.buttonNew
+ closeButton <- GTK.buttonNew
+
+ GTK.boxPackStart windowIcons minimiseButton True True 0
+ GTK.boxPackStart windowIcons fullscreenButton True True 0
+ GTK.boxPackStart windowIcons closeButton True True 0
+
+ minimiseArea <- GTK.drawingAreaNew
+ fullscreenArea <- GTK.drawingAreaNew
+ closeArea <- GTK.drawingAreaNew
+
+ GTK.containerAdd minimiseButton minimiseArea
+ GTK.containerAdd fullscreenButton fullscreenArea
+ GTK.containerAdd closeButton closeArea
+
+ void $ GTK.onWidgetDraw minimiseArea
+ $ Cairo.renderWithContext
+ ( drawMinimise plain )
+
+ void $ GTK.onWidgetDraw fullscreenArea \ cairoContext -> do
+ Just gdkWindow <- GTK.widgetGetWindow window
+ windowState <- GDK.windowGetState gdkWindow
+ if any ( \case { GDK.WindowStateFullscreen -> True; GDK.WindowStateMaximized -> True; _ -> False } ) windowState
+ then Cairo.renderWithContext ( drawRestoreDown plain ) cairoContext
+ else Cairo.renderWithContext ( drawMaximise plain ) cairoContext
+
+ void $ GTK.onWidgetDraw closeArea
+ $ Cairo.renderWithContext
+ ( drawClose plain )
+
+
+ for_ [ minimiseButton, fullscreenButton, closeButton ] \ button -> do
+ widgetAddClass button "windowIcon"
+
+ widgetAddClass closeButton "closeWindowIcon"
+
---------------------------------------------------------
-- Tool bar
widgetAddClass toolBar "toolBar"
+ GTK.widgetSetValign toolBar GTK.AlignStart
+ GTK.widgetSetVexpand toolBar True
+
+ toolBarPhantomRadioButton <- GTK.radioButtonNew ( [] @GTK.RadioButton )
+
+ selectionTool <- GTK.radioButtonNewFromWidget ( Just toolBarPhantomRadioButton )
+ brushTool <- GTK.radioButtonNewFromWidget ( Just toolBarPhantomRadioButton )
+ metaTool <- GTK.radioButtonNewFromWidget ( Just toolBarPhantomRadioButton )
+
+ GTK.boxPackStart toolBar selectionTool True True 0
+ GTK.boxPackStart toolBar brushTool True True 0
+ GTK.boxPackStart toolBar metaTool True True 0
+
+ for_ [ selectionTool, brushTool, metaTool ] \ tool -> do
+ GTK.toggleButtonSetMode tool False -- don't display radio indicator
+ widgetAddClass tool "toolItem"
+
+ selectionToolArea <- GTK.drawingAreaNew
+ brushToolArea <- GTK.drawingAreaNew
+ metaToolArea <- GTK.drawingAreaNew
+
+{-
+ for_ [ selectionToolArea, brushToolArea, metaToolArea ] \ toolArea -> do
+ GTK.widgetSetValign toolArea GTK.AlignCenter
+ GTK.widgetSetHalign toolArea GTK.AlignCenter
+-}
+
+ GTK.containerAdd selectionTool selectionToolArea
+ GTK.containerAdd brushTool brushToolArea
+ GTK.containerAdd metaTool metaToolArea
+
+ void $ GTK.onWidgetDraw selectionToolArea
+ $ Cairo.renderWithContext
+ ( drawCursorIcon logo_base )
+
+ void $ GTK.onWidgetDraw brushToolArea
+ $ Cairo.renderWithContext
+ ( drawBrush logo_base logo_highlight logo_base )
+
+ void $ GTK.onWidgetDraw metaToolArea
+ $ Cairo.renderWithContext
+ ( drawMeta logo_highlight )
+
---------------------------------------------------------
-- File bar
@@ -171,11 +276,11 @@ main = do
GTK.containerAdd fileBar fileTabs
widgetAddClasses fileTabs [ "fileBar", "plain", "text" ]
- phantomRadioButton <- GTK.radioButtonNew ( [] @GTK.RadioButton )
+ fileBarPhantomRadioButton <- GTK.radioButtonNew ( [] @GTK.RadioButton )
for_ [ 1 .. 12 ] \ i -> do
-- File tab elements.
- pgButton <- GTK.radioButtonNewWithLabelFromWidget ( Just phantomRadioButton ) ( "New Document (" <> Text.pack ( show i ) <> ")" )
+ pgButton <- GTK.radioButtonNewWithLabelFromWidget ( Just fileBarPhantomRadioButton ) ( "New Document (" <> Text.pack ( show i ) <> ")" )
GTK.toggleButtonSetMode pgButton False -- don't display radio indicator
closeFileButton <- GTK.buttonNewWithLabel "x"
@@ -189,6 +294,8 @@ main = do
widgetAddClasses pgButton [ "fileBarTabButton" ]
widgetAddClasses closeFileButton [ "fileBarCloseButton" ]
+ -- Make both file tab elements activate styling on the whole tab
+ -- (e.g. hovering over the close file button should highlight the whole tab).
void $ GTK.onButtonClicked pgButton do
active <- GTK.toggleButtonGetActive pgButton
flags <- GTK.widgetGetStateFlags tab
@@ -297,14 +404,27 @@ main = do
---------------------------------------------------------
-- Actions
+ GTK.widgetAddEvents window [GDK.EventMaskKeyPressMask, GDK.EventMaskKeyReleaseMask]
+
+ _ <- GTK.onButtonClicked closeButton GTK.mainQuit
+ _ <- GTK.onButtonClicked minimiseButton ( GTK.windowIconify window )
+ _ <- GTK.onButtonClicked fullscreenButton do
+ Just gdkWindow <- GTK.widgetGetWindow window
+ windowState <- GDK.windowGetState gdkWindow
+ if GDK.WindowStateFullscreen `elem` windowState
+ then GTK.windowUnfullscreen window
+ else
+ if GDK.WindowStateMaximized `elem` windowState
+ then GTK.windowUnmaximize window
+ else GTK.windowMaximize window
+
+ _ <- GTK.onWidgetKeyPressEvent window handleKeyboardPressEvent
+ _ <- GTK.onWidgetKeyReleaseEvent window handleKeyboardReleaseEvent
+ _ <- GTK.onWidgetDestroy window GTK.mainQuit
+
---------------------------------------------------------
-- GTK main loop
- GTK.widgetAddEvents window [GDK.EventMaskKeyPressMask, GDK.EventMaskKeyReleaseMask]
- _ <- GTK.onWidgetKeyPressEvent window handleKeyboardPressEvent
- _ <- GTK.onWidgetKeyReleaseEvent window handleKeyboardReleaseEvent
- _ <- GTK.onWidgetDestroy window GTK.mainQuit
-
GTK.widgetShowAll window
GTK.main
diff --git a/assets/icon.png b/assets/icon.png
new file mode 100644
index 0000000..e1ca047
Binary files /dev/null and b/assets/icon.png differ
diff --git a/assets/theme.css b/assets/theme.css
index a724048..6a74990 100644
--- a/assets/theme.css
+++ b/assets/theme.css
@@ -14,8 +14,6 @@
/* Viewport background colour */
.viewport_bg {
background-color: rgb(236, 223, 210);
- min-width: 60px;
- min-height: 40px;
-GtkWidget-window-dragging: false;
}
@@ -47,6 +45,7 @@
/* Logo area */
.logo {
margin-left: 4px;
+ min-width: 28px;
}
/* Logo base colour */
@@ -112,9 +111,11 @@
font-size: 12px;
}
+/*
.titleBar > * :hover {
background-color: rgb(72,70,61);
}
+*/
.title {
border-top: 2px solid rgb(41, 40, 40);
@@ -132,12 +133,17 @@
border-top: 2px solid rgb(41, 40, 40);
}
-.menuItem:hover {
+/* Menu item hover effect (workaround) */
+.menuItem:selected {
+ border-color: rgb(72,70,61);
+}
+
+/* Styling for active menu item */
+.menuItem:active, .menuItem:checked, .menuItem:hover {
border-color: rgb(234,223,204);
background-color: rgb(72,70,61);
}
-/* Menu drop shadow */
.menuItem > * > * {
box-shadow: 2px 4px 3px -1px rgba(28,25,25,0.5);
border: 1px solid rgb(28,25,25);
@@ -153,6 +159,10 @@
border-left: 2px solid rgb(41, 40, 40);
}
+.submenuItem:hover{
+ background-color: rgb(72,70,61);
+}
+
.submenuItem:disabled {
color: rgb(149,149,149);
}
@@ -166,14 +176,48 @@
border-color: rgb(234,223,204);
}
-/*
.windowIcon {
+ min-width: 24px;
+}
+
+.windowIcon:hover {
+ background-color: rgb(34,131,186);
+}
+
+.windowIcon:active, .windowIcon:checked {
+ background-color: rgb(23,108,156);
+}
+
+.closeWindowIcon:hover {
+ background-color: rgb(181,43,43);
+}
+
+.closeWindowIcon:active, .closeWindowIcon:checked {
+ background-color: rgb(160,37,37);
}
-*/
/* Tool bar */
.toolBar {
- min-width: 60px;
+ min-width: 32px;
+ margin-top: 28px;
+}
+
+.toolItem {
+ border-left: 2px solid rgb(41, 40, 40);
+ min-height: 32px;
+ min-width: 38px;
+ padding-top: 12px;
+ padding-bottom: 8px;
+ padding-left: 6px;
+}
+
+.toolItem:hover {
+ border-color: rgb(72,70,61);
+}
+
+.toolItem:active, .toolItem:checked {
+ border-color: rgb(234,223,204);
+ background-color: rgb(72,70,61);
}
/* File bar */
@@ -184,7 +228,7 @@
}
.fileBarTab {
- border-top: 3px solid rgb(41, 40, 40);
+ border-top: 2px solid rgb(41, 40, 40);
}
.fileBarTab:hover {
diff --git a/img/MetaBrush_ui_mockup.svg b/img/MetaBrush_ui_mockup.svg
index b02bb02..5a1aeb8 100644
--- a/img/MetaBrush_ui_mockup.svg
+++ b/img/MetaBrush_ui_mockup.svg
@@ -5,6 +5,7 @@
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
+ xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
sodipodi:docname="MetaBrush_ui_mockup.svg"
@@ -55,15 +56,19 @@
showgrid="false"
inkscape:current-layer="layer1"
inkscape:document-units="mm"
- inkscape:cy="399.13966"
- inkscape:cx="834.67434"
- inkscape:zoom="0.70710678"
+ inkscape:cy="-120.95892"
+ inkscape:cx="667.79746"
+ inkscape:zoom="1"
inkscape:pageshadow="2"
inkscape:pageopacity="0.0"
borderopacity="1.0"
bordercolor="#666666"
pagecolor="#ffffff"
- id="base" />
+ id="base">
+
+
@@ -447,16 +452,16 @@
d="m 53.697983,130.46852 c -0.398481,-0.58922 -0.794322,-1.7911 -1.048322,-1.73818 -0.137583,-0.0423 -2.879333,4.01184 -3.122749,4.29759 -0.275167,-0.28575 -0.645584,0.0212 -0.677334,0.45508 0,0.22225 0.538837,0.84005 1.005417,0.16933 0.04401,-0.0633 2.128203,-2.97885 2.322592,-3.26489 0.169333,0.34925 0.869778,1.57275 0.912111,1.62567 0.413037,-0.20721 0.507142,-0.33141 0.729392,-0.59599 0.254032,-0.35144 0.287311,-0.3959 0.629738,-0.84526 0.15875,0.32808 0.651865,0.86911 1.100666,1.44991 0.169643,0.21954 0.893474,0.96206 1.105878,0.87896 0.113388,-0.0444 0.516106,-0.40729 0.587459,-0.79224 0.01599,-0.0863 0.05612,-0.41482 -0.01708,-0.48091 -0.05177,-0.0468 -0.483647,0.19656 -0.618249,0.14287 -0.232945,-0.34124 -0.51833,-0.93511 -0.765006,-1.34591 -0.391583,-0.70908 -0.69744,-1.58033 -1.012682,-1.38728 -0.218958,0.13409 -0.343747,0.30086 -0.391584,0.37042 -0.219248,0.31882 -0.322696,0.47584 -0.740261,1.06082 z" />
+ sodipodi:nodetypes="ccccc"
+ id="path4307"
+ d="m 194.23426,-203.9466 v 0.99478 h 3.09843 v -0.99478 z"
+ style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:medium;line-height:normal;font-family:sans-serif;font-variant-ligatures:normal;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-variant-east-asian:normal;font-feature-settings:normal;font-variation-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:normal;word-spacing:normal;text-transform:none;writing-mode:lr-tb;direction:ltr;text-orientation:mixed;dominant-baseline:auto;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;shape-margin:0;inline-size:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;vector-effect:none;fill:#d4be98;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:0.415235;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate;stop-color:#000000;stop-opacity:1" />
@@ -464,25 +469,18 @@
inkscape:connector-curvature="0"
id="path1755"
d="m 151.28645,19.176929 1.56634,-1.56634"
- style="fill:none;stroke:#d4be98;stroke-width:0.20610821;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
+ style="fill:none;stroke:#d4be98;stroke-width:0.22902154;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
-
+ sodipodi:nodetypes="ccccccccccccccccccccc"
+ transform="matrix(0.13348279,0,0,0.13596576,-38.35818,15.738262)"
+ d="m 1378.666,7.5722656 v 5.0508574 h -3.5117 v 9.876341 h 10.8697 v -4.345243 h 3.5117 V 7.5722656 Z m 1.5352,3.0839624 h 7.7838 v 5.974556 h -1.961 v -4.007661 h -5.8228 z m -3.5117,5.05281 h 7.7837 v 5.280661 h -7.7837 z"
+ style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:medium;line-height:normal;font-family:sans-serif;font-variant-ligatures:normal;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-variant-east-asian:normal;font-feature-settings:normal;font-variation-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:normal;word-spacing:normal;text-transform:none;writing-mode:lr-tb;direction:ltr;text-orientation:mixed;dominant-baseline:auto;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;shape-margin:0;inline-size:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;vector-effect:none;fill:#d4be98;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:1.52992;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:stroke fill markers;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate;stop-color:#000000;stop-opacity:1"
+ id="path4298" />
+ style="opacity:1;vector-effect:none;fill:#332727;fill-opacity:0.57647061;stroke:none;stroke-width:0.45031363;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:normal" />
. . .
+
+
+
diff --git a/src/app/MetaBrush/Asset/Cursor.hs b/src/app/MetaBrush/Asset/Cursor.hs
new file mode 100644
index 0000000..00e6064
--- /dev/null
+++ b/src/app/MetaBrush/Asset/Cursor.hs
@@ -0,0 +1,47 @@
+module MetaBrush.Asset.Cursor
+ ( drawCursor, drawCursorIcon )
+ where
+
+-- gi-cairo-render
+import qualified GI.Cairo.Render as Cairo
+
+-- gi-gdk
+import qualified GI.Gdk as GDK
+
+-- MetaBrush
+import MetaBrush.Render.Util
+ ( withRGBA )
+
+--------------------------------------------------------------------------------
+
+-- | "Selection" mouse cursor. 18 x 18.
+drawCursor :: GDK.RGBA -> GDK.RGBA -> Cairo.Render Bool
+drawCursor cursorColour outlineColour = do
+
+ Cairo.setLineWidth 1
+ withRGBA outlineColour Cairo.setSourceRGBA
+ Cairo.newPath
+ Cairo.moveTo 12.625 10.582031
+ Cairo.curveTo 5.699219 11.101563 4.097656 12.3125 0 17.976563
+ Cairo.lineTo 0.078125 0
+ Cairo.closePath
+ Cairo.strokePreserve
+
+ withRGBA cursorColour Cairo.setSourceRGBA
+ Cairo.fillPreserve
+
+ pure True
+
+-- | "Selection" tool icon. 30 x 30.
+drawCursorIcon :: GDK.RGBA -> Cairo.Render Bool
+drawCursorIcon cursorColour = do
+
+ withRGBA cursorColour Cairo.setSourceRGBA
+ Cairo.newPath
+ Cairo.moveTo 24.023438 16.3125
+ Cairo.curveTo 15.636719 16.9375 13.699219 18.40625 8.742188 25.261719
+ Cairo.lineTo 8.835938 3.503906
+ Cairo.closePath
+ Cairo.fillPreserve
+
+ pure True
diff --git a/src/app/MetaBrush/Asset/WindowIcons.hs b/src/app/MetaBrush/Asset/WindowIcons.hs
index 1531ca4..da9bd2b 100644
--- a/src/app/MetaBrush/Asset/WindowIcons.hs
+++ b/src/app/MetaBrush/Asset/WindowIcons.hs
@@ -9,23 +9,98 @@ import qualified GI.Cairo.Render as Cairo
import qualified GI.Gdk as GDK
-- MetaBrush
---import MetaBrush.Render.Util
--- ( withRGBA )
+import MetaBrush.Render.Util
+ ( withRGBA )
--------------------------------------------------------------------------------
--- | Minimise window icon.
-drawMinimise :: GDK.RGBA -> Cairo.Render ()
-drawMinimise iconColour = pure ()
+-- | Minimise window icon.
+drawMinimise :: GDK.RGBA -> Cairo.Render Bool
+drawMinimise iconColour = do
+
+ withRGBA iconColour Cairo.setSourceRGBA
+
+ Cairo.newPath
+ Cairo.moveTo 6.144531 12.914063
+ Cairo.lineTo 6.144531 16.675781
+ Cairo.lineTo 17.855469 16.675781
+ Cairo.lineTo 17.855469 12.914063
+ Cairo.closePath
+ Cairo.fillPreserve
+
+ pure True
-- | Restore down window icon.
-drawRestoreDown :: GDK.RGBA -> Cairo.Render ()
-drawRestoreDown iconColour = pure ()
+drawRestoreDown :: GDK.RGBA -> Cairo.Render Bool
+drawRestoreDown iconColour = do
+
+ withRGBA iconColour Cairo.setSourceRGBA
+
+ Cairo.newPath
+ Cairo.moveTo 8.453125 4.179688
+ Cairo.lineTo 8.453125 9.230469
+ Cairo.lineTo 4.941406 9.230469
+ Cairo.lineTo 4.941406 19.105469
+ Cairo.lineTo 15.8125 19.105469
+ Cairo.lineTo 15.8125 14.761719
+ Cairo.lineTo 19.324219 14.761719
+ Cairo.lineTo 19.324219 4.179688
+ Cairo.closePath
+ Cairo.moveTo 9.988281 7.261719
+ Cairo.lineTo 17.773438 7.261719
+ Cairo.lineTo 17.773438 13.238281
+ Cairo.lineTo 15.8125 13.238281
+ Cairo.lineTo 15.8125 9.230469
+ Cairo.lineTo 9.988281 9.230469
+ Cairo.closePath
+ Cairo.moveTo 6.476563 12.316406
+ Cairo.lineTo 14.261719 12.316406
+ Cairo.lineTo 14.261719 17.597656
+ Cairo.lineTo 6.476563 17.597656
+ Cairo.closePath
+ Cairo.fillPreserve
+
+ pure True
-- | Maximise window icon.
-drawMaximise :: GDK.RGBA -> Cairo.Render ()
-drawMaximise iconColour = pure ()
+drawMaximise :: GDK.RGBA -> Cairo.Render Bool
+drawMaximise iconColour = do
+
+ withRGBA iconColour Cairo.setSourceRGBA
+
+ Cairo.newPath
+ Cairo.moveTo 5.386719 5.449219
+ Cairo.lineTo 5.386719 18.550781
+ Cairo.lineTo 18.613281 18.550781
+ Cairo.lineTo 18.613281 5.449219
+ Cairo.closePath
+ Cairo.moveTo 6.921875 9.128906
+ Cairo.lineTo 17.078125 9.128906
+ Cairo.lineTo 17.078125 17.023438
+ Cairo.lineTo 6.921875 17.023438
+ Cairo.closePath
+ Cairo.fillPreserve
+
+ pure True
-- | Close window icon.
-drawClose :: GDK.RGBA -> Cairo.Render ()
-drawClose iconColour = pure ()
+drawClose :: GDK.RGBA -> Cairo.Render Bool
+drawClose iconColour = do
+
+ Cairo.setLineWidth 2
+ withRGBA iconColour Cairo.setSourceRGBA
+
+ Cairo.setLineCap Cairo.LineCapRound
+ Cairo.setLineJoin Cairo.LineJoinMiter
+
+ Cairo.newPath
+ Cairo.moveTo 6.132813 6.238281
+ Cairo.lineTo 17.867188 17.761719
+ Cairo.strokePreserve
+
+ Cairo.newPath
+ Cairo.moveTo 6.132813 17.761719
+ Cairo.lineTo 17.867188 6.23828
+ Cairo.strokePreserve
+
+ pure True