Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reimplement hover window with floating window for Neovim 0.4.0 or later #767

Merged
merged 19 commits into from
Mar 26, 2019

Conversation

rhysd
Copy link
Contributor

@rhysd rhysd commented Mar 12, 2019

Hi,

I have experimentally reimplemented a hover window for LanguageClient#textDocument_hover() with Neovim's new floating window feature.

Here is a screencast with Neovim 0.4.0-dev and macOS 10.12:

test

This PR is still work in progress. I have not added any tests yet and I think there are some discussion points as follows:

  • There is no way to move cursor into float window so user cannot scroll the contents. Some mappings might be needed.
  • There is no way to close float window by user (No command like :pclose is not provided at this point). I added functionality to close the floating window automatically when cursor is moved. But I'm not sure this behavior makes all users happy
  • Some people may prefer preview window. Using floating window might be opt-in or opt-out
  • CursorLine is used for highlighting the floating window, but I'm not sure it is a good choice to modify background color slightly for every colorscheme. The highlight color might be customizable

@autozimu
Copy link
Owner

Awesome!

@theHamsta
Copy link
Contributor

Nice work!

Currently, one should not switch buffers (e.g. ) when hover is visible. The float is only closed when moving the cursor in the original buffer.

@rhysd rhysd changed the title WIP: Reimplement hover window with floating window for Neovim 0.4.0 or later Reimplement hover window with floating window for Neovim 0.4.0 or later Mar 14, 2019
@rhysd
Copy link
Contributor Author

rhysd commented Mar 14, 2019

I added test for this feature (though I'm not sure it's sufficient).

There is no way to move cursor into float window so user cannot scroll the contents. Some mappings might be needed.

Regarding to this, I feel providing a mapping to move cursor into floating window would be enough. User can scroll the window and yank contents by moving cursor to the window.

Currently, one should not switch buffers (e.g. ) when hover is visible. The float is only closed when moving the cursor in the original buffer.

Thank you for the point. I think WinLeave should trigger closing float window as well. But it is also run when moving cursor into floating window. I think WinEnter would be available instead. Let me try.

since WinEnter cannot close floating hover when the current buffer
switches to another buffer within the same window.
@rhysd
Copy link
Contributor Author

rhysd commented Mar 16, 2019

I noticed WinEnter is not sufficient since it cannot close floating window when user switches current buffer to another buffer within the same window. I changed it to BufEnter and added one more test.

@autozimu
Copy link
Owner

Is this ready for review?

@rhysd
Copy link
Contributor Author

rhysd commented Mar 20, 2019

