##// END OF EJS Templates
add fullscreen support for QtConsole throught shortcut...
Matthias BUSSONNIER -
Show More
@@ -1,528 +1,529 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2 """Usage information for the main IPython applications.
2 """Usage information for the main IPython applications.
3 """
3 """
4 #-----------------------------------------------------------------------------
4 #-----------------------------------------------------------------------------
5 # Copyright (C) 2008-2010 The IPython Development Team
5 # Copyright (C) 2008-2010 The IPython Development Team
6 # Copyright (C) 2001-2007 Fernando Perez. <fperez@colorado.edu>
6 # Copyright (C) 2001-2007 Fernando Perez. <fperez@colorado.edu>
7 #
7 #
8 # Distributed under the terms of the BSD License. The full license is in
8 # Distributed under the terms of the BSD License. The full license is in
9 # the file COPYING, distributed as part of this software.
9 # the file COPYING, distributed as part of this software.
10 #-----------------------------------------------------------------------------
10 #-----------------------------------------------------------------------------
11
11
12 import sys
12 import sys
13 from IPython.core import release
13 from IPython.core import release
14
14
15 cl_usage = """\
15 cl_usage = """\
16 =========
16 =========
17 IPython
17 IPython
18 =========
18 =========
19
19
20 Tools for Interactive Computing in Python
20 Tools for Interactive Computing in Python
21 =========================================
21 =========================================
22
22
23 A Python shell with automatic history (input and output), dynamic object
23 A Python shell with automatic history (input and output), dynamic object
24 introspection, easier configuration, command completion, access to the
24 introspection, easier configuration, command completion, access to the
25 system shell and more. IPython can also be embedded in running programs.
25 system shell and more. IPython can also be embedded in running programs.
26
26
27
27
28 Usage
28 Usage
29
29
30 ipython [subcommand] [options] [files]
30 ipython [subcommand] [options] [files]
31
31
32 If invoked with no options, it executes all the files listed in sequence
32 If invoked with no options, it executes all the files listed in sequence
33 and exits, use -i to enter interactive mode after running the files. Files
33 and exits, use -i to enter interactive mode after running the files. Files
34 ending in .py will be treated as normal Python, but files ending in .ipy
34 ending in .py will be treated as normal Python, but files ending in .ipy
35 can contain special IPython syntax (magic commands, shell expansions, etc.)
35 can contain special IPython syntax (magic commands, shell expansions, etc.)
36
36
37 Almost all configuration in IPython is available via the command-line. Do
37 Almost all configuration in IPython is available via the command-line. Do
38 `ipython --help-all` to see all available options. For persistent
38 `ipython --help-all` to see all available options. For persistent
39 configuration, look into your `ipython_config.py` configuration file for
39 configuration, look into your `ipython_config.py` configuration file for
40 details.
40 details.
41
41
42 This file is typically installed in the `IPYTHON_DIR` directory, and there
42 This file is typically installed in the `IPYTHON_DIR` directory, and there
43 is a separate configuration directory for each profile. The default profile
43 is a separate configuration directory for each profile. The default profile
44 directory will be located in $IPYTHON_DIR/profile_default. For Linux users,
44 directory will be located in $IPYTHON_DIR/profile_default. For Linux users,
45 IPYTHON_DIR defaults to `$HOME/.config/ipython`, and for other Unix systems
45 IPYTHON_DIR defaults to `$HOME/.config/ipython`, and for other Unix systems
46 to `$HOME/.ipython`. For Windows users, $HOME resolves to C:\\Documents
46 to `$HOME/.ipython`. For Windows users, $HOME resolves to C:\\Documents
47 and Settings\\YourUserName in most instances.
47 and Settings\\YourUserName in most instances.
48
48
49 To initialize a profile with the default configuration file, do::
49 To initialize a profile with the default configuration file, do::
50
50
51 $> ipython profile create
51 $> ipython profile create
52
52
53 and start editing `IPYTHON_DIR/profile_default/ipython_config.py`
53 and start editing `IPYTHON_DIR/profile_default/ipython_config.py`
54
54
55 In IPython's documentation, we will refer to this directory as
55 In IPython's documentation, we will refer to this directory as
56 `IPYTHON_DIR`, you can change its default location by creating an
56 `IPYTHON_DIR`, you can change its default location by creating an
57 environment variable with this name and setting it to the desired path.
57 environment variable with this name and setting it to the desired path.
58
58
59 For more information, see the manual available in HTML and PDF in your
59 For more information, see the manual available in HTML and PDF in your
60 installation, or online at http://ipython.org/documentation.html.
60 installation, or online at http://ipython.org/documentation.html.
61 """
61 """
62
62
63 interactive_usage = """
63 interactive_usage = """
64 IPython -- An enhanced Interactive Python
64 IPython -- An enhanced Interactive Python
65 =========================================
65 =========================================
66
66
67 IPython offers a combination of convenient shell features, special commands
67 IPython offers a combination of convenient shell features, special commands
68 and a history mechanism for both input (command history) and output (results
68 and a history mechanism for both input (command history) and output (results
69 caching, similar to Mathematica). It is intended to be a fully compatible
69 caching, similar to Mathematica). It is intended to be a fully compatible
70 replacement for the standard Python interpreter, while offering vastly
70 replacement for the standard Python interpreter, while offering vastly
71 improved functionality and flexibility.
71 improved functionality and flexibility.
72
72
73 At your system command line, type 'ipython -h' to see the command line
73 At your system command line, type 'ipython -h' to see the command line
74 options available. This document only describes interactive features.
74 options available. This document only describes interactive features.
75
75
76 MAIN FEATURES
76 MAIN FEATURES
77
77
78 * Access to the standard Python help. As of Python 2.1, a help system is
78 * Access to the standard Python help. As of Python 2.1, a help system is
79 available with access to object docstrings and the Python manuals. Simply
79 available with access to object docstrings and the Python manuals. Simply
80 type 'help' (no quotes) to access it.
80 type 'help' (no quotes) to access it.
81
81
82 * Magic commands: type %magic for information on the magic subsystem.
82 * Magic commands: type %magic for information on the magic subsystem.
83
83
84 * System command aliases, via the %alias command or the configuration file(s).
84 * System command aliases, via the %alias command or the configuration file(s).
85
85
86 * Dynamic object information:
86 * Dynamic object information:
87
87
88 Typing ?word or word? prints detailed information about an object. If
88 Typing ?word or word? prints detailed information about an object. If
89 certain strings in the object are too long (docstrings, code, etc.) they get
89 certain strings in the object are too long (docstrings, code, etc.) they get
90 snipped in the center for brevity.
90 snipped in the center for brevity.
91
91
92 Typing ??word or word?? gives access to the full information without
92 Typing ??word or word?? gives access to the full information without
93 snipping long strings. Long strings are sent to the screen through the less
93 snipping long strings. Long strings are sent to the screen through the less
94 pager if longer than the screen, printed otherwise.
94 pager if longer than the screen, printed otherwise.
95
95
96 The ?/?? system gives access to the full source code for any object (if
96 The ?/?? system gives access to the full source code for any object (if
97 available), shows function prototypes and other useful information.
97 available), shows function prototypes and other useful information.
98
98
99 If you just want to see an object's docstring, type '%pdoc object' (without
99 If you just want to see an object's docstring, type '%pdoc object' (without
100 quotes, and without % if you have automagic on).
100 quotes, and without % if you have automagic on).
101
101
102 Both %pdoc and ?/?? give you access to documentation even on things which are
102 Both %pdoc and ?/?? give you access to documentation even on things which are
103 not explicitely defined. Try for example typing {}.get? or after import os,
103 not explicitely defined. Try for example typing {}.get? or after import os,
104 type os.path.abspath??. The magic functions %pdef, %source and %file operate
104 type os.path.abspath??. The magic functions %pdef, %source and %file operate
105 similarly.
105 similarly.
106
106
107 * Completion in the local namespace, by typing TAB at the prompt.
107 * Completion in the local namespace, by typing TAB at the prompt.
108
108
109 At any time, hitting tab will complete any available python commands or
109 At any time, hitting tab will complete any available python commands or
110 variable names, and show you a list of the possible completions if there's
110 variable names, and show you a list of the possible completions if there's
111 no unambiguous one. It will also complete filenames in the current directory.
111 no unambiguous one. It will also complete filenames in the current directory.
112
112
113 This feature requires the readline and rlcomplete modules, so it won't work
113 This feature requires the readline and rlcomplete modules, so it won't work
114 if your Python lacks readline support (such as under Windows).
114 if your Python lacks readline support (such as under Windows).
115
115
116 * Search previous command history in two ways (also requires readline):
116 * Search previous command history in two ways (also requires readline):
117
117
118 - Start typing, and then use Ctrl-p (previous,up) and Ctrl-n (next,down) to
118 - Start typing, and then use Ctrl-p (previous,up) and Ctrl-n (next,down) to
119 search through only the history items that match what you've typed so
119 search through only the history items that match what you've typed so
120 far. If you use Ctrl-p/Ctrl-n at a blank prompt, they just behave like
120 far. If you use Ctrl-p/Ctrl-n at a blank prompt, they just behave like
121 normal arrow keys.
121 normal arrow keys.
122
122
123 - Hit Ctrl-r: opens a search prompt. Begin typing and the system searches
123 - Hit Ctrl-r: opens a search prompt. Begin typing and the system searches
124 your history for lines that match what you've typed so far, completing as
124 your history for lines that match what you've typed so far, completing as
125 much as it can.
125 much as it can.
126
126
127 - %hist: search history by index (this does *not* require readline).
127 - %hist: search history by index (this does *not* require readline).
128
128
129 * Persistent command history across sessions.
129 * Persistent command history across sessions.
130
130
131 * Logging of input with the ability to save and restore a working session.
131 * Logging of input with the ability to save and restore a working session.
132
132
133 * System escape with !. Typing !ls will run 'ls' in the current directory.
133 * System escape with !. Typing !ls will run 'ls' in the current directory.
134
134
135 * The reload command does a 'deep' reload of a module: changes made to the
135 * The reload command does a 'deep' reload of a module: changes made to the
136 module since you imported will actually be available without having to exit.
136 module since you imported will actually be available without having to exit.
137
137
138 * Verbose and colored exception traceback printouts. See the magic xmode and
138 * Verbose and colored exception traceback printouts. See the magic xmode and
139 xcolor functions for details (just type %magic).
139 xcolor functions for details (just type %magic).
140
140
141 * Input caching system:
141 * Input caching system:
142
142
143 IPython offers numbered prompts (In/Out) with input and output caching. All
143 IPython offers numbered prompts (In/Out) with input and output caching. All
144 input is saved and can be retrieved as variables (besides the usual arrow
144 input is saved and can be retrieved as variables (besides the usual arrow
145 key recall).
145 key recall).
146
146
147 The following GLOBAL variables always exist (so don't overwrite them!):
147 The following GLOBAL variables always exist (so don't overwrite them!):
148 _i: stores previous input.
148 _i: stores previous input.
149 _ii: next previous.
149 _ii: next previous.
150 _iii: next-next previous.
150 _iii: next-next previous.
151 _ih : a list of all input _ih[n] is the input from line n.
151 _ih : a list of all input _ih[n] is the input from line n.
152
152
153 Additionally, global variables named _i<n> are dynamically created (<n>
153 Additionally, global variables named _i<n> are dynamically created (<n>
154 being the prompt counter), such that _i<n> == _ih[<n>]
154 being the prompt counter), such that _i<n> == _ih[<n>]
155
155
156 For example, what you typed at prompt 14 is available as _i14 and _ih[14].
156 For example, what you typed at prompt 14 is available as _i14 and _ih[14].
157
157
158 You can create macros which contain multiple input lines from this history,
158 You can create macros which contain multiple input lines from this history,
159 for later re-execution, with the %macro function.
159 for later re-execution, with the %macro function.
160
160
161 The history function %hist allows you to see any part of your input history
161 The history function %hist allows you to see any part of your input history
162 by printing a range of the _i variables. Note that inputs which contain
162 by printing a range of the _i variables. Note that inputs which contain
163 magic functions (%) appear in the history with a prepended comment. This is
163 magic functions (%) appear in the history with a prepended comment. This is
164 because they aren't really valid Python code, so you can't exec them.
164 because they aren't really valid Python code, so you can't exec them.
165
165
166 * Output caching system:
166 * Output caching system:
167
167
168 For output that is returned from actions, a system similar to the input
168 For output that is returned from actions, a system similar to the input
169 cache exists but using _ instead of _i. Only actions that produce a result
169 cache exists but using _ instead of _i. Only actions that produce a result
170 (NOT assignments, for example) are cached. If you are familiar with
170 (NOT assignments, for example) are cached. If you are familiar with
171 Mathematica, IPython's _ variables behave exactly like Mathematica's %
171 Mathematica, IPython's _ variables behave exactly like Mathematica's %
172 variables.
172 variables.
173
173
174 The following GLOBAL variables always exist (so don't overwrite them!):
174 The following GLOBAL variables always exist (so don't overwrite them!):
175 _ (one underscore): previous output.
175 _ (one underscore): previous output.
176 __ (two underscores): next previous.
176 __ (two underscores): next previous.
177 ___ (three underscores): next-next previous.
177 ___ (three underscores): next-next previous.
178
178
179 Global variables named _<n> are dynamically created (<n> being the prompt
179 Global variables named _<n> are dynamically created (<n> being the prompt
180 counter), such that the result of output <n> is always available as _<n>.
180 counter), such that the result of output <n> is always available as _<n>.
181
181
182 Finally, a global dictionary named _oh exists with entries for all lines
182 Finally, a global dictionary named _oh exists with entries for all lines
183 which generated output.
183 which generated output.
184
184
185 * Directory history:
185 * Directory history:
186
186
187 Your history of visited directories is kept in the global list _dh, and the
187 Your history of visited directories is kept in the global list _dh, and the
188 magic %cd command can be used to go to any entry in that list.
188 magic %cd command can be used to go to any entry in that list.
189
189
190 * Auto-parentheses and auto-quotes (adapted from Nathan Gray's LazyPython)
190 * Auto-parentheses and auto-quotes (adapted from Nathan Gray's LazyPython)
191
191
192 1. Auto-parentheses
192 1. Auto-parentheses
193 Callable objects (i.e. functions, methods, etc) can be invoked like
193 Callable objects (i.e. functions, methods, etc) can be invoked like
194 this (notice the commas between the arguments):
194 this (notice the commas between the arguments):
195 >>> callable_ob arg1, arg2, arg3
195 >>> callable_ob arg1, arg2, arg3
196 and the input will be translated to this:
196 and the input will be translated to this:
197 --> callable_ob(arg1, arg2, arg3)
197 --> callable_ob(arg1, arg2, arg3)
198 You can force auto-parentheses by using '/' as the first character
198 You can force auto-parentheses by using '/' as the first character
199 of a line. For example:
199 of a line. For example:
200 >>> /globals # becomes 'globals()'
200 >>> /globals # becomes 'globals()'
201 Note that the '/' MUST be the first character on the line! This
201 Note that the '/' MUST be the first character on the line! This
202 won't work:
202 won't work:
203 >>> print /globals # syntax error
203 >>> print /globals # syntax error
204
204
205 In most cases the automatic algorithm should work, so you should
205 In most cases the automatic algorithm should work, so you should
206 rarely need to explicitly invoke /. One notable exception is if you
206 rarely need to explicitly invoke /. One notable exception is if you
207 are trying to call a function with a list of tuples as arguments (the
207 are trying to call a function with a list of tuples as arguments (the
208 parenthesis will confuse IPython):
208 parenthesis will confuse IPython):
209 In [1]: zip (1,2,3),(4,5,6) # won't work
209 In [1]: zip (1,2,3),(4,5,6) # won't work
210 but this will work:
210 but this will work:
211 In [2]: /zip (1,2,3),(4,5,6)
211 In [2]: /zip (1,2,3),(4,5,6)
212 ------> zip ((1,2,3),(4,5,6))
212 ------> zip ((1,2,3),(4,5,6))
213 Out[2]= [(1, 4), (2, 5), (3, 6)]
213 Out[2]= [(1, 4), (2, 5), (3, 6)]
214
214
215 IPython tells you that it has altered your command line by
215 IPython tells you that it has altered your command line by
216 displaying the new command line preceded by -->. e.g.:
216 displaying the new command line preceded by -->. e.g.:
217 In [18]: callable list
217 In [18]: callable list
218 -------> callable (list)
218 -------> callable (list)
219
219
220 2. Auto-Quoting
220 2. Auto-Quoting
221 You can force auto-quoting of a function's arguments by using ',' as
221 You can force auto-quoting of a function's arguments by using ',' as
222 the first character of a line. For example:
222 the first character of a line. For example:
223 >>> ,my_function /home/me # becomes my_function("/home/me")
223 >>> ,my_function /home/me # becomes my_function("/home/me")
224
224
225 If you use ';' instead, the whole argument is quoted as a single
225 If you use ';' instead, the whole argument is quoted as a single
226 string (while ',' splits on whitespace):
226 string (while ',' splits on whitespace):
227 >>> ,my_function a b c # becomes my_function("a","b","c")
227 >>> ,my_function a b c # becomes my_function("a","b","c")
228 >>> ;my_function a b c # becomes my_function("a b c")
228 >>> ;my_function a b c # becomes my_function("a b c")
229
229
230 Note that the ',' MUST be the first character on the line! This
230 Note that the ',' MUST be the first character on the line! This
231 won't work:
231 won't work:
232 >>> x = ,my_function /home/me # syntax error
232 >>> x = ,my_function /home/me # syntax error
233 """
233 """
234
234
235 interactive_usage_min = """\
235 interactive_usage_min = """\
236 An enhanced console for Python.
236 An enhanced console for Python.
237 Some of its features are:
237 Some of its features are:
238 - Readline support if the readline library is present.
238 - Readline support if the readline library is present.
239 - Tab completion in the local namespace.
239 - Tab completion in the local namespace.
240 - Logging of input, see command-line options.
240 - Logging of input, see command-line options.
241 - System shell escape via ! , eg !ls.
241 - System shell escape via ! , eg !ls.
242 - Magic commands, starting with a % (like %ls, %pwd, %cd, etc.)
242 - Magic commands, starting with a % (like %ls, %pwd, %cd, etc.)
243 - Keeps track of locally defined variables via %who, %whos.
243 - Keeps track of locally defined variables via %who, %whos.
244 - Show object information with a ? eg ?x or x? (use ?? for more info).
244 - Show object information with a ? eg ?x or x? (use ?? for more info).
245 """
245 """
246
246
247 quick_reference = r"""
247 quick_reference = r"""
248 IPython -- An enhanced Interactive Python - Quick Reference Card
248 IPython -- An enhanced Interactive Python - Quick Reference Card
249 ================================================================
249 ================================================================
250
250
251 obj?, obj?? : Get help, or more help for object (also works as
251 obj?, obj?? : Get help, or more help for object (also works as
252 ?obj, ??obj).
252 ?obj, ??obj).
253 ?foo.*abc* : List names in 'foo' containing 'abc' in them.
253 ?foo.*abc* : List names in 'foo' containing 'abc' in them.
254 %magic : Information about IPython's 'magic' % functions.
254 %magic : Information about IPython's 'magic' % functions.
255
255
256 Magic functions are prefixed by %, and typically take their arguments without
256 Magic functions are prefixed by %, and typically take their arguments without
257 parentheses, quotes or even commas for convenience.
257 parentheses, quotes or even commas for convenience.
258
258
259 Example magic function calls:
259 Example magic function calls:
260
260
261 %alias d ls -F : 'd' is now an alias for 'ls -F'
261 %alias d ls -F : 'd' is now an alias for 'ls -F'
262 alias d ls -F : Works if 'alias' not a python name
262 alias d ls -F : Works if 'alias' not a python name
263 alist = %alias : Get list of aliases to 'alist'
263 alist = %alias : Get list of aliases to 'alist'
264 cd /usr/share : Obvious. cd -<tab> to choose from visited dirs.
264 cd /usr/share : Obvious. cd -<tab> to choose from visited dirs.
265 %cd?? : See help AND source for magic %cd
265 %cd?? : See help AND source for magic %cd
266
266
267 System commands:
267 System commands:
268
268
269 !cp a.txt b/ : System command escape, calls os.system()
269 !cp a.txt b/ : System command escape, calls os.system()
270 cp a.txt b/ : after %rehashx, most system commands work without !
270 cp a.txt b/ : after %rehashx, most system commands work without !
271 cp ${f}.txt $bar : Variable expansion in magics and system commands
271 cp ${f}.txt $bar : Variable expansion in magics and system commands
272 files = !ls /usr : Capture sytem command output
272 files = !ls /usr : Capture sytem command output
273 files.s, files.l, files.n: "a b c", ['a','b','c'], 'a\nb\nc'
273 files.s, files.l, files.n: "a b c", ['a','b','c'], 'a\nb\nc'
274
274
275 History:
275 History:
276
276
277 _i, _ii, _iii : Previous, next previous, next next previous input
277 _i, _ii, _iii : Previous, next previous, next next previous input
278 _i4, _ih[2:5] : Input history line 4, lines 2-4
278 _i4, _ih[2:5] : Input history line 4, lines 2-4
279 exec _i81 : Execute input history line #81 again
279 exec _i81 : Execute input history line #81 again
280 %rep 81 : Edit input history line #81
280 %rep 81 : Edit input history line #81
281 _, __, ___ : previous, next previous, next next previous output
281 _, __, ___ : previous, next previous, next next previous output
282 _dh : Directory history
282 _dh : Directory history
283 _oh : Output history
283 _oh : Output history
284 %hist : Command history. '%hist -g foo' search history for 'foo'
284 %hist : Command history. '%hist -g foo' search history for 'foo'
285
285
286 Autocall:
286 Autocall:
287
287
288 f 1,2 : f(1,2)
288 f 1,2 : f(1,2)
289 /f 1,2 : f(1,2) (forced autoparen)
289 /f 1,2 : f(1,2) (forced autoparen)
290 ,f 1 2 : f("1","2")
290 ,f 1 2 : f("1","2")
291 ;f 1 2 : f("1 2")
291 ;f 1 2 : f("1 2")
292
292
293 Remember: TAB completion works in many contexts, not just file names
293 Remember: TAB completion works in many contexts, not just file names
294 or python names.
294 or python names.
295
295
296 The following magic functions are currently available:
296 The following magic functions are currently available:
297
297
298 """
298 """
299
299
300 gui_reference = """\
300 gui_reference = """\
301 ===============================
301 ===============================
302 The graphical IPython console
302 The graphical IPython console
303 ===============================
303 ===============================
304
304
305 This console is designed to emulate the look, feel and workflow of a terminal
305 This console is designed to emulate the look, feel and workflow of a terminal
306 environment, while adding a number of enhancements that are simply not possible
306 environment, while adding a number of enhancements that are simply not possible
307 in a real terminal, such as inline syntax highlighting, true multiline editing,
307 in a real terminal, such as inline syntax highlighting, true multiline editing,
308 inline graphics and much more.
308 inline graphics and much more.
309
309
310 This quick reference document contains the basic information you'll need to
310 This quick reference document contains the basic information you'll need to
311 know to make the most efficient use of it. For the various command line
311 know to make the most efficient use of it. For the various command line
312 options available at startup, type ``ipython qtconsole --help`` at the command line.
312 options available at startup, type ``ipython qtconsole --help`` at the command line.
313
313
314
314
315 Multiline editing
315 Multiline editing
316 =================
316 =================
317
317
318 The graphical console is capable of true multiline editing, but it also tries
318 The graphical console is capable of true multiline editing, but it also tries
319 to behave intuitively like a terminal when possible. If you are used to
319 to behave intuitively like a terminal when possible. If you are used to
320 IPyhton's old terminal behavior, you should find the transition painless, and
320 IPyhton's old terminal behavior, you should find the transition painless, and
321 once you learn a few basic keybindings it will be a much more efficient
321 once you learn a few basic keybindings it will be a much more efficient
322 environment.
322 environment.
323
323
324 For single expressions or indented blocks, the console behaves almost like the
324 For single expressions or indented blocks, the console behaves almost like the
325 terminal IPython: single expressions are immediately evaluated, and indented
325 terminal IPython: single expressions are immediately evaluated, and indented
326 blocks are evaluated once a single blank line is entered::
326 blocks are evaluated once a single blank line is entered::
327
327
328 In [1]: print "Hello IPython!" # Enter was pressed at the end of the line
328 In [1]: print "Hello IPython!" # Enter was pressed at the end of the line
329 Hello IPython!
329 Hello IPython!
330
330
331 In [2]: for i in range(10):
331 In [2]: for i in range(10):
332 ...: print i,
332 ...: print i,
333 ...:
333 ...:
334 0 1 2 3 4 5 6 7 8 9
334 0 1 2 3 4 5 6 7 8 9
335
335
336 If you want to enter more than one expression in a single input block
336 If you want to enter more than one expression in a single input block
337 (something not possible in the terminal), you can use ``Control-Enter`` at the
337 (something not possible in the terminal), you can use ``Control-Enter`` at the
338 end of your first line instead of ``Enter``. At that point the console goes
338 end of your first line instead of ``Enter``. At that point the console goes
339 into 'cell mode' and even if your inputs are not indented, it will continue
339 into 'cell mode' and even if your inputs are not indented, it will continue
340 accepting arbitrarily many lines until either you enter an extra blank line or
340 accepting arbitrarily many lines until either you enter an extra blank line or
341 you hit ``Shift-Enter`` (the key binding that forces execution). When a
341 you hit ``Shift-Enter`` (the key binding that forces execution). When a
342 multiline cell is entered, IPython analyzes it and executes its code producing
342 multiline cell is entered, IPython analyzes it and executes its code producing
343 an ``Out[n]`` prompt only for the last expression in it, while the rest of the
343 an ``Out[n]`` prompt only for the last expression in it, while the rest of the
344 cell is executed as if it was a script. An example should clarify this::
344 cell is executed as if it was a script. An example should clarify this::
345
345
346 In [3]: x=1 # Hit C-Enter here
346 In [3]: x=1 # Hit C-Enter here
347 ...: y=2 # from now on, regular Enter is sufficient
347 ...: y=2 # from now on, regular Enter is sufficient
348 ...: z=3
348 ...: z=3
349 ...: x**2 # This does *not* produce an Out[] value
349 ...: x**2 # This does *not* produce an Out[] value
350 ...: x+y+z # Only the last expression does
350 ...: x+y+z # Only the last expression does
351 ...:
351 ...:
352 Out[3]: 6
352 Out[3]: 6
353
353
354 The behavior where an extra blank line forces execution is only active if you
354 The behavior where an extra blank line forces execution is only active if you
355 are actually typing at the keyboard each line, and is meant to make it mimic
355 are actually typing at the keyboard each line, and is meant to make it mimic
356 the IPython terminal behavior. If you paste a long chunk of input (for example
356 the IPython terminal behavior. If you paste a long chunk of input (for example
357 a long script copied form an editor or web browser), it can contain arbitrarily
357 a long script copied form an editor or web browser), it can contain arbitrarily
358 many intermediate blank lines and they won't cause any problems. As always,
358 many intermediate blank lines and they won't cause any problems. As always,
359 you can then make it execute by appending a blank line *at the end* or hitting
359 you can then make it execute by appending a blank line *at the end* or hitting
360 ``Shift-Enter`` anywhere within the cell.
360 ``Shift-Enter`` anywhere within the cell.
361
361
362 With the up arrow key, you can retrieve previous blocks of input that contain
362 With the up arrow key, you can retrieve previous blocks of input that contain
363 multiple lines. You can move inside of a multiline cell like you would in any
363 multiple lines. You can move inside of a multiline cell like you would in any
364 text editor. When you want it executed, the simplest thing to do is to hit the
364 text editor. When you want it executed, the simplest thing to do is to hit the
365 force execution key, ``Shift-Enter`` (though you can also navigate to the end
365 force execution key, ``Shift-Enter`` (though you can also navigate to the end
366 and append a blank line by using ``Enter`` twice).
366 and append a blank line by using ``Enter`` twice).
367
367
368 If you've edited a multiline cell and accidentally navigate out of it with the
368 If you've edited a multiline cell and accidentally navigate out of it with the
369 up or down arrow keys, IPython will clear the cell and replace it with the
369 up or down arrow keys, IPython will clear the cell and replace it with the
370 contents of the one above or below that you navigated to. If this was an
370 contents of the one above or below that you navigated to. If this was an
371 accident and you want to retrieve the cell you were editing, use the Undo
371 accident and you want to retrieve the cell you were editing, use the Undo
372 keybinding, ``Control-z``.
372 keybinding, ``Control-z``.
373
373
374
374
375 Key bindings
375 Key bindings
376 ============
376 ============
377
377
378 The IPython console supports most of the basic Emacs line-oriented keybindings,
378 The IPython console supports most of the basic Emacs line-oriented keybindings,
379 in addition to some of its own.
379 in addition to some of its own.
380
380
381 The keybinding prefixes mean:
381 The keybinding prefixes mean:
382
382
383 - ``C``: Control
383 - ``C``: Control
384 - ``S``: Shift
384 - ``S``: Shift
385 - ``M``: Meta (typically the Alt key)
385 - ``M``: Meta (typically the Alt key)
386
386
387 The keybindings themselves are:
387 The keybindings themselves are:
388
388
389 - ``Enter``: insert new line (may cause execution, see above).
389 - ``Enter``: insert new line (may cause execution, see above).
390 - ``C-Enter``: *force* new line, *never* causes execution.
390 - ``C-Enter``: *force* new line, *never* causes execution.
391 - ``S-Enter``: *force* execution regardless of where cursor is, no newline added.
391 - ``S-Enter``: *force* execution regardless of where cursor is, no newline added.
392 - ``Up``: step backwards through the history.
392 - ``Up``: step backwards through the history.
393 - ``Down``: step forwards through the history.
393 - ``Down``: step forwards through the history.
394 - ``S-Up``: search backwards through the history (like ``C-r`` in bash).
394 - ``S-Up``: search backwards through the history (like ``C-r`` in bash).
395 - ``S-Down``: search forwards through the history.
395 - ``S-Down``: search forwards through the history.
396 - ``C-c``: copy highlighted text to clipboard (prompts are automatically stripped).
396 - ``C-c``: copy highlighted text to clipboard (prompts are automatically stripped).
397 - ``C-S-c``: copy highlighted text to clipboard (prompts are not stripped).
397 - ``C-S-c``: copy highlighted text to clipboard (prompts are not stripped).
398 - ``C-v``: paste text from clipboard.
398 - ``C-v``: paste text from clipboard.
399 - ``C-z``: undo (retrieves lost text if you move out of a cell with the arrows).
399 - ``C-z``: undo (retrieves lost text if you move out of a cell with the arrows).
400 - ``C-S-z``: redo.
400 - ``C-S-z``: redo.
401 - ``C-o``: move to 'other' area, between pager and terminal.
401 - ``C-o``: move to 'other' area, between pager and terminal.
402 - ``C-l``: clear terminal.
402 - ``C-l``: clear terminal.
403 - ``C-a``: go to beginning of line.
403 - ``C-a``: go to beginning of line.
404 - ``C-e``: go to end of line.
404 - ``C-e``: go to end of line.
405 - ``C-k``: kill from cursor to the end of the line.
405 - ``C-k``: kill from cursor to the end of the line.
406 - ``C-y``: yank (paste)
406 - ``C-y``: yank (paste)
407 - ``C-p``: previous line (like up arrow)
407 - ``C-p``: previous line (like up arrow)
408 - ``C-n``: next line (like down arrow)
408 - ``C-n``: next line (like down arrow)
409 - ``C-f``: forward (like right arrow)
409 - ``C-f``: forward (like right arrow)
410 - ``C-b``: back (like left arrow)
410 - ``C-b``: back (like left arrow)
411 - ``C-d``: delete next character.
411 - ``C-d``: delete next character.
412 - ``M-<``: move to the beginning of the input region.
412 - ``M-<``: move to the beginning of the input region.
413 - ``M->``: move to the end of the input region.
413 - ``M->``: move to the end of the input region.
414 - ``M-d``: delete next word.
414 - ``M-d``: delete next word.
415 - ``M-Backspace``: delete previous word.
415 - ``M-Backspace``: delete previous word.
416 - ``C-.``: force a kernel restart (a confirmation dialog appears).
416 - ``C-.``: force a kernel restart (a confirmation dialog appears).
417 - ``C-+``: increase font size.
417 - ``C-+``: increase font size.
418 - ``C--``: decrease font size.
418 - ``C--``: decrease font size.
419 - ``C-M-Space``: toggle full screen. (Command-Control-Space on Mac OS X)
419
420
420 The IPython pager
421 The IPython pager
421 =================
422 =================
422
423
423 IPython will show long blocks of text from many sources using a builtin pager.
424 IPython will show long blocks of text from many sources using a builtin pager.
424 You can control where this pager appears with the ``--paging`` command-line
425 You can control where this pager appears with the ``--paging`` command-line
425 flag:
426 flag:
426
427
427 - ``inside`` [default]: the pager is overlaid on top of the main terminal. You
428 - ``inside`` [default]: the pager is overlaid on top of the main terminal. You
428 must quit the pager to get back to the terminal (similar to how a pager such
429 must quit the pager to get back to the terminal (similar to how a pager such
429 as ``less`` or ``more`` works).
430 as ``less`` or ``more`` works).
430
431
431 - ``vsplit``: the console is made double-tall, and the pager appears on the
432 - ``vsplit``: the console is made double-tall, and the pager appears on the
432 bottom area when needed. You can view its contents while using the terminal.
433 bottom area when needed. You can view its contents while using the terminal.
433
434
434 - ``hsplit``: the console is made double-wide, and the pager appears on the
435 - ``hsplit``: the console is made double-wide, and the pager appears on the
435 right area when needed. You can view its contents while using the terminal.
436 right area when needed. You can view its contents while using the terminal.
436
437
437 - ``none``: the console never pages output.
438 - ``none``: the console never pages output.
438
439
439 If you use the vertical or horizontal paging modes, you can navigate between
440 If you use the vertical or horizontal paging modes, you can navigate between
440 terminal and pager as follows:
441 terminal and pager as follows:
441
442
442 - Tab key: goes from pager to terminal (but not the other way around).
443 - Tab key: goes from pager to terminal (but not the other way around).
443 - Control-o: goes from one to another always.
444 - Control-o: goes from one to another always.
444 - Mouse: click on either.
445 - Mouse: click on either.
445
446
446 In all cases, the ``q`` or ``Escape`` keys quit the pager (when used with the
447 In all cases, the ``q`` or ``Escape`` keys quit the pager (when used with the
447 focus on the pager area).
448 focus on the pager area).
448
449
449 Running subprocesses
450 Running subprocesses
450 ====================
451 ====================
451
452
452 The graphical IPython console uses the ``pexpect`` module to run subprocesses
453 The graphical IPython console uses the ``pexpect`` module to run subprocesses
453 when you type ``!command``. This has a number of advantages (true asynchronous
454 when you type ``!command``. This has a number of advantages (true asynchronous
454 output from subprocesses as well as very robust termination of rogue
455 output from subprocesses as well as very robust termination of rogue
455 subprocesses with ``Control-C``), as well as some limitations. The main
456 subprocesses with ``Control-C``), as well as some limitations. The main
456 limitation is that you can *not* interact back with the subprocess, so anything
457 limitation is that you can *not* interact back with the subprocess, so anything
457 that invokes a pager or expects you to type input into it will block and hang
458 that invokes a pager or expects you to type input into it will block and hang
458 (you can kill it with ``Control-C``).
459 (you can kill it with ``Control-C``).
459
460
460 We have provided as magics ``%less`` to page files (aliased to ``%more``),
461 We have provided as magics ``%less`` to page files (aliased to ``%more``),
461 ``%clear`` to clear the terminal, and ``%man`` on Linux/OSX. These cover the
462 ``%clear`` to clear the terminal, and ``%man`` on Linux/OSX. These cover the
462 most common commands you'd want to call in your subshell and that would cause
463 most common commands you'd want to call in your subshell and that would cause
463 problems if invoked via ``!cmd``, but you need to be aware of this limitation.
464 problems if invoked via ``!cmd``, but you need to be aware of this limitation.
464
465
465 Display
466 Display
466 =======
467 =======
467
468
468 The IPython console can now display objects in a variety of formats, including
469 The IPython console can now display objects in a variety of formats, including
469 HTML, PNG and SVG. This is accomplished using the display functions in
470 HTML, PNG and SVG. This is accomplished using the display functions in
470 ``IPython.core.display``::
471 ``IPython.core.display``::
471
472
472 In [4]: from IPython.core.display import display, display_html
473 In [4]: from IPython.core.display import display, display_html
473
474
474 In [5]: from IPython.core.display import display_png, display_svg
475 In [5]: from IPython.core.display import display_png, display_svg
475
476
476 Python objects can simply be passed to these functions and the appropriate
477 Python objects can simply be passed to these functions and the appropriate
477 representations will be displayed in the console as long as the objects know
478 representations will be displayed in the console as long as the objects know
478 how to compute those representations. The easiest way of teaching objects how
479 how to compute those representations. The easiest way of teaching objects how
479 to format themselves in various representations is to define special methods
480 to format themselves in various representations is to define special methods
480 such as: ``_repr_html_``, ``_repr_svg_`` and ``_repr_png_``. IPython's display formatters
481 such as: ``_repr_html_``, ``_repr_svg_`` and ``_repr_png_``. IPython's display formatters
481 can also be given custom formatter functions for various types::
482 can also be given custom formatter functions for various types::
482
483
483 In [6]: ip = get_ipython()
484 In [6]: ip = get_ipython()
484
485
485 In [7]: html_formatter = ip.display_formatter.formatters['text/html']
486 In [7]: html_formatter = ip.display_formatter.formatters['text/html']
486
487
487 In [8]: html_formatter.for_type(Foo, foo_to_html)
488 In [8]: html_formatter.for_type(Foo, foo_to_html)
488
489
489 For further details, see ``IPython.core.formatters``.
490 For further details, see ``IPython.core.formatters``.
490
491
491 Inline matplotlib graphics
492 Inline matplotlib graphics
492 ==========================
493 ==========================
493
494
494 The IPython console is capable of displaying matplotlib figures inline, in SVG
495 The IPython console is capable of displaying matplotlib figures inline, in SVG
495 or PNG format. If started with the ``pylab=inline``, then all figures are
496 or PNG format. If started with the ``pylab=inline``, then all figures are
496 rendered inline automatically (PNG by default). If started with ``--pylab``
497 rendered inline automatically (PNG by default). If started with ``--pylab``
497 or ``pylab=<your backend>``, then a GUI backend will be used, but IPython's
498 or ``pylab=<your backend>``, then a GUI backend will be used, but IPython's
498 ``display()`` and ``getfigs()`` functions can be used to view plots inline::
499 ``display()`` and ``getfigs()`` functions can be used to view plots inline::
499
500
500 In [9]: display(*getfigs()) # display all figures inline
501 In [9]: display(*getfigs()) # display all figures inline
501
502
502 In[10]: display(*getfigs(1,2)) # display figures 1 and 2 inline
503 In[10]: display(*getfigs(1,2)) # display figures 1 and 2 inline
503 """
504 """
504
505
505
506
506 quick_guide = """\
507 quick_guide = """\
507 ? -> Introduction and overview of IPython's features.
508 ? -> Introduction and overview of IPython's features.
508 %quickref -> Quick reference.
509 %quickref -> Quick reference.
509 help -> Python's own help system.
510 help -> Python's own help system.
510 object? -> Details about 'object', use 'object??' for extra details.
511 object? -> Details about 'object', use 'object??' for extra details.
511 """
512 """
512
513
513 gui_note = """\
514 gui_note = """\
514 %guiref -> A brief reference about the graphical user interface.
515 %guiref -> A brief reference about the graphical user interface.
515 """
516 """
516
517
517 default_banner_parts = [
518 default_banner_parts = [
518 'Python %s\n' % (sys.version.split('\n')[0],),
519 'Python %s\n' % (sys.version.split('\n')[0],),
519 'Type "copyright", "credits" or "license" for more information.\n\n',
520 'Type "copyright", "credits" or "license" for more information.\n\n',
520 'IPython %s -- An enhanced Interactive Python.\n' % (release.version,),
521 'IPython %s -- An enhanced Interactive Python.\n' % (release.version,),
521 quick_guide
522 quick_guide
522 ]
523 ]
523
524
524 default_gui_banner_parts = default_banner_parts + [gui_note]
525 default_gui_banner_parts = default_banner_parts + [gui_note]
525
526
526 default_banner = ''.join(default_banner_parts)
527 default_banner = ''.join(default_banner_parts)
527
528
528 default_gui_banner = ''.join(default_gui_banner_parts)
529 default_gui_banner = ''.join(default_gui_banner_parts)
@@ -1,484 +1,497 b''
1 """ A minimal application using the Qt console-style IPython frontend.
1 """ A minimal application using the Qt console-style IPython frontend.
2
2
3 This is not a complete console app, as subprocess will not be able to receive
3 This is not a complete console app, as subprocess will not be able to receive
4 input, there is no real readline support, among other limitations.
4 input, there is no real readline support, among other limitations.
5
5
6 Authors:
6 Authors:
7
7
8 * Evan Patterson
8 * Evan Patterson
9 * Min RK
9 * Min RK
10 * Erik Tollerud
10 * Erik Tollerud
11 * Fernando Perez
11 * Fernando Perez
12
12
13 """
13 """
14
14
15 #-----------------------------------------------------------------------------
15 #-----------------------------------------------------------------------------
16 # Imports
16 # Imports
17 #-----------------------------------------------------------------------------
17 #-----------------------------------------------------------------------------
18
18
19 # stdlib imports
19 # stdlib imports
20 import os
20 import os
21 import signal
21 import signal
22 import sys
22 import sys
23 from getpass import getpass
23 from getpass import getpass
24
24
25 # System library imports
25 # System library imports
26 from IPython.external.qt import QtGui
26 from IPython.external.qt import QtGui
27 from pygments.styles import get_all_styles
27 from pygments.styles import get_all_styles
28
28
29 # external imports
29 # external imports
30 from IPython.external.ssh import tunnel
30 from IPython.external.ssh import tunnel
31
31
32 # Local imports
32 # Local imports
33 from IPython.config.application import boolean_flag
33 from IPython.config.application import boolean_flag
34 from IPython.core.application import BaseIPythonApplication
34 from IPython.core.application import BaseIPythonApplication
35 from IPython.core.profiledir import ProfileDir
35 from IPython.core.profiledir import ProfileDir
36 from IPython.frontend.qt.console.frontend_widget import FrontendWidget
36 from IPython.frontend.qt.console.frontend_widget import FrontendWidget
37 from IPython.frontend.qt.console.ipython_widget import IPythonWidget
37 from IPython.frontend.qt.console.ipython_widget import IPythonWidget
38 from IPython.frontend.qt.console.rich_ipython_widget import RichIPythonWidget
38 from IPython.frontend.qt.console.rich_ipython_widget import RichIPythonWidget
39 from IPython.frontend.qt.console import styles
39 from IPython.frontend.qt.console import styles
40 from IPython.frontend.qt.kernelmanager import QtKernelManager
40 from IPython.frontend.qt.kernelmanager import QtKernelManager
41 from IPython.parallel.util import select_random_ports
41 from IPython.parallel.util import select_random_ports
42 from IPython.utils.traitlets import (
42 from IPython.utils.traitlets import (
43 Dict, List, Unicode, Int, CaselessStrEnum, CBool, Any
43 Dict, List, Unicode, Int, CaselessStrEnum, CBool, Any
44 )
44 )
45 from IPython.zmq.ipkernel import (
45 from IPython.zmq.ipkernel import (
46 flags as ipkernel_flags,
46 flags as ipkernel_flags,
47 aliases as ipkernel_aliases,
47 aliases as ipkernel_aliases,
48 IPKernelApp
48 IPKernelApp
49 )
49 )
50 from IPython.zmq.session import Session
50 from IPython.zmq.session import Session
51 from IPython.zmq.zmqshell import ZMQInteractiveShell
51 from IPython.zmq.zmqshell import ZMQInteractiveShell
52
52
53
53
54 #-----------------------------------------------------------------------------
54 #-----------------------------------------------------------------------------
55 # Network Constants
55 # Network Constants
56 #-----------------------------------------------------------------------------
56 #-----------------------------------------------------------------------------
57
57
58 from IPython.utils.localinterfaces import LOCALHOST, LOCAL_IPS
58 from IPython.utils.localinterfaces import LOCALHOST, LOCAL_IPS
59
59
60 #-----------------------------------------------------------------------------
60 #-----------------------------------------------------------------------------
61 # Globals
61 # Globals
62 #-----------------------------------------------------------------------------
62 #-----------------------------------------------------------------------------
63
63
64 _examples = """
64 _examples = """
65 ipython qtconsole # start the qtconsole
65 ipython qtconsole # start the qtconsole
66 ipython qtconsole --pylab=inline # start with pylab in inline plotting mode
66 ipython qtconsole --pylab=inline # start with pylab in inline plotting mode
67 """
67 """
68
68
69 #-----------------------------------------------------------------------------
69 #-----------------------------------------------------------------------------
70 # Classes
70 # Classes
71 #-----------------------------------------------------------------------------
71 #-----------------------------------------------------------------------------
72
72
73 class MainWindow(QtGui.QMainWindow):
73 class MainWindow(QtGui.QMainWindow):
74
74
75 #---------------------------------------------------------------------------
75 #---------------------------------------------------------------------------
76 # 'object' interface
76 # 'object' interface
77 #---------------------------------------------------------------------------
77 #---------------------------------------------------------------------------
78
78
79 def __init__(self, app, frontend, existing=False, may_close=True,
79 def __init__(self, app, frontend, existing=False, may_close=True,
80 confirm_exit=True):
80 confirm_exit=True):
81 """ Create a MainWindow for the specified FrontendWidget.
81 """ Create a MainWindow for the specified FrontendWidget.
82
82
83 The app is passed as an argument to allow for different
83 The app is passed as an argument to allow for different
84 closing behavior depending on whether we are the Kernel's parent.
84 closing behavior depending on whether we are the Kernel's parent.
85
85
86 If existing is True, then this Console does not own the Kernel.
86 If existing is True, then this Console does not own the Kernel.
87
87
88 If may_close is True, then this Console is permitted to close the kernel
88 If may_close is True, then this Console is permitted to close the kernel
89 """
89 """
90 super(MainWindow, self).__init__()
90 super(MainWindow, self).__init__()
91 self._app = app
91 self._app = app
92 self._frontend = frontend
92 self._frontend = frontend
93 self._existing = existing
93 self._existing = existing
94 if existing:
94 if existing:
95 self._may_close = may_close
95 self._may_close = may_close
96 else:
96 else:
97 self._may_close = True
97 self._may_close = True
98 self._frontend.exit_requested.connect(self.close)
98 self._frontend.exit_requested.connect(self.close)
99 self._confirm_exit = confirm_exit
99 self._confirm_exit = confirm_exit
100 self.setCentralWidget(frontend)
100 self.setCentralWidget(frontend)
101
101
102 #---------------------------------------------------------------------------
102 #---------------------------------------------------------------------------
103 # QWidget interface
103 # QWidget interface
104 #---------------------------------------------------------------------------
104 #---------------------------------------------------------------------------
105
105
106 def closeEvent(self, event):
106 def closeEvent(self, event):
107 """ Close the window and the kernel (if necessary).
107 """ Close the window and the kernel (if necessary).
108
108
109 This will prompt the user if they are finished with the kernel, and if
109 This will prompt the user if they are finished with the kernel, and if
110 so, closes the kernel cleanly. Alternatively, if the exit magic is used,
110 so, closes the kernel cleanly. Alternatively, if the exit magic is used,
111 it closes without prompt.
111 it closes without prompt.
112 """
112 """
113 keepkernel = None #Use the prompt by default
113 keepkernel = None #Use the prompt by default
114 if hasattr(self._frontend,'_keep_kernel_on_exit'): #set by exit magic
114 if hasattr(self._frontend,'_keep_kernel_on_exit'): #set by exit magic
115 keepkernel = self._frontend._keep_kernel_on_exit
115 keepkernel = self._frontend._keep_kernel_on_exit
116
116
117 kernel_manager = self._frontend.kernel_manager
117 kernel_manager = self._frontend.kernel_manager
118
118
119 if keepkernel is None and not self._confirm_exit:
119 if keepkernel is None and not self._confirm_exit:
120 # don't prompt, just terminate the kernel if we own it
120 # don't prompt, just terminate the kernel if we own it
121 # or leave it alone if we don't
121 # or leave it alone if we don't
122 keepkernel = not self._existing
122 keepkernel = not self._existing
123
123
124 if keepkernel is None: #show prompt
124 if keepkernel is None: #show prompt
125 if kernel_manager and kernel_manager.channels_running:
125 if kernel_manager and kernel_manager.channels_running:
126 title = self.window().windowTitle()
126 title = self.window().windowTitle()
127 cancel = QtGui.QMessageBox.Cancel
127 cancel = QtGui.QMessageBox.Cancel
128 okay = QtGui.QMessageBox.Ok
128 okay = QtGui.QMessageBox.Ok
129 if self._may_close:
129 if self._may_close:
130 msg = "You are closing this Console window."
130 msg = "You are closing this Console window."
131 info = "Would you like to quit the Kernel and all attached Consoles as well?"
131 info = "Would you like to quit the Kernel and all attached Consoles as well?"
132 justthis = QtGui.QPushButton("&No, just this Console", self)
132 justthis = QtGui.QPushButton("&No, just this Console", self)
133 justthis.setShortcut('N')
133 justthis.setShortcut('N')
134 closeall = QtGui.QPushButton("&Yes, quit everything", self)
134 closeall = QtGui.QPushButton("&Yes, quit everything", self)
135 closeall.setShortcut('Y')
135 closeall.setShortcut('Y')
136 box = QtGui.QMessageBox(QtGui.QMessageBox.Question,
136 box = QtGui.QMessageBox(QtGui.QMessageBox.Question,
137 title, msg)
137 title, msg)
138 box.setInformativeText(info)
138 box.setInformativeText(info)
139 box.addButton(cancel)
139 box.addButton(cancel)
140 box.addButton(justthis, QtGui.QMessageBox.NoRole)
140 box.addButton(justthis, QtGui.QMessageBox.NoRole)
141 box.addButton(closeall, QtGui.QMessageBox.YesRole)
141 box.addButton(closeall, QtGui.QMessageBox.YesRole)
142 box.setDefaultButton(closeall)
142 box.setDefaultButton(closeall)
143 box.setEscapeButton(cancel)
143 box.setEscapeButton(cancel)
144 reply = box.exec_()
144 reply = box.exec_()
145 if reply == 1: # close All
145 if reply == 1: # close All
146 kernel_manager.shutdown_kernel()
146 kernel_manager.shutdown_kernel()
147 #kernel_manager.stop_channels()
147 #kernel_manager.stop_channels()
148 event.accept()
148 event.accept()
149 elif reply == 0: # close Console
149 elif reply == 0: # close Console
150 if not self._existing:
150 if not self._existing:
151 # Have kernel: don't quit, just close the window
151 # Have kernel: don't quit, just close the window
152 self._app.setQuitOnLastWindowClosed(False)
152 self._app.setQuitOnLastWindowClosed(False)
153 self.deleteLater()
153 self.deleteLater()
154 event.accept()
154 event.accept()
155 else:
155 else:
156 event.ignore()
156 event.ignore()
157 else:
157 else:
158 reply = QtGui.QMessageBox.question(self, title,
158 reply = QtGui.QMessageBox.question(self, title,
159 "Are you sure you want to close this Console?"+
159 "Are you sure you want to close this Console?"+
160 "\nThe Kernel and other Consoles will remain active.",
160 "\nThe Kernel and other Consoles will remain active.",
161 okay|cancel,
161 okay|cancel,
162 defaultButton=okay
162 defaultButton=okay
163 )
163 )
164 if reply == okay:
164 if reply == okay:
165 event.accept()
165 event.accept()
166 else:
166 else:
167 event.ignore()
167 event.ignore()
168 elif keepkernel: #close console but leave kernel running (no prompt)
168 elif keepkernel: #close console but leave kernel running (no prompt)
169 if kernel_manager and kernel_manager.channels_running:
169 if kernel_manager and kernel_manager.channels_running:
170 if not self._existing:
170 if not self._existing:
171 # I have the kernel: don't quit, just close the window
171 # I have the kernel: don't quit, just close the window
172 self._app.setQuitOnLastWindowClosed(False)
172 self._app.setQuitOnLastWindowClosed(False)
173 event.accept()
173 event.accept()
174 else: #close console and kernel (no prompt)
174 else: #close console and kernel (no prompt)
175 if kernel_manager and kernel_manager.channels_running:
175 if kernel_manager and kernel_manager.channels_running:
176 kernel_manager.shutdown_kernel()
176 kernel_manager.shutdown_kernel()
177 event.accept()
177 event.accept()
178
178
179 #-----------------------------------------------------------------------------
179 #-----------------------------------------------------------------------------
180 # Aliases and Flags
180 # Aliases and Flags
181 #-----------------------------------------------------------------------------
181 #-----------------------------------------------------------------------------
182
182
183 flags = dict(ipkernel_flags)
183 flags = dict(ipkernel_flags)
184 qt_flags = {
184 qt_flags = {
185 'existing' : ({'IPythonQtConsoleApp' : {'existing' : True}},
185 'existing' : ({'IPythonQtConsoleApp' : {'existing' : True}},
186 "Connect to an existing kernel."),
186 "Connect to an existing kernel."),
187 'pure' : ({'IPythonQtConsoleApp' : {'pure' : True}},
187 'pure' : ({'IPythonQtConsoleApp' : {'pure' : True}},
188 "Use a pure Python kernel instead of an IPython kernel."),
188 "Use a pure Python kernel instead of an IPython kernel."),
189 'plain' : ({'ConsoleWidget' : {'kind' : 'plain'}},
189 'plain' : ({'ConsoleWidget' : {'kind' : 'plain'}},
190 "Disable rich text support."),
190 "Disable rich text support."),
191 }
191 }
192 qt_flags.update(boolean_flag(
192 qt_flags.update(boolean_flag(
193 'gui-completion', 'ConsoleWidget.gui_completion',
193 'gui-completion', 'ConsoleWidget.gui_completion',
194 "use a GUI widget for tab completion",
194 "use a GUI widget for tab completion",
195 "use plaintext output for completion"
195 "use plaintext output for completion"
196 ))
196 ))
197 qt_flags.update(boolean_flag(
197 qt_flags.update(boolean_flag(
198 'confirm-exit', 'IPythonQtConsoleApp.confirm_exit',
198 'confirm-exit', 'IPythonQtConsoleApp.confirm_exit',
199 """Set to display confirmation dialog on exit. You can always use 'exit' or 'quit',
199 """Set to display confirmation dialog on exit. You can always use 'exit' or 'quit',
200 to force a direct exit without any confirmation.
200 to force a direct exit without any confirmation.
201 """,
201 """,
202 """Don't prompt the user when exiting. This will terminate the kernel
202 """Don't prompt the user when exiting. This will terminate the kernel
203 if it is owned by the frontend, and leave it alive if it is external.
203 if it is owned by the frontend, and leave it alive if it is external.
204 """
204 """
205 ))
205 ))
206 flags.update(qt_flags)
206 flags.update(qt_flags)
207 # the flags that are specific to the frontend
207 # the flags that are specific to the frontend
208 # these must be scrubbed before being passed to the kernel,
208 # these must be scrubbed before being passed to the kernel,
209 # or it will raise an error on unrecognized flags
209 # or it will raise an error on unrecognized flags
210 qt_flags = qt_flags.keys()
210 qt_flags = qt_flags.keys()
211
211
212 aliases = dict(ipkernel_aliases)
212 aliases = dict(ipkernel_aliases)
213
213
214 qt_aliases = dict(
214 qt_aliases = dict(
215 hb = 'IPythonQtConsoleApp.hb_port',
215 hb = 'IPythonQtConsoleApp.hb_port',
216 shell = 'IPythonQtConsoleApp.shell_port',
216 shell = 'IPythonQtConsoleApp.shell_port',
217 iopub = 'IPythonQtConsoleApp.iopub_port',
217 iopub = 'IPythonQtConsoleApp.iopub_port',
218 stdin = 'IPythonQtConsoleApp.stdin_port',
218 stdin = 'IPythonQtConsoleApp.stdin_port',
219 ip = 'IPythonQtConsoleApp.ip',
219 ip = 'IPythonQtConsoleApp.ip',
220
220
221 style = 'IPythonWidget.syntax_style',
221 style = 'IPythonWidget.syntax_style',
222 stylesheet = 'IPythonQtConsoleApp.stylesheet',
222 stylesheet = 'IPythonQtConsoleApp.stylesheet',
223 colors = 'ZMQInteractiveShell.colors',
223 colors = 'ZMQInteractiveShell.colors',
224
224
225 editor = 'IPythonWidget.editor',
225 editor = 'IPythonWidget.editor',
226 paging = 'ConsoleWidget.paging',
226 paging = 'ConsoleWidget.paging',
227 ssh = 'IPythonQtConsoleApp.sshserver',
227 ssh = 'IPythonQtConsoleApp.sshserver',
228 )
228 )
229 aliases.update(qt_aliases)
229 aliases.update(qt_aliases)
230 # also scrub aliases from the frontend
230 # also scrub aliases from the frontend
231 qt_flags.extend(qt_aliases.keys())
231 qt_flags.extend(qt_aliases.keys())
232
232
233
233
234 #-----------------------------------------------------------------------------
234 #-----------------------------------------------------------------------------
235 # IPythonQtConsole
235 # IPythonQtConsole
236 #-----------------------------------------------------------------------------
236 #-----------------------------------------------------------------------------
237
237
238
238
239 class IPythonQtConsoleApp(BaseIPythonApplication):
239 class IPythonQtConsoleApp(BaseIPythonApplication):
240 name = 'ipython-qtconsole'
240 name = 'ipython-qtconsole'
241 default_config_file_name='ipython_config.py'
241 default_config_file_name='ipython_config.py'
242
242
243 description = """
243 description = """
244 The IPython QtConsole.
244 The IPython QtConsole.
245
245
246 This launches a Console-style application using Qt. It is not a full
246 This launches a Console-style application using Qt. It is not a full
247 console, in that launched terminal subprocesses will not be able to accept
247 console, in that launched terminal subprocesses will not be able to accept
248 input.
248 input.
249
249
250 The QtConsole supports various extra features beyond the Terminal IPython
250 The QtConsole supports various extra features beyond the Terminal IPython
251 shell, such as inline plotting with matplotlib, via:
251 shell, such as inline plotting with matplotlib, via:
252
252
253 ipython qtconsole --pylab=inline
253 ipython qtconsole --pylab=inline
254
254
255 as well as saving your session as HTML, and printing the output.
255 as well as saving your session as HTML, and printing the output.
256
256
257 """
257 """
258 examples = _examples
258 examples = _examples
259
259
260 classes = [IPKernelApp, IPythonWidget, ZMQInteractiveShell, ProfileDir, Session]
260 classes = [IPKernelApp, IPythonWidget, ZMQInteractiveShell, ProfileDir, Session]
261 flags = Dict(flags)
261 flags = Dict(flags)
262 aliases = Dict(aliases)
262 aliases = Dict(aliases)
263
263
264 kernel_argv = List(Unicode)
264 kernel_argv = List(Unicode)
265
265
266 # create requested profiles by default, if they don't exist:
266 # create requested profiles by default, if they don't exist:
267 auto_create = CBool(True)
267 auto_create = CBool(True)
268 # connection info:
268 # connection info:
269 ip = Unicode(LOCALHOST, config=True,
269 ip = Unicode(LOCALHOST, config=True,
270 help="""Set the kernel\'s IP address [default localhost].
270 help="""Set the kernel\'s IP address [default localhost].
271 If the IP address is something other than localhost, then
271 If the IP address is something other than localhost, then
272 Consoles on other machines will be able to connect
272 Consoles on other machines will be able to connect
273 to the Kernel, so be careful!"""
273 to the Kernel, so be careful!"""
274 )
274 )
275
275
276 sshserver = Unicode('', config=True,
276 sshserver = Unicode('', config=True,
277 help="""The SSH server to use to connect to the kernel.""")
277 help="""The SSH server to use to connect to the kernel.""")
278 sshkey = Unicode('', config=True,
278 sshkey = Unicode('', config=True,
279 help="""Path to the ssh key to use for logging in to the ssh server.""")
279 help="""Path to the ssh key to use for logging in to the ssh server.""")
280
280
281 hb_port = Int(0, config=True,
281 hb_port = Int(0, config=True,
282 help="set the heartbeat port [default: random]")
282 help="set the heartbeat port [default: random]")
283 shell_port = Int(0, config=True,
283 shell_port = Int(0, config=True,
284 help="set the shell (XREP) port [default: random]")
284 help="set the shell (XREP) port [default: random]")
285 iopub_port = Int(0, config=True,
285 iopub_port = Int(0, config=True,
286 help="set the iopub (PUB) port [default: random]")
286 help="set the iopub (PUB) port [default: random]")
287 stdin_port = Int(0, config=True,
287 stdin_port = Int(0, config=True,
288 help="set the stdin (XREQ) port [default: random]")
288 help="set the stdin (XREQ) port [default: random]")
289
289
290 existing = CBool(False, config=True,
290 existing = CBool(False, config=True,
291 help="Whether to connect to an already running Kernel.")
291 help="Whether to connect to an already running Kernel.")
292
292
293 stylesheet = Unicode('', config=True,
293 stylesheet = Unicode('', config=True,
294 help="path to a custom CSS stylesheet")
294 help="path to a custom CSS stylesheet")
295
295
296 pure = CBool(False, config=True,
296 pure = CBool(False, config=True,
297 help="Use a pure Python kernel instead of an IPython kernel.")
297 help="Use a pure Python kernel instead of an IPython kernel.")
298 plain = CBool(False, config=True,
298 plain = CBool(False, config=True,
299 help="Use a plaintext widget instead of rich text (plain can't print/save).")
299 help="Use a plaintext widget instead of rich text (plain can't print/save).")
300
300
301 def _pure_changed(self, name, old, new):
301 def _pure_changed(self, name, old, new):
302 kind = 'plain' if self.plain else 'rich'
302 kind = 'plain' if self.plain else 'rich'
303 self.config.ConsoleWidget.kind = kind
303 self.config.ConsoleWidget.kind = kind
304 if self.pure:
304 if self.pure:
305 self.widget_factory = FrontendWidget
305 self.widget_factory = FrontendWidget
306 elif self.plain:
306 elif self.plain:
307 self.widget_factory = IPythonWidget
307 self.widget_factory = IPythonWidget
308 else:
308 else:
309 self.widget_factory = RichIPythonWidget
309 self.widget_factory = RichIPythonWidget
310
310
311 _plain_changed = _pure_changed
311 _plain_changed = _pure_changed
312
312
313 confirm_exit = CBool(True, config=True,
313 confirm_exit = CBool(True, config=True,
314 help="""
314 help="""
315 Set to display confirmation dialog on exit. You can always use 'exit' or 'quit',
315 Set to display confirmation dialog on exit. You can always use 'exit' or 'quit',
316 to force a direct exit without any confirmation.""",
316 to force a direct exit without any confirmation.""",
317 )
317 )
318
318
319 # the factory for creating a widget
319 # the factory for creating a widget
320 widget_factory = Any(RichIPythonWidget)
320 widget_factory = Any(RichIPythonWidget)
321
321
322 def parse_command_line(self, argv=None):
322 def parse_command_line(self, argv=None):
323 super(IPythonQtConsoleApp, self).parse_command_line(argv)
323 super(IPythonQtConsoleApp, self).parse_command_line(argv)
324 if argv is None:
324 if argv is None:
325 argv = sys.argv[1:]
325 argv = sys.argv[1:]
326
326
327 self.kernel_argv = list(argv) # copy
327 self.kernel_argv = list(argv) # copy
328 # kernel should inherit default config file from frontend
328 # kernel should inherit default config file from frontend
329 self.kernel_argv.append("--KernelApp.parent_appname='%s'"%self.name)
329 self.kernel_argv.append("--KernelApp.parent_appname='%s'"%self.name)
330 # scrub frontend-specific flags
330 # scrub frontend-specific flags
331 for a in argv:
331 for a in argv:
332
332
333 if a.startswith('-'):
333 if a.startswith('-'):
334 key = a.lstrip('-').split('=')[0]
334 key = a.lstrip('-').split('=')[0]
335 if key in qt_flags:
335 if key in qt_flags:
336 self.kernel_argv.remove(a)
336 self.kernel_argv.remove(a)
337
337
338 def init_ssh(self):
338 def init_ssh(self):
339 """set up ssh tunnels, if needed."""
339 """set up ssh tunnels, if needed."""
340 if not self.sshserver and not self.sshkey:
340 if not self.sshserver and not self.sshkey:
341 return
341 return
342
342
343 if self.sshkey and not self.sshserver:
343 if self.sshkey and not self.sshserver:
344 self.sshserver = self.ip
344 self.sshserver = self.ip
345 self.ip=LOCALHOST
345 self.ip=LOCALHOST
346
346
347 lports = select_random_ports(4)
347 lports = select_random_ports(4)
348 rports = self.shell_port, self.iopub_port, self.stdin_port, self.hb_port
348 rports = self.shell_port, self.iopub_port, self.stdin_port, self.hb_port
349 self.shell_port, self.iopub_port, self.stdin_port, self.hb_port = lports
349 self.shell_port, self.iopub_port, self.stdin_port, self.hb_port = lports
350
350
351 remote_ip = self.ip
351 remote_ip = self.ip
352 self.ip = LOCALHOST
352 self.ip = LOCALHOST
353 self.log.info("Forwarding connections to %s via %s"%(remote_ip, self.sshserver))
353 self.log.info("Forwarding connections to %s via %s"%(remote_ip, self.sshserver))
354
354
355 if tunnel.try_passwordless_ssh(self.sshserver, self.sshkey):
355 if tunnel.try_passwordless_ssh(self.sshserver, self.sshkey):
356 password=False
356 password=False
357 else:
357 else:
358 password = getpass("SSH Password for %s: "%self.sshserver)
358 password = getpass("SSH Password for %s: "%self.sshserver)
359
359
360 for lp,rp in zip(lports, rports):
360 for lp,rp in zip(lports, rports):
361 tunnel.ssh_tunnel(lp, rp, self.sshserver, remote_ip, self.sshkey, password)
361 tunnel.ssh_tunnel(lp, rp, self.sshserver, remote_ip, self.sshkey, password)
362
362
363 def init_kernel_manager(self):
363 def init_kernel_manager(self):
364 # Don't let Qt or ZMQ swallow KeyboardInterupts.
364 # Don't let Qt or ZMQ swallow KeyboardInterupts.
365 signal.signal(signal.SIGINT, signal.SIG_DFL)
365 signal.signal(signal.SIGINT, signal.SIG_DFL)
366
366
367 # Create a KernelManager and start a kernel.
367 # Create a KernelManager and start a kernel.
368 self.kernel_manager = QtKernelManager(
368 self.kernel_manager = QtKernelManager(
369 shell_address=(self.ip, self.shell_port),
369 shell_address=(self.ip, self.shell_port),
370 sub_address=(self.ip, self.iopub_port),
370 sub_address=(self.ip, self.iopub_port),
371 stdin_address=(self.ip, self.stdin_port),
371 stdin_address=(self.ip, self.stdin_port),
372 hb_address=(self.ip, self.hb_port),
372 hb_address=(self.ip, self.hb_port),
373 config=self.config
373 config=self.config
374 )
374 )
375 # start the kernel
375 # start the kernel
376 if not self.existing:
376 if not self.existing:
377 kwargs = dict(ip=self.ip, ipython=not self.pure)
377 kwargs = dict(ip=self.ip, ipython=not self.pure)
378 kwargs['extra_arguments'] = self.kernel_argv
378 kwargs['extra_arguments'] = self.kernel_argv
379 self.kernel_manager.start_kernel(**kwargs)
379 self.kernel_manager.start_kernel(**kwargs)
380 self.kernel_manager.start_channels()
380 self.kernel_manager.start_channels()
381
381
382
382
383 def init_qt_elements(self):
383 def init_qt_elements(self):
384 # Create the widget.
384 # Create the widget.
385 self.app = QtGui.QApplication([])
385 self.app = QtGui.QApplication([])
386 local_kernel = (not self.existing) or self.ip in LOCAL_IPS
386 local_kernel = (not self.existing) or self.ip in LOCAL_IPS
387 self.widget = self.widget_factory(config=self.config,
387 self.widget = self.widget_factory(config=self.config,
388 local_kernel=local_kernel)
388 local_kernel=local_kernel)
389 self.widget.kernel_manager = self.kernel_manager
389 self.widget.kernel_manager = self.kernel_manager
390 self.window = MainWindow(self.app, self.widget, self.existing,
390 self.window = MainWindow(self.app, self.widget, self.existing,
391 may_close=local_kernel,
391 may_close=local_kernel,
392 confirm_exit=self.confirm_exit)
392 confirm_exit=self.confirm_exit)
393 self.window.setWindowTitle('Python' if self.pure else 'IPython')
393 self.window.setWindowTitle('Python' if self.pure else 'IPython')
394
394
395 def init_colors(self):
395 def init_colors(self):
396 """Configure the coloring of the widget"""
396 """Configure the coloring of the widget"""
397 # Note: This will be dramatically simplified when colors
397 # Note: This will be dramatically simplified when colors
398 # are removed from the backend.
398 # are removed from the backend.
399
399
400 if self.pure:
400 if self.pure:
401 # only IPythonWidget supports styling
401 # only IPythonWidget supports styling
402 return
402 return
403
403
404 # parse the colors arg down to current known labels
404 # parse the colors arg down to current known labels
405 try:
405 try:
406 colors = self.config.ZMQInteractiveShell.colors
406 colors = self.config.ZMQInteractiveShell.colors
407 except AttributeError:
407 except AttributeError:
408 colors = None
408 colors = None
409 try:
409 try:
410 style = self.config.IPythonWidget.colors
410 style = self.config.IPythonWidget.colors
411 except AttributeError:
411 except AttributeError:
412 style = None
412 style = None
413
413
414 # find the value for colors:
414 # find the value for colors:
415 if colors:
415 if colors:
416 colors=colors.lower()
416 colors=colors.lower()
417 if colors in ('lightbg', 'light'):
417 if colors in ('lightbg', 'light'):
418 colors='lightbg'
418 colors='lightbg'
419 elif colors in ('dark', 'linux'):
419 elif colors in ('dark', 'linux'):
420 colors='linux'
420 colors='linux'
421 else:
421 else:
422 colors='nocolor'
422 colors='nocolor'
423 elif style:
423 elif style:
424 if style=='bw':
424 if style=='bw':
425 colors='nocolor'
425 colors='nocolor'
426 elif styles.dark_style(style):
426 elif styles.dark_style(style):
427 colors='linux'
427 colors='linux'
428 else:
428 else:
429 colors='lightbg'
429 colors='lightbg'
430 else:
430 else:
431 colors=None
431 colors=None
432
432
433 # Configure the style.
433 # Configure the style.
434 widget = self.widget
434 widget = self.widget
435 if style:
435 if style:
436 widget.style_sheet = styles.sheet_from_template(style, colors)
436 widget.style_sheet = styles.sheet_from_template(style, colors)
437 widget.syntax_style = style
437 widget.syntax_style = style
438 widget._syntax_style_changed()
438 widget._syntax_style_changed()
439 widget._style_sheet_changed()
439 widget._style_sheet_changed()
440 elif colors:
440 elif colors:
441 # use a default style
441 # use a default style
442 widget.set_default_style(colors=colors)
442 widget.set_default_style(colors=colors)
443 else:
443 else:
444 # this is redundant for now, but allows the widget's
444 # this is redundant for now, but allows the widget's
445 # defaults to change
445 # defaults to change
446 widget.set_default_style()
446 widget.set_default_style()
447
447
448 if self.stylesheet:
448 if self.stylesheet:
449 # we got an expicit stylesheet
449 # we got an expicit stylesheet
450 if os.path.isfile(self.stylesheet):
450 if os.path.isfile(self.stylesheet):
451 with open(self.stylesheet) as f:
451 with open(self.stylesheet) as f:
452 sheet = f.read()
452 sheet = f.read()
453 widget.style_sheet = sheet
453 widget.style_sheet = sheet
454 widget._style_sheet_changed()
454 widget._style_sheet_changed()
455 else:
455 else:
456 raise IOError("Stylesheet %r not found."%self.stylesheet)
456 raise IOError("Stylesheet %r not found."%self.stylesheet)
457
457
458 def initialize(self, argv=None):
458 def initialize(self, argv=None):
459 super(IPythonQtConsoleApp, self).initialize(argv)
459 super(IPythonQtConsoleApp, self).initialize(argv)
460 self.init_ssh()
460 self.init_ssh()
461 self.init_kernel_manager()
461 self.init_kernel_manager()
462 self.init_qt_elements()
462 self.init_qt_elements()
463 self.init_colors()
463 self.init_colors()
464 self.init_window_shortcut()
465
466 def init_window_shortcut(self):
467 fullScreenAction = QtGui.QAction('Toggle Full Screen', self.window)
468 fullScreenAction.setShortcut('Ctrl+Meta+Space')
469 fullScreenAction.triggered.connect(self.toggleFullScreen)
470 self.window.addAction(fullScreenAction)
471
472 def toggleFullScreen(self):
473 if not self.window.isFullScreen():
474 self.window.showFullScreen()
475 else:
476 self.window.showNormal()
464
477
465 def start(self):
478 def start(self):
466
479
467 # draw the window
480 # draw the window
468 self.window.show()
481 self.window.show()
469
482
470 # Start the application main loop.
483 # Start the application main loop.
471 self.app.exec_()
484 self.app.exec_()
472
485
473 #-----------------------------------------------------------------------------
486 #-----------------------------------------------------------------------------
474 # Main entry point
487 # Main entry point
475 #-----------------------------------------------------------------------------
488 #-----------------------------------------------------------------------------
476
489
477 def main():
490 def main():
478 app = IPythonQtConsoleApp()
491 app = IPythonQtConsoleApp()
479 app.initialize()
492 app.initialize()
480 app.start()
493 app.start()
481
494
482
495
483 if __name__ == '__main__':
496 if __name__ == '__main__':
484 main()
497 main()
General Comments 0
You need to be logged in to leave comments. Login now