diff --git a/crates/ui-egui/src/icons.rs b/crates/ui-egui/src/icons.rs
--- a/crates/ui-egui/src/icons.rs
+++ b/crates/ui-egui/src/icons.rs
@@ -248,6 +248,12 @@ pub fn paint(p: &Painter, r: Rect, name: &str, c: Color32, accent: Color32) {
             pen.fcircle(16.5, 13.5, 1.6, a);
             pen.frect(2.0, 16.5, 18.0, 19.0, yellow);
         }
+        // The Shading buttons draw the last colour as their own bar, so this has no bar of its own.
+        "shadingNoBar" => {
+            pen.fill(&[(4.0, 9.0), (10.0, 3.0), (16.0, 9.0), (10.0, 15.0)], Color32::TRANSPARENT);
+            pen.closed(&[(4.0, 9.0), (10.0, 3.0), (16.0, 9.0), (10.0, 15.0)], c);
+            pen.fcircle(16.5, 13.5, 1.6, a);
+        }
         "borders" => {
             for y in [3.0, 10.0, 17.0] {
                 for x in [3.0, 6.5, 10.0, 13.5, 17.0] {
@@ -1649,4 +1655,11 @@ mod tests {
         assert!(has_default_highlight_bar("highlight"));
         assert!(!has_default_highlight_bar("highlightNoColor"));
     }
+
+    /// #4412: the Shading buttons paint the last colour as their bar, so their icon has none of its own.
+    #[test]
+    fn the_shading_button_icon_has_no_bar_of_its_own() {
+        assert!(has_default_highlight_bar("shading"));
+        assert!(!has_default_highlight_bar("shadingNoBar"));
+    }
 }
diff --git a/crates/ui-egui/src/ribbon/home.rs b/crates/ui-egui/src/ribbon/home.rs
--- a/crates/ui-egui/src/ribbon/home.rs
+++ b/crates/ui-egui/src/ribbon/home.rs
@@ -232,7 +232,8 @@ pub(super) fn home(app: &mut WordApp, ui: &mut Ui) {
                     mi(ui, app, "Remove Space After Paragraph", "para.removeSpaceAfter", json!({}));
                     mi(ui, app, "Line Spacing Options…", "para.dialog", json!({}));
                 });
-                split(ui, app, "shading", "Shading", "para.shading", json!({"color": app.canvas.last_shading.clone()}), false, None, |ui, app| {
+                let sw = wordcraft_doc::Rgb::parse(&app.canvas.last_shading).map(crate::theme::c32);
+                split(ui, app, "shadingNoBar", "Shading", "para.shading", json!({"color": app.canvas.last_shading.clone()}), false, sw, |ui, app| {
                     mi(ui, app, "No Color", "para.shading", json!({"color": null}));
                     let theme = app.session.doc.settings.theme_colors.clone();
                     crate::colors::menu(ui, app, &theme, Target::cmd("para.shading").remember(Remember::Shading));
diff --git a/crates/ui-egui/src/ribbon/table.rs b/crates/ui-egui/src/ribbon/table.rs
--- a/crates/ui-egui/src/ribbon/table.rs
+++ b/crates/ui-egui/src/ribbon/table.rs
@@ -73,7 +73,8 @@ pub(super) fn table_design(app: &mut WordApp, ui: &mut Ui) {
                     ui.close();
                 }
             });
-            split(ui, app, "shading", "Shading", "table.shading", json!({"color": app.canvas.last_shading.clone()}), false, None, |ui, app| {
+            let sw = wordcraft_doc::Rgb::parse(&app.canvas.last_shading).map(crate::theme::c32);
+            split(ui, app, "shadingNoBar", "Shading", "table.shading", json!({"color": app.canvas.last_shading.clone()}), false, sw, |ui, app| {
                 mi(ui, app, "No Color", "table.shading", json!({"color": null}));
                 let theme = app.session.doc.settings.theme_colors.clone();
                 crate::colors::menu(ui, app, &theme, Target::cmd("table.shading").remember(Remember::Shading));
diff --git a/crates/ui-egui/src/ribbon/tests.rs b/crates/ui-egui/src/ribbon/tests.rs
--- a/crates/ui-egui/src/ribbon/tests.rs
+++ b/crates/ui-egui/src/ribbon/tests.rs
@@ -1,6 +1,32 @@
 use super::*;
 use wordcraft_engine::Session;
 
+/// #4412: the Shading button's bar is the colour a click applies (the last one picked), as
+/// the Font Color and Text Highlight Color buttons' bars are, not always the icon's yellow.
+#[test]
+fn the_shading_button_shows_the_last_picked_colour() {
+    let mut a = WordApp::new(Session::new(wordcraft_doc::Document::from_text("Text")), crate::Services::default());
+    a.run("view.commentsPane", json!({"value": false})).unwrap();
+    let mut h = egui_kittest::Harness::builder().with_size(egui::vec2(1440.0, 900.0)).build_ui_state(
+        |ui, app: &mut WordApp| {
+            let ctx = ui.ctx().clone();
+            app.logic(&ctx);
+            app.ui(ui);
+        },
+        a,
+    );
+    let ribbon_bars = |h: &egui_kittest::Harness<'_, WordApp>, hex: &str| {
+        let want = crate::theme::c32(wordcraft_doc::Rgb::parse(hex).unwrap());
+        h.output().shapes.iter().any(|s| matches!(&s.shape, egui::Shape::Rect(r) if r.fill == want && r.rect.height() < 4.0 && r.rect.width() > 10.0))
+    };
+    h.run_steps(6);
+    assert!(ribbon_bars(&h, "FFF2CC"), "the default colour");
+    h.state_mut().canvas.last_shading = "00B0F0".into();
+    h.run_steps(3);
+    assert!(ribbon_bars(&h, "00B0F0"), "the picked colour");
+    assert!(!ribbon_bars(&h, "FFF2CC"), "and not the old one");
+}
+
 /// Two clicks arm and disarm the painter; the double-click handling then leaves it sticky (#2785).
 #[test]
 fn double_click_on_format_painter_makes_it_sticky() {
