mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-19 07:37:11 +02:00
Remove the copy of gtk file dialog
This commit is contained in:
parent
85f013ebdb
commit
0b21c04489
8 changed files with 0 additions and 870 deletions
|
@ -861,8 +861,6 @@ PRIVATE
|
|||
platform/linux/linux_gdk_helper.h
|
||||
platform/linux/linux_gsd_media_keys.cpp
|
||||
platform/linux/linux_gsd_media_keys.h
|
||||
platform/linux/linux_gtk_file_dialog.cpp
|
||||
platform/linux/linux_gtk_file_dialog.h
|
||||
platform/linux/linux_gtk_integration_dummy.cpp
|
||||
platform/linux/linux_gtk_integration_p.h
|
||||
platform/linux/linux_gtk_integration.cpp
|
||||
|
@ -1194,8 +1192,6 @@ if (DESKTOP_APP_DISABLE_GTK_INTEGRATION)
|
|||
remove_target_sources(Telegram ${src_loc}
|
||||
platform/linux/linux_gdk_helper.cpp
|
||||
platform/linux/linux_gdk_helper.h
|
||||
platform/linux/linux_gtk_file_dialog.cpp
|
||||
platform/linux/linux_gtk_file_dialog.h
|
||||
platform/linux/linux_gtk_integration_p.h
|
||||
platform/linux/linux_gtk_integration.cpp
|
||||
platform/linux/linux_gtk_open_with_dialog.cpp
|
||||
|
|
|
@ -117,20 +117,6 @@ bool Get(
|
|||
}
|
||||
}
|
||||
#endif // !DESKTOP_APP_DISABLE_DBUS_INTEGRATION
|
||||
if (const auto integration = GtkIntegration::Instance()) {
|
||||
const auto result = integration->getFileDialog(
|
||||
parent,
|
||||
files,
|
||||
remoteContent,
|
||||
caption,
|
||||
filter,
|
||||
type,
|
||||
startFile);
|
||||
|
||||
if (result.has_value()) {
|
||||
return *result;
|
||||
}
|
||||
}
|
||||
return ::FileDialog::internal::GetDefault(
|
||||
parent,
|
||||
files,
|
||||
|
|
|
@ -1,708 +0,0 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#include "platform/linux/linux_gtk_file_dialog.h"
|
||||
|
||||
#include "platform/platform_file_utilities.h"
|
||||
#include "platform/linux/linux_gtk_integration_p.h"
|
||||
#include "platform/linux/linux_gdk_helper.h"
|
||||
#include "platform/linux/linux_desktop_environment.h"
|
||||
#include "lang/lang_keys.h"
|
||||
#include "storage/localstorage.h"
|
||||
#include "base/qt_adapters.h"
|
||||
|
||||
#include <QtGui/QWindow>
|
||||
#include <QtWidgets/QFileDialog>
|
||||
#include <private/qguiapplication_p.h>
|
||||
|
||||
namespace Platform {
|
||||
namespace FileDialog {
|
||||
namespace Gtk {
|
||||
namespace {
|
||||
|
||||
using namespace Platform::Gtk;
|
||||
using Type = ::FileDialog::internal::Type;
|
||||
|
||||
// GTK file chooser image preview: thanks to Chromium
|
||||
|
||||
// The size of the preview we display for selected image files. We set height
|
||||
// larger than width because generally there is more free space vertically
|
||||
// than horiztonally (setting the preview image will alway expand the width of
|
||||
// the dialog, but usually not the height). The image's aspect ratio will always
|
||||
// be preserved.
|
||||
constexpr auto kPreviewWidth = 256;
|
||||
constexpr auto kPreviewHeight = 512;
|
||||
|
||||
const char *filterRegExp =
|
||||
"^(.*)\\(([a-zA-Z0-9_.,*? +;#\\-\\[\\]@\\{\\}/!<>\\$%&=^~:\\|]*)\\)$";
|
||||
|
||||
QStringList makeFilterList(const QString &filter) {
|
||||
QString f(filter);
|
||||
|
||||
if (f.isEmpty())
|
||||
return QStringList();
|
||||
|
||||
QString sep(QLatin1String(";;"));
|
||||
int i = f.indexOf(sep, 0);
|
||||
if (i == -1) {
|
||||
if (f.indexOf(QLatin1Char('\n'), 0) != -1) {
|
||||
sep = QLatin1Char('\n');
|
||||
i = f.indexOf(sep, 0);
|
||||
}
|
||||
}
|
||||
|
||||
return f.split(sep);
|
||||
}
|
||||
|
||||
// Makes a list of filters from a normal filter string "Image Files (*.png *.jpg)"
|
||||
QStringList cleanFilterList(const QString &filter) {
|
||||
QRegExp regexp(QString::fromLatin1(filterRegExp));
|
||||
Assert(regexp.isValid());
|
||||
QString f = filter;
|
||||
int i = regexp.indexIn(f);
|
||||
if (i >= 0)
|
||||
f = regexp.cap(2);
|
||||
return f.split(QLatin1Char(' '), base::QStringSkipEmptyParts);
|
||||
}
|
||||
|
||||
bool Supported() {
|
||||
return (gtk_widget_hide_on_delete != nullptr)
|
||||
&& (gtk_clipboard_store != nullptr)
|
||||
&& (gtk_clipboard_get != nullptr)
|
||||
&& (gtk_widget_destroy != nullptr)
|
||||
&& (gtk_dialog_get_type != nullptr)
|
||||
&& (gtk_dialog_run != nullptr)
|
||||
&& (gtk_widget_realize != nullptr)
|
||||
&& (gdk_window_set_modal_hint != nullptr)
|
||||
&& (gtk_widget_show != nullptr)
|
||||
&& (gdk_window_focus != nullptr)
|
||||
&& (gtk_widget_hide != nullptr)
|
||||
&& (gtk_widget_hide_on_delete != nullptr)
|
||||
&& (gtk_file_chooser_dialog_new != nullptr)
|
||||
&& (gtk_file_chooser_get_type != nullptr)
|
||||
&& (gtk_file_chooser_set_current_folder != nullptr)
|
||||
&& (gtk_file_chooser_get_current_folder != nullptr)
|
||||
&& (gtk_file_chooser_set_current_name != nullptr)
|
||||
&& (gtk_file_chooser_select_filename != nullptr)
|
||||
&& (gtk_file_chooser_get_filenames != nullptr)
|
||||
&& (gtk_file_chooser_set_filter != nullptr)
|
||||
&& (gtk_file_chooser_get_filter != nullptr)
|
||||
&& (gtk_window_get_type != nullptr)
|
||||
&& (gtk_window_set_title != nullptr)
|
||||
&& (gtk_file_chooser_set_local_only != nullptr)
|
||||
&& (gtk_file_chooser_set_action != nullptr)
|
||||
&& (gtk_file_chooser_set_select_multiple != nullptr)
|
||||
&& (gtk_file_chooser_set_do_overwrite_confirmation != nullptr)
|
||||
&& (gtk_file_chooser_remove_filter != nullptr)
|
||||
&& (gtk_file_filter_set_name != nullptr)
|
||||
&& (gtk_file_filter_add_pattern != nullptr)
|
||||
&& (gtk_file_chooser_add_filter != nullptr)
|
||||
&& (gtk_file_filter_new != nullptr);
|
||||
}
|
||||
|
||||
bool PreviewSupported() {
|
||||
return (gdk_pixbuf_new_from_file_at_size != nullptr);
|
||||
}
|
||||
|
||||
bool CustomButtonsSupported() {
|
||||
return (gtk_dialog_get_widget_for_response != nullptr)
|
||||
&& (gtk_button_set_label != nullptr)
|
||||
&& (gtk_button_get_type != nullptr);
|
||||
}
|
||||
|
||||
// This is a patched copy of qgtk2 theme plugin.
|
||||
// We need to use our own gtk file dialog instead of
|
||||
// styling Qt file dialog, because Qt only works with gtk2.
|
||||
// We need to be able to work with gtk2 and gtk3, because
|
||||
// we use gtk3 to work with appindicator3.
|
||||
class QGtkDialog : public QWindow {
|
||||
public:
|
||||
QGtkDialog(GtkWidget *gtkWidget);
|
||||
~QGtkDialog();
|
||||
|
||||
GtkDialog *gtkDialog() const;
|
||||
|
||||
void exec();
|
||||
void show(Qt::WindowFlags flags, Qt::WindowModality modality, QWindow *parent);
|
||||
void hide();
|
||||
|
||||
rpl::producer<> accept();
|
||||
rpl::producer<> reject();
|
||||
|
||||
protected:
|
||||
static void onResponse(QGtkDialog *dialog, int response);
|
||||
|
||||
private:
|
||||
void onParentWindowDestroyed();
|
||||
|
||||
GtkWidget *gtkWidget = nullptr;
|
||||
|
||||
rpl::event_stream<> _accept;
|
||||
rpl::event_stream<> _reject;
|
||||
|
||||
bool _destroyedConnected = false;
|
||||
|
||||
};
|
||||
|
||||
class GtkFileDialog : public QDialog {
|
||||
public:
|
||||
GtkFileDialog(
|
||||
QWidget *parent = nullptr,
|
||||
const QString &caption = QString(),
|
||||
const QString &directory = QString(),
|
||||
const QString &filter = QString());
|
||||
~GtkFileDialog();
|
||||
|
||||
void setVisible(bool visible) override;
|
||||
|
||||
void setWindowTitle(const QString &windowTitle) {
|
||||
_windowTitle = windowTitle;
|
||||
}
|
||||
void setAcceptMode(QFileDialog::AcceptMode acceptMode) {
|
||||
_acceptMode = acceptMode;
|
||||
}
|
||||
void setFileMode(QFileDialog::FileMode fileMode) {
|
||||
_fileMode = fileMode;
|
||||
}
|
||||
void setOption(QFileDialog::Option option, bool on = true) {
|
||||
if (on) {
|
||||
_options |= option;
|
||||
} else {
|
||||
_options &= ~option;
|
||||
}
|
||||
}
|
||||
|
||||
int exec() override;
|
||||
|
||||
bool defaultNameFilterDisables() const;
|
||||
void setDirectory(const QString &directory);
|
||||
QDir directory() const;
|
||||
void selectFile(const QString &filename);
|
||||
QStringList selectedFiles() const;
|
||||
void setFilter();
|
||||
void selectNameFilter(const QString &filter);
|
||||
QString selectedNameFilter() const;
|
||||
|
||||
private:
|
||||
static void onSelectionChanged(GtkDialog *dialog, GtkFileDialog *helper);
|
||||
static void onCurrentFolderChanged(GtkFileDialog *helper);
|
||||
static void onUpdatePreview(GtkDialog *gtkDialog, GtkFileDialog *helper);
|
||||
void applyOptions();
|
||||
void setNameFilters(const QStringList &filters);
|
||||
|
||||
void showHelper(Qt::WindowFlags flags, Qt::WindowModality modality, QWindow *parent);
|
||||
void hideHelper();
|
||||
|
||||
void onAccepted();
|
||||
void onRejected();
|
||||
|
||||
// Options
|
||||
QFileDialog::Options _options;
|
||||
QString _windowTitle = "Choose file";
|
||||
QString _initialDirectory;
|
||||
QStringList _initialFiles;
|
||||
QStringList _nameFilters;
|
||||
QFileDialog::AcceptMode _acceptMode = QFileDialog::AcceptOpen;
|
||||
QFileDialog::FileMode _fileMode = QFileDialog::ExistingFile;
|
||||
|
||||
QString _dir;
|
||||
QStringList _selection;
|
||||
QHash<QString, GtkFileFilter*> _filters;
|
||||
QHash<GtkFileFilter*, QString> _filterNames;
|
||||
QScopedPointer<QGtkDialog> d;
|
||||
GtkWidget *_preview = nullptr;
|
||||
|
||||
rpl::lifetime _lifetime;
|
||||
};
|
||||
|
||||
QGtkDialog::QGtkDialog(GtkWidget *gtkWidget) : gtkWidget(gtkWidget) {
|
||||
g_signal_connect_swapped(G_OBJECT(gtkWidget), "response", G_CALLBACK(onResponse), this);
|
||||
g_signal_connect(G_OBJECT(gtkWidget), "delete-event", G_CALLBACK(gtk_widget_hide_on_delete), nullptr);
|
||||
}
|
||||
|
||||
QGtkDialog::~QGtkDialog() {
|
||||
gtk_clipboard_store(gtk_clipboard_get(GDK_SELECTION_CLIPBOARD));
|
||||
gtk_widget_destroy(gtkWidget);
|
||||
}
|
||||
|
||||
GtkDialog *QGtkDialog::gtkDialog() const {
|
||||
return GTK_DIALOG(gtkWidget);
|
||||
}
|
||||
|
||||
void QGtkDialog::exec() {
|
||||
if (modality() == Qt::ApplicationModal) {
|
||||
// block input to the whole app, including other GTK dialogs
|
||||
gtk_dialog_run(gtkDialog());
|
||||
} else {
|
||||
// block input to the window, allow input to other GTK dialogs
|
||||
QEventLoop loop;
|
||||
rpl::lifetime lifetime;
|
||||
|
||||
accept(
|
||||
) | rpl::start_with_next([&] {
|
||||
loop.quit();
|
||||
}, lifetime);
|
||||
|
||||
reject(
|
||||
) | rpl::start_with_next([&] {
|
||||
loop.quit();
|
||||
}, lifetime);
|
||||
|
||||
loop.exec();
|
||||
}
|
||||
}
|
||||
|
||||
void QGtkDialog::show(Qt::WindowFlags flags, Qt::WindowModality modality, QWindow *parent) {
|
||||
if (!std::exchange(_destroyedConnected, true)) {
|
||||
connect(parent, &QWindow::destroyed, this, [=] { onParentWindowDestroyed(); });
|
||||
}
|
||||
setParent(parent);
|
||||
setFlags(flags);
|
||||
setModality(modality);
|
||||
|
||||
gtk_widget_realize(gtkWidget); // creates X window
|
||||
|
||||
if (parent) {
|
||||
internal::GdkSetTransientFor(gtk_widget_get_window(gtkWidget), parent);
|
||||
}
|
||||
|
||||
if (modality != Qt::NonModal) {
|
||||
gdk_window_set_modal_hint(gtk_widget_get_window(gtkWidget), true);
|
||||
QGuiApplicationPrivate::showModalWindow(this);
|
||||
}
|
||||
|
||||
gtk_widget_show(gtkWidget);
|
||||
gdk_window_focus(gtk_widget_get_window(gtkWidget), 0);
|
||||
}
|
||||
|
||||
void QGtkDialog::hide() {
|
||||
QGuiApplicationPrivate::hideModalWindow(this);
|
||||
gtk_widget_hide(gtkWidget);
|
||||
}
|
||||
|
||||
rpl::producer<> QGtkDialog::accept() {
|
||||
return _accept.events();
|
||||
}
|
||||
|
||||
rpl::producer<> QGtkDialog::reject() {
|
||||
return _reject.events();
|
||||
}
|
||||
|
||||
void QGtkDialog::onResponse(QGtkDialog *dialog, int response) {
|
||||
if (response == GTK_RESPONSE_OK)
|
||||
dialog->_accept.fire({});
|
||||
else
|
||||
dialog->_reject.fire({});
|
||||
}
|
||||
|
||||
void QGtkDialog::onParentWindowDestroyed() {
|
||||
// The Gtk*DialogHelper classes own this object. Make sure the parent doesn't delete it.
|
||||
setParent(nullptr);
|
||||
}
|
||||
|
||||
GtkFileDialog::GtkFileDialog(QWidget *parent, const QString &caption, const QString &directory, const QString &filter) : QDialog(parent)
|
||||
, _windowTitle(caption)
|
||||
, _initialDirectory(directory) {
|
||||
auto filters = makeFilterList(filter);
|
||||
const int numFilters = filters.count();
|
||||
_nameFilters.reserve(numFilters);
|
||||
for (int i = 0; i < numFilters; ++i) {
|
||||
_nameFilters << filters[i].simplified();
|
||||
}
|
||||
|
||||
d.reset(new QGtkDialog(gtk_file_chooser_dialog_new("", nullptr,
|
||||
GTK_FILE_CHOOSER_ACTION_OPEN,
|
||||
tr::lng_cancel(tr::now).toUtf8().constData(), GTK_RESPONSE_CANCEL,
|
||||
tr::lng_box_ok(tr::now).toUtf8().constData(), GTK_RESPONSE_OK, nullptr)));
|
||||
|
||||
d.data()->accept(
|
||||
) | rpl::start_with_next([=] {
|
||||
onAccepted();
|
||||
}, _lifetime);
|
||||
|
||||
d.data()->reject(
|
||||
) | rpl::start_with_next([=] {
|
||||
onRejected();
|
||||
}, _lifetime);
|
||||
|
||||
g_signal_connect(GTK_FILE_CHOOSER(d->gtkDialog()), "selection-changed", G_CALLBACK(onSelectionChanged), this);
|
||||
g_signal_connect_swapped(GTK_FILE_CHOOSER(d->gtkDialog()), "current-folder-changed", G_CALLBACK(onCurrentFolderChanged), this);
|
||||
|
||||
if (PreviewSupported()) {
|
||||
_preview = gtk_image_new();
|
||||
g_signal_connect(G_OBJECT(d->gtkDialog()), "update-preview", G_CALLBACK(onUpdatePreview), this);
|
||||
gtk_file_chooser_set_preview_widget(GTK_FILE_CHOOSER(d->gtkDialog()), _preview);
|
||||
}
|
||||
}
|
||||
|
||||
GtkFileDialog::~GtkFileDialog() {
|
||||
}
|
||||
|
||||
void GtkFileDialog::showHelper(Qt::WindowFlags flags, Qt::WindowModality modality, QWindow *parent) {
|
||||
_dir.clear();
|
||||
_selection.clear();
|
||||
|
||||
applyOptions();
|
||||
return d->show(flags, modality, parent);
|
||||
}
|
||||
|
||||
void GtkFileDialog::setVisible(bool visible) {
|
||||
if (visible) {
|
||||
if (testAttribute(Qt::WA_WState_ExplicitShowHide) && !testAttribute(Qt::WA_WState_Hidden)) {
|
||||
return;
|
||||
}
|
||||
} else if (testAttribute(Qt::WA_WState_ExplicitShowHide) && testAttribute(Qt::WA_WState_Hidden)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (visible) {
|
||||
showHelper(windowFlags(), windowModality(), parentWidget() ? parentWidget()->windowHandle() : nullptr);
|
||||
} else {
|
||||
hideHelper();
|
||||
}
|
||||
|
||||
// Set WA_DontShowOnScreen so that QDialog::setVisible(visible) below
|
||||
// updates the state correctly, but skips showing the non-native version:
|
||||
setAttribute(Qt::WA_DontShowOnScreen);
|
||||
|
||||
QDialog::setVisible(visible);
|
||||
}
|
||||
|
||||
int GtkFileDialog::exec() {
|
||||
d->setModality(windowModality());
|
||||
|
||||
bool deleteOnClose = testAttribute(Qt::WA_DeleteOnClose);
|
||||
setAttribute(Qt::WA_DeleteOnClose, false);
|
||||
|
||||
bool wasShowModal = testAttribute(Qt::WA_ShowModal);
|
||||
setAttribute(Qt::WA_ShowModal, true);
|
||||
setResult(0);
|
||||
|
||||
show();
|
||||
|
||||
QPointer<QDialog> guard = this;
|
||||
d->exec();
|
||||
if (guard.isNull())
|
||||
return QDialog::Rejected;
|
||||
|
||||
setAttribute(Qt::WA_ShowModal, wasShowModal);
|
||||
|
||||
return result();
|
||||
}
|
||||
|
||||
void GtkFileDialog::hideHelper() {
|
||||
// After GtkFileChooserDialog has been hidden, gtk_file_chooser_get_current_folder()
|
||||
// & gtk_file_chooser_get_filenames() will return bogus values -> cache the actual
|
||||
// values before hiding the dialog
|
||||
_dir = directory().absolutePath();
|
||||
_selection = selectedFiles();
|
||||
|
||||
d->hide();
|
||||
}
|
||||
|
||||
bool GtkFileDialog::defaultNameFilterDisables() const {
|
||||
return false;
|
||||
}
|
||||
|
||||
void GtkFileDialog::setDirectory(const QString &directory) {
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(gtkDialog), directory.toUtf8().constData());
|
||||
}
|
||||
|
||||
QDir GtkFileDialog::directory() const {
|
||||
// While GtkFileChooserDialog is hidden, gtk_file_chooser_get_current_folder()
|
||||
// returns a bogus value -> return the cached value before hiding
|
||||
if (!_dir.isEmpty())
|
||||
return _dir;
|
||||
|
||||
QString ret;
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
gchar *folder = gtk_file_chooser_get_current_folder(GTK_FILE_CHOOSER(gtkDialog));
|
||||
if (folder) {
|
||||
ret = QString::fromUtf8(folder);
|
||||
g_free(folder);
|
||||
}
|
||||
return QDir(ret);
|
||||
}
|
||||
|
||||
void GtkFileDialog::selectFile(const QString &filename) {
|
||||
_initialFiles.clear();
|
||||
_initialFiles.append(filename);
|
||||
}
|
||||
|
||||
QStringList GtkFileDialog::selectedFiles() const {
|
||||
// While GtkFileChooserDialog is hidden, gtk_file_chooser_get_filenames()
|
||||
// returns a bogus value -> return the cached value before hiding
|
||||
if (!_selection.isEmpty())
|
||||
return _selection;
|
||||
|
||||
QStringList selection;
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
GSList *filenames = gtk_file_chooser_get_filenames(GTK_FILE_CHOOSER(gtkDialog));
|
||||
for (GSList *it = filenames; it; it = it->next)
|
||||
selection += QString::fromUtf8((const char*)it->data);
|
||||
g_slist_free(filenames);
|
||||
return selection;
|
||||
}
|
||||
|
||||
void GtkFileDialog::setFilter() {
|
||||
applyOptions();
|
||||
}
|
||||
|
||||
void GtkFileDialog::selectNameFilter(const QString &filter) {
|
||||
GtkFileFilter *gtkFilter = _filters.value(filter);
|
||||
if (gtkFilter) {
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
gtk_file_chooser_set_filter(GTK_FILE_CHOOSER(gtkDialog), gtkFilter);
|
||||
}
|
||||
}
|
||||
|
||||
QString GtkFileDialog::selectedNameFilter() const {
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
GtkFileFilter *gtkFilter = gtk_file_chooser_get_filter(GTK_FILE_CHOOSER(gtkDialog));
|
||||
return _filterNames.value(gtkFilter);
|
||||
}
|
||||
|
||||
void GtkFileDialog::onAccepted() {
|
||||
accept();
|
||||
|
||||
// QString filter = selectedNameFilter();
|
||||
// if (filter.isEmpty())
|
||||
// emit filterSelected(filter);
|
||||
|
||||
// QList<QUrl> files = selectedFiles();
|
||||
// emit filesSelected(files);
|
||||
// if (files.count() == 1)
|
||||
// emit fileSelected(files.first());
|
||||
}
|
||||
|
||||
void GtkFileDialog::onRejected() {
|
||||
reject();
|
||||
|
||||
//
|
||||
}
|
||||
|
||||
void GtkFileDialog::onSelectionChanged(GtkDialog *gtkDialog, GtkFileDialog *helper) {
|
||||
// QString selection;
|
||||
// gchar *filename = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(gtkDialog));
|
||||
// if (filename) {
|
||||
// selection = QString::fromUtf8(filename);
|
||||
// g_free(filename);
|
||||
// }
|
||||
// emit helper->currentChanged(QUrl::fromLocalFile(selection));
|
||||
}
|
||||
|
||||
void GtkFileDialog::onCurrentFolderChanged(GtkFileDialog *dialog) {
|
||||
// emit dialog->directoryEntered(dialog->directory());
|
||||
}
|
||||
|
||||
void GtkFileDialog::onUpdatePreview(GtkDialog *gtkDialog, GtkFileDialog *helper) {
|
||||
auto filename = gtk_file_chooser_get_preview_filename(GTK_FILE_CHOOSER(gtkDialog));
|
||||
if (!filename) {
|
||||
gtk_file_chooser_set_preview_widget_active(GTK_FILE_CHOOSER(gtkDialog), false);
|
||||
return;
|
||||
}
|
||||
|
||||
// Don't attempt to open anything which isn't a regular file. If a named pipe,
|
||||
// this may hang. See https://crbug.com/534754.
|
||||
struct stat stat_buf;
|
||||
if (stat(filename, &stat_buf) != 0 || !S_ISREG(stat_buf.st_mode)) {
|
||||
g_free(filename);
|
||||
gtk_file_chooser_set_preview_widget_active(GTK_FILE_CHOOSER(gtkDialog), false);
|
||||
return;
|
||||
}
|
||||
|
||||
// This will preserve the image's aspect ratio.
|
||||
auto pixbuf = gdk_pixbuf_new_from_file_at_size(filename, kPreviewWidth, kPreviewHeight, nullptr);
|
||||
g_free(filename);
|
||||
if (pixbuf) {
|
||||
gtk_image_set_from_pixbuf(GTK_IMAGE(helper->_preview), pixbuf);
|
||||
g_object_unref(pixbuf);
|
||||
}
|
||||
gtk_file_chooser_set_preview_widget_active(GTK_FILE_CHOOSER(gtkDialog), pixbuf ? true : false);
|
||||
}
|
||||
|
||||
GtkFileChooserAction gtkFileChooserAction(QFileDialog::FileMode fileMode, QFileDialog::AcceptMode acceptMode) {
|
||||
switch (fileMode) {
|
||||
case QFileDialog::AnyFile:
|
||||
case QFileDialog::ExistingFile:
|
||||
case QFileDialog::ExistingFiles:
|
||||
if (acceptMode == QFileDialog::AcceptOpen)
|
||||
return GTK_FILE_CHOOSER_ACTION_OPEN;
|
||||
else
|
||||
return GTK_FILE_CHOOSER_ACTION_SAVE;
|
||||
case QFileDialog::Directory:
|
||||
default:
|
||||
if (acceptMode == QFileDialog::AcceptOpen)
|
||||
return GTK_FILE_CHOOSER_ACTION_SELECT_FOLDER;
|
||||
else
|
||||
return GTK_FILE_CHOOSER_ACTION_CREATE_FOLDER;
|
||||
}
|
||||
}
|
||||
|
||||
void GtkFileDialog::applyOptions() {
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
|
||||
gtk_window_set_title(GTK_WINDOW(gtkDialog), _windowTitle.toUtf8().constData());
|
||||
gtk_file_chooser_set_local_only(GTK_FILE_CHOOSER(gtkDialog), true);
|
||||
|
||||
const GtkFileChooserAction action = gtkFileChooserAction(_fileMode, _acceptMode);
|
||||
gtk_file_chooser_set_action(GTK_FILE_CHOOSER(gtkDialog), action);
|
||||
|
||||
const bool selectMultiple = (_fileMode == QFileDialog::ExistingFiles);
|
||||
gtk_file_chooser_set_select_multiple(GTK_FILE_CHOOSER(gtkDialog), selectMultiple);
|
||||
|
||||
const bool confirmOverwrite = !_options.testFlag(QFileDialog::DontConfirmOverwrite);
|
||||
gtk_file_chooser_set_do_overwrite_confirmation(GTK_FILE_CHOOSER(gtkDialog), confirmOverwrite);
|
||||
|
||||
if (!_nameFilters.isEmpty())
|
||||
setNameFilters(_nameFilters);
|
||||
|
||||
if (!_initialDirectory.isEmpty())
|
||||
setDirectory(_initialDirectory);
|
||||
|
||||
for_const (const auto &filename, _initialFiles) {
|
||||
if (_acceptMode == QFileDialog::AcceptSave) {
|
||||
QFileInfo fi(filename);
|
||||
gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(gtkDialog), fi.path().toUtf8().constData());
|
||||
gtk_file_chooser_set_current_name(GTK_FILE_CHOOSER(gtkDialog), fi.fileName().toUtf8().constData());
|
||||
} else if (filename.endsWith('/')) {
|
||||
gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(gtkDialog), filename.toUtf8().constData());
|
||||
} else {
|
||||
gtk_file_chooser_select_filename(GTK_FILE_CHOOSER(gtkDialog), filename.toUtf8().constData());
|
||||
}
|
||||
}
|
||||
|
||||
const QString initialNameFilter = _nameFilters.isEmpty() ? QString() : _nameFilters.front();
|
||||
if (!initialNameFilter.isEmpty())
|
||||
selectNameFilter(initialNameFilter);
|
||||
|
||||
if (CustomButtonsSupported()) {
|
||||
GtkWidget *acceptButton = gtk_dialog_get_widget_for_response(gtkDialog, GTK_RESPONSE_OK);
|
||||
if (acceptButton) {
|
||||
/*if (opts->isLabelExplicitlySet(QFileDialogOptions::Accept))
|
||||
gtk_button_set_label(GTK_BUTTON(acceptButton), opts->labelText(QFileDialogOptions::Accept).toUtf8().constData());
|
||||
else*/ if (_acceptMode == QFileDialog::AcceptOpen)
|
||||
gtk_button_set_label(GTK_BUTTON(acceptButton), tr::lng_open_link(tr::now).toUtf8().constData());
|
||||
else
|
||||
gtk_button_set_label(GTK_BUTTON(acceptButton), tr::lng_settings_save(tr::now).toUtf8().constData());
|
||||
}
|
||||
|
||||
GtkWidget *rejectButton = gtk_dialog_get_widget_for_response(gtkDialog, GTK_RESPONSE_CANCEL);
|
||||
if (rejectButton) {
|
||||
/*if (opts->isLabelExplicitlySet(QFileDialogOptions::Reject))
|
||||
gtk_button_set_label(GTK_BUTTON(rejectButton), opts->labelText(QFileDialogOptions::Reject).toUtf8().constData());
|
||||
else*/
|
||||
gtk_button_set_label(GTK_BUTTON(rejectButton), tr::lng_cancel(tr::now).toUtf8().constData());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void GtkFileDialog::setNameFilters(const QStringList &filters) {
|
||||
GtkDialog *gtkDialog = d->gtkDialog();
|
||||
Q_FOREACH (GtkFileFilter *filter, _filters)
|
||||
gtk_file_chooser_remove_filter(GTK_FILE_CHOOSER(gtkDialog), filter);
|
||||
|
||||
_filters.clear();
|
||||
_filterNames.clear();
|
||||
|
||||
for_const (auto &filter, filters) {
|
||||
GtkFileFilter *gtkFilter = gtk_file_filter_new();
|
||||
auto name = filter;//.left(filter.indexOf(QLatin1Char('(')));
|
||||
auto extensions = cleanFilterList(filter);
|
||||
|
||||
gtk_file_filter_set_name(gtkFilter, name.isEmpty() ? extensions.join(QStringLiteral(", ")).toUtf8().constData() : name.toUtf8().constData());
|
||||
for_const (auto &ext, extensions) {
|
||||
auto caseInsensitiveExt = QString();
|
||||
caseInsensitiveExt.reserve(4 * ext.size());
|
||||
for_const (auto ch, ext) {
|
||||
auto chLower = ch.toLower();
|
||||
auto chUpper = ch.toUpper();
|
||||
if (chLower != chUpper) {
|
||||
caseInsensitiveExt.append('[').append(chLower).append(chUpper).append(']');
|
||||
} else {
|
||||
caseInsensitiveExt.append(ch);
|
||||
}
|
||||
}
|
||||
|
||||
gtk_file_filter_add_pattern(gtkFilter, caseInsensitiveExt.toUtf8().constData());
|
||||
}
|
||||
|
||||
gtk_file_chooser_add_filter(GTK_FILE_CHOOSER(gtkDialog), gtkFilter);
|
||||
|
||||
_filters.insert(filter, gtkFilter);
|
||||
_filterNames.insert(gtkFilter, filter);
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
std::optional<bool> Get(
|
||||
QPointer<QWidget> parent,
|
||||
QStringList &files,
|
||||
QByteArray &remoteContent,
|
||||
const QString &caption,
|
||||
const QString &filter,
|
||||
Type type,
|
||||
QString startFile) {
|
||||
if (!Supported()
|
||||
|| (!qEnvironmentVariableIsSet("TDESKTOP_USE_GTK_FILE_DIALOG")
|
||||
&& !DesktopEnvironment::IsGtkBased())) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
if (cDialogLastPath().isEmpty()) {
|
||||
InitLastPath();
|
||||
}
|
||||
|
||||
GtkFileDialog dialog(parent, caption, QString(), filter);
|
||||
|
||||
dialog.setModal(true);
|
||||
if (type == Type::ReadFile || type == Type::ReadFiles) {
|
||||
dialog.setFileMode((type == Type::ReadFiles) ? QFileDialog::ExistingFiles : QFileDialog::ExistingFile);
|
||||
dialog.setAcceptMode(QFileDialog::AcceptOpen);
|
||||
} else if (type == Type::ReadFolder) {
|
||||
dialog.setAcceptMode(QFileDialog::AcceptOpen);
|
||||
dialog.setFileMode(QFileDialog::Directory);
|
||||
dialog.setOption(QFileDialog::ShowDirsOnly);
|
||||
} else {
|
||||
dialog.setFileMode(QFileDialog::AnyFile);
|
||||
dialog.setAcceptMode(QFileDialog::AcceptSave);
|
||||
}
|
||||
if (startFile.isEmpty() || startFile.at(0) != '/') {
|
||||
startFile = cDialogLastPath() + '/' + startFile;
|
||||
}
|
||||
dialog.selectFile(startFile);
|
||||
|
||||
const auto res = dialog.exec();
|
||||
|
||||
if (type != Type::ReadFolder) {
|
||||
// Save last used directory for all queries except directory choosing.
|
||||
const auto path = dialog.directory().absolutePath();
|
||||
if (!path.isEmpty() && path != cDialogLastPath()) {
|
||||
cSetDialogLastPath(path);
|
||||
Local::writeSettings();
|
||||
}
|
||||
}
|
||||
|
||||
if (res == QDialog::Accepted) {
|
||||
if (type == Type::ReadFiles) {
|
||||
files = dialog.selectedFiles();
|
||||
} else {
|
||||
files = dialog.selectedFiles().mid(0, 1);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
files = QStringList();
|
||||
remoteContent = QByteArray();
|
||||
return false;
|
||||
}
|
||||
|
||||
} // namespace Gtk
|
||||
} // namespace FileDialog
|
||||
} // namespace Platform
|
|
@ -1,27 +0,0 @@
|
|||
/*
|
||||
This file is part of Telegram Desktop,
|
||||
the official desktop application for the Telegram messaging service.
|
||||
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include "core/file_utilities.h"
|
||||
|
||||
namespace Platform {
|
||||
namespace FileDialog {
|
||||
namespace Gtk {
|
||||
|
||||
std::optional<bool> Get(
|
||||
QPointer<QWidget> parent,
|
||||
QStringList &files,
|
||||
QByteArray &remoteContent,
|
||||
const QString &caption,
|
||||
const QString &filter,
|
||||
::FileDialog::internal::Type type,
|
||||
QString startFile);
|
||||
|
||||
} // namespace Gtk
|
||||
} // namespace FileDialog
|
||||
} // namespace Platform
|
|
@ -11,7 +11,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
#include "base/platform/linux/base_linux_gtk_integration_p.h"
|
||||
#include "platform/linux/linux_gtk_integration_p.h"
|
||||
#include "platform/linux/linux_gdk_helper.h"
|
||||
#include "platform/linux/linux_gtk_file_dialog.h"
|
||||
#include "platform/linux/linux_gtk_open_with_dialog.h"
|
||||
|
||||
namespace Platform {
|
||||
|
@ -61,48 +60,14 @@ void GtkIntegration::load() {
|
|||
auto &lib = BaseGtkIntegration::Instance()->library();
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_show);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_hide);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_get_window);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_realize);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_hide_on_delete);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_widget_destroy);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_clipboard_get);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_clipboard_store);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_clipboard_wait_for_contents);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_clipboard_wait_for_image);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_selection_data_targets_include_image);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_selection_data_free);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_dialog_new);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_get_type);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_image_get_type);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_current_folder);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_get_current_folder);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_current_name);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_select_filename);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_get_filenames);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_filter);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_get_filter);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_window_get_type);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_window_set_title);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_local_only);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_action);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_select_multiple);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_do_overwrite_confirmation);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_remove_filter);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_filter_set_name);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_filter_add_pattern);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_add_filter);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_preview_widget);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_get_preview_filename);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_chooser_set_preview_widget_active);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_file_filter_new);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_image_new);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_image_set_from_pixbuf);
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gdk_window_set_modal_hint);
|
||||
LOAD_GTK_SYMBOL(lib, gdk_window_focus);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_dialog_get_type);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_dialog_run);
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gdk_atom_intern);
|
||||
|
||||
|
@ -111,7 +76,6 @@ void GtkIntegration::load() {
|
|||
LOAD_GTK_SYMBOL(lib, gdk_display_get_primary_monitor);
|
||||
LOAD_GTK_SYMBOL(lib, gdk_monitor_get_scale_factor);
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gdk_pixbuf_new_from_file_at_size);
|
||||
LOAD_GTK_SYMBOL(lib, gdk_pixbuf_get_has_alpha);
|
||||
LOAD_GTK_SYMBOL(lib, gdk_pixbuf_get_pixels);
|
||||
LOAD_GTK_SYMBOL(lib, gdk_pixbuf_get_width);
|
||||
|
@ -120,10 +84,6 @@ void GtkIntegration::load() {
|
|||
|
||||
GdkHelperLoad(lib);
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gtk_dialog_get_widget_for_response);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_button_set_label);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_button_get_type);
|
||||
|
||||
LOAD_GTK_SYMBOL(lib, gtk_app_chooser_dialog_new);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_app_chooser_get_app_info);
|
||||
LOAD_GTK_SYMBOL(lib, gtk_app_chooser_get_type);
|
||||
|
@ -158,24 +118,6 @@ std::optional<int> GtkIntegration::scaleFactor() const {
|
|||
return gdk_monitor_get_scale_factor(monitor);
|
||||
}
|
||||
|
||||
std::optional<bool> GtkIntegration::getFileDialog(
|
||||
QPointer<QWidget> parent,
|
||||
QStringList &files,
|
||||
QByteArray &remoteContent,
|
||||
const QString &caption,
|
||||
const QString &filter,
|
||||
::FileDialog::internal::Type type,
|
||||
QString startFile) const {
|
||||
return FileDialog::Gtk::Get(
|
||||
parent,
|
||||
files,
|
||||
remoteContent,
|
||||
caption,
|
||||
filter,
|
||||
type,
|
||||
startFile);
|
||||
}
|
||||
|
||||
bool GtkIntegration::showOpenWithDialog(const QString &filepath) const {
|
||||
return File::internal::ShowGtkOpenWithDialog(filepath);
|
||||
}
|
||||
|
|
|
@ -7,8 +7,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
*/
|
||||
#pragma once
|
||||
|
||||
#include "core/file_utilities.h"
|
||||
|
||||
namespace Platform {
|
||||
namespace internal {
|
||||
|
||||
|
@ -20,15 +18,6 @@ public:
|
|||
|
||||
[[nodiscard]] std::optional<int> scaleFactor() const;
|
||||
|
||||
[[nodiscard]] std::optional<bool> getFileDialog(
|
||||
QPointer<QWidget> parent,
|
||||
QStringList &files,
|
||||
QByteArray &remoteContent,
|
||||
const QString &caption,
|
||||
const QString &filter,
|
||||
::FileDialog::internal::Type type,
|
||||
QString startFile) const;
|
||||
|
||||
[[nodiscard]] bool showOpenWithDialog(const QString &filepath) const;
|
||||
|
||||
[[nodiscard]] QImage getImageFromClipboard() const;
|
||||
|
|
|
@ -24,17 +24,6 @@ std::optional<int> GtkIntegration::scaleFactor() const {
|
|||
return std::nullopt;
|
||||
}
|
||||
|
||||
std::optional<bool> GtkIntegration::getFileDialog(
|
||||
QPointer<QWidget> parent,
|
||||
QStringList &files,
|
||||
QByteArray &remoteContent,
|
||||
const QString &caption,
|
||||
const QString &filter,
|
||||
::FileDialog::internal::Type type,
|
||||
QString startFile) const {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
bool GtkIntegration::showOpenWithDialog(const QString &filepath) const {
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -16,59 +16,22 @@ namespace Platform {
|
|||
namespace Gtk {
|
||||
|
||||
inline void (*gtk_widget_show)(GtkWidget *widget) = nullptr;
|
||||
inline void (*gtk_widget_hide)(GtkWidget *widget) = nullptr;
|
||||
inline GdkWindow* (*gtk_widget_get_window)(GtkWidget *widget) = nullptr;
|
||||
inline void (*gtk_widget_realize)(GtkWidget *widget) = nullptr;
|
||||
inline gboolean (*gtk_widget_hide_on_delete)(GtkWidget *widget) = nullptr;
|
||||
inline void (*gtk_widget_destroy)(GtkWidget *widget) = nullptr;
|
||||
inline GtkClipboard* (*gtk_clipboard_get)(GdkAtom selection) = nullptr;
|
||||
inline void (*gtk_clipboard_store)(GtkClipboard *clipboard) = nullptr;
|
||||
inline GtkSelectionData* (*gtk_clipboard_wait_for_contents)(GtkClipboard *clipboard, GdkAtom target) = nullptr;
|
||||
inline GdkPixbuf* (*gtk_clipboard_wait_for_image)(GtkClipboard *clipboard) = nullptr;
|
||||
inline gboolean (*gtk_selection_data_targets_include_image)(const GtkSelectionData *selection_data, gboolean writable) = nullptr;
|
||||
inline void (*gtk_selection_data_free)(GtkSelectionData *data) = nullptr;
|
||||
inline GType (*gtk_file_chooser_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline GtkWidget* (*gtk_file_chooser_dialog_new)(const gchar *title, GtkWindow *parent, GtkFileChooserAction action, const gchar *first_button_text, ...) G_GNUC_NULL_TERMINATED = nullptr;
|
||||
inline gboolean (*gtk_file_chooser_set_current_folder)(GtkFileChooser *chooser, const gchar *filename) = nullptr;
|
||||
inline gchar* (*gtk_file_chooser_get_current_folder)(GtkFileChooser *chooser) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_current_name)(GtkFileChooser *chooser, const gchar *name) = nullptr;
|
||||
inline gboolean (*gtk_file_chooser_select_filename)(GtkFileChooser *chooser, const gchar *filename) = nullptr;
|
||||
inline GSList* (*gtk_file_chooser_get_filenames)(GtkFileChooser *chooser) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_filter)(GtkFileChooser *chooser, GtkFileFilter *filter) = nullptr;
|
||||
inline GtkFileFilter* (*gtk_file_chooser_get_filter)(GtkFileChooser *chooser) = nullptr;
|
||||
inline GType (*gtk_window_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline void (*gtk_window_set_title)(GtkWindow *window, const gchar *title) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_local_only)(GtkFileChooser *chooser, gboolean local_only) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_action)(GtkFileChooser *chooser, GtkFileChooserAction action) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_select_multiple)(GtkFileChooser *chooser, gboolean select_multiple) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_do_overwrite_confirmation)(GtkFileChooser *chooser, gboolean do_overwrite_confirmation) = nullptr;
|
||||
inline GType (*gtk_dialog_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline GtkWidget* (*gtk_dialog_get_widget_for_response)(GtkDialog *dialog, gint response_id) = nullptr;
|
||||
inline GType (*gtk_button_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline void (*gtk_button_set_label)(GtkButton *button, const gchar *label) = nullptr;
|
||||
inline void (*gtk_file_chooser_remove_filter)(GtkFileChooser *chooser, GtkFileFilter *filter) = nullptr;
|
||||
inline void (*gtk_file_filter_set_name)(GtkFileFilter *filter, const gchar *name) = nullptr;
|
||||
inline void (*gtk_file_filter_add_pattern)(GtkFileFilter *filter, const gchar *pattern) = nullptr;
|
||||
inline void (*gtk_file_chooser_add_filter)(GtkFileChooser *chooser, GtkFileFilter *filter) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_preview_widget)(GtkFileChooser *chooser, GtkWidget *preview_widget) = nullptr;
|
||||
inline gchar* (*gtk_file_chooser_get_preview_filename)(GtkFileChooser *chooser) = nullptr;
|
||||
inline void (*gtk_file_chooser_set_preview_widget_active)(GtkFileChooser *chooser, gboolean active) = nullptr;
|
||||
inline GtkFileFilter* (*gtk_file_filter_new)(void) = nullptr;
|
||||
inline GType (*gtk_image_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline GtkWidget* (*gtk_image_new)(void) = nullptr;
|
||||
inline void (*gtk_image_set_from_pixbuf)(GtkImage *image, GdkPixbuf *pixbuf) = nullptr;
|
||||
inline GType (*gtk_app_chooser_get_type)(void) G_GNUC_CONST = nullptr;
|
||||
inline GtkWidget* (*gtk_app_chooser_dialog_new)(GtkWindow *parent, GtkDialogFlags flags, GFile *file) = nullptr;
|
||||
inline GAppInfo* (*gtk_app_chooser_get_app_info)(GtkAppChooser *self) = nullptr;
|
||||
inline void (*gdk_window_set_modal_hint)(GdkWindow *window, gboolean modal) = nullptr;
|
||||
inline void (*gdk_window_focus)(GdkWindow *window, guint32 timestamp) = nullptr;
|
||||
inline gint (*gtk_dialog_run)(GtkDialog *dialog) = nullptr;
|
||||
inline GdkAtom (*gdk_atom_intern)(const gchar *atom_name, gboolean only_if_exists) = nullptr;
|
||||
inline GdkDisplay* (*gdk_display_get_default)(void) = nullptr;
|
||||
inline GdkMonitor* (*gdk_display_get_monitor)(GdkDisplay *display, int monitor_num) = nullptr;
|
||||
inline GdkMonitor* (*gdk_display_get_primary_monitor)(GdkDisplay *display) = nullptr;
|
||||
inline int (*gdk_monitor_get_scale_factor)(GdkMonitor *monitor) = nullptr;
|
||||
inline GdkPixbuf* (*gdk_pixbuf_new_from_file_at_size)(const gchar *filename, int width, int height, GError **error) = nullptr;
|
||||
inline gboolean (*gdk_pixbuf_get_has_alpha)(const GdkPixbuf *pixbuf) = nullptr;
|
||||
inline guchar* (*gdk_pixbuf_get_pixels)(const GdkPixbuf *pixbuf) = nullptr;
|
||||
inline int (*gdk_pixbuf_get_width)(const GdkPixbuf *pixbuf) = nullptr;
|
||||
|
|
Loading…
Add table
Reference in a new issue