diff --git a/NEWS b/NEWS
new file mode 100644
index 0000000..c8590f2
--- /dev/null
+++ b/NEWS
@@ -0,0 +1,51 @@
+v5.1 - March 2020
+=================
+
+* Add "Open" and "Save drawing"
+* Change some keyboard shortcuts
+* Replace "smoothed stroke" preference with `Ctrl` key modifier
+* Add `space` key modifier to ignore pointer movement #20
+* User style is now stored in user data directory (`user.css`)
+* Customizable square area size #22
+
+v5 - December 2019
+==================
+
+* Improve pointer cursor
+* Add 3.24 version as supported
+* Use maxLevel in line-width OSD
+* Small fix with text shape that displayed keybindings
+
+
+v4.1 - October 2019
+===================
+
+* GS 3.34 compatibility
+* Create drawing menu on demand
+* Allow 0 px line width because stroke lines cannot have color with some transparency
+
+
+v4 - April 2019
+===============
+
+* Add drawing menu
+* Add panel indicator
+* Prefs to disable indicator and notifications
+* Change middle click action
+
+v3 - March 2019
+===============
+
+* Fix area container integration #1
+* Add persistence
+
+v2 - March 2019
+===============
+
+* Add transformations
+* Add square area
+
+v1 - March 2019
+===============
+
+* Initial release
diff --git a/README.md b/README.md
index 8eb7998..39e555a 100644
--- a/README.md
+++ b/README.md
@@ -1,12 +1,11 @@
-__Draw On Your Screen__
-=======================
+# Draw On Your Screen
+
Start drawing with Super+Alt+D.
Then save your beautiful work by taking a screenshot.

