This commit is contained in:
bleakgrey 2018-05-05 18:38:01 +03:00
parent fc5b92257f
commit ce6c0f8760
16 changed files with 83 additions and 77 deletions

View File

@ -1,4 +1,4 @@
public class Tootle.Status{
public class Tootle.Status {
public abstract signal void updated ();

View File

@ -6,7 +6,7 @@ public class Tootle.AccountManager : Object{
public abstract signal void added(Account account);
public abstract signal void removed(Account account);
public Account current;
public Account? current;
public AccountManager(){
Object();

View File

@ -13,8 +13,9 @@ namespace Tootle{
public class Application : Granite.Application {
public abstract signal void toast(string title);
public abstract signal void error(string title, string text);
public abstract signal void refresh ();
public abstract signal void toast (string title);
public abstract signal void error (string title, string text);
construct {
application_id = "com.github.bleakgrey.tootle";

View File

@ -3,10 +3,10 @@ using GLib;
public class Tootle.CacheManager : GLib.Object{
private static string path_images;
private static string path_downloads;
construct{
path_images = GLib.Environment.get_user_special_dir (UserDirectory.DOWNLOAD);
path_downloads = GLib.Environment.get_user_special_dir (UserDirectory.DOWNLOAD);
}
//TODO: actually cache images
@ -23,7 +23,7 @@ public class Tootle.CacheManager : GLib.Object{
loader.close();
avatar.pixbuf = loader.get_pixbuf ();
});
Tootle.network.queue(msg, (sess, mess) => {});
Tootle.network.queue(msg);
}
public void load_image (string url, Gtk.Image image){
@ -34,7 +34,7 @@ public class Tootle.CacheManager : GLib.Object{
loader.close();
image.set_from_pixbuf (loader.get_pixbuf ());
});
Tootle.network.queue(msg, (sess, mess) => {});
Tootle.network.queue(msg);
}
}

View File

@ -137,7 +137,7 @@ public class Tootle.PostDialog : Gtk.Dialog {
try{
var root = Tootle.network.parse (mess);
var status = Status.parse (root);
Tootle.window.home.prepend (status);
debug (status.id.to_string ()); //TODO: Live updates
this.destroy ();
}
catch (GLib.Error e) {

View File

@ -7,11 +7,6 @@ public class Tootle.MainWindow: Gtk.Window {
public Tootle.HeaderBar header;
public Stack primary_stack;
public Stack secondary_stack;
public HomeView home = new HomeView ();
public LocalView feed_local = new LocalView ();
public FederatedView feed_federated = new FederatedView ();
public NotificationsView notifications = new NotificationsView ();
construct {
var provider = new Gtk.CssProvider ();
@ -57,45 +52,45 @@ public class Tootle.MainWindow: Gtk.Window {
Tootle.accounts.init ();
}
private void on_account_switched(Account? account){
secondary_stack.forall (widget => secondary_stack.remove (widget));
if(account == null)
show_setup_views ();
else
show_main_views ();
private void reset () {
header.button_mode.clear_children ();
secondary_stack.forall (widget => widget.destroy ());
}
private void show_setup_views (){
private void on_account_switched(Account? account = Tootle.accounts.current){
reset ();
if(account == null)
build_setup_view ();
else
build_main_view ();
}
private void build_setup_view (){
var add_account = new AddAccountView ();
secondary_stack.add_named (add_account, add_account.get_name ());
header.update (false, true);
}
private void show_main_views (){
header.button_mode.clear_children ();
add_view (home);
add_view (notifications);
add_view (feed_local);
add_view (feed_federated);
header.button_mode.set_active (0);
private void build_main_view (){
add_header_view (new HomeView ());
add_header_view (new NotificationsView ());
add_header_view (new LocalView ());
add_header_view (new FederatedView ());
header.update (true);
}
private void add_view (AbstractView view) {
if (view.show_in_header){
var img = new Gtk.Image.from_icon_name(view.get_icon (), Gtk.IconSize.LARGE_TOOLBAR);
img.tooltip_text = view.get_name ();
header.button_mode.append (img);
view.image = img;
secondary_stack.add_named(view, view.get_name ());
if (view is NotificationsView)
img.pixel_size = 20; // For some reason Notifications icon is too small without this
}
private void add_header_view (AbstractView view) {
var img = new Gtk.Image.from_icon_name(view.get_icon (), Gtk.IconSize.LARGE_TOOLBAR);
img.tooltip_text = view.get_name ();
header.button_mode.append (img);
view.image = img;
secondary_stack.add_named(view, view.get_name ());
if (view is NotificationsView)
img.pixel_size = 20; // For some reason Notifications icon is too small without this
}
public void open_secondary_view (Widget widget) {
public void open_view (Widget widget) {
widget.show ();
var i = int.parse (primary_stack.get_visible_child_name ());
i++;

View File

@ -6,7 +6,6 @@ public class Tootle.NetManager : GLib.Object {
public abstract signal void started();
public abstract signal void finished();
public abstract signal void refresh();
private int requests_processing = 0;
private Soup.Session session;
@ -16,11 +15,15 @@ public class Tootle.NetManager : GLib.Object {
session.ssl_strict = true;
session.ssl_use_system_ca_file = true;
session.timeout = 20;
session.max_conns = 15;
session.request_unqueued.connect (() => {
requests_processing--;
if(requests_processing <= 0)
finished ();
});
// Soup.Logger logger = new Soup.Logger (Soup.LoggerLogLevel.MINIMAL, -1);
// session.add_feature (logger);
}
public NetManager() {

View File

@ -3,7 +3,6 @@ using Gtk;
public abstract class Tootle.AbstractView : Gtk.ScrolledWindow {
public int64 max_id = -1;
public bool show_in_header;
public Gtk.Image image;
public Gtk.Box view;
@ -21,8 +20,7 @@ public abstract class Tootle.AbstractView : Gtk.ScrolledWindow {
pre_construct ();
}
public AbstractView (bool show) {
show_in_header = show;
public AbstractView () {
show_all ();
}

View File

@ -99,7 +99,6 @@ public class Tootle.AccountView : Tootle.HomeView {
}
public AccountView (Account acc) {
base ("account_"+acc.id.to_string ());
account = acc;
account.updated.connect(rebind);
@ -177,16 +176,20 @@ public class Tootle.AccountView : Tootle.HomeView {
return status.get_formal ().account.id == account.id;
}
public override string get_url (){
public override string get_url () {
var url = "%s/api/v1/accounts/%lld/statuses".printf (Tootle.settings.instance_url, account.id);
url += "?limit=25";
if (max_id > 0)
url += "&max_id=" + max_id.to_string ();
url += "&max_id=" + max_id.to_string ();
return url;
}
public override void request (){
if(account != null)
base.request ();
}
public static void open_from_id (int64 id){
var url = "%s/api/v1/accounts/%lld".printf (Tootle.settings.instance_url, id);
var msg = new Soup.Message("GET", url);
@ -195,7 +198,7 @@ public class Tootle.AccountView : Tootle.HomeView {
try{
var root = Tootle.network.parse (mess);
var acc = Account.parse (root);
Tootle.window.open_secondary_view (new AccountView (acc));
Tootle.window.open_view (new AccountView (acc));
}
catch (GLib.Error e) {
warning ("Can't update feed");
@ -214,7 +217,7 @@ public class Tootle.AccountView : Tootle.HomeView {
var object = node.get_object ();
if (object != null){
var acc = Account.parse(object);
Tootle.window.open_secondary_view (new AccountView (acc));
Tootle.window.open_view (new AccountView (acc));
}
else
warning ("No results found for account: "+name); //TODO: toast notifications

View File

@ -110,7 +110,7 @@ public class Tootle.AddAccountView : Tootle.AbstractView {
}
public AddAccountView () {
base (false);
base ();
}
public override string get_name () {

View File

@ -6,16 +6,17 @@ public class Tootle.HomeView : Tootle.AbstractView {
private string timeline;
public HomeView (string timeline = "home") {
base (true);
base ();
this.timeline = timeline;
view.remove.connect (on_remove);
Tootle.accounts.switched.connect(on_account_changed);
Tootle.network.refresh.connect(on_refresh);
Tootle.app.refresh.connect(on_refresh);
// var s = new Status(1);
// s.content = "Test content, wow!";
// prepend (s);
request ();
}
public override string get_icon () {
@ -50,7 +51,7 @@ public class Tootle.HomeView : Tootle.AbstractView {
//TODO: empty state
}
public virtual string get_url (){
public virtual string get_url () {
var url = Tootle.settings.instance_url;
url += "api/v1/timelines/";
url += this.timeline;
@ -62,7 +63,7 @@ public class Tootle.HomeView : Tootle.AbstractView {
return url;
}
public void request (){
public virtual void request (){
var msg = new Soup.Message("GET", get_url ());
Tootle.network.queue(msg, (sess, mess) => {
try{
@ -90,8 +91,8 @@ public class Tootle.HomeView : Tootle.AbstractView {
public virtual void on_account_changed (Account? account){
if(account == null)
return;
clear ();
request ();
on_refresh ();
}
public override void bottom_reached (){

View File

@ -4,11 +4,13 @@ using Gdk;
public class Tootle.NotificationsView : Tootle.AbstractView {
public NotificationsView () {
base (true);
base ();
view.remove.connect (on_remove);
Tootle.accounts.switched.connect(on_account_changed);
Tootle.network.refresh.connect(on_refresh);
Tootle.app.refresh.connect(on_refresh);
request ();
}
public override string get_icon () {
@ -46,9 +48,8 @@ public class Tootle.NotificationsView : Tootle.AbstractView {
public virtual void on_account_changed (Account? account){
if(account == null)
return;
clear ();
request ();
on_refresh ();
}
public void request (){

View File

@ -6,7 +6,7 @@ public class Tootle.StatusView : Tootle.AbstractView {
bool last_was_a_root = false;
public StatusView (Status status) {
base (false);
base ();
root_status = status;
request_context ();
}

View File

@ -54,11 +54,11 @@ public class Tootle.AccountsButton : Gtk.MenuButton{
item_refresh = new Gtk.ModelButton ();
item_refresh.text = _("Refresh");
item_refresh.clicked.connect (() => Tootle.network.refresh ());
item_refresh.clicked.connect (() => Tootle.app.refresh ());
item_favs = new Gtk.ModelButton ();
item_favs.text = _("Favorites");
item_favs.clicked.connect (() => Tootle.window.open_secondary_view (new FavoritesView ()));
item_favs.clicked.connect (() => Tootle.window.open_view (new FavoritesView ()));
item_settings = new Gtk.ModelButton ();
item_settings.text = _("Settings");

View File

@ -8,6 +8,8 @@ public class Tootle.HeaderBar : Gtk.HeaderBar{
Button button_toot;
Button button_back;
private int last_tab = 0;
construct {
spinner = new Spinner ();
spinner.active = true;
@ -39,6 +41,7 @@ public class Tootle.HeaderBar : Gtk.HeaderBar{
button_mode = new Granite.Widgets.ModeButton ();
button_mode.get_style_context ().add_class ("mode");
button_mode.mode_changed.connect(widget => {
last_tab = button_mode.selected;
Tootle.window.secondary_stack.set_visible_child_name(widget.tooltip_text);
});
button_mode.show ();
@ -60,6 +63,7 @@ public class Tootle.HeaderBar : Gtk.HeaderBar{
}
public void update (bool primary_mode, bool hide_all = false){
button_mode.set_active (last_tab);
if (hide_all){
button_mode.opacity = 0;
button_mode.sensitive = false;

View File

@ -120,7 +120,7 @@ public class Tootle.StatusWidget : Gtk.EventBox {
status.updated.connect (rebind);
get_style_context ().add_class ("status");
if (status.reblog != null){
if (status.reblog != null) {
var image = new Gtk.Image.from_icon_name("go-up-symbolic", Gtk.IconSize.SMALL_TOOLBAR);
image.halign = Gtk.Align.END;
image.margin_end = 6;
@ -137,7 +137,7 @@ public class Tootle.StatusWidget : Gtk.EventBox {
grid.attach (label, 2, 0, 2, 1);
}
if (is_spoiler ()){
if (is_spoiler ()) {
revealer.reveal_child = false;
var spoiler_box = new Box (Gtk.Orientation.HORIZONTAL, 6);
spoiler_box.margin_end = 12;
@ -184,12 +184,12 @@ public class Tootle.StatusWidget : Gtk.EventBox {
rebind ();
}
public void highlight (){
public void highlight () {
grid.get_style_context ().add_class ("card");
grid.margin_bottom = 6;
}
public void rebind (){
public void rebind () {
title_user.label = "<b>%s</b>".printf (status.get_formal ().account.display_name);
title_acct.label = "@" + status.account.acct;
content_label.label = status.content;
@ -209,13 +209,13 @@ public class Tootle.StatusWidget : Gtk.EventBox {
Tootle.cache.load_avatar (status.get_formal ().account.avatar, this.avatar, this.avatar_size);
}
public bool is_spoiler (){
public bool is_spoiler () {
return status.spoiler_text != null || status.sensitive;
}
// elementary OS has old GLib, so I have to improvise
// Version >=2.56 provides DateTime.from_iso8601
public void parse_date_iso8601 (string date){
public void parse_date_iso8601 (string date) {
var cmd = "date -d " + date + " +%s";
var runner = new CmdRunner ("/bin/", cmd); //Workaround for Granite SimpleCommand pipes bug
runner.done.connect (exit => {
@ -226,19 +226,19 @@ public class Tootle.StatusWidget : Gtk.EventBox {
runner.run ();
}
public bool on_avatar_clicked (){
public bool on_avatar_clicked () {
var view = new AccountView (status.get_formal ().account);
Tootle.window.open_secondary_view (view);
Tootle.window.open_view (view);
return true;
}
public bool open (){
public bool open () {
var view = new StatusView (status.get_formal ());
Tootle.window.open_secondary_view (view);
Tootle.window.open_view (view);
return false;
}
private Gtk.ToggleButton get_action_button (string icon_path){
private Gtk.ToggleButton get_action_button (string icon_path) {
var icon = new Gtk.Image.from_icon_name (icon_path, Gtk.IconSize.SMALL_TOOLBAR);
var button = new Gtk.ToggleButton ();
button.can_default = false;