Merge pull request #127 from goncalossilva/styles

Preview improvements
ft.font-size
somas95 2019-03-26 20:25:22 +01:00 committed by GitHub
commit fc0c68f41c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
29 changed files with 471 additions and 227 deletions

View File

@ -1,4 +0,0 @@
@define-color dark_bg #353535;
@define-color light_bg #F6F5F4;
@import url("style.css");

View File

@ -1,4 +0,0 @@
@define-color dark_bg #31373D;
@define-color light_bg #EDEDED;
@import url("style.css");

View File

@ -27,19 +27,8 @@
.uberwriter_window { .uberwriter_window {
-gtk-key-bindings: window-bindings; -gtk-key-bindings: window-bindings;
/*border-radius: 7px 7px 3px 3px;*/ /*border-radius: 7px 7px 3px 3px;*/
background: @light_bg; background: @background_color;
caret-color: @dark_bg; caret-color: @foreground_color;
}
.uberwriter_window.dark_mode {
background: @dark_bg;
caret-color: @light_bg;
}
.uberwriter_window.dark_mode .uberwriter-editor text{
background: @dark_bg;
caret-color: @light_bg;
color: @light_bg;
} }
.uberwriter_window.small .uberwriter-editor { .uberwriter_window.small .uberwriter-editor {
@ -47,12 +36,7 @@
font-size: 12px; font-size: 12px;
} }
.uberwriter_window grid { .uberwriter_window grid {
background-color: @light_bg; background-color: @background_color;
}
.uberwriter_window.dark_mode grid,
.uberwriter_window.dark_mode scrolledwindow {
background-color: @dark_bg;
} }
#UberwriterWindow.medium .uberwriter-editor { #UberwriterWindow.medium .uberwriter-editor {
@ -75,25 +59,22 @@
} }
#titlebar_container { #titlebar_container {
background: @light_bg; background: @background_color;
}
#titlebar_container.dark_mode {
background: @dark_bg;
} }
.uberwriter-editor { .uberwriter-editor {
border: none; border: none;
background-color: transparent; background-color: transparent;
color: #222; text-decoration-color: #ff0000;
/*-GtkWidget-cursor-color: shade(#4D9FCE, 0.9);*/ /*-GtkWidget-cursor-color: shade(#4D9FCE, 0.9);*/
/*-GtkWidget-cursor-aspect-ratio: 0.1;*/ /*-GtkWidget-cursor-aspect-ratio: 0.1;*/
-gtk-key-bindings: editor-bindings; -gtk-key-bindings: editor-bindings;
} }
.uberwriter-editor text { .uberwriter-editor text {
background-color: @light_bg; background-color: @background_color;
color: #222; color: @foreground_color;
caret-color: @foreground_color;
} }
.uberwriter-editor:selected { .uberwriter-editor:selected {
@ -120,7 +101,7 @@
.status_bar_box button { .status_bar_box button {
/* finding reset */ /* finding reset */
background-color: @light_bg; background-color: @background_color;
text-shadow: inherit; text-shadow: inherit;
/*icon-shadow: inherit;*/ /*icon-shadow: inherit;*/
box-shadow: initial; box-shadow: initial;
@ -146,13 +127,13 @@
.status_bar_box button:hover, .status_bar_box button:hover,
.status_bar_box button:checked { .status_bar_box button:checked {
transition: 0s ease-in; transition: 0s ease-in;
color: @light_bg; color: @background_color;
background-color: #666; background-color: #666;
} }
.status_bar_box button:hover label, .status_bar_box button:hover label,
.status_bar_box button:checked label { .status_bar_box button:checked label {
color: @light_bg; color: @background_color;
} }
.status_bar_box button:active { .status_bar_box button:active {
@ -161,22 +142,7 @@
background-image: none; background-image: none;
box-shadow: 0 0 2px rgba(0,0,0,0.4) box-shadow: 0 0 2px rgba(0,0,0,0.4)
} }
.dark_mode .status_bar_box button {
background-color: @dark_bg;
}
.dark_mode .status_bar_box label {
color: @light_bg;
}
.dark_mode .status_bar_box button:hover,
.dark_mode .status_bar_box button:checked {
background-color: @light_bg;
color: #666;
}
.dark_mode .status_bar_box button:hover label,
.dark_mode .status_bar_box button:checked label{
color: #666;
}
.status_bar_box separator { .status_bar_box separator {
border-color: #999; border-color: #999;
border-right: none; border-right: none;
@ -198,9 +164,9 @@
/*font: serif 10;*/ /*font: serif 10;*/
font-family: serif; font-family: serif;
font-size: 10px; font-size: 10px;
background: @light_bg; background: @background_color;
border-radius: 4px; border-radius: 4px;
border-color: @light_bg; border-color: @background_color;
margin: 5px; margin: 5px;
padding: 5px; padding: 5px;
} }
@ -211,7 +177,7 @@
border: 1px solid #333; border: 1px solid #333;
background: @ligth_bg; background: @ligth_bg;
border-radius: 3px; border-radius: 3px;
border-color: @light_bg; border-color: @background_color;
} */ } */
#LexikonBubble label { #LexikonBubble label {
@ -219,9 +185,8 @@
} }
#LexikonBubble { #LexikonBubble {
background-color: @light_bg; background-color: @background_color;
border: 5px solid @light_bg; border: 5px solid @background_color;
border-color: @light_bg
} }
#LexikonBubble .lexikon_heading { #LexikonBubble .lexikon_heading {
@ -240,15 +205,15 @@
} }
.QuickPreviewPopup { .QuickPreviewPopup {
background-color: @light_bg; background-color: @background_color;
} }
.QuickPreviewPopup grid { .QuickPreviewPopup grid {
background-color: @light_bg; background-color: @background_color;
color: @dark_bg; color: @foreground_color;
border-color: @light_bg; border-color: @background_color;
} }
.QuickPreviewPopup label { .QuickPreviewPopup label {
color: @dark_bg; color: @foreground_color;
} }

