Show More
@@ -66,11 +66,11 b' class FrontendWidget(HistoryConsoleWidget):' | |||||
66 | self._highlighter = FrontendHighlighter(self) |
|
66 | self._highlighter = FrontendHighlighter(self) | |
67 | self._kernel_manager = None |
|
67 | self._kernel_manager = None | |
68 |
|
68 | |||
69 | self.document().contentsChange.connect(self._document_contents_change) |
|
|||
70 |
|
||||
71 | self.continuation_prompt = '... ' |
|
69 | self.continuation_prompt = '... ' | |
72 | self.kernel_manager = kernel_manager |
|
70 | self.kernel_manager = kernel_manager | |
73 |
|
71 | |||
|
72 | self.document().contentsChange.connect(self._document_contents_change) | |||
|
73 | ||||
74 | def focusOutEvent(self, event): |
|
74 | def focusOutEvent(self, event): | |
75 | """ Reimplemented to hide calltips. |
|
75 | """ Reimplemented to hide calltips. | |
76 | """ |
|
76 | """ | |
@@ -185,8 +185,8 b' class FrontendWidget(HistoryConsoleWidget):' | |||||
185 | xreq = kernel_manager.xreq_channel |
|
185 | xreq = kernel_manager.xreq_channel | |
186 | sub.message_received.connect(self._handle_sub) |
|
186 | sub.message_received.connect(self._handle_sub) | |
187 | xreq.execute_reply.connect(self._handle_execute_reply) |
|
187 | xreq.execute_reply.connect(self._handle_execute_reply) | |
188 |
|
|
188 | xreq.complete_reply.connect(self._handle_complete_reply) | |
189 |
|
|
189 | xreq.object_info_reply.connect(self._handle_object_info_reply) | |
190 |
|
190 | |||
191 | self._show_prompt('>>> ') |
|
191 | self._show_prompt('>>> ') | |
192 |
|
192 | |||
@@ -210,17 +210,9 b' class FrontendWidget(HistoryConsoleWidget):' | |||||
210 | return False |
|
210 | return False | |
211 |
|
211 | |||
212 | # Send the metadata request to the kernel |
|
212 | # Send the metadata request to the kernel | |
213 |
|
|
213 | name = '.'.join(context) | |
214 | msg = self.session.send(self.request_socket, 'metadata_request', |
|
214 | self._calltip_id = self.kernel_manager.xreq_channel.object_info(name) | |
215 | dict(context=text)) |
|
215 | self._calltip_pos = self.textCursor().position() | |
216 |
|
||||
217 | # Give the kernel some time to respond |
|
|||
218 | rep = self._recv_reply_now('metadata_reply') |
|
|||
219 | doc = rep.content.docstring if rep else '' |
|
|||
220 |
|
||||
221 | # Show the call tip |
|
|||
222 | if doc: |
|
|||
223 | self._call_tip_widget.show_tip(doc) |
|
|||
224 | return True |
|
216 | return True | |
225 |
|
217 | |||
226 | def _complete(self): |
|
218 | def _complete(self): | |
@@ -233,18 +225,9 b' class FrontendWidget(HistoryConsoleWidget):' | |||||
233 |
|
225 | |||
234 | # Send the completion request to the kernel |
|
226 | # Send the completion request to the kernel | |
235 | text = '.'.join(context) |
|
227 | text = '.'.join(context) | |
236 | line = self.input_buffer_cursor_line |
|
228 | self._complete_id = self.kernel_manager.xreq_channel.complete( | |
237 | msg = self.session.send(self.request_socket, 'complete_request', |
|
229 | text, self.input_buffer_cursor_line, self.input_buffer) | |
238 | dict(text=text, line=line)) |
|
230 | self._complete_pos = self.textCursor().position() | |
239 |
|
||||
240 | # Give the kernel some time to respond |
|
|||
241 | rep = self._recv_reply_now('complete_reply') |
|
|||
242 | matches = rep.content.matches if rep else [] |
|
|||
243 |
|
||||
244 | # Show the completion at the correct location |
|
|||
245 | cursor = self.textCursor() |
|
|||
246 | cursor.movePosition(QtGui.QTextCursor.Left, n=len(text)) |
|
|||
247 | self._complete_with_items(cursor, matches) |
|
|||
248 | return True |
|
231 | return True | |
249 |
|
232 | |||
250 | def _get_context(self, cursor=None): |
|
233 | def _get_context(self, cursor=None): | |
@@ -294,18 +277,21 b' class FrontendWidget(HistoryConsoleWidget):' | |||||
294 | self._show_prompt('>>> ') |
|
277 | self._show_prompt('>>> ') | |
295 | self.executed.emit(rep) |
|
278 | self.executed.emit(rep) | |
296 |
|
279 | |||
297 | #------ Communication methods ---------------------------------------------- |
|
280 | def _handle_complete_reply(self, rep): | |
298 |
|
281 | cursor = self.textCursor() | ||
299 | def _recv_reply(self): |
|
282 | if rep['parent_header']['msg_id'] == self._complete_id and \ | |
300 | return self.session.recv(self.request_socket) |
|
283 | cursor.position() == self._complete_pos: | |
|
284 | text = '.'.join(self._get_context()) | |||
|
285 | cursor.movePosition(QtGui.QTextCursor.Left, n=len(text)) | |||
|
286 | self._complete_with_items(cursor, rep['content']['matches']) | |||
301 |
|
287 | |||
302 |
def _ |
|
288 | def _handle_object_info_reply(self, rep): | |
303 | for i in xrange(5): |
|
289 | cursor = self.textCursor() | |
304 | rep = self._recv_reply() |
|
290 | if rep['parent_header']['msg_id'] == self._calltip_id and \ | |
305 | if rep is not None and rep.msg_type == msg_type: |
|
291 | cursor.position() == self._calltip_pos: | |
306 | return rep |
|
292 | doc = rep['content']['docstring'] | |
307 | time.sleep(0.1) |
|
293 | if doc: | |
308 | return None |
|
294 | self._call_tip_widget.show_tip(doc) | |
309 |
|
295 | |||
310 |
|
296 | |||
311 | if __name__ == '__main__': |
|
297 | if __name__ == '__main__': |
@@ -142,8 +142,10 b' class Kernel(object):' | |||||
142 | self.completer = KernelCompleter(self.user_ns) |
|
142 | self.completer = KernelCompleter(self.user_ns) | |
143 |
|
143 | |||
144 | # Build dict of handlers for message types |
|
144 | # Build dict of handlers for message types | |
|
145 | msg_types = [ 'execute_request', 'complete_request', | |||
|
146 | 'object_info_request' ] | |||
145 | self.handlers = {} |
|
147 | self.handlers = {} | |
146 | for msg_type in ['execute_request', 'complete_request']: |
|
148 | for msg_type in msg_types: | |
147 | self.handlers[msg_type] = getattr(self, msg_type) |
|
149 | self.handlers[msg_type] = getattr(self, msg_type) | |
148 |
|
150 | |||
149 | def abort_queue(self): |
|
151 | def abort_queue(self): | |
@@ -213,6 +215,43 b' class Kernel(object):' | |||||
213 | def complete(self, msg): |
|
215 | def complete(self, msg): | |
214 | return self.completer.complete(msg.content.line, msg.content.text) |
|
216 | return self.completer.complete(msg.content.line, msg.content.text) | |
215 |
|
217 | |||
|
218 | def object_info_request(self, ident, parent): | |||
|
219 | context = parent['content']['oname'].split('.') | |||
|
220 | object_info = self.object_info(context) | |||
|
221 | msg = self.session.send(self.reply_socket, 'object_info_reply', | |||
|
222 | object_info, parent, ident) | |||
|
223 | print >> sys.__stdout__, msg | |||
|
224 | ||||
|
225 | def object_info(self, context): | |||
|
226 | symbol, leftover = self.symbol_from_context(context) | |||
|
227 | if symbol is not None and not leftover: | |||
|
228 | doc = getattr(symbol, '__doc__', '') | |||
|
229 | else: | |||
|
230 | doc = '' | |||
|
231 | object_info = dict(docstring = doc) | |||
|
232 | return object_info | |||
|
233 | ||||
|
234 | def symbol_from_context(self, context): | |||
|
235 | if not context: | |||
|
236 | return None, context | |||
|
237 | ||||
|
238 | base_symbol_string = context[0] | |||
|
239 | symbol = self.user_ns.get(base_symbol_string, None) | |||
|
240 | if symbol is None: | |||
|
241 | symbol = __builtin__.__dict__.get(base_symbol_string, None) | |||
|
242 | if symbol is None: | |||
|
243 | return None, context | |||
|
244 | ||||
|
245 | context = context[1:] | |||
|
246 | for i, name in enumerate(context): | |||
|
247 | new_symbol = getattr(symbol, name, None) | |||
|
248 | if new_symbol is None: | |||
|
249 | return symbol, context[i:] | |||
|
250 | else: | |||
|
251 | symbol = new_symbol | |||
|
252 | ||||
|
253 | return symbol, [] | |||
|
254 | ||||
216 | def start(self): |
|
255 | def start(self): | |
217 | while True: |
|
256 | while True: | |
218 | ident = self.reply_socket.recv() |
|
257 | ident = self.reply_socket.recv() |
General Comments 0
You need to be logged in to leave comments.
Login now