From 6540c3a3928043f2085a2deab72612b0f0c41776 Mon Sep 17 00:00:00 2001 From: Yaroslav Lepenkin Date: Thu, 6 Oct 2016 19:52:44 +0300 Subject: [PATCH 1/3] [Parameter Name Hints] blacklisting initial --- .../impl/ParameterNameHintsManager.java | 49 +++++----- .../hints/filtering/MethodMatcher.kt | 96 +++++++++++++++++++ .../hints/filtering/StringMatcherBuilder.kt | 56 +++++++++++ .../hints/filtering/MatcherTest.kt | 67 +++++++++++++ .../hints/filtering/PatternExtractionTest.kt | 85 ++++++++++++++++ .../hints/filtering/StringMatchingTest.kt | 52 ++++++++++ 6 files changed, 380 insertions(+), 25 deletions(-) create mode 100644 platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/MethodMatcher.kt create mode 100644 platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/StringMatcherBuilder.kt create mode 100644 platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/MatcherTest.kt create mode 100644 platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/PatternExtractionTest.kt create mode 100644 platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/StringMatchingTest.kt diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/ParameterNameHintsManager.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/ParameterNameHintsManager.java index ed494a786136..6cfe9cd1593d 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/ParameterNameHintsManager.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/ParameterNameHintsManager.java @@ -15,7 +15,8 @@ */ package com.intellij.codeInsight.daemon.impl; -import com.intellij.openapi.util.Couple; +import com.intellij.codeInsight.hints.filtering.Matcher; +import com.intellij.codeInsight.hints.filtering.MatcherConstructor; import com.intellij.psi.*; import com.intellij.psi.tree.IElementType; import com.intellij.psi.util.TypeConversionUtil; @@ -26,22 +27,25 @@ import org.jetbrains.annotations.Nullable; import java.util.Collections; import java.util.List; import java.util.Set; +import java.util.stream.Collectors; +import java.util.stream.Stream; -import static com.intellij.openapi.util.text.StringUtil.containsIgnoreCase; import static com.intellij.psi.CommonClassNames.JAVA_LANG_STRING; public class ParameterNameHintsManager { - private static final List> COMMONLY_USED_PARAMETER_PAIR = ContainerUtil.newArrayList( - Couple.of("begin", "end"), - Couple.of("start", "end"), - Couple.of("first", "last"), - Couple.of("first", "second"), - Couple.of("from", "to"), - Couple.of("key", "value"), - Couple.of("min", "max"), - Couple.of("format", "arg") - ); - + + private static List MATCHERS = Stream.of( + "(begin*, end*)", + "(start*, end*)", + "(first*, last*)", + "(first*, second*)", + "(from*, to*)", + "(min*, max*)", + "(key, value)", + "(format, arg)" + ).map((s) -> MatcherConstructor.INSTANCE.createMatcher(s)) + .collect(Collectors.toList()); + private static final Set COMMON_METHOD_NAMES = ContainerUtil.newHashSet("set", "print", "println"); @NotNull @@ -173,7 +177,7 @@ public class ParameterNameHintsManager { final int totalDescriptors = descriptors.size(); if (totalDescriptors == 1 && shouldIgnoreSingleHint(parameters, descriptors) - || totalDescriptors == 2 && parameters.length == 2 && isParamPairToIgnore(descriptors.get(0), descriptors.get(1))) + || totalDescriptors == 2 && parameters.length == 2 && isParamPairToIgnore(descriptors)) { return ContainerUtil.emptyList(); } @@ -206,18 +210,13 @@ public class ParameterNameHintsManager { return new InlayInfo(paramName, callArgument.getTextRange().getStartOffset(), callArgument); } - private static boolean isParamPairToIgnore(InlayInfo first, InlayInfo second) { - String firstParamName = first.getText(); - String secondParamName = second.getText(); + private static boolean isParamPairToIgnore(List descriptors) { + List params = descriptors + .stream() + .map((e) -> e.getText()) + .collect(Collectors.toList()); - for (Couple knownPair : COMMONLY_USED_PARAMETER_PAIR) { - if (containsIgnoreCase(firstParamName, knownPair.first) - && containsIgnoreCase(secondParamName, knownPair.second)) { - return true; - } - } - - return false; + return MATCHERS.stream().anyMatch((e) -> e.isMatching("", params)); } private static boolean shouldInlineParameterName(@NotNull PsiExpression argument, diff --git a/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/MethodMatcher.kt b/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/MethodMatcher.kt new file mode 100644 index 000000000000..32cfbfdcca76 --- /dev/null +++ b/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/MethodMatcher.kt @@ -0,0 +1,96 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.codeInsight.hints.filtering + +import com.intellij.openapi.util.Couple + + +interface ParamMatcher { + fun isMatching(paramNames: List): Boolean +} + +interface MethodMatcher { + fun isMatching(fullyQualifiedMethodName: String, paramNames: List): Boolean +} + +object AnyParamMatcher: ParamMatcher { + override fun isMatching(paramNames: List) = true +} + +class StringParamMatcher(private val paramMatchers: List): ParamMatcher { + override fun isMatching(paramNames: List): Boolean { + if (paramNames.size != paramMatchers.size) { + return false + } + + return paramMatchers + .zip(paramNames) + .find { !it.first.isMatching(it.second) } == null + } +} + +class Matcher(private val methodNameMatcher: StringMatcher, + private val paramMatchers: ParamMatcher): MethodMatcher +{ + override fun isMatching(fullyQualifiedMethodName: String, paramNames: List): Boolean { + return methodNameMatcher.isMatching(fullyQualifiedMethodName) && paramMatchers.isMatching(paramNames) + } +} + +object MatcherConstructor { + + fun extract(matcher: String): Couple? { + val trimmedMatcher = matcher.trim() + if (trimmedMatcher.isEmpty()) return null + + val index = trimmedMatcher.indexOf('(') + if (index < 0) { + return Couple(trimmedMatcher, "") + } + else if (index == 0) { + return Couple("", trimmedMatcher) + } + + val methodMatcher = trimmedMatcher.substring(0, index) + val paramsMatcher = trimmedMatcher.substring(index) + + return Couple(methodMatcher.trim(), paramsMatcher.trim()) + } + + private fun createParametersMatcher(paramsMatcher: String): ParamMatcher? { + if (paramsMatcher.length <= 2) return null + + val paramsString = paramsMatcher.substring(1, paramsMatcher.length - 1) + val params = paramsString.split(',').map(String::trim) + if (params.find(String::isEmpty) != null) return null + + val matchers = params.mapNotNull { StringMatcherBuilder.create(it) } + return if (matchers.size == params.size) StringParamMatcher(matchers) else null + } + + fun createMatcher(matcher: String): Matcher? { + val pair = extract(matcher) ?: return null + + val methodNameMatcher = StringMatcherBuilder.create(pair.first) ?: return null + val paramMatcher = if (pair.second.isEmpty()) AnyParamMatcher else createParametersMatcher(pair.second) + + return if (paramMatcher != null) Matcher(methodNameMatcher, paramMatcher) else null + } + + +} + + diff --git a/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/StringMatcherBuilder.kt b/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/StringMatcherBuilder.kt new file mode 100644 index 000000000000..f86a6170a224 --- /dev/null +++ b/platform/platform-impl/src/com/intellij/codeInsight/hints/filtering/StringMatcherBuilder.kt @@ -0,0 +1,56 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.codeInsight.hints.filtering + +interface StringMatcher { + fun isMatching(text: String): Boolean +} + +class StringMatcherImpl(private val matcher: (String) -> Boolean) : StringMatcher { + override fun isMatching(text: String) = matcher(text) +} + +object StringMatcherBuilder { + + fun create(matcher: String): StringMatcher? { + if (matcher.isEmpty()) return StringMatcherImpl { true } + + val asterisksCount = matcher.count { it == '*' } + if (asterisksCount > 1) return null + if (asterisksCount == 1) return createAsterisksMatcher(matcher) + + return StringMatcherImpl { it == matcher } + } + + private fun createAsterisksMatcher(matcher: String): StringMatcher? { + if (matcher == "*") { + return StringMatcherImpl { true } + } + + if (matcher.startsWith('*')) { + val target = matcher.substring(1) + return StringMatcherImpl { it.endsWith(target) } + } + + if (matcher.endsWith('*')) { + val target = matcher.substring(0, matcher.length - 1) + return StringMatcherImpl { it.startsWith(target) } + } + + return null + } + +} \ No newline at end of file diff --git a/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/MatcherTest.kt b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/MatcherTest.kt new file mode 100644 index 000000000000..d842cd7e76f1 --- /dev/null +++ b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/MatcherTest.kt @@ -0,0 +1,67 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.codeInsight.hints.filtering + +import junit.framework.TestCase +import org.assertj.core.api.Assertions.assertThat + +class MatcherTest : TestCase() { + + fun Matcher.assertIsMatching(fullyQualifiedMethodName: String, vararg params: String) { + assertThat(isMatching(fullyQualifiedMethodName, listOf(*params))).isTrue() + } + + fun Matcher.assertNotMatching(fullyQualifiedMethodName: String, vararg params: String) { + assertThat(isMatching(fullyQualifiedMethodName, listOf(*params))).isFalse() + } + + fun `test simple matcher`() { + val matcher = MatcherConstructor.createMatcher("*.String(old*, new*)")!! + + matcher.assertIsMatching("java.lang.String", "oldValue", "newValue") + matcher.assertIsMatching("java.lang.String", "old", "new") + + matcher.assertNotMatching("java.lang.String", "valueOld", "valueNew") + matcher.assertNotMatching("Boolean", "old", "new") + } + + fun `test any single param method matcher`() { + val matchers = listOf(MatcherConstructor.createMatcher("*(*)")!!, MatcherConstructor.createMatcher("(*)")!!) + + matchers.forEach { + it.assertIsMatching("java.lang.String.indexOf", "ch") + it.assertIsMatching("java.lang.String.charAt", "index") + it.assertIsMatching("java.lang.Boolean.valueOf", "value") + it.assertNotMatching("java.lang.Boolean.substring", "from", "to") + } + } + + fun `test any with key value`() { + val matcher = MatcherConstructor.createMatcher("*(key, value)")!! + matcher.assertIsMatching("java.util.Map.put", "key", "value") + matcher.assertIsMatching("java.util.HashMap.put", "key", "value") + matcher.assertIsMatching("java.util.HashMap.putIfNeeded", "key", "value") + } + + fun `test couple contains`() { + val matcher = MatcherConstructor.createMatcher("*(first*, last*)")!! + + matcher.assertIsMatching("java.util.Str.subs", "firstIndex", "lastIndex") + matcher.assertIsMatching("java.util.Str.subs", "first", "last") + } + + +} \ No newline at end of file diff --git a/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/PatternExtractionTest.kt b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/PatternExtractionTest.kt new file mode 100644 index 000000000000..a72a87ee8533 --- /dev/null +++ b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/PatternExtractionTest.kt @@ -0,0 +1,85 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.codeInsight.hints.filtering + +import junit.framework.TestCase +import org.assertj.core.api.Assertions.assertThat + +class PatternExtractionTest : TestCase() { + + fun String.assertMatcher(nameMatcher: String, paramsMatcher: String) { + val matcher = MatcherConstructor.extract(this) + if (matcher == null) { + assertThat(nameMatcher).isEmpty() + assertThat(paramsMatcher).isEmpty() + return + } + + assertThat(nameMatcher).isEqualTo(matcher.first) + assertThat(paramsMatcher).isEqualTo(matcher.second) + } + + fun `test match all methods from package`() { + val text = "java.lang.*" + text.assertMatcher("java.lang.*", "") + } + + fun `test match all methods from class String`() { + val text = "java.lang.String.*" + text.assertMatcher("java.lang.String.*", "") + } + + fun `test match all replace methods`() { + val text = "*.replace" + text.assertMatcher("*.replace", "") + } + + fun `test match all replace methods with couple params`() { + val text = "*.replace(*, *)" + text.assertMatcher("*.replace", "(*, *)") + } + + fun `test match only one replace method with couple params`() { + val text = "java.lang.String.replace(*,*)" + text.assertMatcher("java.lang.String.replace", "(*,*)") + } + + fun `test match debug particular method`() { + val text = "org.logger.Log.debug(format,arg)" + text.assertMatcher("org.logger.Log.debug", "(format,arg)") + } + + fun `test match method with single param`() { + val text = "class.method(*)" + text.assertMatcher("class.method", "(*)") + } + + fun `test match all methods with single param`() { + val text = "*(*)" + text.assertMatcher("*", "(*)") + } + + fun `test simplified params matcher`() { + val text = "(*)" + text.assertMatcher("", "(*)") + } + + fun `test shit`() { + val text = " foooo (*) " + text.assertMatcher("foooo", "(*)") + } + +} \ No newline at end of file diff --git a/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/StringMatchingTest.kt b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/StringMatchingTest.kt new file mode 100644 index 000000000000..982e1ed5fd1a --- /dev/null +++ b/platform/platform-tests/testSrc/com/intellij/codeInsight/hints/filtering/StringMatchingTest.kt @@ -0,0 +1,52 @@ +/* + * Copyright 2000-2016 JetBrains s.r.o. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.intellij.codeInsight.hints.filtering + +import junit.framework.TestCase +import org.assertj.core.api.Assertions.assertThat + +class StringMatchingTest : TestCase() { + + fun com.intellij.codeInsight.hints.filtering.StringMatcher.assertMatches(vararg matched: String) { + matched.forEach { assertThat(isMatching(it)).isTrue() } + } + + fun com.intellij.codeInsight.hints.filtering.StringMatcher.assertNotMatches(vararg unmatched: String) { + unmatched.forEach { assertThat(isMatching(it)).isFalse() } + } + + fun `test simple`() { + val matcher = com.intellij.codeInsight.hints.filtering.StringMatcherBuilder.create("aaa")!! + + matcher.assertMatches("aaa") + matcher.assertNotMatches("aaaa", "aab", "", "*", "a", "baaa") + } + + fun `test asterisks before`() { + val matcher = com.intellij.codeInsight.hints.filtering.StringMatcherBuilder.create("aaa*")!! + + matcher.assertMatches("aaa", "aaaa", "aaaaaa", "aaaqwe") + matcher.assertNotMatches("baaa", "nnaaa", "qweaaa") + } + + fun `test asterisks after`() { + val matcher = com.intellij.codeInsight.hints.filtering.StringMatcherBuilder.create("*aaa")!! + + matcher.assertMatches("aaa", "aaaa", "baaa", "aawweraaa") + matcher.assertNotMatches("aaab", "aaabaa") + } + +} \ No newline at end of file From 3b823d454a4c50b3f7051d6161808bc3ad98adf2 Mon Sep 17 00:00:00 2001 From: Julia Beliaeva Date: Thu, 6 Oct 2016 20:07:02 +0300 Subject: [PATCH 2/3] [vcs-log] properly calculate date and author column width --- .../vcs/log/ui/frame/VcsLogGraphTable.java | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java index 6cd606885e80..d7bf44e0ade5 100644 --- a/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java +++ b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java @@ -94,6 +94,7 @@ public class VcsLogGraphTable extends TableWithProgress implements DataProvider, @NotNull private final TableCellRenderer myDummyRenderer = new DefaultTableCellRenderer(); @NotNull private final GraphCommitCellRenderer myGraphCommitCellRenderer; @NotNull private final GraphTableController myController; + private final StringCellRenderer myStringCellRenderer; private boolean myColumnsSizeInitialized = false; @Nullable private Selection mySelection = null; @@ -113,12 +114,13 @@ public class VcsLogGraphTable extends TableWithProgress implements DataProvider, myUi = ui; myLogData = logData; myGraphCommitCellRenderer = new GraphCommitCellRenderer(logData, myGraphCellPainter, this); + myStringCellRenderer = new StringCellRenderer(); myLogData.getProgress().addProgressIndicatorListener(new MyProgressListener(), ui); setDefaultRenderer(VirtualFile.class, new RootCellRenderer(myUi)); setDefaultRenderer(GraphCommitCell.class, myGraphCommitCellRenderer); - setDefaultRenderer(String.class, new StringCellRenderer()); + setDefaultRenderer(String.class, myStringCellRenderer); setShowHorizontalLines(false); setIntercellSpacing(JBUI.emptySize()); @@ -187,11 +189,13 @@ public class VcsLogGraphTable extends TableWithProgress implements DataProvider, maxWidth = Math.max(getFontMetrics(tableFont.deriveFont(Font.BOLD)).stringWidth(value), maxWidth); if (!value.isEmpty()) sizeCalculated = true; } - int min = Math.min(maxWidth + UIUtil.DEFAULT_HGAP, MAX_DEFAULT_AUTHOR_COLUMN_WIDTH); + int min = + Math.min(maxWidth + UIUtil.DEFAULT_HGAP, MAX_DEFAULT_AUTHOR_COLUMN_WIDTH + myStringCellRenderer.getHorizontalTextPadding()); column.setPreferredWidth(min); } else if (i == GraphTableModel.DATE_COLUMN) { // all dates have nearly equal sizes - int min = getFontMetrics(tableFont.deriveFont(Font.BOLD)).stringWidth("mm" + DateFormatUtil.formatDateTime(new Date())); + int min = getFontMetrics(tableFont.deriveFont(Font.BOLD)).stringWidth(DateFormatUtil.formatDateTime(new Date())) + + myStringCellRenderer.getHorizontalTextPadding(); column.setPreferredWidth(min); } } @@ -645,7 +649,12 @@ public class VcsLogGraphTable extends TableWithProgress implements DataProvider, return; } append(value.toString(), applyHighlighters(this, row, column, value.toString(), hasFocus, selected)); - setBorder(null); + } + + public int getHorizontalTextPadding() { + Insets borderInsets = getMyBorder().getBorderInsets(this); + Insets ipad = getIpad(); + return borderInsets.left + borderInsets.right + ipad.left + ipad.right; } } From 1bd0676df5270cb5a3997303fc676464e4c5462c Mon Sep 17 00:00:00 2001 From: Julia Beliaeva Date: Thu, 6 Oct 2016 20:07:44 +0300 Subject: [PATCH 3/3] [vcs-log] minor: optimize imports --- .../com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java index d7bf44e0ade5..3533019d82b6 100644 --- a/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java +++ b/platform/vcs-log/impl/src/com/intellij/vcs/log/ui/frame/VcsLogGraphTable.java @@ -17,15 +17,12 @@ package com.intellij.vcs.log.ui.frame; import com.google.common.primitives.Ints; import com.intellij.ide.CopyProvider; -import com.intellij.ide.IdeTooltip; -import com.intellij.ide.IdeTooltipManager; import com.intellij.openapi.actionSystem.DataContext; import com.intellij.openapi.actionSystem.DataProvider; import com.intellij.openapi.actionSystem.PlatformDataKeys; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.ide.CopyPasteManager; import com.intellij.openapi.ui.LoadingDecorator; -import com.intellij.openapi.ui.popup.Balloon; import com.intellij.openapi.util.Comparing; import com.intellij.openapi.util.Couple; import com.intellij.openapi.util.Pair; @@ -33,7 +30,6 @@ import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.ui.*; import com.intellij.ui.components.JBLabel; -import com.intellij.ui.components.panels.Wrapper; import com.intellij.ui.table.JBTable; import com.intellij.util.containers.ContainerUtil; import com.intellij.util.text.DateFormatUtil; @@ -59,7 +55,6 @@ import com.intellij.vcs.log.ui.VcsLogUiImpl; import com.intellij.vcs.log.ui.render.GraphCommitCell; import com.intellij.vcs.log.ui.render.GraphCommitCellRenderer; import com.intellij.vcs.log.ui.tables.GraphTableModel; -import com.intellij.vcs.log.util.VcsUserUtil; import gnu.trove.TIntHashSet; import org.jetbrains.annotations.NonNls; import org.jetbrains.annotations.NotNull; @@ -74,7 +69,9 @@ import java.awt.datatransfer.StringSelection; import java.awt.event.ComponentAdapter; import java.awt.event.ComponentEvent; import java.awt.event.MouseEvent; -import java.util.*; +import java.util.Collection; +import java.util.Date; +import java.util.EventObject; import java.util.List; public class VcsLogGraphTable extends TableWithProgress implements DataProvider, CopyProvider {