Skip to content

Commit 5d2d61f

Browse files
Merge pull request #853 from GhostManager/hotfix/tinymce-dark-mode
Hotfix: TinyMCE dark mode
2 parents 379a856 + e3cf043 commit 5d2d61f

File tree

18 files changed

+563
-27
lines changed

18 files changed

+563
-27
lines changed

CHANGELOG.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,17 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## [6.2.10] - 27 March 2026
9+
10+
### Changed
11+
12+
* Updated TinyMCE to work better with Ghostwriter's dark mode using a new dark-mode skin
13+
14+
### Fixed
15+
16+
* Fixed TinyMCE editors not initiating correctly for the "Results" field on objectives when adding new forms
17+
* Fixed TinyMCE editors sometimes appearing with a very short height and needing to be resized
18+
819
## [6.2.9] - 23 March 2026
920

1021
### Changed

VERSION

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
1-
v6.2.9
2-
23 March 2026
1+
v6.2.10
2+
27 March 2026

config/settings/base.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,9 @@
1111
# 3rd Party Libraries
1212
import environ
1313

14-
__version__ = "6.2.9"
14+
__version__ = "6.2.10"
1515
VERSION = __version__
16-
RELEASE_DATE = "23 March 2026"
16+
RELEASE_DATE = "27 March 2026"
1717

1818
ROOT_DIR = Path(__file__).resolve(strict=True).parent.parent.parent
1919
APPS_DIR = ROOT_DIR / "ghostwriter"

ghostwriter/rolodex/forms_project.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -610,6 +610,7 @@ class Meta:
610610
}
611611
field_classes = {
612612
"description": JinjaRichTextField,
613+
"result": JinjaRichTextField,
613614
}
614615

615616
def __init__(self, *args, **kwargs):
@@ -622,6 +623,7 @@ def __init__(self, *args, **kwargs):
622623
self.fields["description"].widget.attrs[
623624
"placeholder"
624625
] = "The task is to escalate privileges to a domain admin and..."
626+
self.fields["result"].widget.attrs["placeholder"] = "Document the outcome, evidence, or result of this objective..."
625627
self.fields["priority"].empty_label = "-- Prioritize Objective --"
626628
self.helper = FormHelper()
627629
# Disable the <form> tags because this will be inside an instance of `ProjectForm()`

ghostwriter/rolodex/templates/rolodex/project_form.html

Lines changed: 15 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,14 @@
7676
field.val(new Date().toJSON().slice(0, 19));
7777
}
7878

79+
function initTinyMceEditors($container) {
80+
$container.find('textarea').not('.no-auto-tinymce, .empty-form').each(function () {
81+
if (this.id) {
82+
tinymce.execCommand('mceAddEditor', false, this.id);
83+
}
84+
});
85+
}
86+
7987
{% comment %} Formset Manipulation Buttons {% endcomment %}
8088
$('.formset-add-{{ objectives.prefix }}').click(function () {
8189
let form_idx = $('#id_{{ objectives.prefix }}-TOTAL_FORMS').val();
@@ -84,10 +92,7 @@
8492
let new_form = $('#formset-{{ objectives.prefix }}').find('div.formset-container').last()
8593
new_form.find('span.counter').html(parseInt(form_idx) + 1);
8694
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
87-
let target = 'id_{{ objectives.prefix }}-' + parseInt(form_idx) + '-description'
88-
let objResult = 'id_{{ objectives.prefix }}-' + parseInt(form_idx) + '-result'
89-
tinymce.execCommand('mceAddEditor', false, target);
90-
tinymce.execCommand('mceAddEditor', false, objResult);
95+
initTinyMceEditors(new_form);
9196
});
9297

9398
$('.formset-add-{{ assignments.prefix }}').click(function () {
@@ -97,8 +102,7 @@
97102
let new_form = $('#formset-{{ assignments.prefix }}').find('div.formset-container').last()
98103
new_form.find('span.counter').html(parseInt(form_idx) + 1);
99104
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
100-
let target = 'id_{{ assignments.prefix }}-' + parseInt(form_idx) + '-description'
101-
tinymce.execCommand('mceAddEditor', false, target);
105+
initTinyMceEditors(new_form);
102106
});
103107

