18 changed files with 679 additions and 75 deletions
@ -0,0 +1,14 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<gresources> |
||||
<gresource prefix="/org/gnome/FractalNext/"> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="shortcuts.ui">resources/ui/shortcuts.ui</file> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="content.ui">resources/ui/content.ui</file> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="login.ui">resources/ui/login.ui</file> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="session.ui">resources/ui/session.ui</file> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="sidebar.ui">resources/ui/sidebar.ui</file> |
||||
<file compressed="true" preprocess="xml-stripblanks" alias="window.ui">resources/ui/window.ui</file> |
||||
|
||||
<file compressed="true" alias="style.css">resources/style.css</file> |
||||
<file preprocess="xml-stripblanks" alias="icons/scalable/actions/send-symbolic.svg">resources/icons/scalable/actions/send-symbolic.svg</file> |
||||
</gresource> |
||||
</gresources> |
||||
|
After Width: | Height: | Size: 1.5 KiB |
@ -1,4 +1,16 @@
|
||||
.title-header{ |
||||
.title-header { |
||||
font-size: 36px; |
||||
font-weight: bold; |
||||
} |
||||
|
||||
.content { |
||||
background-color: @theme_base_color; |
||||
} |
||||
|
||||
.content:backdrop { |
||||
background-color: @theme_unfocused_base_color; |
||||
} |
||||
|
||||
.send-message-area { |
||||
margin: 6px; |
||||
} |
||||
|
||||
@ -0,0 +1,88 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<interface> |
||||
<template class="FrctlContent" parent="AdwBin"> |
||||
<property name="vexpand">True</property> |
||||
<property name="hexpand">True</property> |
||||
<child> |
||||
<object class="GtkBox"> |
||||
<property name="orientation">vertical</property> |
||||
<child> |
||||
<object class="AdwHeaderBar" id="headerbar"> |
||||
<property name="show-start-title-buttons" bind-source="FrctlContent" bind-property="compact" bind-flags="sync-create" /> |
||||
<child type="end"> |
||||
<object class="GtkMenuButton" id="room_menu"> |
||||
<property name="icon-name">view-more-symbolic</property> |
||||
</object> |
||||
</child> |
||||
<child type="end"> |
||||
<object class="GtkToggleButton" id="search_content_button"> |
||||
<property name="icon-name">system-search-symbolic</property> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkSearchBar" id="room_search"> |
||||
<property name="search-mode-enabled" bind-source="search_content_button" bind-property="active" /> |
||||
<property name="child"> |
||||
<object class="AdwClamp"> |
||||
<property name="hexpand">True</property> |
||||
<child> |
||||
<object class="GtkSearchEntry"/> |
||||
</child> |
||||
</object> |
||||
</property> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="AdwClamp"> |
||||
<property name="vexpand">True</property> |
||||
<property name="hexpand">True</property> |
||||
<style> |
||||
<class name="content"/> |
||||
</style> |
||||
<child> |
||||
<object class="GtkListView" id="room_history"> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkSeparator" /> |
||||
</child> |
||||
<child> |
||||
<object class="AdwClamp"> |
||||
<child> |
||||
<object class="GtkBox"> |
||||
<property name="spacing">6</property> |
||||
<style> |
||||
<class name="send-message-area"/> |
||||
</style> |
||||
<child> |
||||
<object class="GtkButton"> |
||||
<property name="icon-name">mail-attachment-symbolic</property> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkButton"> |
||||
<property name="icon-name">format-justify-left-symbolic</property> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkEntry" id="message_entry"> |
||||
<property name="hexpand">True</property> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkButton"> |
||||
<property name="icon-name">send-symbolic</property> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</template> |
||||
</interface> |
||||
@ -0,0 +1,18 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<interface> |
||||
<template class="FrctlLogin" parent="AdwBin"> |
||||
<child> |
||||
<object class="GtkBox"> |
||||
<property name="orientation">vertical</property> |
||||
<child> |
||||
<object class="GtkHeaderBar" id="headerbar" /> |
||||
</child> |
||||
<child> |
||||
<object class="AdwStatusPage"> |
||||
<!-- TODO implement login --> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</template> |
||||
</interface> |
||||
@ -0,0 +1,19 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<interface> |
||||
<template class="FrctlSession" parent="AdwBin"> |
||||
<child> |
||||
<object class="AdwLeaflet" id="session"> |
||||
<child> |
||||
<object class="FrctlSidebar" id="sidebar"> |
||||
<property name="compact" bind-source="session" bind-property="folded" bind-flags="sync-create" /> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="FrctlContent" id="content"> |
||||
<property name="compact" bind-source="session" bind-property="folded" bind-flags="sync-create" /> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</template> |
||||
</interface> |
||||
@ -0,0 +1,56 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?> |
||||
<interface> |
||||
<menu id="primary_menu"> |
||||
<section> |
||||
<item> |
||||
<attribute name="label" translatable="yes">_Preferences</attribute> |
||||
<attribute name="action">app.preferences</attribute> |
||||
</item> |
||||
<item> |
||||
<attribute name="label" translatable="yes">_Keyboard Shortcuts</attribute> |
||||
<attribute name="action">win.show-help-overlay</attribute> |
||||
</item> |
||||
<item> |
||||
<attribute name="label" translatable="yes">_About Fractal</attribute> |
||||
<attribute name="action">app.about</attribute> |
||||
</item> |
||||
</section> |
||||
</menu> |
||||
<template class="FrctlSidebar" parent="AdwBin"> |
||||
<style> |
||||
<class name="sidebar"/> |
||||
</style> |
||||
<child> |
||||
<object class="GtkBox"> |
||||
<property name="orientation">vertical</property> |
||||
<child> |
||||
<object class="AdwHeaderBar" id="headerbar"> |
||||
<property name="show-end-title-buttons" bind-source="FrctlSidebar" bind-property="compact" bind-flags="sync-create" /> |
||||
<child type="start"> |
||||
<object class="GtkToggleButton" id="search_button"> |
||||
<property name="icon-name">system-search-symbolic</property> |
||||
</object> |
||||
</child> |
||||
<child type="end"> |
||||
<object class="GtkMenuButton" id="appmenu_button"> |
||||
<property name="icon-name">open-menu-symbolic</property> |
||||
<property name="menu-model">primary_menu</property> |
||||
</object> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkSearchBar" id="room_search"> |
||||
<property name="search-mode-enabled" bind-source="search_button" bind-property="active" /> |
||||
<property name="child"> |
||||
<object class="GtkSearchEntry"/> |
||||
</property> |
||||
</object> |
||||
</child> |
||||
<child> |
||||
<object class="GtkListView" id="listview" /> |
||||
</child> |
||||
</object> |
||||
</child> |
||||
</template> |
||||
</interface> |
||||
@ -0,0 +1,110 @@
|
||||
use adw; |
||||
use adw::subclass::prelude::BinImpl; |
||||
use gtk::subclass::prelude::*; |
||||
use gtk::{self, prelude::*}; |
||||
use gtk::{glib, CompositeTemplate}; |
||||
|
||||
mod imp { |
||||
use super::*; |
||||
use glib::subclass; |
||||
use std::cell::Cell; |
||||
|
||||
#[derive(Debug, CompositeTemplate)] |
||||
#[template(resource = "/org/gnome/FractalNext/content.ui")] |
||||
pub struct FrctlContent { |
||||
pub compact: Cell<bool>, |
||||
#[template_child] |
||||
pub headerbar: TemplateChild<adw::HeaderBar>, |
||||
#[template_child] |
||||
pub room_history: TemplateChild<gtk::ListView>, |
||||
} |
||||
|
||||
impl ObjectSubclass for FrctlContent { |
||||
const NAME: &'static str = "FrctlContent"; |
||||
type Type = super::FrctlContent; |
||||
type ParentType = adw::Bin; |
||||
type Interfaces = (); |
||||
type Instance = subclass::simple::InstanceStruct<Self>; |
||||
type Class = subclass::simple::ClassStruct<Self>; |
||||
|
||||
glib::object_subclass!(); |
||||
|
||||
fn new() -> Self { |
||||
Self { |
||||
compact: Cell::new(false), |
||||
headerbar: TemplateChild::default(), |
||||
room_history: TemplateChild::default(), |
||||
} |
||||
} |
||||
|
||||
fn class_init(klass: &mut Self::Class) { |
||||
Self::bind_template(klass); |
||||
} |
||||
|
||||
// You must call `Widget`'s `init_template()` within `instance_init()`.
|
||||
fn instance_init(obj: &glib::subclass::InitializingObject<Self::Type>) { |
||||
obj.init_template(); |
||||
} |
||||
} |
||||
|
||||
impl ObjectImpl for FrctlContent { |
||||
fn properties() -> &'static [glib::ParamSpec] { |
||||
use once_cell::sync::Lazy; |
||||
static PROPERTIES: Lazy<Vec<glib::ParamSpec>> = Lazy::new(|| { |
||||
vec![glib::ParamSpec::boolean( |
||||
"compact", |
||||
"Compact", |
||||
"Wheter a compact view is used or not", |
||||
false, |
||||
glib::ParamFlags::READWRITE, |
||||
)] |
||||
}); |
||||
|
||||
PROPERTIES.as_ref() |
||||
} |
||||
|
||||
fn set_property( |
||||
&self, |
||||
_obj: &Self::Type, |
||||
_id: usize, |
||||
value: &glib::Value, |
||||
pspec: &glib::ParamSpec, |
||||
) { |
||||
match pspec.get_name() { |
||||
"compact" => { |
||||
let compact = value |
||||
.get() |
||||
.expect("type conformity checked by `Object::set_property`"); |
||||
self.compact.set(compact.unwrap()); |
||||
} |
||||
_ => unimplemented!(), |
||||
} |
||||
} |
||||
|
||||
fn get_property( |
||||
&self, |
||||
_obj: &Self::Type, |
||||
_id: usize, |
||||
pspec: &glib::ParamSpec, |
||||
) -> glib::Value { |
||||
match pspec.get_name() { |
||||
"compact" => self.compact.get().to_value(), |
||||
_ => unimplemented!(), |
||||
} |
||||
} |
||||
} |
||||
|
||||
impl WidgetImpl for FrctlContent {} |
||||
impl BinImpl for FrctlContent {} |
||||
} |
||||
|
||||
glib::wrapper! { |
||||
pub struct FrctlContent(ObjectSubclass<imp::FrctlContent>) |
||||
@extends gtk::Widget, adw::Bin, @implements gtk::Accessible; |
||||
} |
||||
|
||||
impl FrctlContent { |
||||
pub fn new() -> Self { |
||||
glib::Object::new(&[]).expect("Failed to create FrctlContent") |
||||
} |
||||
} |
||||
@ -0,0 +1,58 @@
|
||||
use adw; |
||||
use adw::subclass::prelude::BinImpl; |
||||
use gtk::subclass::prelude::*; |
||||
use gtk::{self, prelude::*}; |
||||
use gtk::{glib, CompositeTemplate}; |
||||
|
||||
mod imp { |
||||
use super::*; |
||||
use glib::subclass; |
||||
|
||||
#[derive(Debug, CompositeTemplate)] |
||||
#[template(resource = "/org/gnome/FractalNext/login.ui")] |
||||
pub struct FrctlLogin { |
||||
#[template_child] |
||||
pub headerbar: TemplateChild<gtk::HeaderBar>, |
||||
} |
||||
|
||||
impl ObjectSubclass for FrctlLogin { |
||||
const NAME: &'static str = "FrctlLogin"; |
||||
type Type = super::FrctlLogin; |
||||
type ParentType = adw::Bin; |
||||
type Interfaces = (); |
||||
type Instance = subclass::simple::InstanceStruct<Self>; |
||||
type Class = subclass::simple::ClassStruct<Self>; |
||||
|
||||
glib::object_subclass!(); |
||||
|
||||
fn new() -> Self { |
||||
Self { |
||||
headerbar: TemplateChild::default(), |
||||
} |
||||
} |
||||
|
||||
fn class_init(klass: &mut Self::Class) { |
||||
Self::bind_template(klass); |
||||
} |
||||
|
||||
// You must call `Widget`'s `init_template()` within `instance_init()`.
|
||||
fn instance_init(obj: &glib::subclass::InitializingObject<Self::Type>) { |
||||
obj.init_template(); |
||||
} |
||||
} |
||||
|
||||
impl ObjectImpl for FrctlLogin {} |
||||
impl WidgetImpl for FrctlLogin {} |
||||
impl BinImpl for FrctlLogin {} |
||||
} |
||||
|
||||
glib::wrapper! { |
||||
pub struct FrctlLogin(ObjectSubclass<imp::FrctlLogin>) |
||||
@extends gtk::Widget, adw::Bin, @implements gtk::Accessible; |
||||
} |
||||
|
||||
impl FrctlLogin { |
||||
pub fn new() -> Self { |
||||
glib::Object::new(&[]).expect("Failed to create FrctlLogin") |
||||
} |
||||
} |
||||
@ -0,0 +1,11 @@
|
||||
mod content; |
||||
mod login; |
||||
mod session; |
||||
mod sidebar; |
||||
mod window; |
||||
|
||||
pub use crate::widgets::content::FrctlContent; |
||||
pub use crate::widgets::login::FrctlLogin; |
||||
pub use crate::widgets::session::FrctlSession; |
||||
pub use crate::widgets::sidebar::FrctlSidebar; |
||||
pub use crate::widgets::window::FrctlWindow; |
||||
@ -0,0 +1,63 @@
|
||||
use crate::widgets::FrctlContent; |
||||
use crate::widgets::FrctlSidebar; |
||||
use adw; |
||||
use adw::subclass::prelude::BinImpl; |
||||
use gtk::subclass::prelude::*; |
||||
use gtk::{self, prelude::*}; |
||||
use gtk::{glib, CompositeTemplate}; |
||||
|
||||
mod imp { |
||||
use super::*; |
||||
use glib::subclass; |
||||
|
||||
#[derive(Debug, CompositeTemplate)] |
||||
#[template(resource = "/org/gnome/FractalNext/session.ui")] |
||||
pub struct FrctlSession { |
||||
#[template_child] |
||||
pub sidebar: TemplateChild<FrctlSidebar>, |
||||
#[template_child] |
||||
pub content: TemplateChild<FrctlContent>, |
||||
} |
||||
|
||||
impl ObjectSubclass for FrctlSession { |
||||
const NAME: &'static str = "FrctlSession"; |
||||
type Type = super::FrctlSession; |
||||
type ParentType = adw::Bin; |
||||
type Interfaces = (); |
||||
type Instance = subclass::simple::InstanceStruct<Self>; |
||||
type Class = subclass::simple::ClassStruct<Self>; |
||||
|
||||
glib::object_subclass!(); |
||||
|
||||
fn new() -> Self { |
||||
Self { |
||||
sidebar: TemplateChild::default(), |
||||
content: TemplateChild::default(), |
||||
} |
||||
} |
||||
|
||||
fn class_init(klass: &mut Self::Class) { |
||||
Self::bind_template(klass); |
||||
} |
||||
|
||||
// You must call `Widget`'s `init_template()` within `instance_init()`.
|
||||
fn instance_init(obj: &glib::subclass::InitializingObject<Self::Type>) { |
||||
obj.init_template(); |
||||
} |
||||
} |
||||
|
||||
impl ObjectImpl for FrctlSession {} |
||||
impl WidgetImpl for FrctlSession {} |
||||
impl BinImpl for FrctlSession {} |
||||
} |
||||
|
||||
glib::wrapper! { |
||||
pub struct FrctlSession(ObjectSubclass<imp::FrctlSession>) |
||||
@extends gtk::Widget, adw::Bin, @implements gtk::Accessible; |
||||
} |
||||
|
||||
impl FrctlSession { |
||||
pub fn new() -> Self { |
||||
glib::Object::new(&[]).expect("Failed to create FrctlSession") |
||||
} |
||||
} |
||||
@ -0,0 +1,110 @@
|
||||
use adw; |
||||
use adw::subclass::prelude::BinImpl; |
||||
use gtk::subclass::prelude::*; |
||||
use gtk::{self, prelude::*}; |
||||
use gtk::{glib, CompositeTemplate}; |
||||
|
||||
mod imp { |
||||
use super::*; |
||||
use glib::subclass; |
||||
use std::cell::Cell; |
||||
|
||||
#[derive(Debug, CompositeTemplate)] |
||||
#[template(resource = "/org/gnome/FractalNext/sidebar.ui")] |
||||
pub struct FrctlSidebar { |
||||
pub compact: Cell<bool>, |
||||
#[template_child] |
||||
pub headerbar: TemplateChild<adw::HeaderBar>, |
||||
#[template_child] |
||||
pub listview: TemplateChild<gtk::ListView>, |
||||
} |
||||
|
||||
impl ObjectSubclass for FrctlSidebar { |
||||
const NAME: &'static str = "FrctlSidebar"; |
||||
type Type = super::FrctlSidebar; |
||||
type ParentType = adw::Bin; |
||||
type Interfaces = (); |
||||
type Instance = subclass::simple::InstanceStruct<Self>; |
||||
type Class = subclass::simple::ClassStruct<Self>; |
||||
|
||||
glib::object_subclass!(); |
||||
|
||||
fn new() -> Self { |
||||
Self { |
||||
compact: Cell::new(false), |
||||
listview: TemplateChild::default(), |
||||
headerbar: TemplateChild::default(), |
||||
} |
||||
} |
||||
|
||||
fn class_init(klass: &mut Self::Class) { |
||||
Self::bind_template(klass); |
||||
} |
||||
|
||||
// You must call `Widget`'s `init_template()` within `instance_init()`.
|
||||
fn instance_init(obj: &glib::subclass::InitializingObject<Self::Type>) { |
||||
obj.init_template(); |
||||
} |
||||
} |
||||
|
||||
impl ObjectImpl for FrctlSidebar { |
||||
fn properties() -> &'static [glib::ParamSpec] { |
||||
use once_cell::sync::Lazy; |
||||
static PROPERTIES: Lazy<Vec<glib::ParamSpec>> = Lazy::new(|| { |
||||
vec![glib::ParamSpec::boolean( |
||||
"compact", |
||||
"Compact", |
||||
"Wheter a compact view is used or not", |
||||
false, |
||||
glib::ParamFlags::READWRITE, |
||||
)] |
||||
}); |
||||
|
||||
PROPERTIES.as_ref() |
||||
} |
||||
|
||||
fn set_property( |
||||
&self, |
||||
_obj: &Self::Type, |
||||
_id: usize, |
||||
value: &glib::Value, |
||||
pspec: &glib::ParamSpec, |
||||
) { |
||||
match pspec.get_name() { |
||||
"compact" => { |
||||
let compact = value |
||||
.get() |
||||
.expect("type conformity checked by `Object::set_property`"); |
||||
self.compact.set(compact.unwrap()); |
||||
} |
||||
_ => unimplemented!(), |
||||
} |
||||
} |
||||
|
||||
fn get_property( |
||||
&self, |
||||
_obj: &Self::Type, |
||||
_id: usize, |
||||
pspec: &glib::ParamSpec, |
||||
) -> glib::Value { |
||||
match pspec.get_name() { |
||||
"compact" => self.compact.get().to_value(), |
||||
_ => unimplemented!(), |
||||
} |
||||
} |
||||
} |
||||
|
||||
impl WidgetImpl for FrctlSidebar {} |
||||
impl BinImpl for FrctlSidebar {} |
||||
} |
||||
|
||||
glib::wrapper! { |
||||
pub struct FrctlSidebar(ObjectSubclass<imp::FrctlSidebar>) |
||||
@extends gtk::Widget, adw::Bin, @implements gtk::Accessible; |
||||
} |
||||
|
||||
impl FrctlSidebar { |
||||
pub fn new() -> Self { |
||||
glib::Object::new(&[]).expect("Failed to create FrctlSidebar") |
||||
} |
||||
} |
||||
Loading…
Reference in new issue