Refactor FileChooserDialogs
Use GtkFileChooserDialog only when we need previews, default to NativeFileChooser otherwise. GtkFileChooserDialogs have a long list of issues, so lets only use it if we gain something from it. Flatpak should only run NativeFileChoosers because its sandboxed and this is needed for security purposes. As a result of that, Flatpak Users dont have image previews in the FileOpenDialogs Refactor all FileChoosers for a more simple approach when we use them Add a new SendFileDialog, so we dont have to put widgets into the FileChooser which forces non-native Dialogs.
This commit is contained in:
parent
bb33e055a5
commit
c38db84e04
|
@ -155,6 +155,7 @@ _dependencies = {
|
||||||
'PYCURL': False,
|
'PYCURL': False,
|
||||||
'GSPELL': False,
|
'GSPELL': False,
|
||||||
'IDLE': False,
|
'IDLE': False,
|
||||||
|
'RUN_AS_FLATPAK': False,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -167,6 +168,9 @@ def is_installed(dependency):
|
||||||
return _dependencies['AVAHI'] or _dependencies['PYBONJOUR']
|
return _dependencies['AVAHI'] or _dependencies['PYBONJOUR']
|
||||||
return _dependencies[dependency]
|
return _dependencies[dependency]
|
||||||
|
|
||||||
|
def is_flatpak():
|
||||||
|
return _dependencies['RUN_AS_FLATPAK']
|
||||||
|
|
||||||
def disable_dependency(dependency):
|
def disable_dependency(dependency):
|
||||||
_dependencies[dependency] = False
|
_dependencies[dependency] = False
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<!-- Generated with glade 3.21.0 -->
|
<!-- Generated with glade 3.22.1 -->
|
||||||
<interface>
|
<interface>
|
||||||
<requires lib="gtk+" version="3.12"/>
|
<requires lib="gtk+" version="3.12"/>
|
||||||
<object class="GtkMenu" id="context_menu">
|
<object class="GtkMenu" id="context_menu">
|
||||||
|
@ -22,70 +22,6 @@
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
<object class="GtkFileChooserDialog" id="filechooserdialog">
|
|
||||||
<property name="can_focus">False</property>
|
|
||||||
<property name="type_hint">dialog</property>
|
|
||||||
<property name="action">save</property>
|
|
||||||
<child internal-child="vbox">
|
|
||||||
<object class="GtkBox" id="dialog-vbox1">
|
|
||||||
<property name="visible">True</property>
|
|
||||||
<property name="can_focus">False</property>
|
|
||||||
<property name="orientation">vertical</property>
|
|
||||||
<property name="spacing">24</property>
|
|
||||||
<child internal-child="action_area">
|
|
||||||
<object class="GtkButtonBox" id="dialog-action_area1">
|
|
||||||
<property name="visible">True</property>
|
|
||||||
<property name="can_focus">False</property>
|
|
||||||
<property name="layout_style">end</property>
|
|
||||||
<child>
|
|
||||||
<object class="GtkButton" id="cancel_button">
|
|
||||||
<property name="label">gtk-cancel</property>
|
|
||||||
<property name="visible">True</property>
|
|
||||||
<property name="can_focus">True</property>
|
|
||||||
<property name="can_default">True</property>
|
|
||||||
<property name="receives_default">False</property>
|
|
||||||
<property name="use_stock">True</property>
|
|
||||||
</object>
|
|
||||||
<packing>
|
|
||||||
<property name="expand">False</property>
|
|
||||||
<property name="fill">False</property>
|
|
||||||
<property name="position">0</property>
|
|
||||||
</packing>
|
|
||||||
</child>
|
|
||||||
<child>
|
|
||||||
<object class="GtkButton" id="save_button">
|
|
||||||
<property name="label">gtk-save</property>
|
|
||||||
<property name="visible">True</property>
|
|
||||||
<property name="can_focus">True</property>
|
|
||||||
<property name="can_default">True</property>
|
|
||||||
<property name="has_default">True</property>
|
|
||||||
<property name="receives_default">False</property>
|
|
||||||
<property name="use_stock">True</property>
|
|
||||||
</object>
|
|
||||||
<packing>
|
|
||||||
<property name="expand">False</property>
|
|
||||||
<property name="fill">False</property>
|
|
||||||
<property name="position">1</property>
|
|
||||||
</packing>
|
|
||||||
</child>
|
|
||||||
</object>
|
|
||||||
<packing>
|
|
||||||
<property name="expand">False</property>
|
|
||||||
<property name="fill">False</property>
|
|
||||||
<property name="pack_type">end</property>
|
|
||||||
<property name="position">0</property>
|
|
||||||
</packing>
|
|
||||||
</child>
|
|
||||||
</object>
|
|
||||||
</child>
|
|
||||||
<action-widgets>
|
|
||||||
<action-widget response="-6">cancel_button</action-widget>
|
|
||||||
<action-widget response="-5">save_button</action-widget>
|
|
||||||
</action-widgets>
|
|
||||||
<child>
|
|
||||||
<placeholder/>
|
|
||||||
</child>
|
|
||||||
</object>
|
|
||||||
<object class="GtkImage" id="image1">
|
<object class="GtkImage" id="image1">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
|
@ -98,6 +34,9 @@
|
||||||
<property name="default_width">650</property>
|
<property name="default_width">650</property>
|
||||||
<property name="default_height">500</property>
|
<property name="default_height">500</property>
|
||||||
<signal name="delete-event" handler="on_history_manager_window_delete_event" swapped="no"/>
|
<signal name="delete-event" handler="on_history_manager_window_delete_event" swapped="no"/>
|
||||||
|
<child>
|
||||||
|
<placeholder/>
|
||||||
|
</child>
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkBox" id="vbox">
|
<object class="GtkBox" id="vbox">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
|
@ -306,8 +245,5 @@ If you plan to do massive deletions, please make sure Gajim is not running. Gene
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
<child>
|
|
||||||
<placeholder/>
|
|
||||||
</child>
|
|
||||||
</object>
|
</object>
|
||||||
</interface>
|
</interface>
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<!-- Generated with glade 3.18.3 -->
|
<!-- Generated with glade 3.22.1 -->
|
||||||
<interface>
|
<interface>
|
||||||
<requires lib="gtk+" version="3.12"/>
|
<requires lib="gtk+" version="3.12"/>
|
||||||
<object class="GtkWindow" id="profile_window">
|
<object class="GtkWindow" id="profile_window">
|
||||||
|
@ -8,6 +8,9 @@
|
||||||
<property name="type_hint">dialog</property>
|
<property name="type_hint">dialog</property>
|
||||||
<signal name="destroy" handler="on_profile_window_destroy" swapped="no"/>
|
<signal name="destroy" handler="on_profile_window_destroy" swapped="no"/>
|
||||||
<signal name="key-press-event" handler="on_profile_window_key_press_event" swapped="no"/>
|
<signal name="key-press-event" handler="on_profile_window_key_press_event" swapped="no"/>
|
||||||
|
<child>
|
||||||
|
<placeholder/>
|
||||||
|
</child>
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkBox" id="vbox1">
|
<object class="GtkBox" id="vbox1">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
|
@ -30,10 +33,10 @@
|
||||||
<object class="GtkLabel" id="label24">
|
<object class="GtkLabel" id="label24">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">0</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Name:</b></property>
|
<property name="label" translatable="yes"><b>Name:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -54,10 +57,10 @@
|
||||||
<object class="GtkLabel" id="label20">
|
<object class="GtkLabel" id="label20">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Nickname:</b></property>
|
<property name="label" translatable="yes"><b>Nickname:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -89,10 +92,10 @@
|
||||||
<object class="GtkLabel" id="label18">
|
<object class="GtkLabel" id="label18">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes" comments="Family Name"><b>Family:</b></property>
|
<property name="label" translatable="yes" comments="Family Name"><b>Family:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -113,10 +116,10 @@
|
||||||
<object class="GtkLabel" id="label17">
|
<object class="GtkLabel" id="label17">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes" comments="Given Name"><b>Given:</b></property>
|
<property name="label" translatable="yes" comments="Given Name"><b>Given:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -137,10 +140,10 @@
|
||||||
<object class="GtkLabel" id="label16">
|
<object class="GtkLabel" id="label16">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes" comments="Middle Name"><b>Middle:</b></property>
|
<property name="label" translatable="yes" comments="Middle Name"><b>Middle:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -151,10 +154,10 @@
|
||||||
<object class="GtkLabel" id="label15">
|
<object class="GtkLabel" id="label15">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes" comments="Prefix in Name"><b>Prefix:</b></property>
|
<property name="label" translatable="yes" comments="Prefix in Name"><b>Prefix:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -185,10 +188,10 @@
|
||||||
<object class="GtkLabel" id="label14">
|
<object class="GtkLabel" id="label14">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes" comments="Suffix in Name"><b>Suffix:</b></property>
|
<property name="label" translatable="yes" comments="Suffix in Name"><b>Suffix:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -217,10 +220,10 @@
|
||||||
<object class="GtkLabel" id="label19">
|
<object class="GtkLabel" id="label19">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">0</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Full Name</b></property>
|
<property name="label" translatable="yes"><b>Full Name</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
|
@ -245,10 +248,10 @@
|
||||||
<object class="GtkLabel" id="label31">
|
<object class="GtkLabel" id="label31">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Street:</b></property>
|
<property name="label" translatable="yes"><b>Street:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -269,10 +272,10 @@
|
||||||
<object class="GtkLabel" id="label29">
|
<object class="GtkLabel" id="label29">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Extra Address:</b></property>
|
<property name="label" translatable="yes"><b>Extra Address:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -293,10 +296,10 @@
|
||||||
<object class="GtkLabel" id="label28">
|
<object class="GtkLabel" id="label28">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>City:</b></property>
|
<property name="label" translatable="yes"><b>City:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -317,10 +320,10 @@
|
||||||
<object class="GtkLabel" id="label26">
|
<object class="GtkLabel" id="label26">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Postal Code:</b></property>
|
<property name="label" translatable="yes"><b>Postal Code:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -341,10 +344,10 @@
|
||||||
<object class="GtkLabel" id="label27">
|
<object class="GtkLabel" id="label27">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>State:</b></property>
|
<property name="label" translatable="yes"><b>State:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -365,10 +368,10 @@
|
||||||
<object class="GtkLabel" id="label25">
|
<object class="GtkLabel" id="label25">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Country:</b></property>
|
<property name="label" translatable="yes"><b>Country:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -391,10 +394,10 @@
|
||||||
<object class="GtkLabel" id="label30">
|
<object class="GtkLabel" id="label30">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">0</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Address</b></property>
|
<property name="label" translatable="yes"><b>Address</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
|
@ -408,10 +411,10 @@
|
||||||
<object class="GtkLabel" id="label22">
|
<object class="GtkLabel" id="label22">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Homepage:</b></property>
|
<property name="label" translatable="yes"><b>Homepage:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -433,9 +436,9 @@
|
||||||
<object class="GtkLabel" id="label57">
|
<object class="GtkLabel" id="label57">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="label" translatable="yes"><b>E-Mail:</b></property>
|
<property name="label" translatable="yes"><b>E-Mail:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -457,10 +460,10 @@
|
||||||
<object class="GtkLabel" id="label23">
|
<object class="GtkLabel" id="label23">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Phone No.:</b></property>
|
<property name="label" translatable="yes"><b>Phone No.:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -492,10 +495,10 @@
|
||||||
<object class="GtkLabel" id="label58">
|
<object class="GtkLabel" id="label58">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Avatar:</b></property>
|
<property name="label" translatable="yes"><b>Avatar:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -506,12 +509,11 @@
|
||||||
<object class="GtkBox" id="hbox3">
|
<object class="GtkBox" id="hbox3">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
|
<property name="spacing">6</property>
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkButton" id="PHOTO_button">
|
<object class="GtkButton" id="PHOTO_button">
|
||||||
<property name="can_focus">True</property>
|
<property name="can_focus">True</property>
|
||||||
<property name="receives_default">False</property>
|
<property name="receives_default">False</property>
|
||||||
<property name="xalign">0</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<signal name="button-press-event" handler="on_PHOTO_button_press_event" swapped="no"/>
|
<signal name="button-press-event" handler="on_PHOTO_button_press_event" swapped="no"/>
|
||||||
<child>
|
<child>
|
||||||
<object class="GtkEventBox" id="PHOTO_eventbox3">
|
<object class="GtkEventBox" id="PHOTO_eventbox3">
|
||||||
|
@ -522,7 +524,6 @@
|
||||||
<object class="GtkImage" id="PHOTO_image">
|
<object class="GtkImage" id="PHOTO_image">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="stock">gtk-missing-image</property>
|
<property name="stock">gtk-missing-image</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
|
@ -543,8 +544,6 @@
|
||||||
<property name="receives_default">False</property>
|
<property name="receives_default">False</property>
|
||||||
<property name="no_show_all">True</property>
|
<property name="no_show_all">True</property>
|
||||||
<property name="use_underline">True</property>
|
<property name="use_underline">True</property>
|
||||||
<property name="xalign">0</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<signal name="button-press-event" handler="on_PHOTO_button_press_event" swapped="no"/>
|
<signal name="button-press-event" handler="on_PHOTO_button_press_event" swapped="no"/>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
|
@ -553,10 +552,31 @@
|
||||||
<property name="position">1</property>
|
<property name="position">1</property>
|
||||||
</packing>
|
</packing>
|
||||||
</child>
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkButton" id="remove_avatar">
|
||||||
|
<property name="label" translatable="yes">Remove Avatar</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="receives_default">True</property>
|
||||||
|
<property name="no_show_all">True</property>
|
||||||
|
<property name="tooltip_text" translatable="yes">Clear Avatar</property>
|
||||||
|
<property name="halign">start</property>
|
||||||
|
<property name="valign">end</property>
|
||||||
|
<signal name="clicked" handler="_clear_photo" swapped="no"/>
|
||||||
|
<style>
|
||||||
|
<class name="destructive-action"/>
|
||||||
|
</style>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="expand">False</property>
|
||||||
|
<property name="fill">True</property>
|
||||||
|
<property name="position">2</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">1</property>
|
<property name="left_attach">1</property>
|
||||||
<property name="top_attach">6</property>
|
<property name="top_attach">6</property>
|
||||||
|
<property name="width">3</property>
|
||||||
</packing>
|
</packing>
|
||||||
</child>
|
</child>
|
||||||
<child>
|
<child>
|
||||||
|
@ -569,10 +589,10 @@
|
||||||
<object class="GtkLabel" id="label13">
|
<object class="GtkLabel" id="label13">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Birthday:</b></property>
|
<property name="label" translatable="yes"><b>Birthday:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
|
@ -581,21 +601,15 @@
|
||||||
<property name="top_attach">5</property>
|
<property name="top_attach">5</property>
|
||||||
</packing>
|
</packing>
|
||||||
</child>
|
</child>
|
||||||
<child>
|
|
||||||
<placeholder/>
|
|
||||||
</child>
|
|
||||||
<child>
|
|
||||||
<placeholder/>
|
|
||||||
</child>
|
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
<child type="tab">
|
<child type="tab">
|
||||||
<object class="GtkLabel" id="label4">
|
<object class="GtkLabel" id="label4">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Personal Info</property>
|
||||||
<property name="xalign">0</property>
|
<property name="xalign">0</property>
|
||||||
<property name="yalign">0</property>
|
<property name="yalign">0</property>
|
||||||
<property name="label" translatable="yes">Personal Info</property>
|
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="tab_fill">False</property>
|
<property name="tab_fill">False</property>
|
||||||
|
@ -612,10 +626,10 @@
|
||||||
<object class="GtkLabel" id="label44">
|
<object class="GtkLabel" id="label44">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Company:</b></property>
|
<property name="label" translatable="yes"><b>Company:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -636,10 +650,10 @@
|
||||||
<object class="GtkLabel" id="label43">
|
<object class="GtkLabel" id="label43">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Department:</b></property>
|
<property name="label" translatable="yes"><b>Department:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -660,10 +674,10 @@
|
||||||
<object class="GtkLabel" id="label42">
|
<object class="GtkLabel" id="label42">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Position:</b></property>
|
<property name="label" translatable="yes"><b>Position:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -684,10 +698,10 @@
|
||||||
<object class="GtkLabel" id="label41">
|
<object class="GtkLabel" id="label41">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Role:</b></property>
|
<property name="label" translatable="yes"><b>Role:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -719,10 +733,10 @@
|
||||||
<object class="GtkLabel" id="label39">
|
<object class="GtkLabel" id="label39">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Street:</b></property>
|
<property name="label" translatable="yes"><b>Street:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -743,10 +757,10 @@
|
||||||
<object class="GtkLabel" id="label38">
|
<object class="GtkLabel" id="label38">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Extra Address:</b></property>
|
<property name="label" translatable="yes"><b>Extra Address:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -767,10 +781,10 @@
|
||||||
<object class="GtkLabel" id="label37">
|
<object class="GtkLabel" id="label37">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>City:</b></property>
|
<property name="label" translatable="yes"><b>City:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -791,10 +805,10 @@
|
||||||
<object class="GtkLabel" id="label35">
|
<object class="GtkLabel" id="label35">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Postal Code:</b></property>
|
<property name="label" translatable="yes"><b>Postal Code:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -815,10 +829,10 @@
|
||||||
<object class="GtkLabel" id="label36">
|
<object class="GtkLabel" id="label36">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>State:</b></property>
|
<property name="label" translatable="yes"><b>State:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -839,10 +853,10 @@
|
||||||
<object class="GtkLabel" id="label34">
|
<object class="GtkLabel" id="label34">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Country:</b></property>
|
<property name="label" translatable="yes"><b>Country:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">2</property>
|
<property name="left_attach">2</property>
|
||||||
|
@ -865,10 +879,10 @@
|
||||||
<object class="GtkLabel" id="label40">
|
<object class="GtkLabel" id="label40">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Address</b></property>
|
<property name="label" translatable="yes"><b>Address</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
</child>
|
</child>
|
||||||
</object>
|
</object>
|
||||||
|
@ -882,10 +896,10 @@
|
||||||
<object class="GtkLabel" id="label32">
|
<object class="GtkLabel" id="label32">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>E-Mail:</b></property>
|
<property name="label" translatable="yes"><b>E-Mail:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -907,10 +921,10 @@
|
||||||
<object class="GtkLabel" id="label33">
|
<object class="GtkLabel" id="label33">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
<property name="xalign">1</property>
|
|
||||||
<property name="yalign">0</property>
|
|
||||||
<property name="label" translatable="yes"><b>Phone No.:</b></property>
|
<property name="label" translatable="yes"><b>Phone No.:</b></property>
|
||||||
<property name="use_markup">True</property>
|
<property name="use_markup">True</property>
|
||||||
|
<property name="xalign">1</property>
|
||||||
|
<property name="yalign">0</property>
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="left_attach">0</property>
|
<property name="left_attach">0</property>
|
||||||
|
@ -942,9 +956,9 @@
|
||||||
<object class="GtkLabel" id="label5">
|
<object class="GtkLabel" id="label5">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Work</property>
|
||||||
<property name="xalign">0</property>
|
<property name="xalign">0</property>
|
||||||
<property name="yalign">0</property>
|
<property name="yalign">0</property>
|
||||||
<property name="label" translatable="yes">Work</property>
|
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="position">1</property>
|
<property name="position">1</property>
|
||||||
|
@ -974,9 +988,9 @@
|
||||||
<object class="GtkLabel" id="label6">
|
<object class="GtkLabel" id="label6">
|
||||||
<property name="visible">True</property>
|
<property name="visible">True</property>
|
||||||
<property name="can_focus">False</property>
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes" comments=""About" is the text of a tab of vcard window">About</property>
|
||||||
<property name="xalign">0</property>
|
<property name="xalign">0</property>
|
||||||
<property name="yalign">0</property>
|
<property name="yalign">0</property>
|
||||||
<property name="label" translatable="yes" comments=""About" is the text of a tab of vcard window">About</property>
|
|
||||||
</object>
|
</object>
|
||||||
<packing>
|
<packing>
|
||||||
<property name="position">2</property>
|
<property name="position">2</property>
|
||||||
|
|
|
@ -0,0 +1,116 @@
|
||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<!-- Generated with glade 3.22.1 -->
|
||||||
|
<interface>
|
||||||
|
<requires lib="gtk+" version="3.20"/>
|
||||||
|
<object class="GtkGrid" id="send_file_grid">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="row_spacing">6</property>
|
||||||
|
<property name="column_spacing">6</property>
|
||||||
|
<child>
|
||||||
|
<object class="GtkScrolledWindow">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="hexpand">True</property>
|
||||||
|
<property name="hscrollbar_policy">never</property>
|
||||||
|
<property name="shadow_type">in</property>
|
||||||
|
<child>
|
||||||
|
<object class="GtkViewport">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<child>
|
||||||
|
<object class="GtkListBox" id="listbox">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="vexpand">True</property>
|
||||||
|
<property name="selection_mode">none</property>
|
||||||
|
<property name="activate_on_single_click">False</property>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">1</property>
|
||||||
|
<property name="width">2</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkLabel">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Description:</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">2</property>
|
||||||
|
<property name="width">2</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkScrolledWindow">
|
||||||
|
<property name="height_request">40</property>
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="hexpand">True</property>
|
||||||
|
<property name="hscrollbar_policy">never</property>
|
||||||
|
<property name="shadow_type">in</property>
|
||||||
|
<child>
|
||||||
|
<object class="GtkTextView" id="description">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="wrap_mode">word-char</property>
|
||||||
|
</object>
|
||||||
|
</child>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">3</property>
|
||||||
|
<property name="width">2</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkButton">
|
||||||
|
<property name="label" translatable="yes">Select Files</property>
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="receives_default">True</property>
|
||||||
|
<property name="halign">start</property>
|
||||||
|
<signal name="clicked" handler="_select_files" swapped="no"/>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">4</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkButton">
|
||||||
|
<property name="label" translatable="yes">Send</property>
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">True</property>
|
||||||
|
<property name="receives_default">True</property>
|
||||||
|
<property name="halign">end</property>
|
||||||
|
<signal name="clicked" handler="_send" swapped="no"/>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">1</property>
|
||||||
|
<property name="top_attach">4</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
<child>
|
||||||
|
<object class="GtkLabel">
|
||||||
|
<property name="visible">True</property>
|
||||||
|
<property name="can_focus">False</property>
|
||||||
|
<property name="label" translatable="yes">Files:</property>
|
||||||
|
<property name="xalign">0</property>
|
||||||
|
</object>
|
||||||
|
<packing>
|
||||||
|
<property name="left_attach">0</property>
|
||||||
|
<property name="top_attach">0</property>
|
||||||
|
<property name="width">2</property>
|
||||||
|
</packing>
|
||||||
|
</child>
|
||||||
|
</object>
|
||||||
|
</interface>
|
|
@ -99,3 +99,7 @@ popover#EmoticonPopover flowboxchild { padding-top: 5px; padding-bottom: 5px; }
|
||||||
|
|
||||||
/*MessageWindow Notebook*/
|
/*MessageWindow Notebook*/
|
||||||
.notebook-tab-label {min-width: 80px}
|
.notebook-tab-label {min-width: 80px}
|
||||||
|
|
||||||
|
/*SendFileDialog*/
|
||||||
|
#SendFileDialog grid {padding: 12px}
|
||||||
|
#SendFileDialog grid list { background-color: @theme_bg_color}
|
||||||
|
|
201
gajim/dialogs.py
201
gajim/dialogs.py
|
@ -1426,74 +1426,6 @@ class HigDialog(Gtk.MessageDialog):
|
||||||
vb.grab_focus()
|
vb.grab_focus()
|
||||||
self.show_all()
|
self.show_all()
|
||||||
|
|
||||||
class FileChooserDialog(Gtk.FileChooserDialog):
|
|
||||||
"""
|
|
||||||
Non-blocking FileChooser Dialog around Gtk.FileChooserDialog
|
|
||||||
"""
|
|
||||||
def __init__(self, title_text, action, buttons, default_response,
|
|
||||||
select_multiple=False, current_folder=None, on_response_ok=None,
|
|
||||||
on_response_cancel=None, preview=False, transient_for=None):
|
|
||||||
|
|
||||||
Gtk.FileChooserDialog.__init__(self, title=title_text,
|
|
||||||
parent=transient_for, action=action)
|
|
||||||
self.add_button(buttons[0],buttons[1])
|
|
||||||
if len(buttons) ==4:
|
|
||||||
self.add_button(buttons[2],buttons[3])
|
|
||||||
self.set_default_response(default_response)
|
|
||||||
self.set_select_multiple(select_multiple)
|
|
||||||
if current_folder and os.path.isdir(current_folder):
|
|
||||||
self.set_current_folder(current_folder)
|
|
||||||
else:
|
|
||||||
self.set_current_folder(os.path.expanduser('~'))
|
|
||||||
self.response_ok, self.response_cancel = \
|
|
||||||
on_response_ok, on_response_cancel
|
|
||||||
# in gtk+-2.10 clicked signal on some of the buttons in a dialog
|
|
||||||
# is emitted twice, so we cannot rely on 'clicked' signal
|
|
||||||
self.connect('response', self.on_dialog_response)
|
|
||||||
|
|
||||||
if preview:
|
|
||||||
self.set_use_preview_label(False)
|
|
||||||
self.set_preview_widget(Gtk.Image())
|
|
||||||
self.connect('selection-changed', self.update_preview)
|
|
||||||
|
|
||||||
self.show_all()
|
|
||||||
|
|
||||||
def on_dialog_response(self, dialog, response):
|
|
||||||
if response in (Gtk.ResponseType.CANCEL, Gtk.ResponseType.CLOSE):
|
|
||||||
if self.response_cancel:
|
|
||||||
if isinstance(self.response_cancel, tuple):
|
|
||||||
self.response_cancel[0](dialog, *self.response_cancel[1:])
|
|
||||||
else:
|
|
||||||
self.response_cancel(dialog)
|
|
||||||
else:
|
|
||||||
self.just_destroy(dialog)
|
|
||||||
elif response == Gtk.ResponseType.OK:
|
|
||||||
if self.response_ok:
|
|
||||||
if isinstance(self.response_ok, tuple):
|
|
||||||
self.response_ok[0](dialog, *self.response_ok[1:])
|
|
||||||
else:
|
|
||||||
self.response_ok(dialog)
|
|
||||||
else:
|
|
||||||
self.just_destroy(dialog)
|
|
||||||
|
|
||||||
def update_preview(self, widget):
|
|
||||||
path_to_file = widget.get_preview_filename()
|
|
||||||
preview = widget.get_preview_widget()
|
|
||||||
if path_to_file is None or os.path.isdir(path_to_file):
|
|
||||||
# nothing to preview or directory
|
|
||||||
# make sure you clean image do show nothing
|
|
||||||
preview.clear()
|
|
||||||
return
|
|
||||||
try:
|
|
||||||
pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_size(path_to_file, 200, 200)
|
|
||||||
except GObject.GError:
|
|
||||||
preview.clear()
|
|
||||||
return
|
|
||||||
widget.get_preview_widget().set_from_pixbuf(pixbuf)
|
|
||||||
|
|
||||||
def just_destroy(self, widget):
|
|
||||||
self.destroy()
|
|
||||||
|
|
||||||
class AspellDictError:
|
class AspellDictError:
|
||||||
def __init__(self, lang):
|
def __init__(self, lang):
|
||||||
ErrorDialog(
|
ErrorDialog(
|
||||||
|
@ -4773,139 +4705,6 @@ class ProgressDialog:
|
||||||
def on_progress_dialog_delete_event(self, widget, event):
|
def on_progress_dialog_delete_event(self, widget, event):
|
||||||
return True # WM's X button or Escape key should not destroy the window
|
return True # WM's X button or Escape key should not destroy the window
|
||||||
|
|
||||||
class ImageChooserDialog(FileChooserDialog):
|
|
||||||
def __init__(self, path_to_file='', on_response_ok=None,
|
|
||||||
on_response_cancel=None):
|
|
||||||
"""
|
|
||||||
Optionally accepts path_to_snd_file so it has that as selected
|
|
||||||
"""
|
|
||||||
def on_ok(widget, callback):
|
|
||||||
'''check if file exists and call callback'''
|
|
||||||
path_to_file = self.get_filename()
|
|
||||||
if not path_to_file:
|
|
||||||
return
|
|
||||||
if os.path.exists(path_to_file):
|
|
||||||
if isinstance(callback, tuple):
|
|
||||||
callback[0](widget, path_to_file, *callback[1:])
|
|
||||||
else:
|
|
||||||
callback(widget, path_to_file)
|
|
||||||
|
|
||||||
path = GLib.get_user_special_dir(GLib.UserDirectory.DIRECTORY_PICTURES)
|
|
||||||
FileChooserDialog.__init__(self,
|
|
||||||
title_text = _('Choose Image'),
|
|
||||||
action = Gtk.FileChooserAction.OPEN,
|
|
||||||
buttons = (Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
|
|
||||||
Gtk.STOCK_OPEN, Gtk.ResponseType.OK),
|
|
||||||
default_response = Gtk.ResponseType.OK,
|
|
||||||
current_folder = path,
|
|
||||||
on_response_ok = (on_ok, on_response_ok),
|
|
||||||
on_response_cancel = on_response_cancel)
|
|
||||||
|
|
||||||
if on_response_cancel:
|
|
||||||
self.connect('destroy', on_response_cancel)
|
|
||||||
|
|
||||||
filter_ = Gtk.FileFilter()
|
|
||||||
filter_.set_name(_('All files'))
|
|
||||||
filter_.add_pattern('*')
|
|
||||||
self.add_filter(filter_)
|
|
||||||
|
|
||||||
filter_ = Gtk.FileFilter()
|
|
||||||
filter_.set_name(_('Images'))
|
|
||||||
filter_.add_mime_type('image/png')
|
|
||||||
filter_.add_mime_type('image/jpeg')
|
|
||||||
filter_.add_mime_type('image/gif')
|
|
||||||
filter_.add_mime_type('image/tiff')
|
|
||||||
filter_.add_mime_type('image/svg+xml')
|
|
||||||
filter_.add_mime_type('image/x-xpixmap') # xpm
|
|
||||||
self.add_filter(filter_)
|
|
||||||
self.set_filter(filter_)
|
|
||||||
|
|
||||||
if path_to_file:
|
|
||||||
self.set_filename(path_to_file)
|
|
||||||
|
|
||||||
self.set_use_preview_label(False)
|
|
||||||
self.set_preview_widget(Gtk.Image())
|
|
||||||
self.connect('selection-changed', self.update_preview)
|
|
||||||
|
|
||||||
def update_preview(self, widget):
|
|
||||||
path_to_file = widget.get_preview_filename()
|
|
||||||
if path_to_file is None or os.path.isdir(path_to_file):
|
|
||||||
# nothing to preview or directory
|
|
||||||
# make sure you clean image do show nothing
|
|
||||||
preview = widget.get_preview_widget()
|
|
||||||
preview.clear()
|
|
||||||
return
|
|
||||||
try:
|
|
||||||
pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_size(path_to_file, 100, 100)
|
|
||||||
except GObject.GError:
|
|
||||||
return
|
|
||||||
widget.get_preview_widget().set_from_pixbuf(pixbuf)
|
|
||||||
|
|
||||||
class AvatarChooserDialog(ImageChooserDialog):
|
|
||||||
def __init__(self, path_to_file='', on_response_ok=None,
|
|
||||||
on_response_cancel=None, on_response_clear=None):
|
|
||||||
ImageChooserDialog.__init__(self, path_to_file, on_response_ok,
|
|
||||||
on_response_cancel)
|
|
||||||
button = Gtk.Button(None, Gtk.STOCK_CLEAR)
|
|
||||||
self.response_clear = on_response_clear
|
|
||||||
if on_response_clear:
|
|
||||||
button.connect('clicked', self.on_clear)
|
|
||||||
button.show_all()
|
|
||||||
action_area = self.get_action_area()
|
|
||||||
action_area.pack_start(button, True, True, 0)
|
|
||||||
action_area.reorder_child(button, 0)
|
|
||||||
|
|
||||||
def on_clear(self, widget):
|
|
||||||
if isinstance(self.response_clear, tuple):
|
|
||||||
self.response_clear[0](widget, *self.response_clear[1:])
|
|
||||||
else:
|
|
||||||
self.response_clear(widget)
|
|
||||||
|
|
||||||
|
|
||||||
class ArchiveChooserDialog(FileChooserDialog):
|
|
||||||
def __init__(self, on_response_ok=None, on_response_cancel=None,
|
|
||||||
transient_for=None):
|
|
||||||
|
|
||||||
def on_ok(widget, callback):
|
|
||||||
'''check if file exists and call callback'''
|
|
||||||
path_to_file = self.get_filename()
|
|
||||||
if not path_to_file:
|
|
||||||
return
|
|
||||||
if os.path.exists(path_to_file):
|
|
||||||
if isinstance(callback, tuple):
|
|
||||||
callback[0](path_to_file, *callback[1:])
|
|
||||||
else:
|
|
||||||
callback(path_to_file)
|
|
||||||
self.destroy()
|
|
||||||
|
|
||||||
path = os.path.expanduser('~')
|
|
||||||
|
|
||||||
FileChooserDialog.__init__(self,
|
|
||||||
title_text=_('Choose Archive'),
|
|
||||||
action=Gtk.FileChooserAction.OPEN,
|
|
||||||
buttons=(Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
|
|
||||||
Gtk.STOCK_OPEN, Gtk.ResponseType.OK),
|
|
||||||
default_response=Gtk.ResponseType.OK,
|
|
||||||
current_folder=path,
|
|
||||||
on_response_ok=(on_ok, on_response_ok),
|
|
||||||
on_response_cancel=on_response_cancel,
|
|
||||||
transient_for=transient_for)
|
|
||||||
|
|
||||||
if on_response_cancel:
|
|
||||||
self.connect('destroy', on_response_cancel)
|
|
||||||
|
|
||||||
filter_ = Gtk.FileFilter()
|
|
||||||
filter_.set_name(_('All files'))
|
|
||||||
filter_.add_pattern('*')
|
|
||||||
self.add_filter(filter_)
|
|
||||||
|
|
||||||
filter_ = Gtk.FileFilter()
|
|
||||||
filter_.set_name(_('Zip files'))
|
|
||||||
filter_.add_pattern('*.zip')
|
|
||||||
|
|
||||||
self.add_filter(filter_)
|
|
||||||
self.set_filter(filter_)
|
|
||||||
|
|
||||||
class TransformChatToMUC:
|
class TransformChatToMUC:
|
||||||
# Keep a reference on windows so garbage collector don't restroy them
|
# Keep a reference on windows so garbage collector don't restroy them
|
||||||
instances = []
|
instances = []
|
||||||
|
|
|
@ -0,0 +1,212 @@
|
||||||
|
# -*- coding: utf-8 -*-
|
||||||
|
#
|
||||||
|
# Copyright (C) 2018 Philipp Hörist <philipp AT hoerist.com>
|
||||||
|
#
|
||||||
|
# This file is part of Gajim.
|
||||||
|
#
|
||||||
|
# Gajim is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# Gajim is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU General Public License
|
||||||
|
# along with Gajim. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
import os
|
||||||
|
from pathlib import Path
|
||||||
|
from collections import namedtuple
|
||||||
|
|
||||||
|
from gi.repository import Gtk
|
||||||
|
from gi.repository import GdkPixbuf
|
||||||
|
from gi.repository import GObject
|
||||||
|
|
||||||
|
from gajim.common import app
|
||||||
|
|
||||||
|
Filter = namedtuple('Filter', 'name pattern default')
|
||||||
|
|
||||||
|
|
||||||
|
# Notes: Adding mime types to Gtk.FileFilter forces non-native dialogs
|
||||||
|
|
||||||
|
class BaseFileChooser:
|
||||||
|
def _on_response(self, dialog, response, accept_cb, cancel_cb):
|
||||||
|
if response == Gtk.ResponseType.ACCEPT:
|
||||||
|
if self.get_select_multiple():
|
||||||
|
accept_cb(dialog.get_filenames())
|
||||||
|
else:
|
||||||
|
accept_cb(dialog.get_filename())
|
||||||
|
|
||||||
|
if response in (Gtk.ResponseType.CANCEL,
|
||||||
|
Gtk.ResponseType.DELETE_EVENT):
|
||||||
|
if cancel_cb is not None:
|
||||||
|
cancel_cb()
|
||||||
|
|
||||||
|
def _add_filters(self, filters):
|
||||||
|
for filterinfo in filters:
|
||||||
|
filter_ = Gtk.FileFilter()
|
||||||
|
filter_.set_name(filterinfo.name)
|
||||||
|
if isinstance(filterinfo.pattern, list):
|
||||||
|
for mime_type in filterinfo.pattern:
|
||||||
|
filter_.add_mime_type(mime_type)
|
||||||
|
else:
|
||||||
|
filter_.add_pattern(filterinfo.pattern)
|
||||||
|
self.add_filter(filter_)
|
||||||
|
if filterinfo.default:
|
||||||
|
self.set_filter(filter_)
|
||||||
|
|
||||||
|
def _update_preview(self, filechooser):
|
||||||
|
path_to_file = filechooser.get_preview_filename()
|
||||||
|
preview = filechooser.get_preview_widget()
|
||||||
|
if path_to_file is None or os.path.isdir(path_to_file):
|
||||||
|
# nothing to preview
|
||||||
|
preview.clear()
|
||||||
|
return
|
||||||
|
try:
|
||||||
|
pixbuf = GdkPixbuf.Pixbuf.new_from_file_at_size(
|
||||||
|
path_to_file, *self._preivew_size)
|
||||||
|
except GObject.GError:
|
||||||
|
preview.clear()
|
||||||
|
return
|
||||||
|
filechooser.get_preview_widget().set_from_pixbuf(pixbuf)
|
||||||
|
|
||||||
|
|
||||||
|
class BaseFileOpenDialog:
|
||||||
|
|
||||||
|
_title = _('Choose File to Send…')
|
||||||
|
_filters = [Filter(_('All files'), '*', True)]
|
||||||
|
|
||||||
|
|
||||||
|
class BaseAvatarChooserDialog:
|
||||||
|
|
||||||
|
_title = _('Choose Avatar…')
|
||||||
|
_preivew_size = (100, 100)
|
||||||
|
|
||||||
|
if app.is_flatpak():
|
||||||
|
_filters = [Filter(_('PNG files'), '*.png', True),
|
||||||
|
Filter(_('JPEG files'), '*.jp*g', False),
|
||||||
|
Filter(_('SVG files'), '*.svg', False)]
|
||||||
|
else:
|
||||||
|
_filters = [Filter(_('Images'), ['image/png',
|
||||||
|
'image/jpeg',
|
||||||
|
'image/svg+xml'], True)]
|
||||||
|
|
||||||
|
|
||||||
|
class NativeFileChooserDialog(Gtk.FileChooserNative, BaseFileChooser):
|
||||||
|
|
||||||
|
_title = ''
|
||||||
|
_filters = []
|
||||||
|
_action = Gtk.FileChooserAction.OPEN
|
||||||
|
|
||||||
|
def __init__(self, accept_cb, cancel_cb=None, transient_for=None,
|
||||||
|
path=None, file_name=None, select_multiple=False,
|
||||||
|
modal=False):
|
||||||
|
|
||||||
|
Gtk.FileChooserNative.__init__(self,
|
||||||
|
title=self._title,
|
||||||
|
action=self._action,
|
||||||
|
transient_for=transient_for)
|
||||||
|
|
||||||
|
self.set_current_folder(path or str(Path.home()))
|
||||||
|
if file_name is not None:
|
||||||
|
self.set_current_name(file_name)
|
||||||
|
self.set_select_multiple(select_multiple)
|
||||||
|
self.set_do_overwrite_confirmation(True)
|
||||||
|
self.set_modal(modal)
|
||||||
|
self._add_filters(self._filters)
|
||||||
|
|
||||||
|
self.connect('response', self._on_response, accept_cb, cancel_cb)
|
||||||
|
self.show()
|
||||||
|
|
||||||
|
|
||||||
|
class ArchiveChooserDialog(NativeFileChooserDialog):
|
||||||
|
|
||||||
|
_title = _('Choose Archive')
|
||||||
|
_filters = [Filter(_('All files'), '*', False),
|
||||||
|
Filter(_('ZIP files'), '*.zip', True)]
|
||||||
|
|
||||||
|
|
||||||
|
class FileSaveDialog(NativeFileChooserDialog):
|
||||||
|
|
||||||
|
_title = _('Save File as…')
|
||||||
|
_filters = [Filter(_('All files'), '*', True)]
|
||||||
|
_action = Gtk.FileChooserAction.SAVE
|
||||||
|
|
||||||
|
|
||||||
|
class AvatarSaveDialog(FileSaveDialog):
|
||||||
|
|
||||||
|
if os.name == 'nt':
|
||||||
|
_filters = [Filter(_('Images'), '*.png;*.jpg;*.jpeg;*.svg', True)]
|
||||||
|
|
||||||
|
|
||||||
|
class NativeFileOpenDialog(BaseFileOpenDialog, NativeFileChooserDialog):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class NativeAvatarChooserDialog(BaseAvatarChooserDialog, NativeFileChooserDialog):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class GtkFileChooserDialog(Gtk.FileChooserDialog, BaseFileChooser):
|
||||||
|
|
||||||
|
_title = ''
|
||||||
|
_filters = []
|
||||||
|
_action = Gtk.FileChooserAction.OPEN
|
||||||
|
_preivew_size = (200, 200)
|
||||||
|
|
||||||
|
def __init__(self, accept_cb, cancel_cb=None, transient_for=None,
|
||||||
|
path=None, file_name=None, select_multiple=False,
|
||||||
|
preview=True, modal=False):
|
||||||
|
|
||||||
|
Gtk.FileChooserDialog.__init__(
|
||||||
|
self,
|
||||||
|
title=self._title,
|
||||||
|
action=self._action,
|
||||||
|
buttons=[Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
|
||||||
|
Gtk.STOCK_OPEN, Gtk.ResponseType.ACCEPT],
|
||||||
|
transient_for=transient_for)
|
||||||
|
|
||||||
|
self.set_current_folder(path or str(Path.home()))
|
||||||
|
if file_name is not None:
|
||||||
|
self.set_current_name(file_name)
|
||||||
|
self.set_select_multiple(select_multiple)
|
||||||
|
self.set_do_overwrite_confirmation(True)
|
||||||
|
self.set_modal(modal)
|
||||||
|
self._add_filters(self._filters)
|
||||||
|
|
||||||
|
if preview:
|
||||||
|
self.set_use_preview_label(False)
|
||||||
|
self.set_preview_widget(Gtk.Image())
|
||||||
|
self.connect('selection-changed', self._update_preview)
|
||||||
|
|
||||||
|
self.connect('response', self._on_response, accept_cb, cancel_cb)
|
||||||
|
self.show()
|
||||||
|
|
||||||
|
def _on_response(self, *args):
|
||||||
|
super()._on_response(*args)
|
||||||
|
self.destroy()
|
||||||
|
|
||||||
|
|
||||||
|
class GtkFileOpenDialog(BaseFileOpenDialog, GtkFileChooserDialog):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class GtkAvatarChooserDialog(BaseAvatarChooserDialog, GtkFileChooserDialog):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
def FileChooserDialog(*args, **kwargs):
|
||||||
|
if app.is_flatpak():
|
||||||
|
return NativeFileOpenDialog(*args, **kwargs)
|
||||||
|
else:
|
||||||
|
return GtkFileOpenDialog(*args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
def AvatarChooserDialog(*args, **kwargs):
|
||||||
|
if app.is_flatpak():
|
||||||
|
return NativeAvatarChooserDialog(*args, **kwargs)
|
||||||
|
else:
|
||||||
|
return GtkAvatarChooserDialog(*args, **kwargs)
|
|
@ -28,6 +28,8 @@ from gi.repository import GLib
|
||||||
from gi.repository import Pango
|
from gi.repository import Pango
|
||||||
import os
|
import os
|
||||||
import time
|
import time
|
||||||
|
from functools import partial
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
from enum import IntEnum, unique
|
from enum import IntEnum, unique
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
|
@ -41,6 +43,7 @@ from gajim.common import helpers
|
||||||
from gajim.common.file_props import FilesProp
|
from gajim.common.file_props import FilesProp
|
||||||
from gajim.common.protocol.bytestream import (is_transfer_active, is_transfer_paused,
|
from gajim.common.protocol.bytestream import (is_transfer_active, is_transfer_paused,
|
||||||
is_transfer_stopped)
|
is_transfer_stopped)
|
||||||
|
from gajim.filechoosers import FileSaveDialog, FileChooserDialog
|
||||||
from nbxmpp.protocol import NS_JINGLE_FILE_TRANSFER_5
|
from nbxmpp.protocol import NS_JINGLE_FILE_TRANSFER_5
|
||||||
import logging
|
import logging
|
||||||
log = logging.getLogger('gajim.filetransfer_window')
|
log = logging.getLogger('gajim.filetransfer_window')
|
||||||
|
@ -322,51 +325,8 @@ class FileTransfersWindow:
|
||||||
account), type_=Gtk.MessageType.ERROR)
|
account), type_=Gtk.MessageType.ERROR)
|
||||||
|
|
||||||
def show_file_send_request(self, account, contact):
|
def show_file_send_request(self, account, contact):
|
||||||
win = Gtk.ScrolledWindow()
|
send_callback = partial(self.send_file, account, contact)
|
||||||
win.set_shadow_type(Gtk.ShadowType.IN)
|
SendFileDialog(send_callback, self.window)
|
||||||
win.set_policy(Gtk.PolicyType.NEVER, Gtk.PolicyType.NEVER)
|
|
||||||
|
|
||||||
from gajim.message_textview import MessageTextView
|
|
||||||
desc_entry = MessageTextView()
|
|
||||||
win.add(desc_entry)
|
|
||||||
|
|
||||||
def on_ok(widget):
|
|
||||||
file_dir = None
|
|
||||||
files_path_list = dialog.get_filenames()
|
|
||||||
desc = desc_entry.get_text()
|
|
||||||
for file_path in files_path_list:
|
|
||||||
if self.send_file(account, contact, file_path, desc) \
|
|
||||||
and file_dir is None:
|
|
||||||
file_dir = os.path.dirname(file_path)
|
|
||||||
if file_dir:
|
|
||||||
app.config.set('last_send_dir', file_dir)
|
|
||||||
dialog.destroy()
|
|
||||||
|
|
||||||
dialog = dialogs.FileChooserDialog(_('Choose File to Send…'),
|
|
||||||
Gtk.FileChooserAction.OPEN, (Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL),
|
|
||||||
Gtk.ResponseType.OK,
|
|
||||||
True, # select multiple true as we can select many files to send
|
|
||||||
app.config.get('last_send_dir'),
|
|
||||||
on_response_ok=on_ok,
|
|
||||||
on_response_cancel=lambda e:dialog.destroy(),
|
|
||||||
preview=True,
|
|
||||||
transient_for=app.interface.roster.window
|
|
||||||
)
|
|
||||||
|
|
||||||
btn = Gtk.Button.new_with_mnemonic(_('_Send'))
|
|
||||||
btn.set_property('can-default', True)
|
|
||||||
# FIXME: add send icon to this button (JUMP_TO)
|
|
||||||
dialog.add_action_widget(btn, Gtk.ResponseType.OK)
|
|
||||||
dialog.set_default_response(Gtk.ResponseType.OK)
|
|
||||||
|
|
||||||
desc_hbox = Gtk.HBox(homogeneous=False, spacing=5)
|
|
||||||
desc_hbox.pack_start(Gtk.Label.new(_('Description: ')), False, False, 0)
|
|
||||||
desc_hbox.pack_start(win, True, True, 0)
|
|
||||||
|
|
||||||
dialog.vbox.pack_start(desc_hbox, False, False, 0)
|
|
||||||
|
|
||||||
btn.show()
|
|
||||||
desc_hbox.show_all()
|
|
||||||
|
|
||||||
def send_file(self, account, contact, file_path, file_desc=''):
|
def send_file(self, account, contact, file_path, file_desc=''):
|
||||||
"""
|
"""
|
||||||
|
@ -411,9 +371,9 @@ class FileTransfersWindow:
|
||||||
app.connections[account].send_file_approval(file_props)
|
app.connections[account].send_file_approval(file_props)
|
||||||
|
|
||||||
def on_file_request_accepted(self, account, contact, file_props):
|
def on_file_request_accepted(self, account, contact, file_props):
|
||||||
def on_ok(widget, account, contact, file_props):
|
def on_ok(account, contact, file_props, file_path):
|
||||||
file_path = dialog2.get_filename()
|
|
||||||
if os.path.exists(file_path):
|
if os.path.exists(file_path):
|
||||||
|
app.config.set('last_save_dir', os.path.dirname(file_path))
|
||||||
# check if we have write permissions
|
# check if we have write permissions
|
||||||
if not os.access(file_path, os.W_OK):
|
if not os.access(file_path, os.W_OK):
|
||||||
file_name = GLib.markup_escape_text(os.path.basename(
|
file_name = GLib.markup_escape_text(os.path.basename(
|
||||||
|
@ -433,13 +393,11 @@ class FileTransfersWindow:
|
||||||
return
|
return
|
||||||
elif response == 100:
|
elif response == 100:
|
||||||
file_props.offset = dl_size
|
file_props.offset = dl_size
|
||||||
dialog2.destroy()
|
|
||||||
self._start_receive(file_path, account, contact, file_props)
|
self._start_receive(file_path, account, contact, file_props)
|
||||||
|
|
||||||
dialog = dialogs.FTOverwriteConfirmationDialog(
|
dialog = dialogs.FTOverwriteConfirmationDialog(
|
||||||
_('This file already exists'), _('What do you want to do?'),
|
_('This file already exists'), _('What do you want to do?'),
|
||||||
propose_resume=not dl_finished, on_response=on_response,
|
propose_resume=not dl_finished, on_response=on_response)
|
||||||
transient_for=dialog2)
|
|
||||||
dialog.set_destroy_with_parent(True)
|
dialog.set_destroy_with_parent(True)
|
||||||
return
|
return
|
||||||
else:
|
else:
|
||||||
|
@ -452,26 +410,15 @@ class FileTransfersWindow:
|
||||||
dirname, _('You do not have permission to create files '
|
dirname, _('You do not have permission to create files '
|
||||||
'in this directory.'))
|
'in this directory.'))
|
||||||
return
|
return
|
||||||
dialog2.destroy()
|
|
||||||
self._start_receive(file_path, account, contact, file_props)
|
self._start_receive(file_path, account, contact, file_props)
|
||||||
|
|
||||||
def on_cancel(widget, account, contact, file_props):
|
con = app.connections[account]
|
||||||
dialog2.destroy()
|
accept_cb = partial(on_ok, account, contact, file_props)
|
||||||
app.connections[account].send_file_rejection(file_props)
|
cancel_cb = partial(con.send_file_rejection, file_props)
|
||||||
|
FileSaveDialog(accept_cb,
|
||||||
dialog2 = dialogs.FileChooserDialog(
|
cancel_cb,
|
||||||
title_text=_('Save File as…'),
|
path=app.config.get('last_save_dir'),
|
||||||
action=Gtk.FileChooserAction.SAVE,
|
file_name=file_props.name)
|
||||||
buttons=(Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
|
|
||||||
Gtk.STOCK_SAVE, Gtk.ResponseType.OK),
|
|
||||||
default_response=Gtk.ResponseType.OK,
|
|
||||||
current_folder=app.config.get('last_save_dir'),
|
|
||||||
on_response_ok=(on_ok, account, contact, file_props),
|
|
||||||
on_response_cancel=(on_cancel, account, contact, file_props))
|
|
||||||
|
|
||||||
dialog2.set_current_name(file_props.name)
|
|
||||||
dialog2.connect('delete-event', lambda widget, event:
|
|
||||||
on_cancel(widget, account, contact, file_props))
|
|
||||||
|
|
||||||
def show_file_request(self, account, contact, file_props):
|
def show_file_request(self, account, contact, file_props):
|
||||||
"""
|
"""
|
||||||
|
@ -1048,3 +995,78 @@ class FileTransfersWindow:
|
||||||
def on_file_transfers_window_key_press_event(self, widget, event):
|
def on_file_transfers_window_key_press_event(self, widget, event):
|
||||||
if event.keyval == Gdk.KEY_Escape: # ESCAPE
|
if event.keyval == Gdk.KEY_Escape: # ESCAPE
|
||||||
self.window.hide()
|
self.window.hide()
|
||||||
|
|
||||||
|
|
||||||
|
class SendFileDialog(Gtk.ApplicationWindow):
|
||||||
|
def __init__(self, send_callback, transient_for):
|
||||||
|
active_window = app.app.get_active_window()
|
||||||
|
Gtk.ApplicationWindow.__init__(self)
|
||||||
|
self.set_name('SendFileDialog')
|
||||||
|
self.set_application(app.app)
|
||||||
|
self.set_show_menubar(False)
|
||||||
|
self.set_resizable(True)
|
||||||
|
self.set_default_size(400, 250)
|
||||||
|
self.set_type_hint(Gdk.WindowTypeHint.DIALOG)
|
||||||
|
self.set_transient_for(active_window)
|
||||||
|
self.set_title(_('Choose a File to Send…'))
|
||||||
|
self.set_destroy_with_parent(True)
|
||||||
|
|
||||||
|
self._send_callback = send_callback
|
||||||
|
|
||||||
|
xml = gtkgui_helpers.get_gtk_builder('send_file_dialog.ui')
|
||||||
|
grid = xml.get_object('send_file_grid')
|
||||||
|
|
||||||
|
self._filebox = xml.get_object('listbox')
|
||||||
|
self._description = xml.get_object('description')
|
||||||
|
|
||||||
|
self.add(grid)
|
||||||
|
self.connect('key-press-event', self._key_press_event)
|
||||||
|
|
||||||
|
xml.connect_signals(self)
|
||||||
|
self.show_all()
|
||||||
|
|
||||||
|
def _send(self, button):
|
||||||
|
for file in self._filebox.get_children():
|
||||||
|
self._send_callback(str(file.path), self._get_description())
|
||||||
|
self.destroy()
|
||||||
|
|
||||||
|
def _select_files(self, button):
|
||||||
|
FileChooserDialog(self._set_files,
|
||||||
|
select_multiple=True,
|
||||||
|
transient_for=self,
|
||||||
|
path=app.config.get('last_send_dir'))
|
||||||
|
|
||||||
|
def _set_files(self, filenames):
|
||||||
|
# Clear the ListBox
|
||||||
|
self._filebox.foreach(self._remove_widget, None)
|
||||||
|
|
||||||
|
for file in filenames:
|
||||||
|
row = FileRow(file)
|
||||||
|
if row.path.is_dir():
|
||||||
|
continue
|
||||||
|
last_dir = row.path.parent
|
||||||
|
self._filebox.add(row)
|
||||||
|
self._filebox.show_all()
|
||||||
|
app.config.set('last_send_dir', str(last_dir))
|
||||||
|
|
||||||
|
def _remove_widget(self, widget, data):
|
||||||
|
self._filebox.remove(widget)
|
||||||
|
|
||||||
|
def _get_description(self):
|
||||||
|
buffer_ = self._description.get_buffer()
|
||||||
|
start, end = buffer_.get_bounds()
|
||||||
|
return buffer_.get_text(start, end, False)
|
||||||
|
|
||||||
|
def _key_press_event(self, widget, event):
|
||||||
|
if event.keyval == Gdk.KEY_Escape:
|
||||||
|
self.destroy()
|
||||||
|
|
||||||
|
|
||||||
|
class FileRow(Gtk.ListBoxRow):
|
||||||
|
def __init__(self, path):
|
||||||
|
Gtk.ListBoxRow.__init__(self)
|
||||||
|
self.path = Path(path)
|
||||||
|
label = Gtk.Label(self.path.name)
|
||||||
|
label.set_ellipsize(Pango.EllipsizeMode.END)
|
||||||
|
label.set_xalign(0)
|
||||||
|
self.add(label)
|
||||||
|
|
|
@ -51,6 +51,7 @@ from gajim.common import i18n
|
||||||
from gajim.common import app
|
from gajim.common import app
|
||||||
from gajim.common import pep
|
from gajim.common import pep
|
||||||
from gajim.common import configpaths
|
from gajim.common import configpaths
|
||||||
|
from gajim.filechoosers import AvatarSaveDialog
|
||||||
|
|
||||||
gtk_icon_theme = Gtk.IconTheme.get_default()
|
gtk_icon_theme = Gtk.IconTheme.get_default()
|
||||||
gtk_icon_theme.append_search_path(configpaths.get('ICONS'))
|
gtk_icon_theme.append_search_path(configpaths.get('ICONS'))
|
||||||
|
@ -450,6 +451,7 @@ def on_avatar_save_as_menuitem_activate(widget, avatar, default_name=''):
|
||||||
if response < 0:
|
if response < 0:
|
||||||
return
|
return
|
||||||
|
|
||||||
|
app.config.set('last_save_dir', os.path.dirname(file_path))
|
||||||
if isinstance(avatar, str):
|
if isinstance(avatar, str):
|
||||||
# We got a SHA
|
# We got a SHA
|
||||||
pixbuf = app.interface.get_avatar(avatar)
|
pixbuf = app.interface.get_avatar(avatar)
|
||||||
|
@ -459,10 +461,8 @@ def on_avatar_save_as_menuitem_activate(widget, avatar, default_name=''):
|
||||||
extension = os.path.splitext(file_path)[1]
|
extension = os.path.splitext(file_path)[1]
|
||||||
if not extension:
|
if not extension:
|
||||||
# Silently save as Jpeg image
|
# Silently save as Jpeg image
|
||||||
image_format = 'jpeg'
|
image_format = 'png'
|
||||||
file_path += '.jpeg'
|
file_path += '.png'
|
||||||
elif extension == 'jpg':
|
|
||||||
image_format = 'jpeg'
|
|
||||||
else:
|
else:
|
||||||
image_format = extension[1:] # remove leading dot
|
image_format = extension[1:] # remove leading dot
|
||||||
|
|
||||||
|
@ -473,19 +473,16 @@ def on_avatar_save_as_menuitem_activate(widget, avatar, default_name=''):
|
||||||
log.error('Error saving avatar: %s' % str(e))
|
log.error('Error saving avatar: %s' % str(e))
|
||||||
if os.path.exists(file_path):
|
if os.path.exists(file_path):
|
||||||
os.remove(file_path)
|
os.remove(file_path)
|
||||||
new_file_path = '.'.join(file_path.split('.')[:-1]) + '.jpeg'
|
new_file_path = '.'.join(file_path.split('.')[:-1]) + '.png'
|
||||||
def on_ok(file_path, pixbuf):
|
def on_ok(file_path, pixbuf):
|
||||||
pixbuf.savev(file_path, 'jpeg', [], [])
|
pixbuf.savev(file_path, 'png', [], [])
|
||||||
dialogs.ConfirmationDialog(_('Extension not supported'),
|
dialogs.ConfirmationDialog(_('Extension not supported'),
|
||||||
_('Image cannot be saved in %(type)s format. Save as '
|
_('Image cannot be saved in %(type)s format. Save as '
|
||||||
'%(new_filename)s?') % {'type': image_format,
|
'%(new_filename)s?') % {'type': image_format,
|
||||||
'new_filename': new_file_path},
|
'new_filename': new_file_path},
|
||||||
on_response_ok = (on_ok, new_file_path, pixbuf))
|
on_response_ok = (on_ok, new_file_path, pixbuf))
|
||||||
else:
|
|
||||||
dialog.destroy()
|
|
||||||
|
|
||||||
def on_ok(widget):
|
def on_ok(file_path):
|
||||||
file_path = dialog.get_filename()
|
|
||||||
if os.path.exists(file_path):
|
if os.path.exists(file_path):
|
||||||
# check if we have write permissions
|
# check if we have write permissions
|
||||||
if not os.access(file_path, os.W_OK):
|
if not os.access(file_path, os.W_OK):
|
||||||
|
@ -496,8 +493,7 @@ def on_avatar_save_as_menuitem_activate(widget, avatar, default_name=''):
|
||||||
return
|
return
|
||||||
dialog2 = dialogs.FTOverwriteConfirmationDialog(
|
dialog2 = dialogs.FTOverwriteConfirmationDialog(
|
||||||
_('This file already exists'), _('What do you want to do?'),
|
_('This file already exists'), _('What do you want to do?'),
|
||||||
propose_resume=False, on_response=(on_continue, file_path),
|
propose_resume=False, on_response=(on_continue, file_path))
|
||||||
transient_for=dialog)
|
|
||||||
dialog2.set_destroy_with_parent(True)
|
dialog2.set_destroy_with_parent(True)
|
||||||
else:
|
else:
|
||||||
dirname = os.path.dirname(file_path)
|
dirname = os.path.dirname(file_path)
|
||||||
|
@ -509,19 +505,11 @@ def on_avatar_save_as_menuitem_activate(widget, avatar, default_name=''):
|
||||||
|
|
||||||
on_continue(0, file_path)
|
on_continue(0, file_path)
|
||||||
|
|
||||||
def on_cancel(widget):
|
transient = app.app.get_active_window()
|
||||||
dialog.destroy()
|
AvatarSaveDialog(on_ok,
|
||||||
|
path=app.config.get('last_save_dir'),
|
||||||
dialog = dialogs.FileChooserDialog(title_text=_('Save Image as…'),
|
file_name='%s.png' % default_name,
|
||||||
action=Gtk.FileChooserAction.SAVE, buttons=(Gtk.STOCK_CANCEL,
|
transient_for=transient)
|
||||||
Gtk.ResponseType.CANCEL, Gtk.STOCK_SAVE, Gtk.ResponseType.OK),
|
|
||||||
default_response=Gtk.ResponseType.OK,
|
|
||||||
current_folder=app.config.get('last_save_dir'), on_response_ok=on_ok,
|
|
||||||
on_response_cancel=on_cancel)
|
|
||||||
|
|
||||||
dialog.set_current_name(default_name + '.jpeg')
|
|
||||||
dialog.connect('delete-event', lambda widget, event:
|
|
||||||
on_cancel(widget))
|
|
||||||
|
|
||||||
def create_combobox(value_list, selected_value = None):
|
def create_combobox(value_list, selected_value = None):
|
||||||
"""
|
"""
|
||||||
|
|
|
@ -39,6 +39,7 @@ import sys
|
||||||
import re
|
import re
|
||||||
import time
|
import time
|
||||||
import hashlib
|
import hashlib
|
||||||
|
from functools import partial
|
||||||
|
|
||||||
from gi.repository import Gtk
|
from gi.repository import Gtk
|
||||||
from gi.repository import GdkPixbuf
|
from gi.repository import GdkPixbuf
|
||||||
|
@ -66,7 +67,7 @@ from gajim import notify
|
||||||
from gajim import message_control
|
from gajim import message_control
|
||||||
from gajim.dialog_messages import get_dialog
|
from gajim.dialog_messages import get_dialog
|
||||||
from gajim.dialogs import ProgressWindow
|
from gajim.dialogs import ProgressWindow
|
||||||
from gajim.dialogs import FileChooserDialog
|
from gajim.filechoosers import FileChooserDialog
|
||||||
|
|
||||||
from gajim.chat_control_base import ChatControlBase
|
from gajim.chat_control_base import ChatControlBase
|
||||||
from gajim.chat_control import ChatControl
|
from gajim.chat_control import ChatControl
|
||||||
|
@ -1147,22 +1148,13 @@ class Interface:
|
||||||
ProgressWindow(file)
|
ProgressWindow(file)
|
||||||
|
|
||||||
def send_httpupload(self, chat_control):
|
def send_httpupload(self, chat_control):
|
||||||
FileChooserDialog(
|
accept_cb = partial(self.on_file_dialog_ok, chat_control)
|
||||||
on_response_ok=lambda widget: self.on_file_dialog_ok(widget,
|
FileChooserDialog(accept_cb,
|
||||||
chat_control),
|
select_multiple=True,
|
||||||
title_text=_('Choose file to send'),
|
transient_for=chat_control.parent_win.window)
|
||||||
action=Gtk.FileChooserAction.OPEN,
|
|
||||||
buttons=(Gtk.STOCK_CANCEL, Gtk.ResponseType.CANCEL,
|
|
||||||
Gtk.STOCK_OPEN, Gtk.ResponseType.OK),
|
|
||||||
select_multiple=True,
|
|
||||||
default_response=Gtk.ResponseType.OK,
|
|
||||||
preview=True,
|
|
||||||
transient_for=chat_control.parent_win.window)
|
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def on_file_dialog_ok(widget, chat_control):
|
def on_file_dialog_ok(chat_control, paths):
|
||||||
paths = widget.get_filenames()
|
|
||||||
widget.destroy()
|
|
||||||
con = app.connections[chat_control.account]
|
con = app.connections[chat_control.account]
|
||||||
groupchat = chat_control.type_id == message_control.TYPE_GC
|
groupchat = chat_control.type_id == message_control.TYPE_GC
|
||||||
for path in paths:
|
for path in paths:
|
||||||
|
|
|
@ -83,10 +83,11 @@ if is_standalone():
|
||||||
configpaths.init()
|
configpaths.init()
|
||||||
|
|
||||||
from gajim.common import app
|
from gajim.common import app
|
||||||
from gajim import gtkgui_helpers
|
|
||||||
from gajim.common.const import JIDConstant, KindConstant
|
from gajim.common.const import JIDConstant, KindConstant
|
||||||
from gajim.common import helpers
|
from gajim.common import helpers
|
||||||
from gajim import dialogs
|
from gajim import dialogs
|
||||||
|
from gajim.filechoosers import FileSaveDialog
|
||||||
|
from gajim import gtkgui_helpers
|
||||||
|
|
||||||
|
|
||||||
@unique
|
@unique
|
||||||
|
@ -465,24 +466,14 @@ class HistoryManager:
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def on_export_menuitem_activate(self, widget):
|
def on_export_menuitem_activate(self, widget):
|
||||||
xml = gtkgui_helpers.get_gtk_builder('history_manager.ui',
|
FileSaveDialog(self._on_export,
|
||||||
'filechooserdialog')
|
transient_for=self.window,
|
||||||
xml.connect_signals(self)
|
modal=True)
|
||||||
|
|
||||||
dlg = xml.get_object('filechooserdialog')
|
def _on_export(self, filename):
|
||||||
dlg.set_title(_('Exporting History Logs…'))
|
liststore, list_of_paths = self.jids_listview.get_selection()\
|
||||||
dlg.set_current_folder(configpaths.get('HOME'))
|
.get_selected_rows()
|
||||||
dlg.props.do_overwrite_confirmation = True
|
self._export_jids_logs_to_file(liststore, list_of_paths, filename)
|
||||||
response = dlg.run()
|
|
||||||
|
|
||||||
if response == Gtk.ResponseType.OK: # user want us to export ;)
|
|
||||||
liststore, list_of_paths = self.jids_listview.get_selection()\
|
|
||||||
.get_selected_rows()
|
|
||||||
path_to_file = dlg.get_filename()
|
|
||||||
self._export_jids_logs_to_file(liststore, list_of_paths,
|
|
||||||
path_to_file)
|
|
||||||
|
|
||||||
dlg.destroy()
|
|
||||||
|
|
||||||
def on_delete_menuitem_activate(self, widget, listview):
|
def on_delete_menuitem_activate(self, widget, listview):
|
||||||
widget_name = Gtk.Buildable.get_name(listview)
|
widget_name = Gtk.Buildable.get_name(listview)
|
||||||
|
|
|
@ -35,7 +35,8 @@ import os
|
||||||
from enum import IntEnum, unique
|
from enum import IntEnum, unique
|
||||||
|
|
||||||
from gajim import gtkgui_helpers
|
from gajim import gtkgui_helpers
|
||||||
from gajim.dialogs import WarningDialog, YesNoDialog, ArchiveChooserDialog
|
from gajim.dialogs import WarningDialog, YesNoDialog
|
||||||
|
from gajim.filechoosers import ArchiveChooserDialog
|
||||||
from gajim.htmltextview import HtmlTextView
|
from gajim.htmltextview import HtmlTextView
|
||||||
from gajim.common import app
|
from gajim.common import app
|
||||||
from gajim.common import configpaths
|
from gajim.common import configpaths
|
||||||
|
@ -309,8 +310,7 @@ class PluginsWindow(object):
|
||||||
sel = self.installed_plugins_treeview.get_selection()
|
sel = self.installed_plugins_treeview.get_selection()
|
||||||
sel.select_iter(iter_)
|
sel.select_iter(iter_)
|
||||||
|
|
||||||
self.dialog = ArchiveChooserDialog(
|
ArchiveChooserDialog(_try_install, transient_for=self.window)
|
||||||
on_response_ok=_try_install, transient_for=self.window)
|
|
||||||
|
|
||||||
|
|
||||||
class GajimPluginConfigDialog(Gtk.Dialog):
|
class GajimPluginConfigDialog(Gtk.Dialog):
|
||||||
|
|
|
@ -33,6 +33,7 @@ import hashlib
|
||||||
|
|
||||||
from gajim import gtkgui_helpers
|
from gajim import gtkgui_helpers
|
||||||
from gajim import dialogs
|
from gajim import dialogs
|
||||||
|
from gajim.filechoosers import AvatarChooserDialog
|
||||||
from gajim.common.const import AvatarSize
|
from gajim.common.const import AvatarSize
|
||||||
|
|
||||||
from gajim.common import app
|
from gajim.common import app
|
||||||
|
@ -107,7 +108,7 @@ class ProfileWindow:
|
||||||
if event.keyval == Gdk.KEY_Escape:
|
if event.keyval == Gdk.KEY_Escape:
|
||||||
self.window.destroy()
|
self.window.destroy()
|
||||||
|
|
||||||
def on_clear_button_clicked(self, widget):
|
def _clear_photo(self, widget):
|
||||||
# empty the image
|
# empty the image
|
||||||
button = self.xml.get_object('PHOTO_button')
|
button = self.xml.get_object('PHOTO_button')
|
||||||
image = button.get_image()
|
image = button.get_image()
|
||||||
|
@ -115,12 +116,14 @@ class ProfileWindow:
|
||||||
button.hide()
|
button.hide()
|
||||||
text_button = self.xml.get_object('NOPHOTO_button')
|
text_button = self.xml.get_object('NOPHOTO_button')
|
||||||
text_button.show()
|
text_button.show()
|
||||||
|
remove_avatar = self.xml.get_object('remove_avatar')
|
||||||
|
remove_avatar.hide()
|
||||||
self.avatar_encoded = None
|
self.avatar_encoded = None
|
||||||
self.avatar_sha = None
|
self.avatar_sha = None
|
||||||
self.avatar_mime_type = None
|
self.avatar_mime_type = None
|
||||||
|
|
||||||
def on_set_avatar_button_clicked(self, widget):
|
def on_set_avatar_button_clicked(self, widget):
|
||||||
def on_ok(widget, path_to_file):
|
def on_ok(path_to_file):
|
||||||
with open(path_to_file, 'rb') as file:
|
with open(path_to_file, 'rb') as file:
|
||||||
data = file.read()
|
data = file.read()
|
||||||
sha = app.interface.save_avatar(data, publish=True)
|
sha = app.interface.save_avatar(data, publish=True)
|
||||||
|
@ -129,9 +132,6 @@ class ProfileWindow:
|
||||||
_('Could not load image'), transient_for=self.window)
|
_('Could not load image'), transient_for=self.window)
|
||||||
return
|
return
|
||||||
|
|
||||||
self.dialog.destroy()
|
|
||||||
self.dialog = None
|
|
||||||
|
|
||||||
scale = self.window.get_scale_factor()
|
scale = self.window.get_scale_factor()
|
||||||
surface = app.interface.get_avatar(sha, AvatarSize.VCARD, scale)
|
surface = app.interface.get_avatar(sha, AvatarSize.VCARD, scale)
|
||||||
|
|
||||||
|
@ -142,26 +142,15 @@ class ProfileWindow:
|
||||||
text_button = self.xml.get_object('NOPHOTO_button')
|
text_button = self.xml.get_object('NOPHOTO_button')
|
||||||
text_button.hide()
|
text_button.hide()
|
||||||
|
|
||||||
|
remove_avatar = self.xml.get_object('remove_avatar')
|
||||||
|
remove_avatar.show()
|
||||||
|
|
||||||
self.avatar_sha = sha
|
self.avatar_sha = sha
|
||||||
publish = app.interface.get_avatar(sha, publish=True)
|
publish = app.interface.get_avatar(sha, publish=True)
|
||||||
self.avatar_encoded = base64.b64encode(publish).decode('utf-8')
|
self.avatar_encoded = base64.b64encode(publish).decode('utf-8')
|
||||||
self.avatar_mime_type = 'image/jpeg'
|
self.avatar_mime_type = 'image/png'
|
||||||
|
|
||||||
def on_clear(widget):
|
AvatarChooserDialog(on_ok, transient_for=self.window)
|
||||||
self.dialog.destroy()
|
|
||||||
self.dialog = None
|
|
||||||
self.on_clear_button_clicked(widget)
|
|
||||||
|
|
||||||
def on_cancel(widget):
|
|
||||||
self.dialog.destroy()
|
|
||||||
self.dialog = None
|
|
||||||
|
|
||||||
if self.dialog:
|
|
||||||
self.dialog.present()
|
|
||||||
else:
|
|
||||||
self.dialog = dialogs.AvatarChooserDialog(
|
|
||||||
on_response_ok=on_ok, on_response_cancel=on_cancel,
|
|
||||||
on_response_clear=on_clear)
|
|
||||||
|
|
||||||
def on_PHOTO_button_press_event(self, widget, event):
|
def on_PHOTO_button_press_event(self, widget, event):
|
||||||
"""
|
"""
|
||||||
|
@ -218,11 +207,13 @@ class ProfileWindow:
|
||||||
button = self.xml.get_object('PHOTO_button')
|
button = self.xml.get_object('PHOTO_button')
|
||||||
image = button.get_image()
|
image = button.get_image()
|
||||||
text_button = self.xml.get_object('NOPHOTO_button')
|
text_button = self.xml.get_object('NOPHOTO_button')
|
||||||
|
remove_avatar = self.xml.get_object('remove_avatar')
|
||||||
if not 'PHOTO' in vcard_:
|
if not 'PHOTO' in vcard_:
|
||||||
# set default image
|
# set default image
|
||||||
image.set_from_pixbuf(None)
|
image.set_from_pixbuf(None)
|
||||||
button.hide()
|
button.hide()
|
||||||
text_button.show()
|
text_button.show()
|
||||||
|
remove_avatar.hide()
|
||||||
for i in vcard_.keys():
|
for i in vcard_.keys():
|
||||||
if i == 'PHOTO':
|
if i == 'PHOTO':
|
||||||
photo_encoded = vcard_[i]['BINVAL']
|
photo_encoded = vcard_[i]['BINVAL']
|
||||||
|
@ -241,6 +232,7 @@ class ProfileWindow:
|
||||||
GdkPixbuf.InterpType.BILINEAR)
|
GdkPixbuf.InterpType.BILINEAR)
|
||||||
image.set_from_pixbuf(pixbuf)
|
image.set_from_pixbuf(pixbuf)
|
||||||
button.show()
|
button.show()
|
||||||
|
remove_avatar.show()
|
||||||
text_button.hide()
|
text_button.hide()
|
||||||
continue
|
continue
|
||||||
if i == 'ADR' or i == 'TEL' or i == 'EMAIL':
|
if i == 'ADR' or i == 'TEL' or i == 'EMAIL':
|
||||||
|
|
Loading…
Reference in New Issue