Yes, you can use com.intellij.diff.DiffManager#createRequestPanel

See also
com.intellij.diff.DiffRequestPanel
com.intellij.diff.DiffContentFactory
com.intellij.diff.DiffRequestFactory
com.intellij.diff.requests.SimpleDiffRequest

Sample usage:
https://github.com/JetBrains/intellij-community/blob/master/java/java-impl/src/com/intellij/refactoring/extractMethod/ExtractMethodSignatureSuggester.java#L411

1

Related to this, one thing that I've wanted to do is to show multiple diff results, equivalent to viewing the diffs of all locally changed files in the VCS. So I could provide a series of DiffRequests, and have those shown with a next/previous button. Is there anything built-in I can use to do that?

0

You can use com.intellij.diff.impl.CacheDiffRequestChainProcessor (it is used in diff frames)

See also
com.intellij.diff.chains.SimpleDiffRequestChain
com.intellij.diff.impl.DiffRequestProcessor 

0

The API really helps!

The further question is that, is it possible for me to scroll the diffPanel to a certain position?

What I am doing is that, I diff two java source code in two different commits, and I want to scroll the diffPanel to display a specific method. I have the method name & parameter list available. 

0

You can scroll to particular line putting `DiffUserDataKeys.SCROLL_TO_LINE` into `UserDataHolder` of `DiffRequest`.
Ex: https://github.com/JetBrains/intellij-community/blob/master/platform/diff-impl/src/com/intellij/diff/actions/CompareClipboardWithSelectionAction.java#L98

There are no API to scroll to particular method though. You'll have to find it somehow.

The good thing is that if you pass project into `DiffContentFactory`, document should already have their Psi built. So you can get it just by `PsiDocumentManager.getInstance(project).getPsiFile(document);`, without using `PsiFileFactory`.

See also
com.intellij.psi.PsiClass#findMethodsByName
com.intellij.psi.PsiClass#findMethodBySignature
com.intellij.openapi.editor.Document#getLineNumber

1
SimpleDiffRequest request = new SimpleDiffRequest("Diff", oldContent, newContent, preHash, postHash);

request.putUserData(DiffUserDataKeys.SCROLL_TO_LINE, Pair.create(Side.RIGHT, preLineNumber));
request.putUserData(DiffUserDataKeys.SCROLL_TO_LINE,Pair.create(Side.LEFT, preLineNumber));


DiffRequestPanel diffPanel = DiffManager.getInstance().createRequestPanel(project, () -> {
//May do something meaningful here
System.out.println("Dispose!");
}, null);


diffPanel.putContextHints(DiffUserDataKeys.PLACE, "ExtractSignature");
diffPanel.setRequest(request);

The API works perfect if I want to scroll one side of the diff component. But if I want to scroll for both sides, it is not working because

DiffUserDataKeys.SCROLL_TO_LINE

can only be mapped to one value.

So is there a way for me to scroll both sides?

Thanks for the patience, Aleksey.

0

`com.intellij.diff.util.DiffUserDataKeysEx#EDITORS_CARET_POSITION` should help.
https://github.com/JetBrains/intellij-community/blob/master/platform/diff-impl/src/com/intellij/diff/tools/util/side/ThreesideTextDiffViewer.java#L390

Note: LogicalPosition allows to put caret inside tabulation (and, iirc, inside some Unicode symbols as well).
So transition "offset <->line/column" might depend on codestyle and Editor settings. But it's unlikely to become a serious issue, as line numbers are not affected (only "column" might be wrong).


Btw, Disposable ("May do something meaningful here") here is to limit life cycle of the panel (ex: to remove global listeners, when the panel is no longer needed).

The usage is usually like
myDisposable = Disposer.newDisposable();
myDiffPanel = createRequestPanel(..., myDisposable, ...)

// somewhen later, when myDiffPanel is no longer needed (its tool window tab was closed, dialog window closed, project closed, etc)
Disposer.dispose(myDisposable)


Or you can use suitable existing Disposable from context (ex: Project, `DialogWrapper.getDisposable()`, `com.intellij.ui.content.Content` for toolwindow tabs, etc).

1

请先登录再写评论。