Skip to content

Commit

Permalink
- Update ThemedDocumentControl/Page to support images and reordering
Browse files Browse the repository at this point in the history
- Add AllowReordering property to enable/disable reordering pages
- Support using DocumentControl.Enabled to disable the control completely (and not children)
- Property fire load/unload events by setting parent
  • Loading branch information
cwensley committed Sep 17, 2017
1 parent f1dcbf2 commit 4d81219
Show file tree
Hide file tree
Showing 7 changed files with 621 additions and 200 deletions.
95 changes: 78 additions & 17 deletions Source/Eto.Gtk/Forms/Controls/DocumentControlHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ namespace Eto.GtkSharp.Forms.Controls
public class DocumentControlHandler : GtkContainer<Gtk.Notebook, DocumentControl, DocumentControl.ICallback>, DocumentControl.IHandler
{
List<DocumentPage> pages;
bool allowReorder;
bool enabled = true;

public DocumentControlHandler()
{
Expand All @@ -24,10 +26,7 @@ protected override void Initialize()
Control.SwitchPage += Connector.HandleSwitchPage;
}

protected override bool IsTransparentControl
{
get { return false; }
}
protected override bool IsTransparentControl => false;

protected override Color DefaultBackgroundColor
{
Expand All @@ -43,13 +42,32 @@ protected override WeakConnector CreateConnector()

protected class DocumentControlConnector : GtkControlConnector
{
int oldIndex = -1;
public new DocumentControlHandler Handler { get { return (DocumentControlHandler)base.Handler; } }

public void HandleSwitchPage(object o, Gtk.SwitchPageArgs args)
{
var handler = Handler;
if (handler != null && handler.Widget.Loaded)
if (handler != null && handler.Enabled)
{
handler.Callback.OnSelectedIndexChanged(handler.Widget, EventArgs.Empty);
oldIndex = (int)args.PageNum;
}
else if (oldIndex >= 0)
{
handler.Control.Page = oldIndex;
}
}

public void HandlePageReordered(object o, Gtk.PageReorderedArgs args)
{
var handler = Handler;
if (handler != null && handler.Enabled)
{
var newIndex = (int)(uint)args.Args[1];
handler.Callback.OnPageReordered(handler.Widget, new DocumentPageReorderEventArgs(handler.GetPage(newIndex), oldIndex, newIndex));
oldIndex = newIndex;
}
}
}

Expand All @@ -59,6 +77,29 @@ public int SelectedIndex
set { Control.CurrentPage = value; }
}

public bool AllowReordering
{
get { return allowReorder; }
set
{
if (allowReorder != value)
{
allowReorder = value;
UpdateReorder();
}
}
}

void UpdateReorder()
{
foreach (var page in pages)
{
var pageHandler = (DocumentPageHandler)page.Handler;
Control.SetTabReorderable(pageHandler.ContainerControl, allowReorder && enabled);
pageHandler.LabelControl.Sensitive = enabled;
}
}

public void InsertPage(int index, DocumentPage page)
{
pages.Add(page);
Expand All @@ -68,33 +109,40 @@ public void InsertPage(int index, DocumentPage page)
if (Widget.Loaded)
{
pageHandler.ContainerControl.ShowAll();
pageHandler.LabelControl.ShowAll();
}

pageHandler.LabelControl.Sensitive = enabled;

if (index == -1)
Control.AppendPage(pageHandler.ContainerControl, pageHandler.LabelControl);
else
Control.InsertPage(pageHandler.ContainerControl, pageHandler.LabelControl, index);

pageHandler.closebutton1.Clicked += (o, args) => ClosePage(pageHandler.ContainerControl, page);
pageHandler.LabelControl.ButtonPressEvent += (o, args) =>
{
if (args.Event.Button == 2 && page.Closable)
ClosePage(pageHandler.ContainerControl, page);
};

Control.SetTabReorderable(pageHandler.ContainerControl, true);
Control.SetTabReorderable(pageHandler.ContainerControl, allowReorder && Enabled);
Control.ShowTabs = Control.NPages > 1;
}

private void ClosePage(Gtk.Widget control, DocumentPage page)
public override bool Enabled
{
get { return enabled; }
set
{
if (enabled != value)
{
enabled = value;
UpdateReorder();
}
}
}

internal void ClosePage(Gtk.Widget control, DocumentPage page)
{
Control.RemovePage(Control.PageNum(control));
Control.ShowTabs = Control.NPages > 1;

var handler = Connector.Handler;
if (handler != null && handler.Widget.Loaded)
handler.Callback.OnPageClosed(handler.Widget, new DocumentPageEventArgs(page));
if (Widget.Loaded)
Callback.OnPageClosed(Widget, new DocumentPageEventArgs(page));
}

public void RemovePage(int index)
Expand All @@ -118,5 +166,18 @@ public int GetPageCount()
{
return Control.NPages;
}

public override void AttachEvent(string id)
{
switch (id)
{
case DocumentControl.PageReorderedEvent:
Control.PageReordered += Connector.HandlePageReordered;
break;
default:
base.AttachEvent(id);
break;
}
}
}
}
38 changes: 22 additions & 16 deletions Source/Eto.Gtk/Forms/Controls/DocumentPageHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,44 +8,50 @@ namespace Eto.GtkSharp.Forms.Controls
public class DocumentPageHandler : GtkPanel<Gtk.VBox, DocumentPage, DocumentPage.ICallback>, DocumentPage.IHandler
{
Gtk.Label label;
internal Gtk.Button closebutton1;
readonly Gtk.EventBox eventBox1;

internal Gtk.Button closeButton;
readonly Gtk.HBox tab;
Gtk.Image gtkimage;
Image image;
public static Size MaxImageSize = new Size(16, 16);

DocumentControlHandler Parent => Widget.LogicalParent?.Handler as DocumentControlHandler;

public DocumentPageHandler()
{
Control = new Gtk.VBox();
eventBox1 = new Gtk.EventBox();
tab = new Gtk.HBox();
closebutton1 = new Gtk.Button();
closebutton1.Relief = Gtk.ReliefStyle.None;
closebutton1.CanFocus = false;
closeButton = new Gtk.Button();
closeButton.Relief = Gtk.ReliefStyle.None;
closeButton.CanFocus = false;

#if GTK3
tab.Expand = true;
closebutton1.Image = new Gtk.Image(Gtk.IconTheme.Default.LoadIcon("window-close", 12, Gtk.IconLookupFlags.ForceSize));
closeButton.Image = new Gtk.Image(Gtk.IconTheme.Default.LoadIcon("window-close", 12, Gtk.IconLookupFlags.ForceSize));
#else
closebutton1.Image = new Gtk.Image(Gtk.IconTheme.Default.LoadIcon("window-close", 12, 0));
closeButton.Image = new Gtk.Image(Gtk.IconTheme.Default.LoadIcon("window-close", 12, 0));
#endif

tab.PackEnd(closebutton1, false, true, 0);
tab.PackEnd(closeButton, false, true, 0);
label = new Gtk.Label();
label.SetAlignment(0.5f, 0.5f);
tab.PackEnd(label, true, true, 0);

eventBox1.Child = tab;
eventBox1.ShowAll();

tab.SizeAllocated += Tab_SizeAllocated;
tab.ShowAll();

closeButton.Clicked += (o, args) => Parent?.ClosePage(ContainerControl, Widget);
tab.ButtonPressEvent += (o, args) =>
{
if (args.Event.Button == 2 && Closable)
Parent?.ClosePage(ContainerControl, Widget);
};
}

private void Tab_SizeAllocated(object o, Gtk.SizeAllocatedArgs args)
{
var imagewidth = (gtkimage != null) ? gtkimage.Allocation.Width : 0;
var closewidth = (closebutton1.Visible) ? closebutton1.Allocation.Width : 0;
var closewidth = (closeButton.Visible) ? closeButton.Allocation.Width : 0;
var width = (float)label.Allocation.Width / (label.Allocation.Width - Math.Abs(closewidth - imagewidth));

if (imagewidth >= closewidth)
Expand All @@ -56,7 +62,7 @@ private void Tab_SizeAllocated(object o, Gtk.SizeAllocatedArgs args)

public Gtk.Widget LabelControl
{
get { return eventBox1; }
get { return tab; }
}

protected override void SetContainerContent(Gtk.Widget content)
Expand All @@ -66,8 +72,8 @@ protected override void SetContainerContent(Gtk.Widget content)

public bool Closable
{
get { return closebutton1.Visible; }
set { closebutton1.Visible = value; }
get { return closeButton.Visible; }
set { closeButton.Visible = value; }
}

public Image Image
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,11 @@ protected override void OnPreLoad(EventArgs e)
public virtual Control Create()
{
tabControl = DefaultTabs();
var allowReorder = new CheckBox { Text = "AllowReordering" };
allowReorder.CheckedBinding.Bind(tabControl, c => c.AllowReordering);

var enabled = new CheckBox { Text = "Enabled" };
enabled.CheckedBinding.Bind(tabControl, c => c.Enabled);

return new StackLayout
{
Expand All @@ -28,22 +33,23 @@ public virtual Control Create()
new StackLayout
{
Orientation = Orientation.Horizontal,
Items = { AddTab(), null }
Items = { AddPage(), RemovePage(), SelectPage(), allowReorder, enabled, null }
},
new StackLayoutItem(tabControl, expand: true)
}
};
}

Control AddTab()
Control AddPage()
{
var control = new Button { Text = "Add Tab" };
var control = new Button { Text = "Add Page" };
control.Click += (s, e) =>
{
var tab = new DocumentPage
{
Text = "Tab " + (tabControl.Pages.Count + 1),
Content = tabControl.Pages.Count % 2 == 0 ? TabOne() : TabTwo()
Content = tabControl.Pages.Count % 2 == 0 ? TabOne() : TabTwo(),
Image = tabControl.Pages.Count % 3 == 0 ? TestIcons.Logo.WithSize(32, 32) : null
};
LogEvents(tab);

Expand All @@ -52,6 +58,29 @@ Control AddTab()
return control;
}

Control RemovePage()
{
var control = new Button { Text = "Remove Page" };
control.Click += (s, e) =>
{
if (tabControl.SelectedIndex >= 0)
tabControl.Pages.RemoveAt(tabControl.SelectedIndex);
};
return control;
}

Control SelectPage()
{
var control = new Button { Text = "Select Page" };
var rnd = new Random();
control.Click += (s, e) =>
{
if (tabControl.Pages.Count > 0)
tabControl.SelectedIndex = rnd.Next(tabControl.Pages.Count);
};
return control;
}

DocumentControl DefaultTabs()
{
var control = CreateDocumentControl();
Expand All @@ -62,7 +91,7 @@ DocumentControl DefaultTabs()
control.Pages.Add(new DocumentPage
{
Text = "Tab 2",
Image = TestIcons.TestIcon,
Image = TestIcons.TestIcon.WithSize(16, 16),
Content = TabTwo()
});

Expand Down Expand Up @@ -100,28 +129,18 @@ Control TabTwo()

void LogEvents(DocumentControl control)
{
control.SelectedIndexChanged += delegate
{
Log.Write(control, "SelectedIndexChanged, Index: {0}", control.SelectedIndex);
};
control.SelectedIndexChanged += (sender, e) => Log.Write(control, $"SelectedIndexChanged, Index: {control.SelectedIndex}");

control.PageClosed += (sender, e) =>
{
Log.Write(control, "PageClosed, Title: {0}", e.Page.Text);
};
control.PageClosed += (sender, e) => Log.Write(control, $"PageClosed, Title: {e.Page.Text}");

control.PageReordered += (sender, e) => Log.Write(control, $"PageReordered, Title: {e.Page.Text}, OldIndex: {e.OldIndex}, NewIndex: {e.NewIndex}");
}

void LogEvents(DocumentPage control)
{
control.Click += delegate
{
Log.Write(control, "Click, Item: {0}", control.Text);
};
control.Click += (sender, e) => Log.Write(control, $"Click, Item: {control.Text}");

control.Closed += (sender, e) =>
{
Log.Write(control, "Closed, Title: {0}", control.Text);
};
control.Closed += (sender, e) => Log.Write(control, $"Closed, Title: {control.Text}");
}
}
}
Expand Down
Loading

0 comments on commit 4d81219

Please sign in to comment.