104108
$('.formset-add-{{ invites.prefix }}').click(function () {
@@ -108,8 +112,7 @@
108112
let new_form = $('#formset-{{ invites.prefix }}').find('div.formset-container').last()
109113
new_form.find('span.counter').html(parseInt(form_idx) + 1);
110114
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
111-
let target = 'id_{{ invites.prefix }}-' + parseInt(form_idx) + '-comment'
112-
tinymce.execCommand('mceAddEditor', false, target);
115+
initTinyMceEditors(new_form);
113116
});
114117

115118
$('.formset-add-{{ scopes.prefix }}').click(function () {
@@ -119,8 +122,7 @@
119122
let new_form = $('#formset-{{ scopes.prefix }}').find('div.formset-container').last()
120123
new_form.find('span.counter').html(parseInt(form_idx) + 1);
121124
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
122-
let target = 'id_{{ scopes.prefix }}-' + parseInt(form_idx) + '-description'
123-
tinymce.execCommand('mceAddEditor', false, target);
125+
initTinyMceEditors(new_form);
124126
});
125127

126128
$('.formset-add-{{ targets.prefix }}').click(function () {
@@ -130,8 +132,7 @@
130132
let new_form = $('#formset-{{ targets.prefix }}').find('div.formset-container').last()
131133
new_form.find('span.counter').html(parseInt(form_idx) + 1);
132134
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
133-
let target = 'id_{{ targets.prefix }}-' + parseInt(form_idx) + '-description'
134-
tinymce.execCommand('mceAddEditor', false, target);
135+
initTinyMceEditors(new_form);
135136
});
136137

137138
$('.formset-add-{{ whitecards.prefix }}').click(function () {
@@ -141,8 +142,7 @@
141142
let new_form = $('#formset-{{ whitecards.prefix }}').find('div.formset-container').last()
142143
new_form.find('span.counter').html(parseInt(form_idx) + 1);
143144
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
144-
let target = 'id_{{ whitecards.prefix }}-' + parseInt(form_idx) + '-description'
145-
tinymce.execCommand('mceAddEditor', false, target);
145+
initTinyMceEditors(new_form);
146146
});
147147

148148
$('.formset-add-{{ contacts.prefix }}').click(function () {
@@ -152,8 +152,7 @@
152152
let new_form = $('#formset-{{ contacts.prefix }}').find('div.formset-container').last()
153153
new_form.find('span.counter').html(parseInt(form_idx) + 1);
154154
new_form.fadeOut(100).fadeIn(100).fadeOut(100).fadeIn(100);
155-
let target = 'id_{{ contacts.prefix }}-' + parseInt(form_idx) + '-description'
156-
tinymce.execCommand('mceAddEditor', false, target);
155+
initTinyMceEditors(new_form);
157156
});
158157

159158
{% comment %} Roll Codename with AJAX {% endcomment %}

ghostwriter/static/css/base_styles.css

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
--warning-color: #F4B083;
1818
--ghost-white: #F0EFF4;
1919
--ghost-grey: #6C809A;
20+
--placeholder-color: #aaa;
2021

2122
/* TEXT */
2223
--h1-font-color: #6D70A7;

ghostwriter/static/css/styles.css

Lines changed: 155 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4185,6 +4185,160 @@ input[type="color"]:focus,
41854185
color: #fff;
41864186
}
41874187

