using Gtk; using Adw; using GtkCommonMark; using Invercargill; namespace Publicate.Editors { public class MetadataEditor : Box, EditorWidget, Savable { private Ppub.Metadata metadata; private Ppub.Asset asset; private TabPage page; private EntryRow title; private EntryRow author; private EntryRow author_email; private FileChooserRow poster; private EntryRow description; private EntryRow tags; private FileChooserRow licence; private EntryRow copyright; private ViewerWindow window; private bool unsaved = false; public bool has_unsaved_changes { get{ return unsaved; } } public MetadataEditor(ViewerWindow win, TabView tab_view) { window = win; var scroll_window = new ScrolledWindow (); scroll_window.hexpand = true; scroll_window.vexpand = true; var box = new Box(Orientation.VERTICAL, 0); scroll_window.child = box; append(scroll_window); var group = new PreferencesGroup(); group.margin_bottom = 18; group.margin_end = 18; group.margin_start = 18; group.margin_top = 18; group.title = "Publication Details"; group.description = ""; title = new EntryRow (); title.title = "Title"; title.changed.connect (something_changed); group.add(title); author = new EntryRow (); author.title = "Author"; author.changed.connect (something_changed); group.add(author); author_email = new EntryRow (); author_email.title = "Author Email"; author_email.changed.connect (something_changed); group.add(author_email); poster = new FileChooserRow (window); poster.title = "Poster Image"; poster.asset_selected.connect (something_changed); group.add(poster); description = new EntryRow (); description.enable_emoji_completion = true; description.title = "Description"; description.changed.connect (something_changed); group.add(description); tags = new EntryRow (); tags.title = "Tags (space separated)"; tags.changed.connect (something_changed); group.add(tags); box.append(group); var group2 = new PreferencesGroup(); group2.margin_bottom = 18; group2.margin_end = 18; group2.margin_start = 18; group2.margin_top = 18; group2.title = "Licence and Copyright"; group2.description = ""; copyright = new EntryRow (); copyright.title = "Copyright Notice"; copyright.changed.connect (something_changed); group2.add(copyright); licence = new FileChooserRow (window); licence.title = "Licence"; licence.asset_selected.connect (something_changed); group2.add(licence); box.append(group2); this.page = tab_view.add_page (this, null); } public async void load_asset (Ppub.Publication publication, Ppub.Asset asset) { this.asset = asset; var stream = publication.read_asset (asset.name); metadata = new Ppub.Metadata.from_stream (stream); poster.set_assets(publication.assets.where(a => a.mimetype.has_prefix ("image/"))); licence.set_assets(publication.assets.where(a => a.mimetype.has_prefix ("text/"))); title.text = metadata.title ?? ""; author.text = metadata.author_name ?? ""; author_email.text = metadata.author_email ?? ""; poster.set_selected_item (metadata.poster ?? ""); description.text = metadata.description ?? ""; tags.text = ate(metadata.tags).to_string (a => a, " "); copyright.text = metadata.copyright ?? ""; licence.set_selected_item (metadata.licence ?? ""); set_changed(false); } public string asset_name { get { return asset.name; } } public Adw.TabPage tab_page { get { return page; }} private string? process_string(string str) { var stripped = str.chomp().chug(); if(stripped == "") { return null; } return stripped; } public void save_asset (Ppub.Builder builder) { metadata.title = process_string(title.text); var email = author_email.text.chomp().chug(); if(email != "") { metadata.author = @"$(author.text) <$email>"; } else { metadata.author = process_string(author.text); } print(@"$(poster.selected_asset)\n"); metadata.poster = process_string (poster.selected_asset); metadata.description = process_string(description.text); metadata.tags = tags.text.chug().chomp().split (" "); metadata.copyright = process_string(copyright.text); metadata.licence = process_string (licence.selected_asset); // TODO, this should probably done on every save globally? metadata.date = new DateTime.now_local(); var stream = new MemoryInputStream.from_data((uint8[])metadata.to_string().to_utf8()); var compression_info = new Ppub.CompressionInfo(stream); stream.seek(0, SeekType.SET); builder.add_asset(asset.name, asset.mimetype, stream, Invercargill.empty(), compression_info); set_changed(false); } private void set_changed(bool changed) { this.page.title = changed ? "⏺ Publication Metadata" : "Publication Metadata"; unsaved = changed; } private void something_changed() { set_changed(true); } } }