-Features :
-----------
+## Features
* Basic shapes (rectangle, circle, ellipse, line, curve, text, free)
* Smooth stroke
@@ -15,13 +14,26 @@ Features :
* Multi-monitor support
* Export to SVG
-Install :
-----------
+## Install
1. Download and decompress or clone the repository
-2. Place the resulting directory in ~/.local/share/gnome-shell/extensions
-3. IMPORTANT: change the directory name to drawOnYourScreen@abakkk.framagit.org
-4. A small shot of `alt + F2` `r` to restart Gnome-shell under Xorg, restart or relogin under Wayland
-5. Enable the extension in Gnome-tweak-tool
+2. Place the resulting directory in `~/.local/share/gnome-shell/extensions`
+3. **Change the directory name** to `drawOnYourScreen@abakkk.framagit.org`
+4. Xorg: type `alt + F2` and `r` to restart gnome-shell
+ Wayland: restart or re-login
+5. Enable the extension in gnome-tweaks
6. `Super + Alt + D` to test
7. [https://framagit.org/abakkk/DrawOnYourScreen/issues](https://framagit.org/abakkk/DrawOnYourScreen/issues) to say it doesn't work
+
+## Details
+
+* Draw arrows:
+
+ Intersect two lines and curve the second thanks to the `Ctrl` key.
+
+ 
+
+* Screenshot Tool extension:
+
+ [Screenshot Tool](https://extensions.gnome.org/extension/1112/screenshot-tool/) is a convenient extension to “create, copy, store and upload screenshots”. To use it while drawing mode is active, toggle the area selection mode thanks to the Screenshot Tool shortcut (`Super + F11` by default, see its preferences) and **hold** the `space` key when selecting the area with pointer to avoid drawing.
+
diff --git a/data/default.css b/data/default.css
new file mode 100644
index 0000000..b5ab3ef
--- /dev/null
+++ b/data/default.css
@@ -0,0 +1,54 @@
+/*
+ * Except for the font, you don't need to restart the extension.
+ * Just save this file as ~/.local/share/drawOnYourScreen/user.css and the changes will be applied for your next brushstroke.
+ *
+ * ~/.local/share/drawOnYourScreen/user.css file is automatically generated by activating "Edit style".
+ * Delete ~/.local/share/drawOnYourScreen/user.css file to retrieve default drawing style.
+ *
+ * line-join (no string):
+ * 0 : miter, 1 : round, 2 : bevel
+ * line-cap (no string):
+ * 0 : butt, 1 : round, 2 : square
+ *
+ * dash:
+ * dash-array-on is the length of dashes (no dashes if 0, you can put 0.1 to get dots or square according to line-cap).
+ * dash-array-off is the length of gaps (no dashes if 0).
+ *
+ * square area:
+ * Drawing in a square area is convenient when using the extension as a vector graphics editor. By default,
+ * when toggling 'Square drawing area', the area is sized to 75% of monitor size. You can fix and customize this size
+ * by uncommenting square-area-width and square-area-height lines.
+ *
+ * font:
+ * Only one family : no comma separated list of families like "font1, font2, ..., Sans-Serif".
+ * Font family can be any font installed, or a generic family name (Serif, Sans-Serif, Monospace, Cursive, Fantasy).
+ * Font weight and font style : no upper case when string.
+ * Weight <= 500 (or lighter, normal, medium) is rendered as normal.
+ * Weight > 500 (or bolder, bold) is rendered as bold.
+ * Oblique and italic style supports depend on the font family and seem to be rendered identically.
+ *
+ */
+
+.draw-on-your-screen {
+ -drawing-line-width: 5px;
+ -drawing-line-join: 1;
+ -drawing-line-cap: 1;
+ -drawing-dash-array-on: 5px;
+ -drawing-dash-array-off: 15px;
+ -drawing-dash-offset: 0px;
+ -drawing-color1: HotPink;
+ -drawing-color2: Cyan;
+ -drawing-color3: yellow;
+ -drawing-color4: Orangered;
+ -drawing-color5: Chartreuse;
+ -drawing-color6: DarkViolet;
+ -drawing-color7: #ffffff;
+ -drawing-color8: rgba(130, 130, 130, 0.3);
+ -drawing-color9: rgb(0, 0, 0);
+ -drawing-background-color: #2e3436;
+ /*-drawing-square-area-width: 512px;*/
+ /*-drawing-square-area-height: 512px;*/
+ font-family: Cantarell;
+ font-weight: normal;
+ font-style: normal;
+}
diff --git a/icons/dashed-line-symbolic.svg b/data/icons/dashed-line-symbolic.svg
similarity index 100%
rename from icons/dashed-line-symbolic.svg
rename to data/icons/dashed-line-symbolic.svg
diff --git a/icons/fill-symbolic.svg b/data/icons/fill-symbolic.svg
similarity index 100%
rename from icons/fill-symbolic.svg
rename to data/icons/fill-symbolic.svg
diff --git a/icons/full-line-symbolic.svg b/data/icons/full-line-symbolic.svg
similarity index 100%
rename from icons/full-line-symbolic.svg
rename to data/icons/full-line-symbolic.svg
diff --git a/icons/linecap-symbolic.svg b/data/icons/linecap-symbolic.svg
similarity index 100%
rename from icons/linecap-symbolic.svg
rename to data/icons/linecap-symbolic.svg
diff --git a/icons/linejoin-symbolic.svg b/data/icons/linejoin-symbolic.svg
similarity index 100%
rename from icons/linejoin-symbolic.svg
rename to data/icons/linejoin-symbolic.svg
diff --git a/icons/stroke-symbolic.svg b/data/icons/stroke-symbolic.svg
similarity index 100%
rename from icons/stroke-symbolic.svg
rename to data/icons/stroke-symbolic.svg
diff --git a/draw.js b/draw.js
index 20b8b05..ae75252 100644
--- a/draw.js
+++ b/draw.js
@@ -3,7 +3,7 @@
/*
* Copyright 2019 Abakkk
*
- * This file is part of DrowOnYourScreen, a drawing extension for GNOME Shell.
+ * This file is part of DrawOnYourScreen, a drawing extension for GNOME Shell.
* https://framagit.org/abakkk/DrawOnYourScreen
*
* This program is free software: you can redistribute it and/or modify
@@ -20,6 +20,7 @@
* along with this program. If not, see .
*/
+const ByteArray = imports.byteArray;
const Cairo = imports.cairo;
const Clutter = imports.gi.Clutter;
const Gio = imports.gi.Gio;
@@ -40,29 +41,66 @@ const Screenshot = imports.ui.screenshot;
const Tweener = imports.ui.tweener;
const ExtensionUtils = imports.misc.extensionUtils;
-const Extension = ExtensionUtils.getCurrentExtension();
-const Convenience = Extension.imports.convenience;
-const ExtensionJs = Extension.imports.extension;
-const Prefs = Extension.imports.prefs;
-const _ = imports.gettext.domain(Extension.metadata["gettext-domain"]).gettext;
+const Me = ExtensionUtils.getCurrentExtension();
+const Convenience = ExtensionUtils.getSettings ? ExtensionUtils : Me.imports.convenience;
+const Extension = Me.imports.extension;
+const Prefs = Me.imports.prefs;
+const _ = imports.gettext.domain(Me.metadata['gettext-domain']).gettext;
const GS_VERSION = Config.PACKAGE_VERSION;
-const FILL_ICON_PATH = Extension.dir.get_child('icons').get_child('fill-symbolic.svg').get_path();
-const STROKE_ICON_PATH = Extension.dir.get_child('icons').get_child('stroke-symbolic.svg').get_path();
-const LINEJOIN_ICON_PATH = Extension.dir.get_child('icons').get_child('linejoin-symbolic.svg').get_path();
-const LINECAP_ICON_PATH = Extension.dir.get_child('icons').get_child('linecap-symbolic.svg').get_path();
-const DASHED_LINE_ICON_PATH = Extension.dir.get_child('icons').get_child('dashed-line-symbolic.svg').get_path();
-const FULL_LINE_ICON_PATH = Extension.dir.get_child('icons').get_child('full-line-symbolic.svg').get_path();
+const FILL_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('fill-symbolic.svg').get_path();
+const STROKE_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('stroke-symbolic.svg').get_path();
+const LINEJOIN_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('linejoin-symbolic.svg').get_path();
+const LINECAP_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('linecap-symbolic.svg').get_path();
+const DASHED_LINE_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('dashed-line-symbolic.svg').get_path();
+const FULL_LINE_ICON_PATH = Me.dir.get_child('data').get_child('icons').get_child('full-line-symbolic.svg').get_path();
var Shapes = { NONE: 0, LINE: 1, ELLIPSE: 2, RECTANGLE: 3, TEXT: 4 };
-var TextState = { DRAWING: 0, WRITING: 1 };
-var ShapeNames = { 0: "Free drawing", 1: "Line", 2: "Ellipse", 3: "Rectangle", 4: "Text" };
-var LineCapNames = { 0: 'Butt', 1: 'Round', 2: 'Square' };
-var LineJoinNames = { 0: 'Miter', 1: 'Round', 2: 'Bevel' };
-var FontWeightNames = { 0: 'Normal', 1: 'Bold' };
-var FontStyleNames = { 0: 'Normal', 1: 'Italic', 2: 'Oblique' };
-var FontFamilyNames = { 0: 'Default', 1: 'Sans-Serif', 2: 'Serif', 3: 'Monospace', 4: 'Cursive', 5: 'Fantasy' };
+const TextState = { DRAWING: 0, WRITING: 1 };
+const ShapeNames = { 0: "Free drawing", 1: "Line", 2: "Ellipse", 3: "Rectangle", 4: "Text" };
+const LineCapNames = { 0: 'Butt', 1: 'Round', 2: 'Square' };
+const LineJoinNames = { 0: 'Miter', 1: 'Round', 2: 'Bevel' };
+const FontWeightNames = { 0: 'Normal', 1: 'Bold' };
+const FontStyleNames = { 0: 'Normal', 1: 'Italic', 2: 'Oblique' };
+const FontFamilyNames = { 0: 'Default', 1: 'Sans-Serif', 2: 'Serif', 3: 'Monospace', 4: 'Cursive', 5: 'Fantasy' };
+
+const getDateString = function() {
+ let date = GLib.DateTime.new_now_local();
+ return `${date.format("%F")} ${date.format("%X")}`;
+};
+
+const getJsonFiles = function() {
+ let directory = Gio.File.new_for_path(GLib.build_filenamev([GLib.get_user_data_dir(), Me.metadata['data-dir']]));
+
+ let enumerator;
+ try {
+ enumerator = directory.enumerate_children('standard::name,standard::display-name,standard::content-type,time::modified', Gio.FileQueryInfoFlags.NONE, null);
+ } catch(e) {
+ return [];
+ }
+
+ let jsonFiles = [];
+ let fileInfo = enumerator.next_file(null);
+ while (fileInfo) {
+ if (fileInfo.get_content_type().indexOf('json') != -1 && fileInfo.get_name() != `${Me.metadata['persistent-file-name']}.json`) {
+ let file = enumerator.get_child(fileInfo);
+ jsonFiles.push({ name: fileInfo.get_name().slice(0, -5),
+ displayName: fileInfo.get_display_name().slice(0, -5),
+ // fileInfo.get_modification_date_time: Gio 2.62+
+ modificationUnixTime: fileInfo.get_attribute_uint64('time::modified'),
+ delete: () => file.delete(null) });
+ }
+ fileInfo = enumerator.next_file(null);
+ }
+ enumerator.close(null);
+
+ jsonFiles.sort((a, b) => {
+ return b.modificationUnixTime - a.modificationUnixTime;
+ });
+
+ return jsonFiles;
+};
// DrawingArea is the widget in which we draw, thanks to Cairo.
// It creates and manages a DrawingElement for each "brushstroke".
@@ -70,13 +108,11 @@ var FontFamilyNames = { 0: 'Default', 1: 'Sans-Serif', 2: 'Serif', 3: 'Monospac
var DrawingArea = new Lang.Class({
Name: 'DrawOnYourScreenDrawingArea',
Extends: St.DrawingArea,
- Signals: { 'show-osd': { param_types: [GObject.TYPE_STRING, GObject.TYPE_DOUBLE] },
+ Signals: { 'show-osd': { param_types: [GObject.TYPE_STRING, GObject.TYPE_STRING, GObject.TYPE_DOUBLE] },
'stop-drawing': {} },
- _init: function(params, monitor, helper, loadJson) {
- this.parent({ style_class: 'draw-on-your-screen', name: params && params.name ? params.name : ""});
-
- this.connect('repaint', this._repaint.bind(this));
+ _init: function(params, monitor, helper, loadPersistent) {
+ this.parent({ style_class: 'draw-on-your-screen', name: params.name});
this.settings = Convenience.getSettings();
this.monitor = monitor;
@@ -93,13 +129,13 @@ var DrawingArea = new Lang.Class({
this.fill = false;
this.colors = [Clutter.Color.new(0, 0, 0, 255)];
- if (loadJson)
- this._loadJson();
+ if (loadPersistent)
+ this._loadPersistent();
},
get menu() {
if (!this._menu)
- this._menu = new DrawingMenu(this);
+ this._menu = new DrawingMenu(this, this.monitor);
return this._menu;
},
@@ -124,6 +160,8 @@ var DrawingArea = new Lang.Class({
this.fontFamily = font.get_family();
this.currentFontWeight = font.get_weight();
this.currentFontStyle = font.get_style();
+ this.squareAreaWidth = themeNode.get_length('-drawing-square-area-width');
+ this.squareAreaHeight = themeNode.get_length('-drawing-square-area-height');
} catch(e) {
logError(e);
}
@@ -142,8 +180,8 @@ var DrawingArea = new Lang.Class({
this.currentFontStyle = this.currentFontStyle == 2 ? 1 : ( this.currentFontStyle == 1 ? 2 : 0);
},
- _repaint: function(area) {
- let cr = area.get_context();
+ vfunc_repaint: function() {
+ let cr = this.get_context();
for (let i = 0; i < this.elements.length; i++) {
let isStraightLine = this.elements[i].shape == Shapes.LINE &&
@@ -173,6 +211,9 @@ var DrawingArea = new Lang.Class({
},
_onButtonPressed: function(actor, event) {
+ if (this.spaceKeyPressed)
+ return Clutter.EVENT_PROPAGATE;
+
let button = event.get_button();
let [x, y] = event.get_coords();
let shiftPressed = event.has_shift_modifier();
@@ -210,6 +251,20 @@ var DrawingArea = new Lang.Class({
return Clutter.EVENT_STOP;
},
+ _onStageKeyPressed: function(actor, event) {
+ if (event.get_key_symbol() == Clutter.KEY_space)
+ this.spaceKeyPressed = true;
+
+ return Clutter.EVENT_PROPAGATE;
+ },
+
+ _onStageKeyReleased: function(actor, event) {
+ if (event.get_key_symbol() == Clutter.KEY_space)
+ this.spaceKeyPressed = false;
+
+ return Clutter.EVENT_PROPAGATE;
+ },
+
_onKeyPressed: function(actor, event) {
if (event.get_key_symbol() == Clutter.Escape) {
this.emit('stop-drawing');
@@ -218,12 +273,12 @@ var DrawingArea = new Lang.Class({
} else if (this.currentElement && this.currentElement.shape == Shapes.TEXT && this.currentElement.state == TextState.WRITING) {
if (event.get_key_symbol() == Clutter.KEY_BackSpace) {
this.currentElement.text = this.currentElement.text.slice(0, -1);
- this._updateCursorTimeout();
+ this._updateTextCursorTimeout();
} else if (event.has_control_modifier() && event.get_key_symbol() == 118) {
// Ctrl + V
St.Clipboard.get_default().get_text(St.ClipboardType.CLIPBOARD, (clipBoard, clipText) => {
this.currentElement.text += clipText;
- this._updateCursorTimeout();
+ this._updateTextCursorTimeout();
this._redisplay();
});
return Clutter.EVENT_STOP;
@@ -237,7 +292,7 @@ var DrawingArea = new Lang.Class({
} else {
let unicode = event.get_key_unicode();
this.currentElement.text += unicode;
- this._updateCursorTimeout();
+ this._updateTextCursorTimeout();
}
this._redisplay();
return Clutter.EVENT_STOP;
@@ -270,8 +325,6 @@ var DrawingArea = new Lang.Class({
this._stopDrawing();
});
- this.smoothedStroke = this.settings.get_boolean('smoothed-stroke');
-
this.currentElement = new DrawingElement ({
shape: this.currentShape,
color: this.currentColor.to_string(),
@@ -294,6 +347,9 @@ var DrawingArea = new Lang.Class({
}
this.motionHandler = this.connect('motion-event', (actor, event) => {
+ if (this.spaceKeyPressed)
+ return;
+
let coords = event.get_coords();
let [s, x, y] = this.transform_stage_point(coords[0], coords[1]);
if (!s)
@@ -322,8 +378,8 @@ var DrawingArea = new Lang.Class({
if (this.currentElement.shape == Shapes.TEXT && this.currentElement.state == TextState.DRAWING) {
this.currentElement.state = TextState.WRITING;
this.currentElement.text = '';
- this.emit('show-osd', _("Type your text\nand press Enter"), -1);
- this._updateCursorTimeout();
+ this.emit('show-osd', null, _("Type your text\nand press Enter"), -1);
+ this._updateTextCursorTimeout();
this.textHasCursor = true;
this._redisplay();
this.updatePointerCursor();
@@ -342,7 +398,7 @@ var DrawingArea = new Lang.Class({
if (!this.currentElement)
return;
if (this.currentElement.shape == Shapes.NONE)
- this.currentElement.addPoint(x, y, this.smoothedStroke);
+ this.currentElement.addPoint(x, y, controlPressed);
else if ((this.currentElement.shape == Shapes.RECTANGLE || this.currentElement.shape == Shapes.TEXT) && (controlPressed || this.currentElement.transform.active))
this.currentElement.transformRectangle(x, y);
else if (this.currentElement.shape == Shapes.ELLIPSE && (controlPressed || this.currentElement.transform.active))
@@ -360,14 +416,14 @@ var DrawingArea = new Lang.Class({
if (this.currentElement.text.length > 0)
this.elements.push(this.currentElement);
this.currentElement = null;
- this._stopCursorTimeout();
+ this._stopTextCursorTimeout();
this._redisplay();
},
setPointerCursor: function(pointerCursorName) {
if (!this.currentPointerCursorName || this.currentPointerCursorName != pointerCursorName) {
this.currentPointerCursorName = pointerCursorName;
- ExtensionJs.setCursor(pointerCursorName);
+ Extension.setCursor(pointerCursorName);
}
},
@@ -378,20 +434,20 @@ var DrawingArea = new Lang.Class({
this.setPointerCursor('MOVE_OR_RESIZE_WINDOW');
},
- _stopCursorTimeout: function() {
- if (this.cursorTimeoutId) {
- Mainloop.source_remove(this.cursorTimeoutId);
- this.cursorTimeoutId = null;
+ _stopTextCursorTimeout: function() {
+ if (this.textCursorTimeoutId) {
+ Mainloop.source_remove(this.textCursorTimeoutId);
+ this.textCursorTimeoutId = null;
}
this.textHasCursor = false;
},
- _updateCursorTimeout: function() {
- this._stopCursorTimeout();
- this.cursorTimeoutId = Mainloop.timeout_add(600, () => {
+ _updateTextCursorTimeout: function() {
+ this._stopTextCursorTimeout();
+ this.textCursorTimeoutId = Mainloop.timeout_add(600, () => {
this.textHasCursor = !this.textHasCursor;
this._redisplay();
- return true;
+ return GLib.SOURCE_CONTINUE;
});
},
@@ -413,7 +469,7 @@ var DrawingArea = new Lang.Class({
this.buttonReleasedHandler = null;
}
this.currentElement = null;
- this._stopCursorTimeout();
+ this._stopTextCursorTimeout();
} else {
this.elements.pop();
}
@@ -447,9 +503,10 @@ var DrawingArea = new Lang.Class({
toggleSquareArea: function() {
this.isSquareArea = !this.isSquareArea;
if (this.isSquareArea) {
- let squareWidth = Math.min(this.monitor.width, this.monitor.height) * 3 / 4;
- this.set_position(Math.floor(this.monitor.width / 2 - squareWidth / 2), Math.floor(this.monitor.height / 2 - squareWidth / 2));
- this.set_size(squareWidth, squareWidth);
+ let width = this.squareAreaWidth || this.squareAreaHeight || Math.min(this.monitor.width, this.monitor.height) * 3 / 4;
+ let height = this.squareAreaHeight || this.squareAreaWidth || Math.min(this.monitor.width, this.monitor.height) * 3 / 4;
+ this.set_position(Math.floor(this.monitor.width / 2 - width / 2), Math.floor(this.monitor.height / 2 - height / 2));
+ this.set_size(width, height);
this.add_style_class_name('draw-on-your-screen-square-area');
} else {
this.set_position(0, 0);
@@ -468,38 +525,38 @@ var DrawingArea = new Lang.Class({
this.currentElement.color = this.currentColor.to_string();
this._redisplay();
}
- this.emit('show-osd', `${this.currentColor.to_string()}`, -1);
+ this.emit('show-osd', null, `${this.currentColor.to_string()}`, -1);
},
selectShape: function(shape) {
this.currentShape = shape;
- this.emit('show-osd', _(ShapeNames[shape]), -1);
+ this.emit('show-osd', null, _(ShapeNames[shape]), -1);
this.updatePointerCursor();
},
toggleFill: function() {
this.fill = !this.fill;
- this.emit('show-osd', this.fill ? _("Fill") : _("Stroke"), -1);
+ this.emit('show-osd', null, this.fill ? _("Fill") : _("Stroke"), -1);
},
toggleDash: function() {
this.dashedLine = !this.dashedLine;
- this.emit('show-osd', this.dashedLine ? _("Dashed line") : _("Full line"), -1);
+ this.emit('show-osd', null, this.dashedLine ? _("Dashed line") : _("Full line"), -1);
},
incrementLineWidth: function(increment) {
this.currentLineWidth = Math.max(this.currentLineWidth + increment, 0);
- this.emit('show-osd', this.currentLineWidth + " " + _("px"), 2 * this.currentLineWidth);
+ this.emit('show-osd', null, this.currentLineWidth + " " + _("px"), 2 * this.currentLineWidth);
},
toggleLineJoin: function() {
this.currentLineJoin = this.currentLineJoin == 2 ? 0 : this.currentLineJoin + 1;
- this.emit('show-osd', _(LineJoinNames[this.currentLineJoin]), -1);
+ this.emit('show-osd', null, _(LineJoinNames[this.currentLineJoin]), -1);
},
toggleLineCap: function() {
this.currentLineCap = this.currentLineCap == 2 ? 0 : this.currentLineCap + 1;
- this.emit('show-osd', _(LineCapNames[this.currentLineCap]), -1);
+ this.emit('show-osd', null, _(LineCapNames[this.currentLineCap]), -1);
},
toggleFontWeight: function() {
@@ -508,7 +565,7 @@ var DrawingArea = new Lang.Class({
this.currentElement.font.weight = this.currentFontWeight;
this._redisplay();
}
- this.emit('show-osd', `${_(FontWeightNames[this.currentFontWeight])}`, -1);
+ this.emit('show-osd', null, `${_(FontWeightNames[this.currentFontWeight])}`, -1);
},
toggleFontStyle: function() {
@@ -517,7 +574,7 @@ var DrawingArea = new Lang.Class({
this.currentElement.font.style = this.currentFontStyle;
this._redisplay();
}
- this.emit('show-osd', `${_(FontStyleNames[this.currentFontStyle])}`, -1);
+ this.emit('show-osd', null, `${_(FontStyleNames[this.currentFontStyle])}`, -1);
},
toggleFontFamily: function() {
@@ -527,7 +584,7 @@ var DrawingArea = new Lang.Class({
this.currentElement.font.family = currentFontFamily;
this._redisplay();
}
- this.emit('show-osd', `${_(currentFontFamily)}`, -1);
+ this.emit('show-osd', null, `${_(currentFontFamily)}`, -1);
},
toggleHelp: function() {
@@ -538,7 +595,9 @@ var DrawingArea = new Lang.Class({
},
enterDrawingMode: function() {
- this.keyPressedHandler = this.connect('key-press-event', this._onKeyPressed.bind(this));
+ this.stageKeyPressedHandler = global.stage.connect('key-press-event', this._onStageKeyPressed.bind(this));
+ this.stageKeyReleasedHandler = global.stage.connect('key-release-event', this._onStageKeyReleased.bind(this));
+ this.keyPressedHandler = this.connect('key-press-event', this._onKeyPressed.bind(this));
this.buttonPressedHandler = this.connect('button-press-event', this._onButtonPressed.bind(this));
this._onKeyboardPopupMenuHandler = this.connect('popup-menu', this._onKeyboardPopupMenu.bind(this));
this.scrollHandler = this.connect('scroll-event', this._onScroll.bind(this));
@@ -547,6 +606,14 @@ var DrawingArea = new Lang.Class({
},
leaveDrawingMode: function(save) {
+ if (this.stageKeyPressedHandler) {
+ global.stage.disconnect(this.stageKeyPressedHandler);
+ this.stageKeyPressedHandler = null;
+ }
+ if (this.stageKeyReleasedHandler) {
+ global.stage.disconnect(this.stageKeyReleasedHandler);
+ this.stageKeyReleasedHandler = null;
+ }
if (this.keyPressedHandler) {
this.disconnect(this.keyPressedHandler);
this.keyPressedHandler = null;
@@ -576,15 +643,16 @@ var DrawingArea = new Lang.Class({
this.helper.hideHelp();
this.currentElement = null;
- this._stopCursorTimeout();
+ this._stopTextCursorTimeout();
this.currentShape = Shapes.NONE;
this.dashedLine = false;
this.fill = false;
this._redisplay();
- this.menu.close();
+ if (this._menu)
+ this._menu.close();
this.get_parent().set_background_color(null);
if (save)
- this.saveAsJson();
+ this.savePersistent();
},
saveAsSvg: function() {
@@ -605,8 +673,7 @@ var DrawingArea = new Lang.Class({
}
content += "\n";
- let date = GLib.DateTime.new_now_local();
- let filename = `DrawOnYourScreen ${date.format("%F")} ${date.format("%X")}.svg`;
+ let filename = `${Me.metadata['svg-file-name']} ${getDateString()}.svg`;
let dir = GLib.get_user_special_dir(GLib.UserDirectory.DIRECTORY_PICTURES);
let path = GLib.build_filenamev([dir, filename]);
if (GLib.file_test(path, GLib.FileTest.EXISTS))
@@ -626,34 +693,73 @@ var DrawingArea = new Lang.Class({
}
},
- saveAsJson: function() {
- let filename = `DrawOnYourScreen.json`;
- let dir = GLib.get_user_data_dir();
- let path = GLib.build_filenamev([dir, filename]);
-
- let oldContents;
- if (GLib.file_test(path, GLib.FileTest.EXISTS)) {
- oldContents = GLib.file_get_contents(path)[1];
- if (oldContents instanceof Uint8Array)
- oldContents = imports.byteArray.toString(oldContents);
+ _saveAsJson: function(name, notify) {
+ // stop drawing or writing
+ if (this.currentElement && this.currentElement.shape == Shapes.TEXT && this.currentElement.state == TextState.WRITING) {
+ this._stopWriting();
+ } else if (this.currentElement && this.currentElement.shape != Shapes.TEXT) {
+ this._stopDrawing();
}
- // do not create a file to write just an empty array
- if (!oldContents && this.elements.length == 0)
- return;
+ let dir = GLib.build_filenamev([GLib.get_user_data_dir(), Me.metadata['data-dir']]);
+ if (!GLib.file_test(dir, GLib.FileTest.EXISTS))
+ GLib.mkdir_with_parents(dir, 0o700);
+ let path = GLib.build_filenamev([dir, `${name}.json`]);
+
+ let oldContents;
+
+ if (name == Me.metadata['persistent-file-name']) {
+ if (GLib.file_test(path, GLib.FileTest.EXISTS)) {
+ oldContents = GLib.file_get_contents(path)[1];
+ if (oldContents instanceof Uint8Array)
+ oldContents = ByteArray.toString(oldContents);
+ }
+
+ // do not create a file to write just an empty array
+ if (!oldContents && this.elements.length == 0)
+ return;
+ }
// do not use "content = JSON.stringify(this.elements, null, 2);", neither "content = JSON.stringify(this.elements);"
// because of compromise between disk usage and human readability
let contents = `[\n ` + new Array(...this.elements.map(element => JSON.stringify(element))).join(`,\n\n `) + `\n]`;
- if (contents != oldContents)
- GLib.file_set_contents(path, contents);
+ if (name == Me.metadata['persistent-file-name'] && contents == oldContents)
+ return;
+
+ GLib.file_set_contents(path, contents);
+ if (notify)
+ this.emit('show-osd', 'document-save-symbolic', name, -1);
+ if (name != Me.metadata['persistent-file-name']) {
+ this.jsonName = name;
+ this.lastJsonContents = contents;
+ }
},
- _loadJson: function() {
- let filename = `DrawOnYourScreen.json`;
+ saveAsJsonWithName: function(name) {
+ this._saveAsJson(name);
+ },
+
+ saveAsJson: function() {
+ this._saveAsJson(getDateString(), true);
+ },
+
+ savePersistent: function() {
+ this._saveAsJson(Me.metadata['persistent-file-name']);
+ },
+
+ syncPersistent: function() {
+ // do not override peristent.json with an empty drawing when changing persistency setting
+ if (!this.elements.length)
+ this._loadPersistent();
+ else
+ this.savePersistent();
+
+ },
+
+ _loadJson: function(name, notify) {
let dir = GLib.get_user_data_dir();
- let path = GLib.build_filenamev([dir, filename]);
+ let path = GLib.build_filenamev([dir, Me.metadata['data-dir'], `${name}.json`]);
if (!GLib.file_test(path, GLib.FileTest.EXISTS))
return;
@@ -661,8 +767,52 @@ var DrawingArea = new Lang.Class({
if (!success)
return;
if (contents instanceof Uint8Array)
- contents = imports.byteArray.toString(contents);
+ contents = ByteArray.toString(contents);
this.elements.push(...JSON.parse(contents).map(object => new DrawingElement(object)));
+
+ if (notify)
+ this.emit('show-osd', 'document-open-symbolic', name, -1);
+ if (name != Me.metadata['persistent-file-name']) {
+ this.jsonName = name;
+ this.lastJsonContents = contents;
+ }
+ },
+
+ _loadPersistent: function() {
+ this._loadJson(Me.metadata['persistent-file-name']);
+ },
+
+ loadJson: function(name, notify) {
+ this.elements = [];
+ this.currentElement = null;
+ this._stopTextCursorTimeout();
+ this._loadJson(name, notify);
+ this._redisplay();
+ },
+
+ loadNextJson: function() {
+ let names = getJsonFiles().map(file => file.name);
+
+ if (!names.length)
+ return;
+
+ let nextName = names[this.jsonName && names.indexOf(this.jsonName) != names.length - 1 ? names.indexOf(this.jsonName) + 1 : 0];
+ this.loadJson(nextName, true);
+ },
+
+ loadPreviousJson: function() {
+ let names = getJsonFiles().map(file => file.name);
+
+ if (!names.length)
+ return;
+
+ let previousName = names[this.jsonName && names.indexOf(this.jsonName) > 0 ? names.indexOf(this.jsonName) - 1 : names.length - 1];
+ this.loadJson(previousName, true);
+ },
+
+ get drawingContentsHasChanged() {
+ let contents = `[\n ` + new Array(...this.elements.map(element => JSON.stringify(element))).join(`,\n\n `) + `\n]`;
+ return contents != this.lastJsonContents;
},
disable: function() {
@@ -674,7 +824,7 @@ var DrawingArea = new Lang.Class({
// DrawingElement represents a "brushstroke".
// It can be converted into a cairo path as well as a svg element.
// See DrawingArea._startDrawing() to know its params.
-var DrawingElement = new Lang.Class({
+const DrawingElement = new Lang.Class({
Name: 'DrawOnYourScreenDrawingElement',
_init: function(params) {
@@ -893,7 +1043,7 @@ var DrawingElement = new Lang.Class({
},
});
-function getAngle(xO, yO, xA, yA, xB, yB) {
+const getAngle = function(xO, yO, xA, yA, xB, yB) {
// calculate angle of rotation in absolute value
// cos(AOB) = (OA.OB)/(||OA||*||OB||) where OA.OB = (xA-xO)*(xB-xO) + (yA-yO)*(yB-yO)
let angle = Math.acos( ((xA - xO)*(xB - xO) + (yA - yO)*(yB - yO)) / (Math.hypot(xA - xO, yA - yO) * Math.hypot(xB - xO, yB - yO)) );
@@ -907,11 +1057,11 @@ function getAngle(xO, yO, xA, yA, xB, yB) {
if (xA < xO)
angle = - angle;
return angle;
-}
+};
-var HELPER_ANIMATION_TIME = 0.25;
-var MEDIA_KEYS_SCHEMA = 'org.gnome.settings-daemon.plugins.media-keys';
-var MEDIA_KEYS_KEYS = {
+const HELPER_ANIMATION_TIME = 0.25;
+const MEDIA_KEYS_SCHEMA = 'org.gnome.settings-daemon.plugins.media-keys';
+const MEDIA_KEYS_KEYS = {
'screenshot': "Screenshot",
'screenshot-clip': "Screenshot to clipboard",
'area-screenshot': "Area screenshot",
@@ -952,7 +1102,7 @@ var DrawingHelper = new Lang.Class({
for (let i = 0; i < Prefs.OTHER_SHORTCUTS.length; i++) {
if (Prefs.OTHER_SHORTCUTS[i].desc.indexOf('-separator-') != -1) {
- this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-separator' }));
+ this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-helper-separator' }));
continue;
}
let hbox = new St.BoxLayout({ vertical: false });
@@ -961,11 +1111,11 @@ var DrawingHelper = new Lang.Class({
this.vbox.add(hbox);
}
- this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-separator' }));
+ this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-helper-separator' }));
for (let settingKey in Prefs.INTERNAL_KEYBINDINGS) {
if (settingKey.indexOf('-separator-') != -1) {
- this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-separator' }));
+ this.vbox.add(new St.BoxLayout({ vertical: false, style_class: 'draw-on-your-screen-helper-separator' }));
continue;
}
let hbox = new St.BoxLayout({ vertical: false });
@@ -997,7 +1147,7 @@ var DrawingHelper = new Lang.Class({
this.opacity = 0;
this.show();
- let maxHeight = this.monitor.height*(3/4);
+ let maxHeight = this.monitor.height * 3 / 4;
this.set_height(Math.min(this.height, maxHeight));
this.set_position(Math.floor(this.monitor.width / 2 - this.width / 2),
Math.floor(this.monitor.height / 2 - this.height / 2));
@@ -1024,10 +1174,14 @@ var DrawingHelper = new Lang.Class({
},
});
-var DrawingMenu = new Lang.Class({
+const getActor = function(object) {
+ return GS_VERSION < '3.33.0' ? object.actor : object;
+};
+
+const DrawingMenu = new Lang.Class({
Name: 'DrawOnYourScreenDrawingMenu',
- _init: function(area) {
+ _init: function(area, monitor) {
this.area = area;
let side = Clutter.get_default_text_direction() == Clutter.TextDirection.RTL ? St.Side.RIGHT : St.Side.LEFT;
this.menu = new PopupMenu.PopupMenu(Main.layoutManager.dummyCursor, 0.25, side);
@@ -1036,12 +1190,25 @@ var DrawingMenu = new Lang.Class({
Main.layoutManager.uiGroup.add_actor(this.menu.actor);
this.menu.actor.add_style_class_name('background-menu draw-on-your-screen-menu');
+ this.menu.actor.set_style('max-height:' + monitor.height + 'px;');
this.menu.actor.hide();
// do not close the menu on item activated
this.menu.itemActivated = () => {};
this.menu.connect('open-state-changed', this._onMenuOpenStateChanged.bind(this));
+ // Case where the menu is closed (escape key) while the save entry clutter_text is active:
+ // St.Entry clutter_text set the DEFAULT cursor on leave event with a delay and
+ // overrides the cursor set by area.updatePointerCursor().
+ // In order to update drawing cursor on menu closed, we need to leave the saveEntry before closing menu.
+ // Since escape key press event can't be captured easily, the job is done in the menu close function.
+ let menuCloseFunc = this.menu.close;
+ this.menu.close = (animate) => {
+ if (this.saveDrawingSubMenu && this.saveDrawingSubMenu.isOpen)
+ this.saveDrawingSubMenu.close();
+ menuCloseFunc.bind(this.menu)(animate);
+ };
+
this.strokeIcon = new Gio.FileIcon({ file: Gio.File.new_for_path(STROKE_ICON_PATH) });
this.fillIcon = new Gio.FileIcon({ file: Gio.File.new_for_path(FILL_ICON_PATH) });
this.linejoinIcon = new Gio.FileIcon({ file: Gio.File.new_for_path(LINEJOIN_ICON_PATH) });
@@ -1062,7 +1229,8 @@ var DrawingMenu = new Lang.Class({
} else {
this.area.updatePointerCursor();
// actionMode has changed, set previous actionMode in order to keep internal shortcuts working
- Main.actionMode = ExtensionJs.DRAWING_ACTION_MODE | Shell.ActionMode.NORMAL;
+ Main.actionMode = Extension.DRAWING_ACTION_MODE | Shell.ActionMode.NORMAL;
+ this.area.grab_key_focus();
}
},
@@ -1127,15 +1295,19 @@ var DrawingMenu = new Lang.Class({
this.menu.addMenuItem(fontSection);
this.fontSection = fontSection;
- let manager = ExtensionJs.manager;
+ let manager = Extension.manager;
this._addSwitchItemWithCallback(this.menu, _("Hide panel and dock"), manager.hiddenList ? true : false, manager.togglePanelAndDockOpacity.bind(manager));
this._addSwitchItemWithCallback(this.menu, _("Add a drawing background"), this.area.hasBackground, this.area.toggleBackground.bind(this.area));
this._addSwitchItemWithCallback(this.menu, _("Square drawing area"), this.area.isSquareArea, this.area.toggleSquareArea.bind(this.area));
this._addSeparator(this.menu);
- this.menu.addAction(_("Save drawing as a SVG file"), this.area.saveAsSvg.bind(this.area), 'document-save-symbolic');
- this.menu.addAction(_("Open stylesheet.css"), manager.openStylesheetFile.bind(manager), 'document-open-symbolic');
- this.menu.addAction(_("Show help"), this.area.toggleHelp.bind(this.area), 'preferences-desktop-keyboard-shortcuts-symbolic');
+ this._addDrawingNameItem(this.menu);
+ this._addOpenDrawingSubMenuItem(this.menu);
+ this._addSaveDrawingSubMenuItem(this.menu);
+
+ this.menu.addAction(_("Save drawing as a SVG file"), this.area.saveAsSvg.bind(this.area), 'image-x-generic-symbolic');
+ this.menu.addAction(_("Edit style"), manager.openUserStyleFile.bind(manager), 'document-page-setup-symbolic');
+ this.menu.addAction(_("Show help"), () => { this.close(); this.area.toggleHelp(); }, 'preferences-desktop-keyboard-shortcuts-symbolic');
this.updateSectionVisibility();
},
@@ -1154,10 +1326,9 @@ var DrawingMenu = new Lang.Class({
_addSwitchItem: function(menu, label, iconFalse, iconTrue, target, targetProperty) {
let item = new PopupMenu.PopupSwitchMenuItem(label, target[targetProperty]);
- let itemActor = GS_VERSION < '3.33.0' ? item.actor : item;
item.icon = new St.Icon({ style_class: 'popup-menu-icon' });
- itemActor.insert_child_at_index(item.icon, 1);
+ getActor(item).insert_child_at_index(item.icon, 1);
item.icon.set_gicon(target[targetProperty] ? iconTrue : iconFalse);
item.connect('toggled', (item, state) => {
@@ -1176,34 +1347,32 @@ var DrawingMenu = new Lang.Class({
_addSliderItem: function(menu, target, targetProperty) {
let item = new PopupMenu.PopupBaseMenuItem({ activate: false });
- let itemActor = GS_VERSION < '3.33.0' ? item.actor : item;
let label = new St.Label({ text: target[targetProperty] + " " + _("px"), style_class: 'draw-on-your-screen-menu-slider-label' });
let slider = new Slider.Slider(target[targetProperty] / 50);
- let sliderActor = GS_VERSION < '3.33.0' ? slider.actor : slider;
if (GS_VERSION < '3.33.0') {
slider.connect('value-changed', (slider, value, property) => {
target[targetProperty] = Math.max(Math.round(value * 50), 0);
label.set_text(target[targetProperty] + " px");
if (target[targetProperty] === 0)
- label.add_style_class_name(ExtensionJs.WARNING_COLOR_STYLE_CLASS_NAME);
+ label.add_style_class_name(Extension.WARNING_COLOR_STYLE_CLASS_NAME);
else
- label.remove_style_class_name(ExtensionJs.WARNING_COLOR_STYLE_CLASS_NAME);
+ label.remove_style_class_name(Extension.WARNING_COLOR_STYLE_CLASS_NAME);
});
} else {
slider.connect('notify::value', () => {
target[targetProperty] = Math.max(Math.round(slider.value * 50), 0);
label.set_text(target[targetProperty] + " px");
if (target[targetProperty] === 0)
- label.add_style_class_name(ExtensionJs.WARNING_COLOR_STYLE_CLASS_NAME);
+ label.add_style_class_name(Extension.WARNING_COLOR_STYLE_CLASS_NAME);
else
- label.remove_style_class_name(ExtensionJs.WARNING_COLOR_STYLE_CLASS_NAME);
+ label.remove_style_class_name(Extension.WARNING_COLOR_STYLE_CLASS_NAME);
});
}
- itemActor.add(sliderActor, { expand: true });
- itemActor.add(label);
- itemActor.connect('key-press-event', slider.onKeyPressEvent.bind(slider));
+ getActor(item).add(getActor(slider), { expand: true });
+ getActor(item).add(label);
+ getActor(item).connect('key-press-event', slider.onKeyPressEvent.bind(slider));
menu.addMenuItem(item);
},
@@ -1269,11 +1438,200 @@ var DrawingMenu = new Lang.Class({
menu.addMenuItem(item);
},
+ _addDrawingNameItem: function(menu) {
+ this.drawingNameMenuItem = new PopupMenu.PopupMenuItem('', { reactive: false, activate: false });
+ this.drawingNameMenuItem.setSensitive(false);
+ menu.addMenuItem(this.drawingNameMenuItem);
+ this._updateDrawingNameMenuItem();
+ },
+
+ _updateDrawingNameMenuItem: function() {
+ getActor(this.drawingNameMenuItem).visible = this.area.jsonName ? true : false;
+ if (this.area.jsonName) {
+ let prefix = this.area.drawingContentsHasChanged ? "* " : "";
+ this.drawingNameMenuItem.label.set_text(`${prefix}${this.area.jsonName}`);
+ this.drawingNameMenuItem.label.get_clutter_text().set_use_markup(true);
+ }
+ },
+
+ _addOpenDrawingSubMenuItem: function(menu) {
+ let item = new PopupMenu.PopupSubMenuMenuItem(_("Open drawing"), true);
+ this.openDrawingSubMenuItem = item;
+ this.openDrawingSubMenu = item.menu;
+ item.icon.set_icon_name('document-open-symbolic');
+
+ item.menu.itemActivated = () => {
+ item.menu.close();
+ };
+
+ Mainloop.timeout_add(0, () => {
+ this._populateOpenDrawingSubMenu();
+ // small trick to prevent the menu from "jumping" on first opening
+ item.menu.open();
+ item.menu.close();
+ return GLib.SOURCE_REMOVE;
+ });
+ menu.addMenuItem(item);
+ },
+
+ _populateOpenDrawingSubMenu: function() {
+ this.openDrawingSubMenu.removeAll();
+ let jsonFiles = getJsonFiles();
+ jsonFiles.forEach(file => {
+ let item = this.openDrawingSubMenu.addAction(`${file.displayName}`, () => {
+ this.area.loadJson(file.name);
+ this._updateDrawingNameMenuItem();
+ this._updateSaveDrawingSubMenuItemSensitivity();
+ });
+ item.label.get_clutter_text().set_use_markup(true);
+
+ let expander = new St.Bin({
+ style_class: 'popup-menu-item-expander',
+ x_expand: true,
+ });
+ getActor(item).add_child(expander);
+
+ let deleteButton = new St.Button({ style_class: 'draw-on-your-screen-menu-delete-button',
+ child: new St.Icon({ icon_name: 'edit-delete-symbolic',
+ style_class: 'popup-menu-icon',
+ x_align: Clutter.ActorAlign.END }) });
+ getActor(item).add_child(deleteButton);
+
+ deleteButton.connect('clicked', () => {
+ file.delete();
+ this._populateOpenDrawingSubMenu();
+ });
+ });
+
+ this.openDrawingSubMenuItem.setSensitive(!this.openDrawingSubMenu.isEmpty());
+ },
+
+ _addSaveDrawingSubMenuItem: function(menu) {
+ let item = new PopupMenu.PopupSubMenuMenuItem(_("Save drawing"), true);
+ this.saveDrawingSubMenuItem = item;
+ this._updateSaveDrawingSubMenuItemSensitivity();
+ this.saveDrawingSubMenu = item.menu;
+ item.icon.set_icon_name('document-save-symbolic');
+
+ item.menu.itemActivated = () => {
+ item.menu.close();
+ };
+
+ Mainloop.timeout_add(0, () => {
+ this._populateSaveDrawingSubMenu();
+ // small trick to prevent the menu from "jumping" on first opening
+ item.menu.open();
+ item.menu.close();
+ return GLib.SOURCE_REMOVE;
+ });
+ menu.addMenuItem(item);
+ },
+
+ _updateSaveDrawingSubMenuItemSensitivity: function() {
+ this.saveDrawingSubMenuItem.setSensitive(this.area.elements.length > 0);
+ },
+
+ _populateSaveDrawingSubMenu: function() {
+ this.saveEntry = new DrawingMenuEntry({ initialTextGetter: getDateString,
+ entryActivateCallback: (text) => {
+ this.area.saveAsJsonWithName(text);
+ this.saveDrawingSubMenu.toggle();
+ this._updateDrawingNameMenuItem();
+ this._populateOpenDrawingSubMenu();
+ },
+ invalidStrings: [Me.metadata['persistent-file-name'], '/'],
+ primaryIconName: 'insert-text' });
+ this.saveDrawingSubMenu.addMenuItem(this.saveEntry.item);
+ },
+
_addSeparator: function(menu) {
- let separator = new PopupMenu.PopupSeparatorMenuItem(' ');
- let separatorActor = GS_VERSION < '3.33.0' ? separator.actor : separator;
- separatorActor.add_style_class_name('draw-on-your-screen-menu-separator');
- menu.addMenuItem(separator);
+ let separatorItem = new PopupMenu.PopupSeparatorMenuItem(' ');
+ getActor(separatorItem).add_style_class_name('draw-on-your-screen-menu-separator-item');
+ menu.addMenuItem(separatorItem);
}
});
+// based on searchItem.js, https://github.com/leonardo-bartoli/gnome-shell-extension-Recents
+const DrawingMenuEntry = new Lang.Class({
+ Name: 'DrawOnYourScreenDrawingMenuEntry',
+
+ _init: function(params) {
+ this.params = params;
+ this.item = new PopupMenu.PopupBaseMenuItem({ style_class: 'draw-on-your-screen-menu-entry-item',
+ activate: false,
+ reactive: true,
+ can_focus: false });
+
+ this.itemActor = GS_VERSION < '3.33.0' ? this.item.actor : this.item;
+
+ this.entry = new St.Entry({
+ style_class: 'search-entry draw-on-your-screen-menu-entry',
+ track_hover: true,
+ reactive: true,
+ can_focus: true
+ });
+
+ this.entry.set_primary_icon(new St.Icon({ style_class: 'search-entry-icon',
+ icon_name: this.params.primaryIconName }));
+
+ this.entry.clutter_text.connect('text-changed', this._onTextChanged.bind(this));
+ this.entry.clutter_text.connect('activate', this._onTextActivated.bind(this));
+
+ this.clearIcon = new St.Icon({
+ style_class: 'search-entry-icon',
+ icon_name: 'edit-clear-symbolic'
+ });
+ this.entry.connect('secondary-icon-clicked', this._reset.bind(this));
+
+ getActor(this.item).add(this.entry, { expand: true });
+ getActor(this.item).connect('notify::mapped', (actor) => {
+ if (actor.mapped) {
+ this.entry.set_text(this.params.initialTextGetter());
+ this.entry.clutter_text.grab_key_focus();
+ }
+ });
+ },
+
+ _setError: function(hasError) {
+ if (hasError)
+ this.entry.add_style_class_name('draw-on-your-screen-menu-entry-error');
+ else
+ this.entry.remove_style_class_name('draw-on-your-screen-menu-entry-error');
+ },
+
+ _reset: function() {
+ this.entry.text = '';
+ this.entry.clutter_text.set_cursor_visible(true);
+ this.entry.clutter_text.set_selection(0, 0);
+ this._setError(false);
+ },
+
+ _onTextActivated: function(clutterText) {
+ let text = clutterText.get_text();
+ if (text.length == 0)
+ return;
+ if (this._getIsInvalid())
+ return;
+ this._reset();
+ this.params.entryActivateCallback(text);
+ },
+
+ _onTextChanged: function(clutterText) {
+ let text = clutterText.get_text();
+ this.entry.set_secondary_icon(text.length ? this.clearIcon : null);
+
+ if (text.length)
+ this._setError(this._getIsInvalid());
+ },
+
+ _getIsInvalid: function() {
+ for (let i = 0; i < this.params.invalidStrings.length; i++) {
+ if (this.entry.text.indexOf(this.params.invalidStrings[i]) != -1)
+ return true;
+ }
+
+ return false;
+ }
+});
+
+
diff --git a/extension.js b/extension.js
index 5e712e2..ef5d9ed 100644
--- a/extension.js
+++ b/extension.js
@@ -3,7 +3,7 @@
/*
* Copyright 2019 Abakkk
*
- * This file is part of DrowOnYourScreen, a drawing extension for GNOME Shell.
+ * This file is part of DrawOnYourScreen, a drawing extension for GNOME Shell.
* https://framagit.org/abakkk/DrawOnYourScreen
*
* This program is free software: you can redistribute it and/or modify
@@ -21,6 +21,7 @@
*/
const Gio = imports.gi.Gio;
+const GLib = imports.gi.GLib;
const Lang = imports.lang;
const Meta = imports.gi.Meta;
const Shell = imports.gi.Shell;
@@ -31,10 +32,11 @@ const Main = imports.ui.main;
const OsdWindow = imports.ui.osdWindow;
const PanelMenu = imports.ui.panelMenu;
-const Extension = imports.misc.extensionUtils.getCurrentExtension();
-const Convenience = Extension.imports.convenience;
-const Draw = Extension.imports.draw;
-const _ = imports.gettext.domain(Extension.metadata["gettext-domain"]).gettext;
+const ExtensionUtils = imports.misc.extensionUtils;
+const Me = ExtensionUtils.getCurrentExtension();
+const Convenience = ExtensionUtils.getSettings && ExtensionUtils.initTranslations ? ExtensionUtils : Me.imports.convenience;
+const Draw = Me.imports.draw;
+const _ = imports.gettext.domain(Me.metadata['gettext-domain']).gettext;
const GS_VERSION = Config.PACKAGE_VERSION;
@@ -92,16 +94,25 @@ var AreaManager = new Lang.Class({
this.desktopSettingHandler = this.settings.connect('changed::drawing-on-desktop', this.onDesktopSettingChanged.bind(this));
this.persistentSettingHandler = this.settings.connect('changed::persistent-drawing', this.onPersistentSettingChanged.bind(this));
- if (Extension.stylesheet) {
- this.stylesheetMonitor = Extension.stylesheet.monitor(Gio.FileMonitorFlags.NONE, null);
- this.stylesheetChangedHandler = this.stylesheetMonitor.connect('changed', (monitor, file, otherFile, eventType) => {
- if ((eventType != 0 && eventType != 3) || !Extension.stylesheet.query_exists(null))
- return;
- let theme = St.ThemeContext.get_for_stage(global.stage).get_theme();
- theme.unload_stylesheet(Extension.stylesheet);
- theme.load_stylesheet(Extension.stylesheet);
- });
+ this.userStyleFile = Gio.File.new_for_path(GLib.build_filenamev([GLib.get_user_data_dir(), Me.metadata['data-dir'], 'user.css']));
+
+ if (this.userStyleFile.query_exists(null)) {
+ let theme = St.ThemeContext.get_for_stage(global.stage).get_theme();
+ theme.load_stylesheet(this.userStyleFile);
}
+
+ this.userStyleMonitor = this.userStyleFile.monitor_file(Gio.FileMonitorFlags.WATCH_MOVES, null);
+ this.userStyleHandler = this.userStyleMonitor.connect('changed', (monitor, file, otherFile, eventType) => {
+ // 'CHANGED' events are followed by a 'CHANGES_DONE_HINT' event
+ if (eventType == Gio.FileMonitorEvent.CHANGED || eventType == Gio.FileMonitorEvent.ATTRIBUTE_CHANGED)
+ return;
+
+ let theme = St.ThemeContext.get_for_stage(global.stage).get_theme();
+ if (theme.get_custom_stylesheets().indexOf(this.userStyleFile) != -1)
+ theme.unload_stylesheet(this.userStyleFile);
+ if (this.userStyleFile.query_exists(null))
+ theme.load_stylesheet(this.userStyleFile);
+ });
},
onDesktopSettingChanged: function() {
@@ -113,7 +124,7 @@ var AreaManager = new Lang.Class({
onPersistentSettingChanged: function() {
if (this.settings.get_boolean('persistent-drawing'))
- this.areas[Main.layoutManager.primaryIndex].saveAsJson();
+ this.areas[Main.layoutManager.primaryIndex].syncPersistent();
},
updateIndicator: function() {
@@ -136,8 +147,8 @@ var AreaManager = new Lang.Class({
let monitor = this.monitors[i];
let container = new St.Widget({ name: 'drawOnYourSreenContainer' + i });
let helper = new Draw.DrawingHelper({ name: 'drawOnYourSreenHelper' + i }, monitor);
- let load = i == Main.layoutManager.primaryIndex && this.settings.get_boolean('persistent-drawing');
- let area = new Draw.DrawingArea({ name: 'drawOnYourSreenArea' + i }, monitor, helper, load);
+ let loadPersistent = i == Main.layoutManager.primaryIndex && this.settings.get_boolean('persistent-drawing');
+ let area = new Draw.DrawingArea({ name: 'drawOnYourSreenArea' + i }, monitor, helper, loadPersistent);
container.add_child(area);
container.add_child(helper);
@@ -161,6 +172,9 @@ var AreaManager = new Lang.Class({
'delete-last-element': this.activeArea.deleteLastElement.bind(this.activeArea),
'smooth-last-element': this.activeArea.smoothLastElement.bind(this.activeArea),
'save-as-svg': this.activeArea.saveAsSvg.bind(this.activeArea),
+ 'save-as-json': this.activeArea.saveAsJson.bind(this.activeArea),
+ 'open-previous-json': this.activeArea.loadPreviousJson.bind(this.activeArea),
+ 'open-next-json': this.activeArea.loadNextJson.bind(this.activeArea),
'toggle-background': this.activeArea.toggleBackground.bind(this.activeArea),
'toggle-square-area': this.activeArea.toggleSquareArea.bind(this.activeArea),
'increment-line-width': () => this.activeArea.incrementLineWidth(1),
@@ -181,7 +195,7 @@ var AreaManager = new Lang.Class({
'toggle-font-style': this.activeArea.toggleFontStyle.bind(this.activeArea),
'toggle-panel-and-dock-visibility': this.togglePanelAndDockOpacity.bind(this),
'toggle-help': this.activeArea.toggleHelp.bind(this.activeArea),
- 'open-stylesheet': this.openStylesheetFile.bind(this)
+ 'open-user-stylesheet': this.openUserStyleFile.bind(this)
};
for (let key in this.internalKeybindings) {
@@ -212,9 +226,19 @@ var AreaManager = new Lang.Class({
}
},
- openStylesheetFile: function() {
- if (Extension.stylesheet && Extension.stylesheet.query_exists(null))
- Gio.AppInfo.launch_default_for_uri(Extension.stylesheet.get_uri(), global.create_app_launch_context(0, -1));
+ openUserStyleFile: function() {
+ if (!this.userStyleFile.query_exists(null)) {
+ if (!this.userStyleFile.get_parent().query_exists(null))
+ this.userStyleFile.get_parent().make_directory_with_parents(null);
+ let defaultStyleFile = Me.dir.get_child('data').get_child('default.css');
+ if (!defaultStyleFile.query_exists(null))
+ return;
+ let success = defaultStyleFile.copy(this.userStyleFile, Gio.FileCopyFlags.NONE, null, null);
+ if (!success)
+ return;
+ }
+
+ Gio.AppInfo.launch_default_for_uri(this.userStyleFile.get_uri(), global.create_app_launch_context(0, -1));
if (this.activeArea)
this.toggleDrawing();
},
@@ -223,7 +247,7 @@ var AreaManager = new Lang.Class({
for (let i = 0; i < this.areas.length; i++)
this.areas[i].erase();
if (this.settings.get_boolean('persistent-drawing'))
- this.areas[Main.layoutManager.primaryIndex].saveAsJson();
+ this.areas[Main.layoutManager.primaryIndex].savePersistent();
},
togglePanelAndDockOpacity: function() {
@@ -315,11 +339,12 @@ var AreaManager = new Lang.Class({
},
// use level -1 to set no level (null)
- showOsd: function(emitter, label, level, maxLevel) {
+ showOsd: function(emitter, iconName, label, level) {
if (this.osdDisabled)
return;
let activeIndex = this.areas.indexOf(this.activeArea);
if (activeIndex != -1) {
+ let maxLevel;
if (level == -1)
level = null;
else if (level > 100)
@@ -329,7 +354,9 @@ var AreaManager = new Lang.Class({
// GS 3.34+ : bar from 0 to 1
if (level && GS_VERSION > '3.33.0')
level = level / 100;
- Main.osdWindowManager.show(activeIndex, this.enterGicon, label, level, maxLevel);
+
+ let icon = iconName && new Gio.ThemedIcon({ name: iconName });
+ Main.osdWindowManager.show(activeIndex, icon || this.enterGicon, label, level, maxLevel);
Main.osdWindowManager._osdWindows[activeIndex]._label.get_clutter_text().set_use_markup(true);
if (level === 0) {
@@ -357,9 +384,13 @@ var AreaManager = new Lang.Class({
},
disable: function() {
- if (this.stylesheetChangedHandler) {
- this.stylesheetMonitor.disconnect(this.stylesheetChangedHandler);
- this.stylesheetChangedHandler = null;
+ if (this.userStyleHandler && this.userStyleMonitor) {
+ this.userStyleMonitor.disconnect(this.userStyleHandler);
+ this.userStyleHandler = null;
+ }
+ if (this.userStyleMonitor) {
+ this.userStyleMonitor.cancel();
+ this.userStyleMonitor = null;
}
if (this.monitorChangedHandler) {
Main.layoutManager.disconnect(this.monitorChangedHandler);
diff --git a/locale/draw-on-your-screen.pot b/locale/draw-on-your-screen.pot
index e579156..2df55f0 100644
--- a/locale/draw-on-your-screen.pot
+++ b/locale/draw-on-your-screen.pot
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: Draw On Your Screen VERSION\n"
"Report-Msgid-Bugs-To: https://framagit.org/abakkk/DrawOnYourScreen/issues\n"
-"POT-Creation-Date: 2019-03-04 16:40+0100\n"
+"POT-Creation-Date: 2020-01-03 08:00+0100\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME \n"
"Language-Team: LANGUAGE \n"
@@ -19,17 +19,17 @@ msgstr ""
# Add your name here, for example:
# (add "\n" as separator if there is many translators)
-# msgid "Translators"
+# msgid "translator-credits"
# msgstr "Me"
# or, with mail:
-# msgid "Translators"
+# msgid "translator-credits"
# msgstr "Me"
# or, with page:
-# msgid "Translators"
+# msgid "translator-credits"
# msgstr "Me"
# else keep it empty.
# It will be displayed in about page
-msgid "Translators"
+msgid "translator-credits"
msgstr ""
#: extension.js
@@ -108,6 +108,12 @@ msgstr ""
msgid "Color"
msgstr ""
+msgid "Open drawing"
+msgstr ""
+
+msgid "Save drawing"
+msgstr ""
+
#: prefs.js
msgid "Preferences"
@@ -196,10 +202,20 @@ msgstr ""
msgid "Square drawing area"
msgstr ""
+msgid "Open previous drawing"
+msgstr ""
+
+msgid "Open next drawing"
+msgstr ""
+
+# already in draw.js
+#msgid "Save drawing"
+#msgstr ""
+
msgid "Save drawing as a SVG file"
msgstr ""
-msgid "Open stylesheet.css"
+msgid "Edit style"
msgstr ""
msgid "Show help"
@@ -246,6 +262,12 @@ msgstr ""
msgid "Shift key held"
msgstr ""
+msgid "Ignore pointer movement"
+msgstr ""
+
+msgid "Space key held"
+msgstr ""
+
msgid "Leave"
msgstr ""
@@ -269,18 +291,18 @@ msgstr ""
msgid "Global"
msgstr ""
-msgid "Drawing on the desktop"
-msgstr ""
-
-msgid "Draw On Your Screen becomes Draw On Your Desktop"
-msgstr ""
-
msgid "Persistent"
msgstr ""
msgid "Persistent drawing through session restart"
msgstr ""
+msgid "Drawing on the desktop"
+msgstr ""
+
+msgid "Draw On Your Screen becomes Draw On Your Desktop"
+msgstr ""
+
msgid "Disable on-screen notifications"
msgstr ""
@@ -297,32 +319,24 @@ msgid ""
"By pressing Ctrl key during the drawing process, you can:\n"
" . rotate a rectangle or a text area\n"
" . extend and rotate an ellipse\n"
-" . curve a line (cubic Bezier curve)"
-msgstr ""
-
-msgid "Smooth stroke during the drawing process"
+" . curve a line (cubic Bezier curve)\n"
+" . smooth a free drawing stroke (you may prefer to smooth the stroke afterward, see “%s”)"
msgstr ""
msgid ""
-"You can also smooth the stroke afterward\n"
-"See “%s”"
-msgstr ""
-
-msgid "Change the style"
-msgstr ""
-
-msgid "See stylesheet.css"
+"Default drawing style attributes (color palette, font, line, dash) are defined in an editable css file.\n"
+"See “%s”."
msgstr ""
msgid ""
-"Note: When you save elements made with eraser in a SVG file,\n"
+"Note: When you save elements made with eraser in a SVG file, "
"they are colored with background color, transparent if it is disabled.\n"
-"(See “%s” or edit the SVG file afterwards)"
+"See “%s” or edit the SVG file afterwards."
msgstr ""
# The following words refer to SVG attributes.
-# You have the choice to translate or not
+# You are free to translate them or not.
#msgid "Butt"
#msgstr ""
diff --git a/locale/it_IT/LC_MESSAGES/draw-on-your-screen.mo b/locale/it_IT/LC_MESSAGES/draw-on-your-screen.mo
new file mode 100644
index 0000000..feda332
Binary files /dev/null and b/locale/it_IT/LC_MESSAGES/draw-on-your-screen.mo differ
diff --git a/locale/it_IT/LC_MESSAGES/draw-on-your-screen.po b/locale/it_IT/LC_MESSAGES/draw-on-your-screen.po
new file mode 100644
index 0000000..7fc7c82
--- /dev/null
+++ b/locale/it_IT/LC_MESSAGES/draw-on-your-screen.po
@@ -0,0 +1,325 @@
+# Copyright (C) 2019 Listed translators
+#
+# This file is distributed under the same license as Draw On Your Screen.
+# FIRST AUTHOR , YEAR.
+#
+msgid ""
+msgstr ""
+"Project-Id-Version: Draw On Your Screen VERSION\n"
+"Report-Msgid-Bugs-To: https://framagit.org/abakkk/DrawOnYourScreen/issues\n"
+"POT-Creation-Date: 2019-06-15 08:47+0200\n"
+"PO-Revision-Date: 2019-06-15 09:52+0200\n"
+"Language-Team: \n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Generator: Poedit 1.8.7.1\n"
+"Last-Translator: albano battistella \n"
+"Plural-Forms: nplurals=2; plural=(n != 1);\n"
+"Language: it_IT\n"
+
+# add your name here, for example:
+# "Albano Battistella\n"
+# "Ali\n"
+# "丽"
+# It will be displayed in About page
+msgid "Translators"
+msgstr "Albano Battistella"
+
+#: extension.js
+msgid "Leaving drawing mode"
+msgstr "Lascia la modalità di disegno"
+
+msgid "Press Ctrl + F1 for help"
+msgstr "Premi Ctrl + F1 per aiuto"
+
+msgid "Entering drawing mode"
+msgstr "Entra in modalità disegno"
+
+#: draw.js
+msgid "Free drawing"
+msgstr "Disegno libero"
+
+msgid "Line"
+msgstr "Linea"
+
+msgid "Ellipse"
+msgstr "Ellisse"
+
+msgid "Rectangle"
+msgstr "Rettangolo"
+
+msgid "Text"
+msgstr "Testo"
+
+msgid "Fill"
+msgstr "Riempi"
+
+msgid "Stroke"
+msgstr "Tratto"
+
+msgid "Dashed line"
+msgstr "Linea tratteggiata"
+
+msgid "Full line"
+msgstr "Linea piena"
+
+msgid ""
+"Type your text\n"
+"and press Enter"
+msgstr ""
+"Digita il tuo testo\n"
+"e premere Invio"
+
+msgid "Screenshot"
+msgstr "Screenshot"
+
+msgid "Screenshot to clipboard"
+msgstr "Screenshot negli appunti"
+
+msgid "Area screenshot"
+msgstr "Area screenshot"
+
+msgid "Area screenshot to clipboard"
+msgstr "Area screenshot negli appunti"
+
+msgid "System"
+msgstr "Sistema"
+
+msgid "Undo"
+msgstr "Annulla"
+
+msgid "Redo"
+msgstr "Ripeti"
+
+msgid "Erase"
+msgstr "Cancella"
+
+msgid "Smooth"
+msgstr "Liscio"
+
+msgid "Dashed"
+msgstr "tratteggiato"
+
+msgid "Color"
+msgstr "Colore"
+
+#: prefs.js
+msgid "Preferences"
+msgstr "Preferenze"
+
+msgid "About"
+msgstr "Informazioni su"
+
+# GLOBAL_KEYBINDINGS
+msgid "Enter/leave drawing mode"
+msgstr "Entra/esci dalla modalità disegno"
+
+msgid "Erase all drawings"
+msgstr "Cancella tutti i disegni"
+
+# INTERNAL_KEYBINDINGS
+msgid "Undo last brushstroke"
+msgstr "Annulla l'ultima pennellata"
+
+msgid "Redo last brushstroke"
+msgstr "Ripeti l'ultima pennellata"
+
+msgid "Erase last brushstroke"
+msgstr "Cancella l'ultima pennellata"
+
+msgid "Smooth last brushstroke"
+msgstr "Liscia l'ultima pennellata"
+
+msgid "Select line"
+msgstr "Seleziona la linea"
+
+msgid "Select ellipse"
+msgstr "Seleziona l'ellisse"
+
+msgid "Select rectangle"
+msgstr "Seleziona il rettangolo"
+
+msgid "Select text"
+msgstr "Seleziona il testo"
+
+msgid "Unselect shape (free drawing)"
+msgstr "Deseleziona forma (disegno libero)"
+
+msgid "Toggle fill/stroke"
+msgstr "Attiva / disattiva riempimento / tratto"
+
+msgid "Increment line width"
+msgstr "Incrementa la larghezza della linea"
+
+msgid "Decrement line width"
+msgstr "Decrementa la larghezza della linea"
+
+msgid "Increment line width even more"
+msgstr "Aumentare la larghezza della linea ancora di più"
+
+msgid "Decrement line width even more"
+msgstr "Decrementa la larghezza della linea ancora di più"
+
+msgid "Change linejoin"
+msgstr "Cambia linejoin"
+
+msgid "Change linecap"
+msgstr "Cambia il limite di riga"
+
+# already in draw.js
+# msgid "Dashed line"
+# msgstr ""
+msgid "Change font family (generic name)"
+msgstr "Cambia la famiglia del font (nome generico)"
+
+msgid "Change font weight"
+msgstr "Cambiare spessore del font"
+
+msgid "Change font style"
+msgstr "Cambia stile del font"
+
+msgid "Hide panel and dock"
+msgstr "Nascondi pannello e dock"
+
+msgid "Add a drawing background"
+msgstr "Aggiungi uno sfondo di disegno"
+
+msgid "Square drawing area"
+msgstr "Area di disegno quadrata"
+
+msgid "Save drawing as a SVG file"
+msgstr "Salva disegno come file SVG"
+
+msgid "Open stylesheet.css"
+msgstr "Apri stylesheet.css"
+
+msgid "Show help"
+msgstr "Mostra aiuto"
+
+# OTHER_SHORTCUTS
+msgid "Draw"
+msgstr "Disegna"
+
+msgid "Left click"
+msgstr "Clic sinistro"
+
+msgid "Menu"
+msgstr "Menu"
+
+msgid "Right click"
+msgstr "Clic destro"
+
+msgid "Center click"
+msgstr "clic centro"
+
+msgid "Transform shape (when drawing)"
+msgstr "Trasforma la forma (quando si disegna)"
+
+msgid "Ctrl key"
+msgstr "Tasto Ctrl"
+
+msgid "Increment/decrement line width"
+msgstr "Incrementa/decrementa larghezza della linea"
+
+msgid "Scroll"
+msgstr "Scorri"
+
+msgid "Select color"
+msgstr "Seleziona colore"
+
+msgid "Ctrl+1...9"
+msgstr "Ctrl+1...9"
+
+msgid "Select eraser"
+msgstr "Seleziona gomma"
+
+msgid "Shift key held"
+msgstr "Tasto MAIUSC premuto"
+
+msgid "Leave"
+msgstr "Lascia"
+
+msgid "Escape key"
+msgstr "tasto Esc"
+
+# About page
+# you are free to translate the extension name
+# msgid "Draw On You Screen"
+# msgstr ""
+msgid "Version %d"
+msgstr "Versione %d"
+
+msgid ""
+"Start drawing with Super+Alt+D and save your beautiful work by taking a "
+"screenshot"
+msgstr ""
+"Inizia a disegnare con Super + Alt + D e salva il tuo bellissimo lavoro "
+"scattando uno screenshot"
+
+# Prefs page
+msgid "Global"
+msgstr "Globale"
+
+msgid "Drawing on the desktop"
+msgstr "Disegno sul desktop"
+
+msgid "Draw On Your Screen becomes Draw On Your Desktop"
+msgstr "Draw On Your Screen diventa Draw On Your Desktop"
+
+msgid "Persistent"
+msgstr "Persistente"
+
+msgid "Persistent drawing through session restart"
+msgstr "Disegno persistente attraverso il riavvio della sessione"
+
+msgid "Disable on-screen notifications"
+msgstr "Disabilita le notifiche sullo schermo"
+
+msgid "Disable panel indicator"
+msgstr "Disabilita indicatore del pannello"
+
+msgid "Internal"
+msgstr "Interno"
+
+msgid "(in drawing mode)"
+msgstr "(in modalità disegno)"
+
+msgid ""
+"By pressing Ctrl key during the drawing process, you can:\n"
+" . rotate a rectangle or a text area\n"
+" . extend and rotate an ellipse\n"
+" . curve a line (cubic Bezier curve)"
+msgstr ""
+"Premendo il tasto Ctrl b> durante b> del processo di disegno, "
+"puoi:\n"
+" . ruotare un rettangolo o un'area di testo\n"
+" . estendere e ruotare un'ellisse\n"
+" . curvare una linea (curva Bezier cubica)"
+
+msgid "Smooth stroke during the drawing process"
+msgstr "Colpo liscio durante il processo di disegno"
+
+msgid ""
+"You can also smooth the stroke afterward\n"
+"See “%s”"
+msgstr ""
+"Puoi anche lisciare il tratto in seguito\n"
+"Vedi \"% s\""
+
+msgid "Change the style"
+msgstr "Cambia lo stile"
+
+msgid "See stylesheet.css"
+msgstr "Vedi stylesheet.css"
+
+msgid ""
+"Note: When you save elements made with eraser in a SVG "
+"file,\n"
+"they are colored with background color, transparent if it is disabled.\n"
+"(See “%s” or edit the SVG file afterwards)"
+msgstr ""
+" Nota u>: quando salvi gli elementi creati con gomma da "
+"cancellare b> in un file SVG b>,\n"
+"questi sono colorati con il colore di sfondo, trasparente se disabilitati.\n"
+"(Vedi \"% s\" o modifica il file SVG in seguito)"
diff --git a/metadata.json b/metadata.json
index b612103..fe0a0cd 100644
--- a/metadata.json
+++ b/metadata.json
@@ -5,6 +5,9 @@
"url": "https://framagit.org/abakkk/DrawOnYourScreen",
"settings-schema": "org.gnome.shell.extensions.draw-on-your-screen",
"gettext-domain": "draw-on-your-screen",
+ "data-dir": "drawOnYourScreen",
+ "persistent-file-name": "persistent",
+ "svg-file-name": "DrawOnYourScreen",
"shell-version": [
"3.24",
"3.26",
@@ -13,5 +16,5 @@
"3.32",
"3.34"
],
- "version": 5
+ "version": 5.1
}
diff --git a/prefs.js b/prefs.js
index e35e294..3971165 100644
--- a/prefs.js
+++ b/prefs.js
@@ -3,7 +3,7 @@
/*
* Copyright 2019 Abakkk
*
- * This file is part of DrowOnYourScreen, a drawing extension for GNOME Shell.
+ * This file is part of DrawOnYourScreen, a drawing extension for GNOME Shell.
* https://framagit.org/abakkk/DrawOnYourScreen
*
* This program is free software: you can redistribute it and/or modify
@@ -26,10 +26,9 @@ const Lang = imports.lang;
const Mainloop = imports.mainloop;
const ExtensionUtils = imports.misc.extensionUtils;
-const Extension = ExtensionUtils.getCurrentExtension();
-const Convenience = Extension.imports.convenience;
-const Metadata = Extension.metadata;
-const _ = imports.gettext.domain(Extension.metadata["gettext-domain"]).gettext;
+const Me = ExtensionUtils.getCurrentExtension();
+const Convenience = ExtensionUtils.getSettings && ExtensionUtils.initTranslations ? ExtensionUtils : Me.imports.convenience;
+const _ = imports.gettext.domain(Me.metadata['gettext-domain']).gettext;
const _GTK = imports.gettext.domain('gtk30').gettext;
const MARGIN = 10;
@@ -68,8 +67,11 @@ var INTERNAL_KEYBINDINGS = {
'toggle-background': "Add a drawing background",
'toggle-square-area': "Square drawing area",
'-separator-5': '',
+ 'open-previous-json': "Open previous drawing",
+ 'open-next-json': "Open next drawing",
+ 'save-as-json': "Save drawing",
'save-as-svg': "Save drawing as a SVG file",
- 'open-stylesheet': "Open stylesheet.css",
+ 'open-user-stylesheet': "Edit style",
'toggle-help': "Show help"
};
@@ -81,6 +83,7 @@ var OTHER_SHORTCUTS = [
{ desc: "Increment/decrement line width", shortcut: "Scroll" },
{ desc: "Select color", shortcut: "Ctrl+1...9" },
{ desc: "Select eraser", shortcut: "Shift key held" },
+ { desc: "Ignore pointer movement", shortcut: "Space key held" },
{ desc: "Leave", shortcut: "Escape key" }
];
@@ -103,7 +106,7 @@ function buildPrefsWidget() {
return topStack;
}
-var TopStack = new GObject.Class({
+const TopStack = new GObject.Class({
Name: 'DrawOnYourScreenTopStack',
GTypeName: 'DrawOnYourScreenTopStack',
Extends: Gtk.Stack,
@@ -117,7 +120,7 @@ var TopStack = new GObject.Class({
}
});
-var AboutPage = new GObject.Class({
+const AboutPage = new GObject.Class({
Name: 'DrawOnYourScreenAboutPage',
GTypeName: 'DrawOnYourScreenAboutPage',
Extends: Gtk.ScrolledWindow,
@@ -128,10 +131,10 @@ var AboutPage = new GObject.Class({
let vbox= new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL, margin: MARGIN*3 });
this.add(vbox);
- let name = " " + _(Metadata.name) + "";
- let version = _("Version %d").format(Metadata.version);
- let description = _(Metadata.description);
- let link = "" + Metadata.url + "";
+ let name = " " + _(Me.metadata.name) + "";
+ let version = _("Version %d").format(Me.metadata.version);
+ let description = _(Me.metadata.description);
+ let link = "" + Me.metadata.url + "";
let licenceName = _GTK("GNU General Public License, version 2 or later");
let licenceLink = "https://www.gnu.org/licenses/old-licenses/gpl-2.0.html";
let licence = "" + _GTK("This program comes with absolutely no warranty.\nSee the %s for details.").format(licenceLink, licenceName) + "";
@@ -152,11 +155,11 @@ var AboutPage = new GObject.Class({
creditBox.pack_start(rightBox, true, true, 5);
vbox.add(creditBox);
- if (_("Translators") != "Translators" && _("Translators") != "") {
+ if (_("translator-credits") != "translator-credits" && _("translator-credits") != "") {
leftBox.pack_start(new Gtk.Label(), false, false, 0);
rightBox.pack_start(new Gtk.Label(), false, false, 0);
leftLabel = new Gtk.Label({ wrap: true, valign: 1, halign: 2, justify: 1, use_markup: true, label: "" + _GTK("Translated by") + "" });
- rightLabel = new Gtk.Label({ wrap: true, valign: 1, halign: 1, justify: 0, use_markup: true, label: "" + _("Translators") + "" });
+ rightLabel = new Gtk.Label({ wrap: true, valign: 1, halign: 1, justify: 0, use_markup: true, label: "" + _("translator-credits") + "" });
leftBox.pack_start(leftLabel, false, false, 0);
rightBox.pack_start(rightLabel, false, false, 0);
}
@@ -164,7 +167,7 @@ var AboutPage = new GObject.Class({
});
-var PrefsPage = new GObject.Class({
+const PrefsPage = new GObject.Class({
Name: 'DrawOnYourScreenPrefsPage',
GTypeName: 'DrawOnYourScreenPrefsPage',
Extends: Gtk.ScrolledWindow,
@@ -174,83 +177,88 @@ var PrefsPage = new GObject.Class({
this.settings = Convenience.getSettings();
- let box = new Gtk.Box({orientation: Gtk.Orientation.VERTICAL, margin: MARGIN*3 });
+ let box = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL, margin: MARGIN*3 });
this.add(box);
- let listBox = new Gtk.ListBox({ selection_mode: 0, hexpand: true });
- box.add(listBox);
+ let globalFrame = new Gtk.Frame({ label_yalign: 1.0 });
+ globalFrame.set_label_widget(new Gtk.Label({ margin_bottom: MARGIN/2, use_markup: true, label: "" + _("Global") + "" }));
+ box.add(globalFrame);
+
+ let listBox = new Gtk.ListBox({ selection_mode: 0, hexpand: true, margin_top: MARGIN/2, margin_bottom: MARGIN/2 });
+ globalFrame.add(listBox);
let styleContext = listBox.get_style_context();
styleContext.add_class('background');
- let globalTitleBox = new Gtk.Box({ margin: MARGIN });
- let globalTitleLabel = new Gtk.Label({ use_markup: true, label: "" + _("Global") + " :" });
- globalTitleLabel.set_halign(1);
- globalTitleBox.pack_start(globalTitleLabel, true, true, 4);
- listBox.add(globalTitleBox);
-
let globalKeybindingsWidget = new KeybindingsWidget(GLOBAL_KEYBINDINGS, this.settings);
globalKeybindingsWidget.margin = MARGIN;
listBox.add(globalKeybindingsWidget);
- let desktopBox = new Gtk.Box({ margin: MARGIN });
- let desktopLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
- let desktopLabel1 = new Gtk.Label({label: _("Drawing on the desktop")});
- let desktopLabel2 = new Gtk.Label({ use_markup: true, halign: 1, label: "" + _("Draw On Your Screen becomes Draw On Your Desktop") + "" });
- desktopLabel1.set_halign(1);
- desktopLabel2.get_style_context().add_class("dim-label");
- desktopLabelBox.pack_start(desktopLabel1, true, true, 0);
- desktopLabelBox.pack_start(desktopLabel2, true, true, 0);
- let desktopSwitch = new Gtk.Switch({valign: 3});
- this.settings.bind("drawing-on-desktop", desktopSwitch, "active", 0);
- desktopBox.pack_start(desktopLabelBox, true, true, 4);
- desktopBox.pack_start(desktopSwitch, false, false, 4);
- listBox.add(desktopBox);
-
- let persistentBox = new Gtk.Box({ margin: MARGIN });
+ let persistentBox = new Gtk.Box({ margin_top: MARGIN/2, margin_bottom: MARGIN/2, margin_left: MARGIN, margin_right: MARGIN });
let persistentLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
let persistentLabel1 = new Gtk.Label({label: _("Persistent")});
- let persistentLabel2 = new Gtk.Label({ use_markup: true, halign: 1, label: "" + _("Persistent drawing through session restart") + "" });
+ let persistentLabel2 = new Gtk.Label({ use_markup: true, halign: 1, wrap: true, xalign: 0, label: "" + _("Persistent drawing through session restart") + "" });
persistentLabel1.set_halign(1);
- persistentLabel2.get_style_context().add_class("dim-label");
+ persistentLabel2.get_style_context().add_class('dim-label');
persistentLabelBox.pack_start(persistentLabel1, true, true, 0);
persistentLabelBox.pack_start(persistentLabel2, true, true, 0);
let persistentSwitch = new Gtk.Switch({valign: 3});
- this.settings.bind("persistent-drawing", persistentSwitch, "active", 0);
+ this.settings.bind('persistent-drawing', persistentSwitch, 'active', 0);
persistentBox.pack_start(persistentLabelBox, true, true, 4);
persistentBox.pack_start(persistentSwitch, false, false, 4);
listBox.add(persistentBox);
- let osdBox = new Gtk.Box({ margin: MARGIN });
+ let desktopBox = new Gtk.Box({ margin_top: MARGIN/2, margin_bottom: MARGIN/2, margin_left: MARGIN, margin_right: MARGIN });
+ let desktopLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
+ let desktopLabel1 = new Gtk.Label({label: _("Drawing on the desktop")});
+ let desktopLabel2 = new Gtk.Label({ use_markup: true, halign: 1, wrap: true, xalign: 0, label: "" + _("Draw On Your Screen becomes Draw On Your Desktop") + "" });
+ desktopLabel1.set_halign(1);
+ desktopLabel2.get_style_context().add_class('dim-label');
+ desktopLabelBox.pack_start(desktopLabel1, true, true, 0);
+ desktopLabelBox.pack_start(desktopLabel2, true, true, 0);
+ let desktopSwitch = new Gtk.Switch({valign: 3});
+ this.settings.bind('drawing-on-desktop', desktopSwitch, 'active', 0);
+ desktopBox.pack_start(desktopLabelBox, true, true, 4);
+ desktopBox.pack_start(desktopSwitch, false, false, 4);
+ listBox.add(desktopBox);
+
+ let osdBox = new Gtk.Box({ margin_top: MARGIN/2, margin_bottom: MARGIN/2, margin_left: MARGIN, margin_right: MARGIN });
let osdLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
let osdLabel1 = new Gtk.Label({label: _("Disable on-screen notifications")});
osdLabel1.set_halign(1);
osdLabelBox.pack_start(osdLabel1, true, true, 0);
let osdSwitch = new Gtk.Switch({valign: 3});
- this.settings.bind("osd-disabled", osdSwitch, "active", 0);
+ this.settings.bind('osd-disabled', osdSwitch, 'active', 0);
osdBox.pack_start(osdLabelBox, true, true, 4);
osdBox.pack_start(osdSwitch, false, false, 4);
listBox.add(osdBox);
- let indicatorBox = new Gtk.Box({ margin: MARGIN });
+ let indicatorBox = new Gtk.Box({ margin_top: MARGIN/2, margin_bottom: MARGIN/2, margin_left: MARGIN, margin_right: MARGIN });
let indicatorLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
let indicatorLabel1 = new Gtk.Label({label: _("Disable panel indicator")});
indicatorLabel1.set_halign(1);
indicatorLabelBox.pack_start(indicatorLabel1, true, true, 0);
let indicatorSwitch = new Gtk.Switch({valign: 3});
- this.settings.bind("indicator-disabled", indicatorSwitch, "active", 0);
+ this.settings.bind('indicator-disabled', indicatorSwitch, 'active', 0);
indicatorBox.pack_start(indicatorLabelBox, true, true, 4);
indicatorBox.pack_start(indicatorSwitch, false, false, 4);
listBox.add(indicatorBox);
- this.addSeparator(listBox);
- let internalTitleBox = new Gtk.Box({ margin: MARGIN });
- let internalTitleLabel = new Gtk.Label({ use_markup: true, label: "" + _("Internal") + " " + _("(in drawing mode)") + " :" });
- internalTitleLabel.set_halign(1);
- internalTitleBox.pack_start(internalTitleLabel, true, true, 4);
- listBox.add(internalTitleBox);
+ let children = listBox.get_children();
+ for (let i = 0; i < children.length; i++) {
+ if (children[i].activatable)
+ children[i].set_activatable(false);
+ }
- listBox.add(new Gtk.Box({ margin_top: MARGIN/2, margin_left: MARGIN, margin_right: MARGIN }));
+ let internalFrame = new Gtk.Frame({ margin_top: 3*MARGIN, label_yalign: 1.0 });
+ internalFrame.set_label_widget(new Gtk.Label({ margin_bottom: MARGIN/2, use_markup: true, label: "" + _("Internal") + " " + _("(in drawing mode)") }));
+ box.add(internalFrame);
+
+ listBox = new Gtk.ListBox({ selection_mode: 0, hexpand: true, margin_top: MARGIN });
+ internalFrame.add(listBox);
+
+ styleContext = listBox.get_style_context();
+ styleContext.add_class('background');
for (let i = 0; i < OTHER_SHORTCUTS.length; i++) {
if (OTHER_SHORTCUTS[i].desc.indexOf('-separator-') != -1) {
@@ -266,70 +274,63 @@ var PrefsPage = new GObject.Class({
listBox.add(otherBox);
}
- listBox.add(new Gtk.Box({ margin_top: MARGIN, margin_left: MARGIN, margin_right: MARGIN }));
-
- let controlBox = new Gtk.Box({ margin_top: MARGIN, margin_left: MARGIN, margin_right: MARGIN, margin_bottom:MARGIN });
+ let controlBox = new Gtk.Box({ margin: MARGIN, margin_top: 2*MARGIN });
let controlLabel = new Gtk.Label({
+ wrap: true,
+ xalign: 0,
use_markup: true,
- label: _("By pressing Ctrl key during the drawing process, you can:\n . rotate a rectangle or a text area\n . extend and rotate an ellipse\n . curve a line (cubic Bezier curve)")
+ label: _("By pressing Ctrl key during the drawing process, you can:\n" +
+ " . rotate a rectangle or a text area\n" +
+ " . extend and rotate an ellipse\n" +
+ " . curve a line (cubic Bezier curve)\n" +
+ " . smooth a free drawing stroke (you may prefer to smooth the stroke afterward, see “%s”)").format(_("Smooth last brushstroke"))
});
controlLabel.set_halign(1);
- controlLabel.get_style_context().add_class("dim-label");
+ controlLabel.get_style_context().add_class('dim-label');
controlBox.pack_start(controlLabel, true, true, 4);
listBox.add(controlBox);
- let smoothBox = new Gtk.Box({ margin: MARGIN });
- let smoothLabelBox = new Gtk.Box({ orientation: Gtk.Orientation.VERTICAL });
- let smoothLabel1 = new Gtk.Label({label: _("Smooth stroke during the drawing process")});
- let smoothLabel2 = new Gtk.Label({ use_markup: true, halign: 1, label: "" + _("You can also smooth the stroke afterward\nSee “%s”").format(_("Smooth last brushstroke")) + "" });
- smoothLabel1.set_halign(1);
- smoothLabel2.get_style_context().add_class("dim-label");
- smoothLabelBox.pack_start(smoothLabel1, true, true, 0);
- smoothLabelBox.pack_start(smoothLabel2, true, true, 0);
- let smoothSwitch = new Gtk.Switch({valign: 3});
- this.settings.bind("smoothed-stroke", smoothSwitch, "active", 0);
- smoothBox.pack_start(smoothLabelBox, true, true, 4);
- smoothBox.pack_start(smoothSwitch, false, false, 4);
- listBox.add(smoothBox);
-
let internalKeybindingsWidget = new KeybindingsWidget(INTERNAL_KEYBINDINGS, this.settings);
internalKeybindingsWidget.margin = MARGIN;
listBox.add(internalKeybindingsWidget);
- let styleBox = new Gtk.Box({ margin_top: MARGIN, margin_left: MARGIN, margin_right: MARGIN, margin_bottom:MARGIN });
- let styleLabel = new Gtk.Label({ label: _("Change the style") });
+ let styleBox = new Gtk.Box({ margin: MARGIN });
+ let styleLabel = new Gtk.Label({
+ wrap: true,
+ xalign: 0,
+ use_markup: true,
+ label: _("Default drawing style attributes (color palette, font, line, dash) are defined in an editable css file.\n" +
+ "See “%s”.").format(_("Edit style"))
+ });
styleLabel.set_halign(1);
- let styleLabel2 = new Gtk.Label({ label: _("See stylesheet.css") });
+ styleLabel.get_style_context().add_class('dim-label');
styleBox.pack_start(styleLabel, true, true, 4);
- styleBox.pack_start(styleLabel2, false, false, 4);
listBox.add(styleBox);
- let noteBox = new Gtk.Box({ margin_top: MARGIN, margin_left: MARGIN, margin_right: MARGIN, margin_bottom:MARGIN });
+ let noteBox = new Gtk.Box({ margin: MARGIN });
let noteLabel = new Gtk.Label({
+ wrap: true,
+ xalign: 0,
use_markup: true,
- label: _("Note: When you save elements made with eraser in a SVG file,\nthey are colored with background color, transparent if it is disabled.\n(See “%s” or edit the SVG file afterwards)").format(_("Add a drawing background"))
+ label: _("Note: When you save elements made with eraser in a SVG file, " +
+ "they are colored with background color, transparent if it is disabled.\n" +
+ "See “%s” or edit the SVG file afterwards.").format(_("Add a drawing background"))
});
noteLabel.set_halign(1);
- noteLabel.get_style_context().add_class("dim-label");
+ noteLabel.get_style_context().add_class('dim-label');
noteBox.pack_start(noteLabel, true, true, 4);
listBox.add(noteBox);
- let children = listBox.get_children();
+ children = listBox.get_children();
for (let i = 0; i < children.length; i++) {
if (children[i].activatable)
children[i].set_activatable(false);
}
- },
-
- addSeparator: function(container) {
- let separatorRow = new Gtk.ListBoxRow({sensitive: false});
- separatorRow.add(new Gtk.Separator({ margin: MARGIN }));
- container.add(separatorRow);
}
});
// this code comes from Sticky Notes View by Sam Bull, https://extensions.gnome.org/extension/568/notes/
-var KeybindingsWidget = new GObject.Class({
+const KeybindingsWidget = new GObject.Class({
Name: 'DrawOnYourScreenKeybindings.Widget',
GTypeName: 'DrawOnYourScreenKeybindingsWidget',
Extends: Gtk.Box,
diff --git a/schemas/gschemas.compiled b/schemas/gschemas.compiled
index 329554d..eebc890 100644
Binary files a/schemas/gschemas.compiled and b/schemas/gschemas.compiled differ
diff --git a/schemas/org.gnome.shell.extensions.draw-on-your-screen.gschema.xml b/schemas/org.gnome.shell.extensions.draw-on-your-screen.gschema.xml
index 9864222..8890675 100644
--- a/schemas/org.gnome.shell.extensions.draw-on-your-screen.gschema.xml
+++ b/schemas/org.gnome.shell.extensions.draw-on-your-screen.gschema.xml
@@ -1,11 +1,6 @@
-
- false
- smoothed stroke
- smoothed stroke
-
false
move drawing on desktop
@@ -107,12 +102,12 @@
decrement the line width
- ["<Primary>Page_Up"]
+ ["<Primary><Shift>KP_Add"]
increment the line width even more
increment the line width even more
- ["<Primary>Page_Down"]
+ ["<Primary><Shift>KP_Subtract"]
decrement the line width even more
decrement the line width even more
@@ -196,16 +191,31 @@
toggle font style
toggle font style
-
+
["<Primary>o"]
- open stylesheet
- open stylesheet
+ open user stylesheet to edit style
+ open user stylesheet to edit style
- ["<Primary>s"]
+ ["<Primary><Shift>s"]
Save drawing as a svg file
Save drawing as a svg file
+
+ ["<Primary>s"]
+ Save drawing as a json file
+ Save drawing as a json file
+
+
+ ["<Primary>Page_Down"]
+ Open previous json file
+ Open previous json file
+
+
+ ["<Primary>Page_Up"]
+ Open next json file
+ Open next json file
+
["<Primary>F1"]
toggle help
diff --git a/stylesheet.css b/stylesheet.css
index 862879a..bd02a07 100644
--- a/stylesheet.css
+++ b/stylesheet.css
@@ -1,50 +1,6 @@
-/*
- * Except for the font,
- * you don't need to restart the extension.
- * Just save this file and the changes will be applied for your next brushstroke.
- *
- * line-join (no string):
- * 0 : miter, 1 : round, 2 : bevel
- * line-cap (no string):
- * 0 : butt, 1 : round, 2 : square
- *
- * dash:
- * dash-array-on is the length of dashes (no dashes if 0, you can put 0.1 to get dots or square according to line-cap)
- * dash-array-off is the length of gaps (no dashes if 0)
- *
- * font:
- * only one family : no comma separated list of families like "font1, font2, ..., Sans-Serif"
- * font family can be any font installed, or a generic family name (Serif, Sans-Serif, Monospace, Cursive, Fantasy)
- * font weight and font style : no upper case when string
- * weight <= 500 (or lighter, normal, medium) is rendered as normal
- * weight > 500 (or bolder, bold) is rendered as bold
- * oblique and italic style support depends on the font family and seem to be rendered identically
- *
- */
+@import "./data/default.css";
-.draw-on-your-screen {
- -drawing-line-width: 5px;
- -drawing-line-join: 1;
- -drawing-line-cap: 1;
- -drawing-dash-array-on: 5px;
- -drawing-dash-array-off: 15px;
- -drawing-dash-offset: 0px;
- -drawing-color1: HotPink;
- -drawing-color2: Cyan;
- -drawing-color3: yellow;
- -drawing-color4: Orangered;
- -drawing-color5: Chartreuse;
- -drawing-color6: DarkViolet;
- -drawing-color7: #ffffff;
- -drawing-color8: rgba(130, 130, 130, 0.3);
- -drawing-color9: rgb(0, 0, 0);
- -drawing-background-color: #2e3436; /* GS osd_bg_color: #2e3436, GTK Adwaita-dark theme_base_color: #2d2c2e */
- font-family: Cantarell;
- font-weight: normal;
- font-style: normal;
-}
-
-/*********************************************/
+/* The following styles don't affect the drawing */
/* square area */
@@ -56,8 +12,7 @@
outline: none;
}
-/* The following styles don't affect the drawing,
- * but the "Ctrl + F1" on-screen-display */
+ /* "Ctrl + F1" on-screen-display */
.draw-on-your-screen-helper {
margin: 0;
@@ -73,36 +28,71 @@
font-weight: normal;
}
-.draw-on-your-screen-separator {
+.draw-on-your-screen-helper-separator {
min-height: 0.6em;
}
/* context menu */
.draw-on-your-screen-menu {
- font-size: 0.98em; /* default: 1em */
+ font-size: 0.97em; /* default: 1em */
}
.draw-on-your-screen-menu .popup-menu-item {
- padding-top: .37em; /* default: .4em */
- padding-bottom: .37em;
+ padding-top: .3em; /* default: .4em */
+ padding-bottom: .3em;
}
.draw-on-your-screen-menu .popup-menu-icon {
- icon-size: 1.04em; /* default: 1.09 */
+ icon-size: 1em; /* default: 1.09 */
+ padding-top: 0.03em;
}
.draw-on-your-screen-menu .toggle-switch {
- height: 20px; /* default: 22px */
-}
+ height: 1.35em; /* default: 22px */
+}
-.draw-on-your-screen-menu-separator StLabel {
+.draw-on-your-screen-menu-separator-item {
+ padding-top: 0.14em;
+ padding-bottom: 0.14em;
+}
+
+.draw-on-your-screen-menu-separator-item StLabel {
font-size: 0;
}
+.draw-on-your-screen-menu-separator-item .popup-separator-menu-item {
+ margin-top: 0.2em; /* default 6px */
+ margin-bottom: 0.2em; /* default 6px */
+}
+
.draw-on-your-screen-menu-slider-label {
min-width: 3em;
text-align: right;
}
+
+.draw-on-your-screen-menu-entry-item {
+ padding-right: 1.15em; /* default 1.75em */
+ spacing: 0; /* default 12px */
+}
+
+.draw-on-your-screen-menu-entry {
+ border: none;
+ border-radius: 3px;
+ padding: 0.35em 0.57em;
+ width: 10em;
+}
+
+.draw-on-your-screen-menu-entry-error {
+ color: #f57900; /* upstream warning_color */
+}
+
+.draw-on-your-screen-menu-entry:focus {
+ padding: 0.35em 0.57em;
+}
+
+.draw-on-your-screen-menu-delete-button:hover {
+ color: #f57900;
+}