4188+
/* TinyMCE dark mode */
4189+
[data-theme="dark"] .tox,
4190+
[data-theme="dark"] .tox .tox-tbtn,
4191+
[data-theme="dark"] .tox .tox-mbtn,
4192+
[data-theme="dark"] .tox .tox-statusbar,
4193+
[data-theme="dark"] .tox .tox-statusbar a,
4194+
[data-theme="dark"] .tox .tox-statusbar__path-item,
4195+
[data-theme="dark"] .tox .tox-statusbar__wordcount,
4196+
[data-theme="dark"] .tox .tox-collection__item,
4197+
[data-theme="dark"] .tox .tox-collection__group-heading,
4198+
[data-theme="dark"] .tox .tox-dialog__title,
4199+
[data-theme="dark"] .tox .tox-label,
4200+
[data-theme="dark"] .tox .tox-textfield,
4201+
[data-theme="dark"] .tox .tox-textarea,
4202+
[data-theme="dark"] .tox .tox-listboxfield .tox-listbox--select,
4203+
[data-theme="dark"] .tox .tox-selectfield select {
4204+
color: var(--main-txt-color);
4205+
}
4206+
4207+
[data-theme="dark"] .tox.tox-tinymce,
4208+
[data-theme="dark"] .tox .tox-editor-header,
4209+
[data-theme="dark"] .tox .tox-toolbar-overlord,
4210+
[data-theme="dark"] .tox .tox-toolbar,
4211+
[data-theme="dark"] .tox .tox-toolbar__primary,
4212+
[data-theme="dark"] .tox .tox-toolbar__overflow,
4213+
[data-theme="dark"] .tox .tox-menubar,
4214+
[data-theme="dark"] .tox .tox-statusbar,
4215+
[data-theme="dark"] .tox .tox-tinymce-aux,
4216+
[data-theme="dark"] .tox .tox-menu,
4217+
[data-theme="dark"] .tox .tox-collection,
4218+
[data-theme="dark"] .tox .tox-autocompleter,
4219+
[data-theme="dark"] .tox .tox-dialog,
4220+
[data-theme="dark"] .tox .tox-dialog__header,
4221+
[data-theme="dark"] .tox .tox-dialog__body,
4222+
[data-theme="dark"] .tox .tox-dialog__footer,
4223+
[data-theme="dark"] .tox .tox-dialog__body-nav,
4224+
[data-theme="dark"] .tox .tox-pop {
4225+
background-color: var(--search-input-background-color);
4226+
}
4227+
4228+
[data-theme="dark"] .tox.tox-tinymce,
4229+
[data-theme="dark"] .tox .tox-editor-header,
4230+
[data-theme="dark"] .tox .tox-toolbar-overlord,
4231+
[data-theme="dark"] .tox .tox-menubar,
4232+
[data-theme="dark"] .tox .tox-statusbar,
4233+
[data-theme="dark"] .tox .tox-toolbar__group,
4234+
[data-theme="dark"] .tox .tox-tbtn,
4235+
[data-theme="dark"] .tox .tox-mbtn,
4236+
[data-theme="dark"] .tox .tox-menu,
4237+
[data-theme="dark"] .tox .tox-collection,
4238+
[data-theme="dark"] .tox .tox-dialog,
4239+
[data-theme="dark"] .tox .tox-dialog__header,
4240+
[data-theme="dark"] .tox .tox-dialog__footer,
4241+
[data-theme="dark"] .tox .tox-dialog__body-nav,
4242+
[data-theme="dark"] .tox .tox-textfield,
4243+
[data-theme="dark"] .tox .tox-textarea,
4244+
[data-theme="dark"] .tox .tox-listboxfield .tox-listbox--select,
4245+
[data-theme="dark"] .tox .tox-selectfield select,
4246+
[data-theme="dark"] .tox .tox-checkbox__icons,
4247+
[data-theme="dark"] .tox .tox-collection--list .tox-collection__item,
4248+
[data-theme="dark"] .tox .tox-menu-nav__js,
4249+
[data-theme="dark"] .tox .tox-swatches-menu {
4250+
border-color: var(--search-box-shadow);
4251+
}
4252+
4253+
[data-theme="dark"] .tox .tox-icon svg,
4254+
[data-theme="dark"] .tox .tox-tbtn svg,
4255+
[data-theme="dark"] .tox .tox-mbtn svg,
4256+
[data-theme="dark"] .tox .tox-collection__item-icon svg,
4257+
[data-theme="dark"] .tox .tox-statusbar__resize-handle svg,
4258+
[data-theme="dark"] .tox .tox-dialog__header .tox-icon svg {
4259+
fill: var(--main-txt-color);
4260+
}
4261+
4262+
[data-theme="dark"] .tox .tox-mbtn:hover,
4263+
[data-theme="dark"] .tox .tox-mbtn:focus,
4264+
[data-theme="dark"] .tox .tox-tbtn:hover,
4265+
[data-theme="dark"] .tox .tox-tbtn:focus,
4266+
[data-theme="dark"] .tox .tox-collection__item--enabled:hover,
4267+
[data-theme="dark"] .tox .tox-collection__item--active,
4268+
[data-theme="dark"] .tox .tox-listboxfield .tox-listbox--select:hover,
4269+
[data-theme="dark"] .tox .tox-selectfield select:hover,
4270+
[data-theme="dark"] .tox .tox-dialog__body-nav-item:hover {
4271+
background-color: var(--sidebar-hover-background-color);
4272+
color: var(--ghost-white);
4273+
}
4274+
4275+
[data-theme="dark"] .tox .tox-mbtn:hover svg,
4276+
[data-theme="dark"] .tox .tox-mbtn:focus svg,
4277+
[data-theme="dark"] .tox .tox-tbtn:hover svg,
4278+
[data-theme="dark"] .tox .tox-tbtn:focus svg,
4279+
[data-theme="dark"] .tox .tox-collection__item--enabled:hover svg,
4280+
[data-theme="dark"] .tox .tox-collection__item--active svg {
4281+
fill: var(--ghost-white);
4282+
}
4283+
4284+
[data-theme="dark"] .tox .tox-tbtn--enabled,
4285+
[data-theme="dark"] .tox .tox-tbtn--enabled:hover,
4286+
[data-theme="dark"] .tox .tox-mbtn--active,
4287+
[data-theme="dark"] .tox .tox-dialog__body-nav-item--active,
4288+
[data-theme="dark"] .tox .tox-collection__item--active:not(.tox-collection__item--state-disabled) {
4289+
background-color: rgba(80, 176, 113, 0.18);
4290+
color: var(--ghost-white);
4291+
}
4292+
4293+
[data-theme="dark"] .tox .tox-dialog__body-nav-item--active {
4294+
border-bottom-color: var(--primary-color);
4295+
}
4296+
4297+
[data-theme="dark"] .tox .tox-button:not(.tox-button--naked) {
4298+
background-color: var(--button-primary-color);
4299+
border-color: var(--button-primary-color);
4300+
color: #fff;
4301+
}
4302+
4303+
[data-theme="dark"] .tox .tox-button:not(.tox-button--naked):hover,
4304+
[data-theme="dark"] .tox .tox-button:not(.tox-button--naked):focus {
4305+
background-color: #5fc587;
4306+
border-color: #5fc587;
4307+
color: #fff;
4308+
}
4309+
4310+
[data-theme="dark"] .tox .tox-dialog-wrap__backdrop {
4311+
background-color: rgba(0, 0, 0, 0.55);
4312+
}
4313+
4314+
[data-theme="dark"] .tox .tox-tooltip__body {
4315+
background-color: var(--sidebar-background-color);
4316+
color: var(--main-txt-color);
4317+
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.35);
4318+
}
4319+
4320+
[data-theme="dark"] .tox .tox-tooltip--down .tox-tooltip__arrow {
4321+
border-top-color: var(--sidebar-background-color);
4322+
}
4323+
4324+
[data-theme="dark"] .tox .tox-tooltip--up .tox-tooltip__arrow {
4325+
border-bottom-color: var(--sidebar-background-color);
4326+
}
4327+
4328+
[data-theme="dark"] .tox .tox-tooltip--right .tox-tooltip__arrow {
4329+
border-left-color: var(--sidebar-background-color);
4330+
}
4331+
4332+
[data-theme="dark"] .tox .tox-tooltip--left .tox-tooltip__arrow {
4333+
border-right-color: var(--sidebar-background-color);
4334+
}
4335+
4336+
[data-theme="dark"] .tox .tox-textfield::placeholder,
4337+
[data-theme="dark"] .tox .tox-textarea::placeholder {
4338+
color: #999;
4339+
opacity: 1;
4340+
}
4341+
41884342
[data-theme="dark"] .richtext-evidence-name,
41894343
[data-theme="dark"] .richtext-evidence-caption,
41904344
[data-theme="dark"] .tiptap blockquote p,
@@ -4647,4 +4801,4 @@ html[data-bs-theme="dark"] .modal .close {
46474801
max-width: 100%;
46484802
font-family: 'Courier New', Courier, monospace;
46494803
font-size: 0.9rem;
4650-
}
4804+
}

ghostwriter/static/css/wysiwyg_styles.css

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,6 @@
66
----------------------------------------------------- */
77

88
.mce-content-body[data-mce-placeholder]:not(.mce-visualblocks)::before {
9-
color: var(--primary-color);
9+
color: var(--placeholder-color, #aaa);
1010
opacity: 0.75;
1111
}

0 commit comments

Comments
 (0)