I am using Tkinter with Python 2.6 and 2.7 for programming graphic user interfaces.
These User Interfaces contain dialogs for opening files and saving data from the tkFileDialog module. I would like to adapt the dialogs and add some further entry widgets e.g. for letting the user leave comments.
Is there any way for doing so?
It seems that the file dialogs are taken directly from the operating system. In Tkinter they are derived from the Dialog class in the tkCommonDialog module and call the tk.call("tk_getSaveFile") method of a frame widget (in this case for saving data).
I could not find out where this method is defined.
call method is defined in _tkinter.c, but there is nothing interesting for your particular task there. It just calls a Tcl command, and the command tk_getSaveFile does all the work.
And yes, when there is a native file dialog on the operating system, tk_getSaveFile uses them (e.g. GetSaveFileName is used on Windows). It could be possible to add widgets there, but not without tampering with C sources of Tk. If you're sure that your target uses non-native Tk dialogs, you could add something to its widget hierarchy by hacking ::tk::dialog::file:: procedure from Tk (see library/tkfbox.tcl).
I would rather take an alternative implementation of tk_getSaveFile, written in pure Tcl/Tk and never using the OS facility. This way, we can be sure that its layout is the same for all OSes, and it won't suddenly change with a new version of Tk. It's still far from trivial to provide a convenient API for python around it, but at least, it is possible.
I had to get rid of the canvasx/y statements. That line now simply reads set item [$data(canvas) find closest $x $y], which works well. $data(canvas) canvasx $x for its own works well but not in connection with find closest, neither if it is written in two lines.
Related
I’d like to create a restricted folder/ file explorer in Python (I have version 2.7.9, but I don’t mind changing that) for Windows.
Essentially, I want to initially specify the folder to which the code opens. For example, the code should initially open to: C:\Users\myName\Desktop\myDemoFolder (the user must not know this folder simply by looking at the GUI).
The user must be able to browse downwards (deeper into folders) and backwards (but only up to the initial folder to which the code opens). The user must be able to click to open a file (for example: pdf), and the file must automatically open in its default application.
An example of what I’d like is presented in figure 1. (The look of the interface is not important)
Currently, I am able to get figure 2 using the code presented here:
from Tkinter import Tk
from tkFileDialog import askopenfilename
Tk().withdraw()
filename = askopenfilename()
print(filename)
Research has indicated that it is not possible to change the default buttons in Tkinter windows. Is this true? If it can’t be done with Tkinter (and that’s fine), how else can we do it?
I’d happily choose simple, non-Tkinter code (perhaps using wxPython’s wx.GenericDirCtrl()) rather than elaborate Tkinter code, but no restrictive libraries please.
A modular design approach is not needed. I’d rather have simple (functional) code that is shorter than object-oriented code.
I was trying to do the same thing when I realized that maybe you could create all the buttons you need and then set the color of the buttons you don't need to your background color using:
button-name.config(bg = "background-color")
Just change the "button-name" to your button's name and set "background-color" to the background color!
I'm a bit confused with some gtk and gnome concepts. I'm trying to get list of non minimized windows on my gnome2 desktop, but after reading the pygtk documentation and inspecting the results, I can't understand the results.
Neither of the two snippets below appears to work.
First I tried this..
>>> gtk.gdk.window_get_toplevels()
[<gtk.gdk.Window object at 0xb74339b4 (GdkWindow at 0x8a4c170)>]
>>> gtk.gdk.window_get_toplevels()[0].get_children()
[]
then this
>>> d = gtk.gdk.DisplayManager()
>>> d.get_default_display().get_screen(0).get_root_window().get_children()
[<gtk.gdk.Window object at 0x89dcc84 (GdkWindow at 0x8a4c170)>, <gtk.gdk.Window object at 0x89dccac (GdkWindow at 0x8a4c0c0)>]
As seen in the console output, the second option returns two windows. But I haven't been able to figure out what they are. None of them has any children and I allways get those two windows regardless how many windows I have on my desktop.
Could anybody explain the hierarchy of objects of the typical gtk based desktop environment?
I can't understand why the above code doesn't work.
Please refrain from posting alternative solutions that resource to wnck, xlib, qt, etc. I'm more interested in understanding what I am doing wrong than in getting advice such us checking other libraries.
Your constraint is like saying "I want to build a CD player using only a banana. Please refrain from posting alternative solutions that resort to lasers." GTK can't do that, you're using the wrong tool for the job.
Here's an explanation of what a "window" actually means and why your code doesn't work:
First off, you need to understand the difference between a gtk.Window and a gtk.gdk.Window. A GTK window is a top level GTK widget that can contain other widgets. It is usually linked to a window on your desktop, but doesn't have to be - in GTK 3 there is an OffscreenWindow.
A GDK window, on the other hand, is platform-dependent. On an X desktop it is a thin wrapper around an X window, which is not necessarily a toplevel desktop window. On other systems it exists to abstract away the windowing system. A GDK window receives events, so some GTK non-window widgets have their own GDK windows. "Window" is really a terrible name for these objects, but it was inherited from X and it's probably not going to change.
Each GTK process only knows about its own windows. You can get a list of the toplevel GTK windows of your own application using gtk.window_list_toplevels(). Getting the children of these windows should return you the GTK widgets that they contain. However, you can't descend into the widget hierarchy of other processes' windows. For example, what if another process has a window with a child widget that is a custom widget that your process doesn't know about? What should it report as the type of that widget?
Getting a list of the toplevel GDK windows with gtk.gdk.window_get_toplevels() is basically the same as getting a list of the toplevel X windows, as far as I understand it. You have no way of knowing what kind of windows they are - they might be the Gnome Panel, or they might be Qt windows, or they might be something else altogether that doesn't correspond with a desktop window.
Libwnck (link to the overview of what it does) can get you a list of non-minimized windows, and their titles, but it won't allow you to see inside them. There's no way to do that. Libwnck uses GDK internally, so technically you could do it using GDK, but why would you bother if there's already a library that does that for you? If you really want to do it yourself, look at the libwnck source code.
The windows you get are the windows that were created within your process. To get the list of windows, you need to query the properties of the root window, like this:
import gtk.gdk
root = gtk.gdk.get_default_root_window()
for id in root.property_get('_NET_CLIENT_LIST')[2]:
w = gtk.gdk.window_foreign_new(id)
if w:
print(w.property_get('WM_NAME')[2])
Please note that GDK is a thin layer over underlying OS graphics engine (X11/Quartz/Aqua/GDI etc) and result may differ on different NIX devices.
I'm looking for a cross-platform way of making my Python script process a file's path by implementing a drag n drop method. At the moment I manually go to the terminal and use the sys.argv method:
python myscript.py /Python/myfile.xls
However this is slow and "techy". Ideally I would a quick and interactive way of allowing a file be processed by my Python script. I primarily need this to work for Mac but cross-platform would be better.
If you want to use Tkinter, have a look at the Tkinter DnD binding from here http://klappnase.bubble.org/TkinterDnD/index.html
When run, the binding shows an example with a listbox that allows you to drag a file on to it.
Do you want to drag and drop the myfile.xls onto your python script within your file navigator ? Say Finder or whatever on Mac, Explorer on Win, Nautilus etc. ? In that case there will not be a simple cross-platform solution, given that you will have to hook into different software on different systems.
For a Mac specific solution try AppleScript - here is a sample
And for something Pythonic there is http://appscript.sourceforge.net/ , http://docs.python.org/library/macosa.html
Otherwise the solution is in the answer above. Use a custom GUI built in Tk, or wx or QT. You can look up their respective documentation for drag and drop, they do have cross-platform ways of doing it.
It'd be easiest to just write a small GUI with Tkinter or something similar and have the user select a file from within the GUI. Something along these lines:
import tkFileDialog
f = tkFileDialog.askopenfilename()
# Go on from there; f is a handle to the file that the user picked
I'm not aware of any cross platform methods to get a script to work with drag and drop, however. This is probably easier, though.
I am planning to do the folliwing:
Create a PyGtk GUI (hardcoded, no Glade) with some widgets, and at the bottom of the screen put some sort of VTE (Virtual Terminal Emulator) from where I could manipulate the widgets, for example changing their attributes and calling their methods from the commandline.
The result would be similar to using AutoCAD's commands, only that I would be acting upon the GUI objects.
I have already found very few things about gtk.VteTerminal widget, but not only could not find a working example or make one myself, it also seem to be a system terminal, not a "current session" python terminal where I could run python commands and access GUI objects.
Any suggestion?
Thanks for reading
What you want exists already: GtkParasite. It's meant for debugging, but I'm sure if you wanted it to actually be a part of your application, you could adapt it.
I'm late to the party, but I had a similar problem.
Look here
Virtual Terminal Question
It's an option if you decide to do something different than what you might have already done.
I've got a Python/GTK project I've been working on for a while, and some of the functionality I want already exists in Gnome panel applets. Based on my reading, panel applets are already in a subclass of the standard GTK Bin, so I would think there'd be a way that I can use the C-based GTK objects in my Python-based application.
For instance, I've got the fish applet in /usr/lib/gnome-panel/fish-applet-2 as a binary
Can I do some GTK magic to get that object so it can be embedded into my Python/GTK gui?
I'm not expecting a step-by-step walkthrough, but if anyone can point me in the right direction, I'd appreciate it.
The code for applets in gnome panel is quite complex. It's based on the gnome Bonobo framework (which in turn is based on CORBA). But now the whole thing is in a bit of a flux because gnome is moving away from Bonobo to a new dbus-based design. So if it's loading existing gnome panel applets you want you should absolutely use the code from gnome panel to do it. There is (or at least was) an example program included that does nothing but load an applet into a window.
If you want to display a widget from one of your own programs (a custom applet) inside another of your programs it's much easier. There are a set of widgets called GtkSocket and GtkPlug for this purpose. Of course the to programs doesn't need to run on the same machine. But there is always the delicate problem of getting them together in the first place.