Skip to content

Commit a70bcbe

Browse files
committed
introduce view macro
1 parent 87b095d commit a70bcbe

File tree

3 files changed

+161
-115
lines changed

3 files changed

+161
-115
lines changed

src/macros.rs

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
#[macro_export]
2+
macro_rules! self_action {
3+
($self:ident, $name:literal, $method:ident) => {
4+
{
5+
let this = &$self;
6+
let action = gio::SimpleAction::new($name, None);
7+
action.connect_activate(clone!(@weak this => move |_,_| this.$method()));
8+
$self.add_action(&action);
9+
}
10+
}
11+
}
12+
13+
#[macro_export]
14+
macro_rules! view {
15+
($name:ident = ($obj_e:expr) {$($tt:tt)+} $($ctt:tt)*) => {
16+
let $name = $obj_e;
17+
view!(@expand-build $name $($tt)+);
18+
view!($($ctt)*);
19+
};
20+
($name:ident = $obj_ty:path {$($tt:tt)+} $($ctt:tt)*) => {
21+
let _obj: $obj_ty = glib::Object::new(&[]).unwrap();
22+
view!($name = (_obj) {$($tt)+});
23+
view!($($ctt)*);
24+
};
25+
() => {};
26+
(@expand-build $obj:ident) => {};
27+
(@expand-build $obj:ident $member:ident : $wrap_tt:tt ($($inner_tt:tt)+), $($tt:tt)*) => {
28+
$obj.$member(
29+
$wrap_tt(view!(@expand-wrapped $($inner_tt)+))
30+
);
31+
view!(@expand-build $obj $($tt)*);
32+
};
33+
(@expand-wrapped $name:ident = $($ptt:tt)+) => {
34+
{
35+
view!($name = $($ptt)+);
36+
$name
37+
}
38+
};
39+
(@expand-wrapped $wrap_tt:tt ($name:ident = $($ptt:tt)+)) => {
40+
$wrap_tt({
41+
view!($name = $($ptt)+);
42+
$name
43+
})
44+
};
45+
(@expand-wrapped $wrap_tt:tt ($($inner_tt:tt)*)) => {
46+
$wrap_tt($($inner_tt)*)
47+
};
48+
(@expand-wrapped $($inner_tt:tt)*) => {
49+
$($inner_tt)*
50+
};
51+
(@expand-build $obj:ident $member:ident : $name:ident = $($itt:tt)+, $($tt:tt)*) => {
52+
view!($name = $($itt)+);
53+
$obj.$member($name);
54+
view!(@expand-build $obj $($tt)*);
55+
};
56+
(@expand-build $obj:ident $member:ident : $e:expr, $($tt:tt)*) => {
57+
$obj.$member($e);
58+
view!(@expand-build $obj $($tt)*);
59+
};
60+
(@expand-build $obj:ident $member:ident($($e:expr),+), $($tt:tt)*) => {
61+
$obj.$member($($e),+);
62+
view!(@expand-build $obj $($tt)*);
63+
};
64+
(@expand-build $obj:ident bind $prop:literal $from_ty:ident $source:literal $($tt:tt)*) => {
65+
$from_ty.bind_property($obj, $source, $prop);
66+
}
67+
}

src/main.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ mod common;
1414
mod config;
1515
mod draw_ctx;
1616
mod gemini;
17+
mod macros;
1718
mod tab;
1819
mod window;
1920

src/window.rs

Lines changed: 93 additions & 115 deletions
Original file line numberDiff line numberDiff line change
@@ -16,25 +16,20 @@ use url::Url;
1616
use crate::common::{bookmarks_url, glibctx, BOOKMARK_FILE_PATH};
1717
use crate::config;
1818
use crate::tab::{Tab, TabPropertiesExt};
19+
use crate::{self_action, view};
1920