Let me add a mapping to move cursor into a floating window. Tomorrow is holiday in Japan. So I think I can have some progress on this branch tomorrow (I'm sorry for the delay).

@autozimu
Copy link
Owner

autozimu commented Mar 20, 2019

Not at all. Please take your pace.

@rhysd
Copy link
Contributor Author

rhysd commented Mar 21, 2019

I finished the work.

Instead of adding a new mapping, I slightly changed the behavior of LanguageClient#textDocument_hover(). When opening a hover and calling it again before moving cursor, it moves the cursor into the floating window. Then user can scroll content and yank some text. :close or :quit in the window simply close the hover window.

test

I also added

  • g:LanguageClient_useFloatingHover
  • Documentation
  • More test for scenario moving the cursor into floating window

Now I believe this branch is ready for review 👍

@lorenzo
Copy link

lorenzo commented Mar 21, 2019

I think having another function we can call to force the hover to be in a separate panel would be ideal. While most of the times I would use this floating window, there are also times that I want to leave the docs for a function open as I keep coding. Having both possibilities would make this the ideal feature

@rhysd
Copy link
Contributor Author

rhysd commented Mar 21, 2019

Sounds good. It may be more useful than moving cursor into floating window but I'm not sure. Anyway, I'll try to implement the function to close floating window and reopen the content in preview window again.

to reopen floating hover in separate preview window
@rhysd
Copy link
Contributor Author

rhysd commented Mar 21, 2019

I implemented LanguageClient#reopenHoverInSeparateWindow(). Could you check the behavior?

@lorenzo
Copy link

lorenzo commented Mar 21, 2019

Why is it reopenIn and not just openIn?

@rhysd
Copy link
Contributor Author

rhysd commented Mar 21, 2019

Why is it reopenIn and not just openIn?

Since it is only effective when floating window is already open. If openIn is more natural, I'll revert the commit. I'm not native English user. So the naming may be not proper. If my English usage is not proper, please let me know. It's very helpful for me (in terms of learning English).

@JeanMertz
Copy link
Contributor

I think what @lorenzo was getting at is that it perhaps makes more sense to have two functions:

  • openHoverInFloatingWIndow – this opens the "hover" definition in the new floating window
  • openHoverInRegularWindow – this opens the "hover" definition in a regular window

But I'm not sure it makes sense to have this. There's already LanguageClient_useFloatingHover, so you could have your own function that first sets LanguageClient_useFloatingHover=0 and then calls LanguageClient#textDocument_hover(), to achieve the exact same result, I think?

Unless of course, I'm mistaken, and that's not what @lorenzo is talking about.

I like the reopenHoverInSeparateWindow though, it allows to quickly swap to a separate window if you're in a hover, and realise you want to keep this documentation open while you continue working.

@lorenzo
Copy link

lorenzo commented Mar 21, 2019

The idea is not to have your own function, as few people actually write vimL. I don’t, and have been a bum user for years.

I did mean to have 2 separate function to open the panel in different places. For example, you could keep one panel open while using a floating window for something else as you write a long function.

Moving a floating window to a panel does make sense to me as well, I can see the use case.

@rhysd
Copy link
Contributor Author

rhysd commented Mar 21, 2019

Thank you for further explanation. I got the point.

Two options come in my mind for this.

Add argument to hover function

I feel creating multiple functions is a bit too much. How about adding an argument for specifying window type?

  • LanguageClient#textDocument_hover(): Auto (use floating window as much as possible
  • LanguageClient#textDocument_hover('preview'): Open in preview window
  • LanguageClient#textDocument_hover('float'): Open in floating window

Separate two mappings can be defined such as nnoremap K :<C-u>call LanguageClient#textDocument_hover()<CR> and nnoremap gK :<C-u>call LanguageClient#textDocument_hover('preview'). It may be useful to add another type such as 'vsplit' (opens new normal window by :vsplit).

  • Pros:
    • Simple and stateless
  • Cons:
    • User needs to define two mappings

Add special window-local mapping

Defines buffer local (floating window local) mapping p to reopen the window in separate window.

User opens floating window with K and moves cursor by entering K again. User enter p to open the document in separate window. It may be more useful to provide another local mapping such as q for closing the window.

  • Pros:
    • It does not require new mapping
  • Cons:
    • Operation is complicated. User needs to enter the floating window to reopen it in separate window

I prefer second one because I would almost always use floating window and opening it in separate window would be comparably rare case.

In terms of implementation, either (or both) is easy to implement.

@asymmetric
Copy link

I’m not sure the use-case of permanently opening the hover/tooltip is necessary enough to block this otherwise very useful PR. I’ve never found this behavior in other editors and personally never expected it.

Can I suggest we merge this and iterate over the “permanent hover” behavior in a separate PR?

@autozimu
Copy link
Owner

Agree with @asymmetric. Let's have the support first. Then we can cover the special use case.

doc/LanguageClient.txt Outdated Show resolved Hide resolved
@rhysd
Copy link
Contributor Author

rhysd commented Mar 23, 2019

@asymmetric @autozimu

OK, let me remove the part for now.

@rhysd
Copy link
Contributor Author

rhysd commented Mar 23, 2019

@autozimu I addressed your review comments at 79e36ba and a785c80.

@autozimu autozimu merged commit 53ce2fe into autozimu:next Mar 26, 2019
@autozimu
Copy link
Owner

Thanks!

@autozimu autozimu mentioned this pull request Mar 27, 2019
@YaLTeR
Copy link
Contributor

YaLTeR commented Mar 27, 2019

I just tried this and it works amazingly! This is so much better than what was possible previously, thanks a lot.

One thing I noticed: when the hover window is opened, Ctrl-E and Ctrl-Y don't move it with the buffer so it kind of becomes detached from the cursor. Not sure if this would be easy (or in scope) to fix though.

@rhysd
Copy link
Contributor Author

rhysd commented Mar 27, 2019

Yeah, it's a bit difficult case. Currently floating window is closed automatically on CursorMoved, BufEnter and InsertEnter. But <C-e> and <C-y> is none of the cases. It just scrolls screen and position of cursor is maintained. I don't know the way to hook <C-e> and <C-y> actually..

wincent added a commit to wincent/wincent that referenced this pull request Aug 22, 2019
See screenshots in: autozimu/LanguageClient-neovim#767

* roles/dotfiles/files/.vim/pack/bundle/opt/LanguageClient-neovim 5685989...12e65e7 (80):
  > Send messages for jdt files
  > Remove unused lazycell
  > cargo update
  > Update lsp-types and url
  > Bump jsonrpc-core
  > Declare support for LocationLinks
  > Update rust version in CI
  > Try to have idempotent install based on version checking
  > Update go sample
  > restore goto jdt content feature
  >  Add LanguageClient_closeFloatingHover()  (#865)
  > rangeFormatting does not properly transmit range
  > Treat ShowMessageRequest with no actions as ShowMessage
  > Better handling of text-edits at completion
  > (cargo-release) version 0.1.147
  > Cleanup
  > signal usage of rustfmt using empty rustfmt.toml
  > add client-side support for "rust-analyzer.applySourceChange"
  > add CreateFile support in apply_WorkspaceEdit
  > Update lsp_types
  > Cargo update
  > Expand tilde in linux and macos logger paths
  > [#835] Set hover window as modifiable
  > Add missing space between severity, code, and message
  > Cleanup.
  > Add example scala and css project.
  > Support CodeActions
  > update jsonrpc-core
  > cargo update
  > Clearify language server is needed
  > Remove deoplete from Quick Start section.
  > Generate binary sha256 file on before deploy
  > support LocationLink responses for GotoDefinition
  > update lsp-types
  > update jsonrpc-core
  > Cargo update
  > cargo update
  > add new root marker for python projects: pyproject.toml
  > Remove word extraction from `textEdit`.
  > (cargo-release) version 0.1.146
  > Workaround `text_edit` is present but `new_text` is empty.
  > Add examples about how to configure for Ruby (#799)
  > Remove unnecessary closures (#797)
  > Use self to avoid name repetition (#796)
  > Do not apply fzf workaround to enter insert mode when neovim >= 0.4.
  > Cross platform PowerShell install script (#794)
  > Refactor code to use references (#790)
  > (cargo-release) version 0.1.145
  > clippy.
  > Add back x86_64-unknown-freebsd to CI.
  > (cargo-release) version 0.1.144
  > Reimplement hover window with floating window for Neovim 0.4.0 or later (#767)
  > Add option to allow disable echo project root.
  > Fix filetype key typescript.tsx.
  > (cargo-release) version 0.1.143
  > fix diagnostic sign issues (#769)
  > Support root detection for tsx files.
  > Use :normal! instead of :normal (#766)
  > (cargo-release) version 0.1.142
  > fmt.
  > Cleanup.
  > Implement window/showMessageRequest (#755)
  > Bumpup lsp_typs from v0.54.0 to v0.56.0
  > Mention integration with MUcomplete.
  > Fix errorneous endofline warning.
  > refactor: Delete unusing module
  > fix: Fix RawMessage enum path
  > refactor: vim::RawMessage enum move to types module
  > Bumpup jsonrpc-core from v9.0.0 to v10.1.0
  > cargo update
  > (cargo-release) version 0.1.141
  > Optimize update signs.
  > Properly cleanup signs and virtual texts at stop.
  > Update rustc in Docker.
  > Lint.
  > Restruct approach to get values from params and vim.
  > Update doc.
  > Add LanguageClient.txt target to help doc
  > Fix nits on grammar
  > Document where a relative g:LanguageClient_settingsPath is relative to.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

8 participants