View File

@ -1,45 +1,60 @@
@font-face { @font-face {
font-family: fira-sans; font-family: fira-sans;
src: url('fonts/fira-sans-v9-greek_latin-ext_latin_cyrillic-ext_cyrillic_greek-ext_vietnamese-regular.woff2') format('woff2'); src: url("../fonts/fira-sans-v9-vietnamese_latin_cyrillic-ext_cyrillic_greek-ext_latin-ext_greek-regular.woff2") format("woff2");
} }
@font-face { @font-face {
font-family: fira-mono; font-family: fira-mono;
src: url('fonts/fira-mono-v7-greek_latin-ext_latin_cyrillic-ext_cyrillic_greek-ext-regular.woff2') format('woff2'); src: url("../fonts/fira-mono-v7-latin_cyrillic-ext_cyrillic_greek-ext_latin-ext_greek-regular.woff2") format("woff2");
} }
@font-face { @font-face {
font-family: "color-emoji"; font-family: color-emoji;
src: local("Noto Color Emoji"), local("Apple Color Emoji"), local("Segoe UI Emoji"), local("Segoe UI Symbol"); src: local("Noto Color Emoji"), local("Apple Color Emoji"), local("Segoe UI Emoji"), local("Segoe UI Symbol");
} }
:root { :root {
--text-color: #242424; /* This is GitHub's default color scheme, which should be overridden per theme. */
--background-color: #f6f5f4; --text-color: #24292e;
--alt-background-color: #ebebeb; --background-color: #ffffff;
--alt-background-color: #f6f8fa;
--link-color: #0366d6; --link-color: #0366d6;
--blockquote-text-color: #606060; --blockquote-text-color: #6a737d;
--blockquote-border-color: #d8d8d8; --blockquote-border-color: #dfe2e5;
--header-border-color: #e2e2e2; --header-border-color: #eaecef;
--hr-background-color: #dadada; --hr-background-color: #e1e4e8;
--hr-border-color: #e4e4e4; --table-tr-border-color: #c6cbd1;
--code-background-color: #eeeeee; --table-td-border-color: #dfe2e5;
--table-td-border-color: #d8d8d8; --kbd-text-color: #444d56;
--table-tr-border-color: #c1c1c1; --kbd-background-color: #fafbfc;
--kbd-text-color: #444444; --kbd-border-color: #c6cbd1;
--kbd-background-color: #f2f2f2; --kbd-shadow-color: #959da5;
--kbd-border-color: #c1c1c1;
--kbd-shadow-color: #939393;
} }
* { * {
box-sizing: border-box; box-sizing: border-box;
} }
html {
font-size: 16px;
}
@media screen and (max-width: 799px) {
html {
font-size: 14px;
}
}
@media screen and (min-width: 1000px) {
html {
font-size: 18px;
}
}
body { body {
color: var(--text-color); color: var(--text-color);
background-color: var(--background-color); background-color: var(--background-color);
font-family: fira-sans, sans-serif, color-emoji; font-family: "Fira Sans", fira-sans, sans-serif, color-emoji;
line-height: 1.5; line-height: 1.5;
text-size-adjust: 100%; text-size-adjust: 100%;
word-wrap: break-word; word-wrap: break-word;
@ -77,7 +92,6 @@ hr {
overflow: hidden; overflow: hidden;
background-color: var(--hr-background-color); background-color: var(--hr-background-color);
border: 0; border: 0;
border-bottom: 1px solid var(--hr-border-color);
} }
hr::before { hr::before {
@ -183,8 +197,7 @@ dd {
code, code,
kbd, kbd,
pre { pre {
font-family: fira-mono, monospace, color-emoji; font-family: "Fira Mono", fira-mono, monospace, color-emoji;
background-color: var(--code-background-color);
font-size: 1em; font-size: 1em;
word-wrap: normal; word-wrap: normal;
} }

View File

@ -0,0 +1,5 @@
@define-color foreground_color #2e3436;
@define-color background_color #f6f5f4;
@define-color math_text_color #00364c;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #eeeeec;
@define-color background_color #353535;
@define-color math_text_color #ffc9b3;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #3b3e45;
@define-color background_color #f5f6f7;
@define-color math_text_color #00364c;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #d3dae3;
@define-color background_color #383c4a;
@define-color math_text_color #ffc9b3;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #3b3e45;
@define-color background_color #f5f6f7;
@define-color math_text_color #00364C;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #000000;
@define-color background_color #ffffff;
@define-color math_text_color #000000;
@import url("_gtk_base.css");

View File

@ -0,0 +1,5 @@
@define-color foreground_color #ffffff;
@define-color background_color #000000;
@define-color math_text_color #ffffff;
@import url("_gtk_base.css");

View File

@ -0,0 +1,19 @@
@import url("_web_base.css");
:root {
--text-color: #2e3436;
--background-color: #f6f5f4;
--alt-background-color: #edeeef;
--link-color: #0d71de;
--blockquote-text-color: #747e85;
--blockquote-border-color: #d6d8da;
--header-border-color: #e1e2e4;
--hr-background-color: #d8dadd;
--table-tr-border-color: #bdc1c6;
--table-td-border-color: #d6d8da;
--kbd-text-color: #4e585e;
--kbd-background-color: #f1f1f1;
--kbd-border-color: #bdc1c6;
--kbd-shadow-color: #8c939a;
}

View File

@ -1,19 +1,17 @@
@import url("github-md.css"); @import url("_web_base.css");
:root { :root {
--text-color: #dbdbdb; --text-color: #eeeeec;
--background-color: #353535; --background-color: #353535;
--alt-background-color: #3a3a3a; --alt-background-color: #3a3a3a;
--link-color: #4388d6; --link-color: #b5daff;
--blockquote-text-color: #959595; --blockquote-text-color: #a8a8a6;
--blockquote-border-color: #525252; --blockquote-border-color: #525252;
--header-border-color: #474747; --header-border-color: #474747;
--hr-background-color: #505050; --hr-background-color: #505050;
--hr-border-color: #464646;
--code-background-color: #3e3e3e;
--table-td-border-color: #525252;
--table-tr-border-color: #696969; --table-tr-border-color: #696969;
--kbd-text-color: #bbbbbb; --table-td-border-color: #525252;
--kbd-text-color: #cececc;
--kbd-background-color: #3c3c3c; --kbd-background-color: #3c3c3c;
--kbd-border-color: #696969; --kbd-border-color: #696969;
--kbd-shadow-color: #979797; --kbd-shadow-color: #979797;

View File

@ -0,0 +1,18 @@
@import url("_web_base.css");
:root {
--text-color: #3b3e45;
--background-color: #f5f6f7;
--alt-background-color: #eceff2;
--link-color: #1a7bed;
--blockquote-text-color: #818894;
--blockquote-border-color: #d5d9dd;
--header-border-color: #e0e3e7;
--hr-background-color: #d7dbe0;
--table-tr-border-color: #bcc2c9;
--table-td-border-color: #d5d9dd;
--kbd-text-color: #5b626d;
--kbd-background-color: #f0f2f4;
--kbd-border-color: #bcc2c9;
--kbd-shadow-color: #8b949d;
}

View File

@ -0,0 +1,18 @@
@import url("_web_base.css");
:root {
--text-color: #d3dae3;
--background-color: #383c4a;
--alt-background-color: #3d414f;
--link-color: #9ac6ff;
--blockquote-text-color: #8d949d;
--blockquote-border-color: #555967;
--header-border-color: #4a4e5c;
--hr-background-color: #535765;
--table-tr-border-color: #6c707e;
--table-td-border-color: #555967;
--kbd-text-color: #b3bac3;
--kbd-background-color: #3f4351;
--kbd-border-color: #6c707e;
--kbd-shadow-color: #9a9eac;
}

View File

@ -0,0 +1 @@
@import url("web_arc.css");

View File

@ -0,0 +1,26 @@
@import url("_web_base.css");
a {
text-decoration: underline;
}
pre {
border: 1px solid;
}
:root {
--text-color: #000000;
--background-color: #ffffff;
--alt-background-color: #ffffff;
--link-color: #000000;
--blockquote-text-color: #000000;
--blockquote-border-color: #000000;
--header-border-color: #000000;
--hr-background-color: #000000;
--table-tr-border-color: #000000;
--table-td-border-color: #000000;
--kbd-text-color: #000000;
--kbd-background-color: #ffffff;
--kbd-border-color: #000000;
--kbd-shadow-color: #000000;
}

View File

@ -0,0 +1,26 @@
@import url("_web_base.css");
a {
text-decoration: underline;
}
pre {
border: 1px solid;
}
:root {
--text-color: #ffffff;
--background-color: #000000;
--alt-background-color: #000000;
--link-color: #ffffff;
--blockquote-text-color: #ffffff;
--blockquote-border-color: #ffffff;
--header-border-color: #ffffff;
--hr-background-color: #ffffff;
--table-tr-border-color: #ffffff;
--table-td-border-color: #ffffff;
--kbd-text-color: #ffffff;
--kbd-background-color: #000000;
--kbd-border-color: #ffffff;
--kbd-shadow-color: #ffffff;
}

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,102 @@
#!/usr/bin/python3
#
# Generates color palettes based on the specified background/foreground colors.
#
# Usage: python color_palette_generator.py #fg_hex #bg_hex light|dark
#
# The light variant is based on GitHub's style, while the dark variant is based on pre-existing UberWriter styles.
#
# Accessibility is not accounted for, so make sure to verify contrast: https://webaim.org/resources/contrastchecker/
import operator
import os
import sys
def hex_to_tuple(h):
return tuple(int(h.lstrip('#')[i:i + 2], 16) for i in (0, 2, 4))
def tuple_to_hex(t):
(r, g, b) = t
if r < 0 or g < 0 or b < 0 or r > 255 or g > 255 or b > 255:
return '#%02x%02x%02x (clamped)' % tuple(map(lambda x: max(0, min(x, 255)), t))
else:
return '#%02x%02x%02x' % t
def sub_tuples(t1, t2):
return tuple(map(operator.sub, t1, t2))
if __name__ == '__main__':
if len(sys.argv) != 4:
print("Usage: {} foreground_color background_color light|dark\n" +
"Both colors must be in hexadecimal format, eg. #f6f5f4".format(os.path.basename(__file__)))
exit()
target_foreground_color = hex_to_tuple(sys.argv[1])
target_background_color = hex_to_tuple(sys.argv[2])
dark = sys.argv[3] == "dark"
gh_text_color = hex_to_tuple("#dbdbdb" if dark else "#24292e")
gh_background_color = hex_to_tuple("#353535" if dark else "#ffffff")
gh_alt_background_color = hex_to_tuple("#3a3a3a" if dark else "#f6f8fa")
gh_link_color = hex_to_tuple("#a2c7f8" if dark else "#0366d6")
gh_blockquote_text_color = hex_to_tuple("#959595" if dark else "#6a737d")
gh_blockquote_border_color = hex_to_tuple("#525252" if dark else "#dfe2e5")
gh_header_border_color = hex_to_tuple("#474747" if dark else "#eaecef")
gh_hr_background_color = hex_to_tuple("#505050" if dark else "#e1e4e8")
gh_table_tr_border_color = hex_to_tuple("#696969" if dark else "#c6cbd1")
gh_table_td_border_color = hex_to_tuple("#525252" if dark else "#dfe2e5")
gh_kbd_text_color = hex_to_tuple("#bbbbbb" if dark else "#444d56")
gh_kbd_background_color = hex_to_tuple("#3c3c3c" if dark else "#fafbfc")
gh_kbd_border_color = hex_to_tuple("#696969" if dark else "#c6cbd1")
gh_kbd_shadow_color = hex_to_tuple("#979797" if dark else "#959da5")
text_color_diff = sub_tuples(gh_text_color, target_foreground_color)
background_color_diff = sub_tuples(gh_background_color, target_background_color)
text_color = tuple_to_hex(target_foreground_color)
background_color = tuple_to_hex(target_background_color)
alt_background_color = tuple_to_hex(sub_tuples(gh_alt_background_color, background_color_diff))
link_color = tuple_to_hex(sub_tuples(gh_link_color, text_color_diff))
blockquote_text_color = tuple_to_hex(sub_tuples(gh_blockquote_text_color, text_color_diff))
blockquote_border_color = tuple_to_hex(sub_tuples(gh_blockquote_border_color, background_color_diff))
header_border_color = tuple_to_hex(sub_tuples(gh_header_border_color, background_color_diff))
hr_background_color = tuple_to_hex(sub_tuples(gh_hr_background_color, background_color_diff))
table_tr_border_color = tuple_to_hex(sub_tuples(gh_table_tr_border_color, background_color_diff))
table_td_border_color = tuple_to_hex(sub_tuples(gh_table_td_border_color, background_color_diff))
kbd_text_color = tuple_to_hex(sub_tuples(gh_kbd_text_color, text_color_diff))
kbd_background_color = tuple_to_hex(sub_tuples(gh_kbd_background_color, background_color_diff))
kbd_border_color = tuple_to_hex(sub_tuples(gh_kbd_border_color, background_color_diff))
kbd_shadow_color = tuple_to_hex(sub_tuples(gh_kbd_shadow_color, background_color_diff))
print(("--text-color: {};\n" +
"--background-color: {};\n" +
"--alt-background-color: {};\n" +
"--link-color: {};\n" +
"--blockquote-text-color: {};\n" +
"--blockquote-border-color: {};\n" +
"--header-border-color: {};\n" +
"--hr-background-color: {};\n" +
"--table-tr-border-color: {};\n" +
"--table-td-border-color: {};\n" +
"--kbd-text-color: {};\n" +
"--kbd-background-color: {};\n" +
"--kbd-border-color: {};\n" +
"--kbd-shadow-color: {};\n").format(
text_color,
background_color,
alt_background_color,
link_color,
blockquote_text_color,
blockquote_border_color,
header_border_color,
hr_background_color,
table_tr_border_color,
table_td_border_color,
kbd_text_color,
kbd_background_color,
kbd_border_color,
kbd_shadow_color))

View File

@ -16,6 +16,7 @@
import re import re
import gi import gi
gi.require_version('Gtk', '3.0') gi.require_version('Gtk', '3.0')
from gi.repository import Gtk from gi.repository import Gtk
from gi.repository import Pango from gi.repository import Pango
@ -46,14 +47,10 @@ class MarkupBuffer():
self.normal_indent = self.text_buffer.create_tag('normal_indent', indent=100) self.normal_indent = self.text_buffer.create_tag('normal_indent', indent=100)
self.green_text = self.text_buffer.create_tag("greentext", self.math_text = self.text_buffer.create_tag('math_text')
foreground="#00364C")
self.grayfont = self.text_buffer.create_tag('graytag', self.unfocused_text = self.text_buffer.create_tag('graytag',
foreground="gray") foreground="gray")
self.blackfont = self.text_buffer.create_tag('blacktag',
foreground="#222")
self.underline = self.text_buffer.create_tag("underline", self.underline = self.text_buffer.create_tag("underline",
underline=Pango.Underline.SINGLE) underline=Pango.Underline.SINGLE)
@ -101,7 +98,8 @@ class MarkupBuffer():
self.table_env.set_property('pixels-above-lines', 0) self.table_env.set_property('pixels-above-lines', 0)
self.table_env.set_property('pixels-below-lines', 0) self.table_env.set_property('pixels-below-lines', 0)
# self.ftag = self.TextBuffer.create_tag("pix_front", pixels_above_lines = 100) self.update_style()
regex = { regex = {
"ITALIC": re.compile(r"(\*|_)(.*?)\1", re.UNICODE), # *asdasd* // _asdasd asd asd_ "ITALIC": re.compile(r"(\*|_)(.*?)\1", re.UNICODE), # *asdasd* // _asdasd asd asd_
"STRONG": re.compile(r"(\*\*|__)(.*?)\1", re.UNICODE), # **as das** // __asdasd asd ad a__ "STRONG": re.compile(r"(\*\*|__)(.*?)\1", re.UNICODE), # **as das** // __asdasd asd ad a__
@ -120,6 +118,13 @@ class MarkupBuffer():
"LINK": re.compile(r"\(http(.+?)\)") "LINK": re.compile(r"\(http(.+?)\)")
} }
def update_style(self):
(found, color) = self.parent.get_style_context().lookup_color('math_text_color')
if not found:
(_, color) = self.parent.get_style_context().lookup_color('foreground_color')
self.math_text.set_property("foreground", color.to_string())
def markup_buffer(self, mode=0): def markup_buffer(self, mode=0):
buf = self.text_buffer buf = self.text_buffer
@ -178,13 +183,13 @@ class MarkupBuffer():
end_iter = buf.get_iter_at_offset(context_offset + match.end()) end_iter = buf.get_iter_at_offset(context_offset + match.end())
self.text_buffer.apply_tag(self.strikethrough, start_iter, end_iter) self.text_buffer.apply_tag(self.strikethrough, start_iter, end_iter)
self.text_buffer.remove_tag(self.green_text, context_start, context_end) self.text_buffer.remove_tag(self.math_text, context_start, context_end)
matches = re.finditer(self.regex["MATH"], text) matches = re.finditer(self.regex["MATH"], text)
for match in matches: for match in matches:
start_iter = buf.get_iter_at_offset(context_offset + match.start()) start_iter = buf.get_iter_at_offset(context_offset + match.start())
end_iter = buf.get_iter_at_offset(context_offset + match.end()) end_iter = buf.get_iter_at_offset(context_offset + match.end())
self.text_buffer.apply_tag(self.green_text, start_iter, end_iter) self.text_buffer.apply_tag(self.math_text, start_iter, end_iter)
for margin in self.rev_leftmargin: for margin in self.rev_leftmargin:
self.text_buffer.remove_tag(margin, context_start, context_end) self.text_buffer.remove_tag(margin, context_start, context_end)
@ -266,15 +271,13 @@ class MarkupBuffer():
self.focusmode_highlight() self.focusmode_highlight()
def focusmode_highlight(self): def focusmode_highlight(self):
self.text_buffer.apply_tag( start_document = self.text_buffer.get_start_iter()
self.grayfont, end_document = self.text_buffer.get_end_iter()
self.text_buffer.get_start_iter(),
self.text_buffer.get_end_iter())
self.text_buffer.remove_tag( self.text_buffer.remove_tag(
self.blackfont, self.unfocused_text,
self.text_buffer.get_start_iter(), start_document,
self.text_buffer.get_end_iter()) end_document)
cursor = self.text_buffer.get_mark("insert") cursor = self.text_buffer.get_mark("insert")
cursor_iter = self.text_buffer.get_iter_at_mark(cursor) cursor_iter = self.text_buffer.get_iter_at_mark(cursor)
@ -293,9 +296,14 @@ class MarkupBuffer():
start_sentence = cursor_iter.copy() start_sentence = cursor_iter.copy()
start_sentence.backward_sentence_start() start_sentence.backward_sentence_start()
# grey out everything before
self.text_buffer.apply_tag( self.text_buffer.apply_tag(
self.blackfont, self.unfocused_text,
start_sentence, end_sentence) self.text_buffer.get_start_iter(), start_sentence)
self.text_buffer.apply_tag(
self.unfocused_text,
end_sentence, self.text_buffer.get_end_iter())
def set_multiplier(self, multiplier): def set_multiplier(self, multiplier):
self.multiplier = multiplier self.multiplier = multiplier
@ -311,13 +319,3 @@ class MarkupBuffer():
new_margin = (lm - multiplier) + multiplier + multiplier * (i + 1) new_margin = (lm - multiplier) + multiplier + multiplier * (i + 1)
self.leftmargin[i].set_property("left-margin", 0 if new_margin < 0 else new_margin) self.leftmargin[i].set_property("left-margin", 0 if new_margin < 0 else new_margin)
self.leftmargin[i].set_property("indent", - (multiplier - 1) * (i + 1) - multiplier) self.leftmargin[i].set_property("indent", - (multiplier - 1) * (i + 1) - multiplier)
def dark_mode(self, active=False):
if active:
self.green_text.set_property("foreground", "#FA5B0F")
self.grayfont.set_property("foreground", "#666")
self.blackfont.set_property("foreground", "#CCC")
else:
self.green_text.set_property("foreground", "#00364C")
self.grayfont.set_property("foreground", "gray")
self.blackfont.set_property("foreground", "#222")

View File

@ -0,0 +1,61 @@
from gi.repository import Gtk
from uberwriter.Settings import Settings
from uberwriter_lib.helpers import get_css_path
class Theme:
"""
The Theme enum lists all supported themes using their "gtk-theme-name" value.
The light variant is listed first, followed by the dark variant, if any.
"""
settings = Settings.new()
def __init__(self, name, gtk_css_path, web_css_path, is_dark, inverse_name):
self.name = name
self.gtk_css_path = gtk_css_path
self.web_css_path = web_css_path
self.is_dark = is_dark
self.inverse_name = inverse_name
@classmethod
def get_for_name(cls, name, default=None):
current_theme = default or defaultThemes[0]
for theme in defaultThemes:
if name == theme.name:
current_theme = theme
return current_theme
@classmethod
def get_current(cls):
theme_name = Gtk.Settings.get_default().get_property('gtk-theme-name')
dark_mode = cls.settings.get_value('dark-mode').get_boolean()
current_theme = cls.get_for_name(theme_name)
# Technically, we could very easily allow the user to force the light ui on a dark theme.
# However, as there is no inverse of "gtk-application-prefer-dark-theme", we shouldn't do that.
if dark_mode and not current_theme.is_dark and current_theme.inverse_name:
current_theme = cls.get_for_name(current_theme.inverse_name, current_theme.name)
return current_theme
defaultThemes = [
# https://gitlab.gnome.org/GNOME/gtk/tree/master/gtk/theme/Adwaita
Theme('Adwaita', get_css_path('gtk_adwaita.css'),
get_css_path('web_adwaita.css'), False, 'Adwaita-dark'),
Theme('Adwaita-dark', get_css_path('gtk_adwaita_dark.css'),
get_css_path('web_adwaita_dark.css'), True, 'Adwaita'),
# https://github.com/NicoHood/arc-theme/tree/master/common/gtk-3.0/3.20/sass
Theme('Arc', get_css_path('gtk_arc.css'),
get_css_path('web_arc.css'), False, 'Arc-Dark'),
Theme('Arc-Darker', get_css_path('gtk_arc_darker.css'),
get_css_path('web_arc_darker.css'), False, 'Arc-Dark'),
Theme('Arc-Dark', get_css_path('gtk_arc_dark.css'),
get_css_path('web_arc_dark.css'), True, 'Arc'),
# https://gitlab.gnome.org/GNOME/gtk/tree/master/gtk/theme/HighContrast
Theme('HighContrast', get_css_path('gtk_high_contrast.css'),
get_css_path('web_high_contrast.css'), False, 'HighContrastInverse'),
Theme('HighContrastInverse', get_css_path('gtk_high_contrast_inverse.css'),
get_css_path('web_high_contrast_inverse.css'), True, 'HighContrast'),
]

View File

@ -24,6 +24,9 @@ import logging
from gettext import gettext as _ from gettext import gettext as _
import gi import gi
from uberwriter.Theme import Theme
gi.require_version('Gtk', '3.0') gi.require_version('Gtk', '3.0')
from gi.repository import Gtk from gi.repository import Gtk
@ -215,7 +218,7 @@ class Export:
args.append("-o%s.odt" % basename) args.append("-o%s.odt" % basename)
elif export_format == "html": elif export_format == "html":
css = helpers.get_media_file('github-md.css') css = Theme.ADWAITA.get_gtk_css_file()
relativize = helpers.get_script_path('relative_to_absolute.lua') relativize = helpers.get_script_path('relative_to_absolute.lua')
task_list = helpers.get_script_path('task-list.lua') task_list = helpers.get_script_path('task-list.lua')
args.append("-c%s" % css) args.append("-c%s" % css)

View File

@ -14,20 +14,22 @@
# with this program. If not, see <http://www.gnu.org/licenses/>. # with this program. If not, see <http://www.gnu.org/licenses/>.
# END LICENSE # END LICENSE
import locale
import subprocess
import os
import codecs import codecs
import webbrowser import locale
import urllib
import logging import logging
import mimetypes import mimetypes
import os
import re import re
import subprocess
import urllib
import webbrowser
from gettext import gettext as _ from gettext import gettext as _
import gi import gi
from gi.repository.GObject import param_spec_string
from uberwriter.Theme import Theme
gi.require_version('Gtk', '3.0') gi.require_version('Gtk', '3.0')
gi.require_version('WebKit2', '4.0') # pylint: disable=wrong-import-position gi.require_version('WebKit2', '4.0') # pylint: disable=wrong-import-position
from gi.repository import Gtk, Gdk, GObject, GLib, Gio from gi.repository import Gtk, Gdk, GObject, GLib, Gio
@ -181,21 +183,13 @@ class UberwriterWindow(Gtk.ApplicationWindow):
# Init file name with None # Init file name with None
self.set_filename() self.set_filename()
# self.style_provider = Gtk.CssProvider()
# self.style_provider.load_from_path(helpers.get_media_path('arc_style.css'))
# Gtk.StyleContext.add_provider_for_screen(
# Gdk.Screen.get_default(), self.style_provider,
# Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION
# )
# Markup and Shortcuts for the TextBuffer # Markup and Shortcuts for the TextBuffer
self.markup_buffer = MarkupBuffer( self.markup_buffer = MarkupBuffer(
self, self.text_buffer, base_leftmargin) self, self.text_buffer, base_leftmargin)
self.markup_buffer.markup_buffer() self.markup_buffer.markup_buffer()
# Setup dark mode if so # Set current theme
self.toggle_dark_mode(self.settings.get_value("dark-mode")) self.apply_current_theme()
# Scrolling -> Dark or not? # Scrolling -> Dark or not?
self.textchange = False self.textchange = False
@ -266,6 +260,18 @@ class UberwriterWindow(Gtk.ApplicationWindow):
'close-window': (GObject.SIGNAL_ACTION, None, ()) 'close-window': (GObject.SIGNAL_ACTION, None, ())
} }
def apply_current_theme(self):
"""Adjusts both the window and the CSD for the current theme.
"""
self.markup_buffer.update_style()
# Reload preview if it exists, otherwise redraw contents of window (self)
if self.preview_webview:
self.show_preview()
else:
self.queue_draw()
def scrolled(self, widget): def scrolled(self, widget):
"""if window scrolled + focusmode make font black again""" """if window scrolled + focusmode make font black again"""
# if self.focusmode: # if self.focusmode:
@ -387,7 +393,7 @@ class UberwriterWindow(Gtk.ApplicationWindow):
else: else:
self.remove_typewriter() self.remove_typewriter()
self.focusmode = False self.focusmode = False
self.text_buffer.remove_tag(self.markup_buffer.grayfont, self.text_buffer.remove_tag(self.markup_buffer.unfocused_text,
self.text_buffer.get_start_iter(), self.text_buffer.get_start_iter(),
self.text_buffer.get_end_iter()) self.text_buffer.get_end_iter())
self.text_buffer.remove_tag(self.markup_buffer.blackfont, self.text_buffer.remove_tag(self.markup_buffer.blackfont,
@ -487,8 +493,8 @@ class UberwriterWindow(Gtk.ApplicationWindow):
self.window_height = widget.get_allocation().height self.window_height = widget.get_allocation().height
w_width = widget.get_allocation().width w_width = widget.get_allocation().width
# Calculate left / right margin # Calculate left / right margin
width_request = 600
if w_width < 900: if w_width < 900:
width_request = 600
self.markup_buffer.set_multiplier(8) self.markup_buffer.set_multiplier(8)
self.current_font_size = 12 self.current_font_size = 12
self.alignment_padding = 30 self.alignment_padding = 30
@ -498,8 +504,8 @@ class UberwriterWindow(Gtk.ApplicationWindow):
self.get_style_context().add_class("small") self.get_style_context().add_class("small")
elif w_width < 1400: elif w_width < 1400:
self.markup_buffer.set_multiplier(10)
width_request = 800 width_request = 800
self.markup_buffer.set_multiplier(10)
self.current_font_size = 15 self.current_font_size = 15
self.alignment_padding = 40 self.alignment_padding = 40
lm = 7 * 10 lm = 7 * 10
@ -508,9 +514,9 @@ class UberwriterWindow(Gtk.ApplicationWindow):
self.get_style_context().add_class("medium") self.get_style_context().add_class("medium")
else: else:
width_request = 1000
self.markup_buffer.set_multiplier(13) self.markup_buffer.set_multiplier(13)
self.current_font_size = 17 self.current_font_size = 17
width_request = 1000
self.alignment_padding = 60 self.alignment_padding = 60
lm = 7 * 13 lm = 7 * 13
self.get_style_context().remove_class("medium") self.get_style_context().remove_class("medium")
@ -865,20 +871,13 @@ class UberwriterWindow(Gtk.ApplicationWindow):
base_path = '' base_path = ''
os.environ['PANDOC_PREFIX'] = base_path + '/' os.environ['PANDOC_PREFIX'] = base_path + '/'
# Set the styles according the color theme
if self.settings.get_value("dark-mode"):
stylesheet = helpers.get_media_path('github-md-dark.css')
else:
stylesheet = helpers.get_media_path('github-md.css')
args = ['pandoc', args = ['pandoc',
'-s', '-s',
'--from=markdown', '--from=markdown',
'--to=html5', '--to=html5',
'--mathjax', '--mathjax',
'--css=' + stylesheet, '--css=' + Theme.get_current().web_css_path,
'--lua-filter=' + '--lua-filter=' + helpers.get_script_path('relative_to_absolute.lua'),
helpers.get_script_path('relative_to_absolute.lua'),
'--lua-filter=' + helpers.get_script_path('task-list.lua')] '--lua-filter=' + helpers.get_script_path('task-list.lua')]
proc = subprocess.Popen( proc = subprocess.Popen(
@ -906,32 +905,6 @@ class UberwriterWindow(Gtk.ApplicationWindow):
self.preview_webview.load_html(output.decode("utf-8"), 'file://localhost/') self.preview_webview.load_html(output.decode("utf-8"), 'file://localhost/')
def toggle_dark_mode(self, state):
"""Toggle the dark mode, both for the window and for the CSD
Arguments:
state {gtk bool} -- Desired state of the dark mode (enabled/disabled)
"""
# Save state for saving settings later
if state:
# Dark Mode is on
self.get_style_context().add_class("dark_mode")
self.headerbar.hb_container.get_style_context().add_class("dark_mode")
self.markup_buffer.dark_mode(True)
else:
# Dark mode off
self.get_style_context().remove_class("dark_mode")
self.headerbar.hb_container.get_style_context().remove_class("dark_mode")
self.markup_buffer.dark_mode(False)
# Reload preview if it exists
if self.preview_webview:
self.show_preview()
# Redraw contents of window (self)
self.queue_draw()
def load_file(self, filename=None): def load_file(self, filename=None):
"""Open File from command line or open / open recent etc.""" """Open File from command line or open / open recent etc."""
if self.check_change() == Gtk.ResponseType.CANCEL: if self.check_change() == Gtk.ResponseType.CANCEL:

View File

@ -16,13 +16,14 @@ from gettext import gettext as _
import gi import gi
from uberwriter.Theme import Theme
gi.require_version('Gtk', '3.0') # pylint: disable=wrong-import-position gi.require_version('Gtk', '3.0') # pylint: disable=wrong-import-position
from gi.repository import GLib, Gio, Gtk, Gdk, GdkPixbuf from gi.repository import GLib, Gio, Gtk, Gdk, GdkPixbuf
from uberwriter import UberwriterWindow from uberwriter import UberwriterWindow
from uberwriter.Settings import Settings from uberwriter.Settings import Settings
from uberwriter_lib import set_up_logging from uberwriter_lib import set_up_logging
from uberwriter_lib import helpers
from uberwriter_lib.PreferencesDialog import PreferencesDialog from uberwriter_lib.PreferencesDialog import PreferencesDialog
from . helpers import get_builder, get_media_path from . helpers import get_builder, get_media_path
@ -36,30 +37,6 @@ class Application(Gtk.Application):
self.window = None self.window = None
self.settings = Settings.new() self.settings = Settings.new()
def init(self):
"""Init main application"""
# set theme variant (dark/light)
dark = self.settings.get_value("dark-mode")
Gtk.Settings.get_default().set_property("gtk-application-prefer-dark-theme", dark)
# set css for current theme
self.style_provider = Gtk.CssProvider()
themes = {
"Arc": "arc_style.css",
"Arc-Dark": "arc_style.css",
"Arc-Darker": "arc_style.css",
}
theme = Gtk.Settings.get_default().get_property("gtk-theme-name")
self.style_provider.load_from_path(helpers.get_media_path(themes.get(theme,"adwaita_style.css")))
Gtk.StyleContext.add_provider_for_screen(
Gdk.Screen.get_default(), self.style_provider,
Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION
)
def do_startup(self, *args, **kwargs): def do_startup(self, *args, **kwargs):
Gtk.Application.do_startup(self) Gtk.Application.do_startup(self)
@ -176,7 +153,7 @@ class Application(Gtk.Application):
self.set_accels_for_action("app.save", ["<Ctl>s"]) self.set_accels_for_action("app.save", ["<Ctl>s"])
self.set_accels_for_action("app.save_as", ["<Ctl><shift>s"]) self.set_accels_for_action("app.save_as", ["<Ctl><shift>s"])
self.init() self.apply_current_theme()
def do_activate(self, *args, **kwargs): def do_activate(self, *args, **kwargs):
# We only allow a single window and raise any existing ones # We only allow a single window and raise any existing ones
@ -209,6 +186,23 @@ class Application(Gtk.Application):
self.activate() self.activate()
return 0 return 0
def apply_current_theme(self):
# get current theme
theme = Theme.get_current()
# set theme variant (dark/light)
Gtk.Settings.get_default().set_property(
"gtk-application-prefer-dark-theme",
GLib.Variant("b", theme.is_dark))
# set theme css
style_provider = Gtk.CssProvider()
style_provider.load_from_path(theme.gtk_css_path)
Gtk.StyleContext.add_provider_for_screen(
Gdk.Screen.get_default(), style_provider,
Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION
)
def on_about(self, _action, _param): def on_about(self, _action, _param):
builder = get_builder('About') builder = get_builder('About')
about_dialog = builder.get_object("AboutDialog") about_dialog = builder.get_object("AboutDialog")
@ -234,14 +228,13 @@ class Application(Gtk.Application):
def on_dark_mode(self, action, value): def on_dark_mode(self, action, value):
action.set_state(value) action.set_state(value)
self.settings.set_value("dark-mode", self.settings.set_value("dark-mode", GLib.Variant("b", value))
GLib.Variant("b", value))
self.window.toggle_dark_mode(value)
# this changes the headerbar theme accordingly # this changes the headerbar theme accordingly
self.dark_setting = Gtk.Settings.get_default() self.apply_current_theme()
self.dark_setting.set_property(
"gtk-application-prefer-dark-theme", value) # adjust window for theme
self.window.apply_current_theme()
def on_focus_mode(self, action, value): def on_focus_mode(self, action, value):
action.set_state(value) action.set_state(value)

View File

@ -49,16 +49,12 @@ def get_builder(builder_file_name):
# Owais Lone : To get quick access to icons and stuff. # Owais Lone : To get quick access to icons and stuff.
def get_media_file(media_file_name): def get_media_file(media_file_path):
"""Return the full path of a given filename under the media dir """Return the full path of a given filename under the media dir
(starts with file:///) (starts with file:///)
""" """
media_filename = get_data_file('media', '%s' % (media_file_name,)) return "file:///" + get_media_path(media_file_path)
if not os.path.exists(media_filename):
media_filename = None
return "file:///" + media_filename
def get_media_path(media_file_name): def get_media_path(media_file_name):
@ -66,19 +62,26 @@ def get_media_path(media_file_name):
(doesn't start with file:///) (doesn't start with file:///)
""" """
media_filename = get_data_file('media', '%s' % (media_file_name,)) media_path = get_data_file('media', '%s' % (media_file_name,))
if not os.path.exists(media_filename): if not os.path.exists(media_path):
media_filename = None media_path = None
return media_filename return media_path
def get_css_path(css_file_name):
"""Return the full path of a given filename under the css dir
(doesn't start with file:///)
"""
return get_media_path("css/{}".format(css_file_name))
def get_script_path(script_file_name): def get_script_path(script_file_name):
"""Return the full path of a given filename under the script dir """Return the full path of a given filename under the script dir
""" """
script_filename = get_data_file('lua', '%s' % (script_file_name,)) script_path = get_data_file('lua', '%s' % (script_file_name,))
if not os.path.exists(script_filename): if not os.path.exists(script_path):
script_filename = None script_path = None
return script_filename return script_path
class NullHandler(logging.Handler): class NullHandler(logging.Handler):