2021
pub mod imp {
2122
use super::*;
2223
#[derive(Debug, Default, Properties)]
2324
pub struct Window {
2425
pub(crate) url_bar: gtk::SearchEntry,
25-
pub(crate) bottom_bar: adw::HeaderBar,
2626
pub(crate) bottom_bar_revealer: gtk::Revealer,
2727
pub(crate) bottom_entry: gtk::SearchEntry,
28-
pub(crate) flat_header: adw::HeaderBar,
29-
pub(crate) window_title: adw::WindowTitle,
28+
pub(crate) header_small: adw::HeaderBar,
3029
pub(crate) squeezer: adw::Squeezer,
3130
pub(crate) progress_bar: gtk::ProgressBar,
32-
pub(crate) back_btn: gtk::Button,
33-
pub(crate) menu_btn: gtk::MenuButton,
34-
pub(crate) tab_bar: adw::TabBar,
3531
pub(crate) tab_view: adw::TabView,
3632
pub(crate) config: RefCell<config::Config>,
37-
pub(crate) add_tab_btn: gtk::Button,
3833
pub(crate) progress_animation: RefCell<Option<adw::SpringAnimation>>,
3934
pub(crate) binded_tab_properties: RefCell<Vec<glib::Binding>>,
4035
#[prop(get, set)]
@@ -112,118 +107,120 @@ glib::wrapper! {
112107
@implements gio::ActionMap, gio::ActionGroup;
113108
}
114109

115-
macro_rules! self_action {
116-
($self:ident, $name:literal, $method:ident) => {
117-
{
118-
let this = &$self;
119-
let action = gio::SimpleAction::new($name, None);
120-
action.connect_activate(clone!(@weak this => move |_,_| this.$method()));
121-
$self.add_action(&action);
122-
}
123-
}
124-
}
125110
impl Window {
126111
pub fn new(app: &adw::Application, config: config::Config) -> Self {
127112
let this: Self = glib::Object::new(&[("application", app)]).unwrap();
128113
let imp = this.imp();
129114
imp.config.replace(config);
130115

131-
let content = gtk::Box::new(gtk::Orientation::Vertical, 0);
132-
133-
let header_bar = adw::HeaderBar::new();
134-
135-
imp.back_btn.set_icon_name("go-previous-symbolic");
136-
imp.add_tab_btn.set_icon_name("tab-new-symbolic");
137-
138-
imp.menu_btn.set_icon_name("open-menu");
139-
imp.menu_btn
140-
.set_menu_model(Some(&Self::build_menu_common()));
141-
142-
header_bar.pack_start(&imp.back_btn);
143-
header_bar.pack_start(&imp.add_tab_btn);
144-
header_bar.pack_end(&imp.menu_btn);
145-
146116
imp.url_bar.set_width_request(360);
147117
imp.url_bar.set_hexpand(true);
148-
149-
let bar_clamp = adw::Clamp::new();
150-
bar_clamp.set_child(Some(&imp.url_bar));
151-
bar_clamp.set_maximum_size(768);
152-
bar_clamp.set_tightening_threshold(720);
153-
header_bar.set_title_widget(Some(&bar_clamp));
154-
155-
imp.squeezer
156-
.set_transition_type(adw::SqueezerTransitionType::Crossfade);
157-
158-
imp.window_title.set_title("Geopard");
159-
imp.flat_header.set_title_widget(Some(&imp.window_title));
160-
imp.squeezer.add(&header_bar);
161-
imp.squeezer.add(&imp.flat_header);
162-
163-
content.append(&imp.squeezer);
164-
165-
imp.tab_bar.set_view(Some(&imp.tab_view));
166-
content.append(&imp.tab_bar);
167-
168-
let overlay = gtk::Overlay::new();
169-
let content_view = gtk::Box::new(gtk::Orientation::Vertical, 0);
170-
overlay.set_child(Some(&content_view));
171-
172-
content_view.append(&imp.tab_view);
173-
174118
imp.progress_bar.add_css_class("osd");
175119
imp.progress_bar.set_valign(gtk::Align::Start);
176-
overlay.add_overlay(&imp.progress_bar);
177-
content.append(&overlay);
178-
179-
imp.bottom_bar.set_show_end_title_buttons(false);
180-
imp.bottom_bar.set_show_start_title_buttons(false);
181120

182-
let bottom_menu = gtk::MenuButton::new();
183-
bottom_menu.add_css_class("flat");
184-
let bottom_menu_model = Self::build_menu_common();
185-
let section = gio::Menu::new();
186-
section.append(Some("Back"), Some("win.back"));
187-
section.append(Some("New Tab"), Some("win.new-tab"));
188-
bottom_menu_model.append_section(None, &section);
189-
bottom_menu.set_menu_model(Some(&bottom_menu_model));
190-
bottom_menu.set_icon_name("open-menu");
121+
view!(
122+
header_small = (imp.header_small.clone()) {
123+
set_title_widget: Some(&(w = adw::WindowTitle {
124+
set_title: "Geopard",
125+
})),
126+
}
127+
header_bar = adw::HeaderBar {
128+
pack_start: &(b = gtk::Button {
129+
set_icon_name: "go-previous-symbolic",
130+
set_action_name: Some("win.back"),
131+
}),
132+
pack_start: &(b = gtk::Button {
133+
set_icon_name: "tab-new-symbolic",
134+
set_action_name: Some("win.new-tab"),
135+
}),
136+
pack_end: &(b = gtk::MenuButton {
137+
set_icon_name: "open-menu",
138+
set_menu_model: Some(&Self::build_menu_common()),
139+
}),
140+
set_title_widget: Some(&(c = adw::Clamp {
141+
set_child: Some(&(se = (imp.url_bar.clone()) {
142+
set_hexpand: true,
143+
connect_activate: |url_bar| {
144+
url_bar
145+
.activate_action("win.open-omni", Some(&url_bar.text().to_variant()))
146+
.unwrap();
147+
},
148+
})),
149+
set_maximum_size: 768,
150+
set_tightening_threshold: 720,
151+
})),
152+
}
153+
mobile_section = gio::Menu {
154+
append(Some("Back"), Some("win.back")),
155+
append(Some("New Tab"), Some("win.new-tab")),
156+
}
157+
bottom_bar = adw::HeaderBar {
158+
set_show_end_title_buttons: false,
159+
set_show_start_title_buttons: false,
160+
pack_start: &(b = gtk::Button {
161+
set_icon_name: "go-previous-symbolic",
162+
set_action_name: Some("win.back"),
163+
}),
164+
pack_start: &(b = gtk::Button {
165+
set_icon_name: "go-next-symbolic",
166+
set_action_name: Some("win.next"),
167+
}),
168+
pack_end: &(b = gtk::Button {
169+
set_icon_name: "tab-new-symbolic",
170+
set_action_name: Some("win.new-tab"),
171+
}),
172+
}
173+
tab_view = (imp.tab_view.clone()) {
174+
connect_selected_page_notify:
175+
clone!(@weak this => move |tab_view| this.page_switched(tab_view)),
176+
}
177+
content = gtk::Box {
178+
set_orientation: gtk::Orientation::Vertical,
179+
append: &(squeezer = (imp.squeezer.clone()) {
180+
add: &header_bar,
181+
add: &header_small,
182+
connect_visible_child_notify:
183+
clone!(@weak this => move |_| this.squeezer_changed()),
184+
}),
185+
append: &(tab_bar = adw::TabBar {
186+
set_view: Some(&tab_view),
187+
}),
188+
append: &(overlay = gtk::Overlay {
189+
set_child: Some(&tab_view),
190+
add_overlay: &imp.progress_bar,
191+
}),
192+
append: &imp.bottom_bar_revealer,
193+
}
194+
);
191195

192196
imp.bottom_entry.set_hexpand(true);
193-
194-
let bar_box = gtk::Box::new(gtk::Orientation::Horizontal, 8);
195-
bar_box.set_hexpand(true);
196-
bar_box.append(&imp.bottom_entry);
197-
bar_box.append(&bottom_menu);
198-
imp.bottom_bar.set_title_widget(Some(&bar_box));
199-
200-
imp.bottom_bar_revealer.set_child(Some(&imp.bottom_bar));
201-
202-
content.append(&imp.bottom_bar_revealer);
197+
imp.bottom_bar_revealer.set_child(Some(&bottom_bar));
203198

204199
this.set_default_size(800, 600);
205200
this.set_content(Some(&content));
206201
this.squeezer_changed();
207202

208-
this.bind_signals();
209203
this.setup_actions();
210204
this.open_in_new_tab(bookmarks_url().as_str());
211205
this
212206
}
213207

214208
fn build_menu_common() -> gio::Menu {
215-
let menu_model = gio::Menu::new();
216-
217-
let menu_model_bookmarks = gio::Menu::new();
218-
menu_model_bookmarks.append(Some("All Bookmarks"), Some("win.show-bookmarks"));
219-
menu_model_bookmarks.append(Some("Add Bookmark"), Some("win.bookmark-current"));
220-
menu_model.insert_section(0, None, &menu_model_bookmarks);
221-
222-
let menu_model_about = gio::Menu::new();
223-
menu_model_about.append(Some("Keyboard Shortcuts"), Some("win.shortcuts"));
224-
menu_model_about.append(Some("About"), Some("win.about"));
225-
menu_model_about.append(Some("Donate 💝"), Some("win.donate"));
226-
menu_model.insert_section(1, None, &menu_model_about);
209+
view!(
210+
bookmarks = gio::Menu {
211+
append(Some("All Bookmarks"), Some("win.show-bookmarks")),
212+
append(Some("Add Bookmark"), Some("win.bookmark-current")),
213+
}
214+
about = gio::Menu {
215+
append(Some("Keyboard Shortcuts"), Some("win.shortcuts")),
216+
append(Some("About"), Some("win.about")),
217+
append(Some("Donate 💝"), Some("win.donate")),
218+
}
219+
menu_model = gio::Menu {
220+
append_section(None, &bookmarks),
221+
append_section(None, &about),
222+
}
223+
);
227224
menu_model
228225
}
229226
fn setup_actions(&self) {
@@ -429,30 +426,11 @@ impl Window {
429426
.visible_child()
430427
.map(|child| child.downcast().ok())
431428
.flatten()
432-
.map(|w: adw::HeaderBar| w == self.imp().flat_header)
429+
.map(|w: adw::HeaderBar| w == self.imp().header_small)
433430
.unwrap_or(false);
434431

435432
imp.bottom_bar_revealer.set_reveal_child(title_visible);
436433
}
437-
fn bind_signals(&self) {
438-
let imp = self.imp();
439-
imp.url_bar.connect_activate(|url_bar| {
440-
url_bar
441-
.activate_action("win.open-omni", Some(&url_bar.text().to_variant()))
442-
.unwrap();
443-
});
444-
imp.back_btn.set_action_name(Some("win.back"));
445-
imp.add_tab_btn.set_action_name(Some("win.new-tab"));
446-
imp.tab_view.connect_selected_page_notify(
447-
clone!(@weak self as this => move |tab_view| this.page_switched(tab_view)),
448-
);
449-
let is_window_title_visible = |_: &glib::Binding, child: &glib::Value| {
450-
dbg!(&child);
451-
};
452-
imp.squeezer.connect_visible_child_notify(
453-
clone!(@weak self as this => move |_| this.squeezer_changed()),
454-
);
455-
}
456434
fn present_shortcuts(&self) {
457435
let builder = gtk::Builder::from_string(
458436
r#"

0 commit comments

Comments
 (0)