diff --git a/platform/vcs-log/api/resources/messages/VcsLogBundle.properties b/platform/vcs-log/api/resources/messages/VcsLogBundle.properties index 7cfac4bcf3f4..4584ced49663 100644 --- a/platform/vcs-log/api/resources/messages/VcsLogBundle.properties +++ b/platform/vcs-log/api/resources/messages/VcsLogBundle.properties @@ -95,6 +95,8 @@ action.Vcs.Log.CompareRevisions.text=Compare Versions action.Vcs.Log.CompareRevisions.description=Compare selected versions action.Vcs.Log.ResumeIndexing.text=Resume Indexing action.Vcs.Log.ResumeIndexing.description=Indexing was paused as it took longer than expected. Resume. +action.Vcs.Log.SelectInLog.text=Show in Vcs Log +action.Vcs.Log.SelectInLog.text.template=Show in {0} Log group.Vcs.Log.PresentationSettings.text=View Options group.Vcs.Log.PresentationSettings.description=Configure presentation of the Log group.Vcs.Log.ChangesBrowser.PresentationSettings.text=View Options diff --git a/platform/vcs-log/impl/src/META-INF/vcs-log.xml b/platform/vcs-log/impl/src/META-INF/vcs-log.xml index 8e65eb96393a..5ae7ff764411 100644 --- a/platform/vcs-log/impl/src/META-INF/vcs-log.xml +++ b/platform/vcs-log/impl/src/META-INF/vcs-log.xml @@ -157,6 +157,9 @@ + + + + { + return getLogProviders(project).values.mapTo(mutableSetOf()) { it.supportedVcs } + } + @JvmStatic fun getInstance(project: Project): VcsProjectLog = project.service() diff --git a/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/actions/ShowCommitInLogAction.java b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/actions/ShowCommitInLogAction.java new file mode 100644 index 000000000000..b493f77e2cd0 --- /dev/null +++ b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/actions/ShowCommitInLogAction.java @@ -0,0 +1,114 @@ +// Copyright 2000-2024 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license. +package com.intellij.vcs.log.ui.actions; + +import com.intellij.openapi.actionSystem.ActionUpdateThread; +import com.intellij.openapi.actionSystem.AnActionEvent; +import com.intellij.openapi.actionSystem.CommonDataKeys; +import com.intellij.openapi.diagnostic.Logger; +import com.intellij.openapi.progress.PerformInBackgroundOption; +import com.intellij.openapi.progress.ProgressIndicator; +import com.intellij.openapi.progress.ProgressManager; +import com.intellij.openapi.progress.Task; +import com.intellij.openapi.project.DumbAwareAction; +import com.intellij.openapi.project.Project; +import com.intellij.openapi.util.NlsActions; +import com.intellij.openapi.vcs.AbstractVcs; +import com.intellij.openapi.vcs.VcsDataKeys; +import com.intellij.openapi.vcs.VcsKey; +import com.intellij.openapi.vcs.history.VcsFileRevision; +import com.intellij.openapi.vcs.history.VcsRevisionNumber; +import com.intellij.vcs.log.Hash; +import com.intellij.vcs.log.VcsLogBundle; +import com.intellij.vcs.log.impl.HashImpl; +import com.intellij.vcs.log.impl.VcsLogContentUtil; +import com.intellij.vcs.log.impl.VcsLogNavigationUtil; +import com.intellij.vcs.log.impl.VcsProjectLog; +import com.intellij.vcs.log.ui.VcsLogUiEx; +import com.intellij.vcsUtil.VcsUtil; +import org.jetbrains.annotations.ApiStatus; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.concurrent.CancellationException; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.Future; + +public class ShowCommitInLogAction extends DumbAwareAction { + private static final Logger LOG = Logger.getInstance(ShowCommitInLogAction.class); + + @Override + public void actionPerformed(@NotNull AnActionEvent event) { + Project project = event.getData(CommonDataKeys.PROJECT); + if (project == null) return; + VcsRevisionNumber revision = getRevisionNumber(event); + if (revision == null) return; + + jumpToRevision(project, HashImpl.build(revision.asString())); + } + + protected @Nullable VcsRevisionNumber getRevisionNumber(@NotNull AnActionEvent event) { + VcsRevisionNumber revision = event.getData(VcsDataKeys.VCS_REVISION_NUMBER); + if (revision == null) { + VcsFileRevision fileRevision = event.getData(VcsDataKeys.VCS_FILE_REVISION); + if (fileRevision != null) { + revision = fileRevision.getRevisionNumber(); + } + } + return revision; + } + + protected @Nullable VcsKey getVcsKey(@NotNull AnActionEvent event) { + return event.getData(VcsDataKeys.VCS); + } + + @Override + public @NotNull ActionUpdateThread getActionUpdateThread() { + return ActionUpdateThread.BGT; + } + + @Override + public void update(@NotNull AnActionEvent e) { + Project project = e.getProject(); + VcsKey vcsKey = getVcsKey(e); + e.getPresentation().setEnabled(project != null && getRevisionNumber(e) != null && vcsKey != null + && VcsProjectLog.getSupportedVcs(project).contains(vcsKey)); + e.getPresentation().setText(getActionText(project, vcsKey)); + } + + private static @NlsActions.ActionText @NotNull String getActionText(@Nullable Project project, @Nullable VcsKey vcsKey) { + if (project != null && vcsKey != null) { + AbstractVcs vcs = VcsUtil.findVcsByKey(project, vcsKey); + if (vcs != null) return VcsLogBundle.message("action.Vcs.Log.SelectInLog.text.template", vcs.getDisplayName()); + } + return VcsLogBundle.message("action.Vcs.Log.SelectInLog.text"); + } + + @ApiStatus.Internal + public static void jumpToRevision(@NotNull Project project, @NotNull Hash hash) { + VcsLogContentUtil.runInMainLog(project, logUi -> jumpToRevisionUnderProgress(project, logUi, hash)); + } + + private static void jumpToRevisionUnderProgress(@NotNull Project project, + @NotNull VcsLogUiEx logUi, + @NotNull Hash hash) { + Future future = VcsLogNavigationUtil.jumpToHash(logUi, hash.asString(), false, true); + if (!future.isDone()) { + ProgressManager.getInstance().run(new Task.Backgroundable(project, + VcsLogBundle.message("vcs.log.show.commit.in.log.process", hash.asString()), + false/*can not cancel*/, + PerformInBackgroundOption.ALWAYS_BACKGROUND) { + @Override + public void run(@NotNull ProgressIndicator indicator) { + try { + future.get(); + } + catch (CancellationException | InterruptedException ignored) { + } + catch (ExecutionException e) { + LOG.error(e); + } + } + }); + } + } +} diff --git a/platform/vcs-log/impl/src/com/intellij/vcs/log/util/VcsLogUtil.java b/platform/vcs-log/impl/src/com/intellij/vcs/log/util/VcsLogUtil.java index ccc301d2f8f6..d605b9213b4b 100644 --- a/platform/vcs-log/impl/src/com/intellij/vcs/log/util/VcsLogUtil.java +++ b/platform/vcs-log/impl/src/com/intellij/vcs/log/util/VcsLogUtil.java @@ -337,6 +337,10 @@ public final class VcsLogUtil { @NotNull Collection logProviders) { Set vcs = ContainerUtil.map2SetNotNull(logProviders, provider -> VcsUtil.findVcsByKey(project, provider.getSupportedVcs())); + return getVcsDisplayName(vcs); + } + + public static @Nls @NotNull String getVcsDisplayName(@NotNull Set vcs) { if (vcs.size() != 1) return VcsLogBundle.message("vcs"); return Objects.requireNonNull(getFirstItem(vcs)).getDisplayName(); } diff --git a/plugins/git4idea/resources/META-INF/plugin.xml b/plugins/git4idea/resources/META-INF/plugin.xml index 96a044852567..8b1e93fc766e 100644 --- a/plugins/git4idea/resources/META-INF/plugin.xml +++ b/plugins/git4idea/resources/META-INF/plugin.xml @@ -38,9 +38,6 @@ - - - @@ -289,8 +286,6 @@ - - diff --git a/plugins/git4idea/resources/messages/GitBundle.properties b/plugins/git4idea/resources/messages/GitBundle.properties index b8ea26e87dfc..4700e373c358 100644 --- a/plugins/git4idea/resources/messages/GitBundle.properties +++ b/plugins/git4idea/resources/messages/GitBundle.properties @@ -542,6 +542,7 @@ git.unstash.clear.confirmation.message=Remove all stashes? This cannot be undone git.unstash.clear.confirmation.title=Remove All Stashes? git.unstash.drop.confirmation.message=Do you want to remove {0}?
"{1}" git.unstash.drop.confirmation.title=Remove Stash {0}? +# suppress inspection "UnusedProperty": used by 3-party plugins vcs.history.action.gitlog=Show in Git Log exportable.Git.Application.Settings.presentable.name=Git @@ -1111,6 +1112,7 @@ git.history.diff.handler.choose.parent.popup=Choose Parent to Compare git.history.diff.handler.load.changes.process=Loading changes\u2026 git.history.diff.handler.git.show.error=Error happened while executing git show {0}:{1} git.history.diff.handler.no.changes.in.file.info=There are no changes to file {0} in this merge commit +# suppress inspection "UnusedProperty": used by 3-party plugins git.log.show.commit.in.log.process=Searching for Revision {0} git.compare.branches.empty.status={0} contains all commits from {1} git.compare.branches.explanation.message=Commits that exist in {0} but don''t exist in {1} diff --git a/plugins/git4idea/src/git4idea/log/GitCommitTooltipLinkHandler.java b/plugins/git4idea/src/git4idea/log/GitCommitTooltipLinkHandler.java index a68ada2a7721..58d1c7a8f406 100644 --- a/plugins/git4idea/src/git4idea/log/GitCommitTooltipLinkHandler.java +++ b/plugins/git4idea/src/git4idea/log/GitCommitTooltipLinkHandler.java @@ -9,6 +9,7 @@ import com.intellij.openapi.util.text.HtmlChunk; import com.intellij.openapi.vcs.history.VcsRevisionNumber; import com.intellij.vcs.log.Hash; import com.intellij.vcs.log.impl.HashImpl; +import com.intellij.vcs.log.ui.actions.ShowCommitInLogAction; import org.jetbrains.annotations.Nls; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -27,7 +28,7 @@ public class GitCommitTooltipLinkHandler extends TooltipLinkHandler { return false; } - GitShowCommitInLogAction.jumpToRevision(project, hash); + ShowCommitInLogAction.jumpToRevision(project, hash); return true; } diff --git a/plugins/git4idea/src/git4idea/log/GitShowCommitInLogAction.java b/plugins/git4idea/src/git4idea/log/GitShowCommitInLogAction.java index b7fd686c95a9..d40a06f08816 100644 --- a/plugins/git4idea/src/git4idea/log/GitShowCommitInLogAction.java +++ b/plugins/git4idea/src/git4idea/log/GitShowCommitInLogAction.java @@ -1,103 +1,8 @@ -// Copyright 2000-2023 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license. +// Copyright 2000-2024 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license. package git4idea.log; -import com.intellij.openapi.actionSystem.ActionUpdateThread; -import com.intellij.openapi.actionSystem.AnActionEvent; -import com.intellij.openapi.actionSystem.CommonDataKeys; -import com.intellij.openapi.diagnostic.Logger; -import com.intellij.openapi.progress.PerformInBackgroundOption; -import com.intellij.openapi.progress.ProgressIndicator; -import com.intellij.openapi.progress.ProgressManager; -import com.intellij.openapi.progress.Task; -import com.intellij.openapi.project.DumbAwareAction; -import com.intellij.openapi.project.Project; -import com.intellij.openapi.util.Comparing; -import com.intellij.openapi.vcs.VcsDataKeys; -import com.intellij.openapi.vcs.VcsKey; -import com.intellij.openapi.vcs.history.VcsFileRevision; -import com.intellij.openapi.vcs.history.VcsRevisionNumber; -import com.intellij.vcs.log.Hash; -import com.intellij.vcs.log.impl.HashImpl; -import com.intellij.vcs.log.impl.VcsLogContentUtil; -import com.intellij.vcs.log.impl.VcsLogNavigationUtil; -import com.intellij.vcs.log.ui.VcsLogUiEx; -import git4idea.GitVcs; -import git4idea.i18n.GitBundle; -import org.jetbrains.annotations.NotNull; -import org.jetbrains.annotations.Nullable; +import com.intellij.vcs.log.ui.actions.ShowCommitInLogAction; -import java.util.concurrent.CancellationException; -import java.util.concurrent.ExecutionException; -import java.util.concurrent.Future; - -public class GitShowCommitInLogAction extends DumbAwareAction { - private static final Logger LOG = Logger.getInstance(GitShowCommitInLogAction.class); - - public GitShowCommitInLogAction() { - super(GitBundle.messagePointer("vcs.history.action.gitlog")); - } - - @Override - public void actionPerformed(@NotNull AnActionEvent event) { - Project project = event.getData(CommonDataKeys.PROJECT); - if (project == null) return; - VcsRevisionNumber revision = getRevisionNumber(event); - if (revision == null) return; - - jumpToRevision(project, HashImpl.build(revision.asString())); - } - - protected @Nullable VcsRevisionNumber getRevisionNumber(@NotNull AnActionEvent event) { - VcsRevisionNumber revision = event.getData(VcsDataKeys.VCS_REVISION_NUMBER); - if (revision == null) { - VcsFileRevision fileRevision = event.getData(VcsDataKeys.VCS_FILE_REVISION); - if (fileRevision != null) { - revision = fileRevision.getRevisionNumber(); - } - } - return revision; - } - - protected @Nullable VcsKey getVcsKey(@NotNull AnActionEvent event) { - return event.getData(VcsDataKeys.VCS); - } - - @Override - public @NotNull ActionUpdateThread getActionUpdateThread() { - return ActionUpdateThread.BGT; - } - - @Override - public void update(@NotNull AnActionEvent e) { - Project project = e.getProject(); - e.getPresentation().setEnabled(project != null && getRevisionNumber(e) != null && Comparing.equal(getVcsKey(e), GitVcs.getKey())); - } - - static void jumpToRevision(@NotNull Project project, @NotNull Hash hash) { - VcsLogContentUtil.runInMainLog(project, logUi -> jumpToRevisionUnderProgress(project, logUi, hash)); - } - - private static void jumpToRevisionUnderProgress(@NotNull Project project, - @NotNull VcsLogUiEx logUi, - @NotNull Hash hash) { - Future future = VcsLogNavigationUtil.jumpToHash(logUi, hash.asString(), false, true); - if (!future.isDone()) { - ProgressManager.getInstance().run(new Task.Backgroundable(project, - GitBundle.message("git.log.show.commit.in.log.process", hash.asString()), - false/*can not cancel*/, - PerformInBackgroundOption.ALWAYS_BACKGROUND) { - @Override - public void run(@NotNull ProgressIndicator indicator) { - try { - future.get(); - } - catch (CancellationException | InterruptedException ignored) { - } - catch (ExecutionException e) { - LOG.error(e); - } - } - }); - } - } +@Deprecated +public class GitShowCommitInLogAction extends ShowCommitInLogAction { }