lazy toolwindow content manager creation

GitOrigin-RevId: 5e96dc71f0d3c0cd161d2839ad0e7dea2fa2ecab
This commit is contained in:
Vladimir Krivosheev
2019-12-12 10:44:41 +01:00
committed by intellij-monorepo-bot
parent a8ef074d02
commit 0a26756d32
39 changed files with 966 additions and 1516 deletions

View File

@@ -7,7 +7,6 @@ import com.intellij.ide.errorTreeView.ErrorTreeElement;
import com.intellij.ide.errorTreeView.ErrorTreeElementKind;
import com.intellij.ide.errorTreeView.ErrorViewStructure;
import com.intellij.ide.errorTreeView.GroupingElement;
import com.intellij.openapi.Disposable;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.ModalityState;
import com.intellij.openapi.compiler.CompileScope;
@@ -57,13 +56,6 @@ final class ProblemsViewImpl extends ProblemsView {
content.setHelpId("reference.problems.tool.window");
// todo: setup content?
toolWindow.getContentManager().addContent(content);
Disposer.register(project, new Disposable() {
@Override
public void dispose() {
toolWindow.getContentManager().removeAllContents(true);
}
});
if (myPanel == null) {
myViewUpdater.execute(() -> doUpdateIcon(toolWindow));
}

View File

@@ -16,7 +16,7 @@ import java.util.Collections;
*
* @author konstantin.aleev
*/
class PanelContentUI implements ContentUI {
final class PanelContentUI implements ContentUI {
private JPanel myPanel;
private ContentManager myContentManager;
@@ -126,11 +126,4 @@ class PanelContentUI implements ContentUI {
public String getNextContentActionName() {
return "";
}
@Override
public void dispose() {
if (myPanel != null) {
myPanel.removeAll();
}
}
}

View File

@@ -51,7 +51,7 @@ import java.util.stream.Collectors;
name = "RunDashboard",
storages = @Storage(StoragePathMacros.WORKSPACE_FILE)
)
public class RunDashboardManagerImpl implements RunDashboardManager, PersistentStateComponent<RunDashboardManagerImpl.State> {
public final class RunDashboardManagerImpl implements RunDashboardManager, PersistentStateComponent<RunDashboardManagerImpl.State> {
private static final ExtensionPointName<RunDashboardCustomizer> CUSTOMIZER_EP_NAME =
ExtensionPointName.create("com.intellij.runDashboardCustomizer");
private static final ExtensionPointName<RunDashboardDefaultTypesProvider> DEFAULT_TYPES_PROVIDER_EP_NAME =

View File

@@ -528,22 +528,25 @@ public class ThreeComponentsSplitter extends JPanel implements Disposable {
/**
* Sets component which is located as the "inner" splitted area. The method doesn't validate and
* repaint the splitter.
*
*/
public void setInnerComponent(@Nullable JComponent component) {
if (myInnerComponent != component) {
if (myInnerComponent != null) {
remove(myInnerComponent);
}
myInnerComponent = component;
updateComponentTreeUI(myInnerComponent);
if (myInnerComponent == component) {
return;
}
if (myInnerComponent != null) {
add(myInnerComponent);
myInnerComponent.invalidate();
}
if (myInnerComponent != null) {
remove(myInnerComponent);
}
myInnerComponent = component;
updateComponentTreeUI(myInnerComponent);
if (myInnerComponent != null) {
add(myInnerComponent);
myInnerComponent.invalidate();
}
}
public void setMinSize(int minSize) {
myMinSize = Math.max(0, minSize);
doLayout();

View File

@@ -7,7 +7,6 @@ import com.intellij.openapi.actionSystem.DataContext;
import com.intellij.openapi.application.Application;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.ModalityState;
import com.intellij.openapi.components.ServiceManager;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.ActionCallback;
import com.intellij.openapi.util.ExpirableRunnable;
@@ -144,7 +143,7 @@ public abstract class IdeFocusManager implements FocusRequestor {
return getGlobalInstance();
}
else {
return ServiceManager.getService(project, IdeFocusManager.class);
return project.getService(IdeFocusManager.class);
}
}

View File

@@ -6,6 +6,7 @@ import com.intellij.openapi.util.ActionCallback;
import com.intellij.openapi.util.BusyObject;
import com.intellij.openapi.util.Key;
import com.intellij.ui.content.ContentManager;
import com.intellij.ui.content.ContentManagerListener;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -164,10 +165,13 @@ public interface ToolWindow extends BusyObject {
/**
* @return component which represents window content.
*/
@NotNull
JComponent getComponent();
ContentManager getContentManager();
void addContentManagerListener(@NotNull ContentManagerListener listener);
void setDefaultState(@Nullable ToolWindowAnchor anchor, @Nullable ToolWindowType type, @Nullable Rectangle floatingBounds);
void setToHideOnEmptyContent(boolean hideOnEmpty);

View File

@@ -1,32 +1,5 @@
/*
* Copyright 2000-2009 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.
*/
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.ui.content;
import org.jetbrains.annotations.NotNull;
public class ContentManagerAdapter implements ContentManagerListener {
@Override
public void contentAdded(@NotNull ContentManagerEvent event) {}
@Override
public void contentRemoved(@NotNull ContentManagerEvent event) {}
@Override
public void contentRemoveQuery(@NotNull ContentManagerEvent event) {}
@Override
public void selectionChanged(@NotNull ContentManagerEvent event) {}
}

View File

@@ -1,27 +1,20 @@
/*
* Copyright 2000-2009 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.
*/
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.ui.content;
import org.jetbrains.annotations.NotNull;
import java.util.EventListener;
public interface ContentManagerListener extends EventListener{
void contentAdded(@NotNull ContentManagerEvent event);
void contentRemoved(@NotNull ContentManagerEvent event);
void contentRemoveQuery(@NotNull ContentManagerEvent event);
void selectionChanged(@NotNull ContentManagerEvent event);
public interface ContentManagerListener extends EventListener {
default void contentAdded(@NotNull ContentManagerEvent event) {
}
default void contentRemoved(@NotNull ContentManagerEvent event) {
}
default void contentRemoveQuery(@NotNull ContentManagerEvent event) {
}
default void selectionChanged(@NotNull ContentManagerEvent event) {
}
}

View File

@@ -1,13 +1,12 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.ui.content;
import com.intellij.openapi.Disposable;
import org.jetbrains.annotations.Nls;
import org.jetbrains.annotations.NotNull;
import javax.swing.*;
public interface ContentUI extends Disposable {
public interface ContentUI {
JComponent getComponent();
void setManager(@NotNull ContentManager manager);

View File

@@ -11,25 +11,24 @@ import com.intellij.openapi.project.Project;
import com.intellij.openapi.wm.ToolWindow;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.ContentManager;
import com.intellij.ui.content.ContentManagerAdapter;
import com.intellij.ui.content.ContentManagerEvent;
import com.intellij.ui.content.ContentManagerListener;
import com.intellij.util.SmartList;
import com.intellij.util.containers.ContainerUtil;
import com.intellij.util.containers.JBIterable;
import com.intellij.util.ui.UIUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import java.awt.*;
import java.util.Collections;
import java.util.List;
import java.util.function.Supplier;
/**
* @author gregsh
*/
public class ToggleToolbarAction extends ToggleAction implements DumbAware {
public final class ToggleToolbarAction extends ToggleAction implements DumbAware {
@NotNull
public static DefaultActionGroup createToggleToolbarGroup(@NotNull Project project, @NotNull ToolWindow toolWindow) {
return new DefaultActionGroup(new OptionsGroup(toolWindow),
@@ -45,27 +44,29 @@ public class ToggleToolbarAction extends ToggleAction implements DumbAware {
@NotNull
public static ToggleToolbarAction createToolWindowAction(@NotNull ToolWindow toolWindow, @NotNull PropertiesComponent properties) {
toolWindow.getContentManager().addContentManagerListener(new ContentManagerAdapter() {
toolWindow.addContentManagerListener(new ContentManagerListener() {
@Override
public void contentAdded(@NotNull ContentManagerEvent event) {
JComponent component = event.getContent().getComponent();
setToolbarVisible(JBIterable.of(component), isToolbarVisible(toolWindow, properties));
setToolbarVisible(Collections.singletonList(component), isToolbarVisible(toolWindow, properties));
// support nested content managers, e.g. RunnerLayoutUi as content component
ContentManager contentManager =
component instanceof DataProvider ? PlatformDataKeys.CONTENT_MANAGER.getData((DataProvider)component) : null;
if (contentManager != null) contentManager.addContentManagerListener(this);
ContentManager contentManager = component instanceof DataProvider ? PlatformDataKeys.CONTENT_MANAGER.getData((DataProvider)component) : null;
if (contentManager != null) {
contentManager.addContentManagerListener(this);
}
}
});
return new ToggleToolbarAction(properties, getShowToolbarProperty(toolWindow),
() -> JBIterable.of(toolWindow.getContentManager().getComponent()));
return new ToggleToolbarAction(properties, getShowToolbarProperty(toolWindow), () -> {
return Collections.singletonList(toolWindow.getContentManager().getComponent());
});
}
public static void setToolbarVisible(@NotNull ToolWindow toolWindow,
@NotNull PropertiesComponent properties,
@Nullable Boolean visible) {
boolean state = visible == null ? isToolbarVisible(toolWindow, properties) : visible;
setToolbarVisibleImpl(getShowToolbarProperty(toolWindow), properties, JBIterable.of(toolWindow.getComponent()), state);
setToolbarVisibleImpl(getShowToolbarProperty(toolWindow), properties, Collections.singletonList(toolWindow.getComponent()), state);
}
public static void setToolbarVisible(@NotNull String id,
@@ -95,7 +96,6 @@ public class ToggleToolbarAction extends ToggleAction implements DumbAware {
return isSelectedImpl(properties, getShowToolbarProperty(toolWindow));
}
private final PropertiesComponent myPropertiesComponent;
private final String myProperty;
private final Supplier<? extends Iterable<JComponent>> myProducer;
@@ -134,7 +134,6 @@ public class ToggleToolbarAction extends ToggleAction implements DumbAware {
setToolbarVisible(components, visible);
}
boolean isSelected() {
return isSelectedImpl(myPropertiesComponent, myProperty);
}
@@ -180,7 +179,7 @@ public class ToggleToolbarAction extends ToggleAction implements DumbAware {
JComponent contentComponent = selectedContent != null ? selectedContent.getComponent() : null;
if (contentComponent == null || e == null) return EMPTY_ARRAY;
List<AnAction> result = new SmartList<>();
for (final ActionToolbar toolbar : iterateToolbars(JBIterable.of(contentComponent))) {
for (final ActionToolbar toolbar : iterateToolbars(Collections.singletonList(contentComponent))) {
JComponent c = toolbar.getComponent();
if (c.isVisible() || !c.isValid()) continue;
if (!result.isEmpty() && !(ContainerUtil.getLastItem(result) instanceof Separator)) {

View File

@@ -18,12 +18,12 @@ final class ActiveStack {
* Contains {@code id}s of tool window that were activated. This stack
* is cleared each time when editor is being activated.
*/
private final Stack<String> myStack;
private final Stack<ToolWindowEntry> myStack;
/**
* This stack is not cleared when editor is being activated. It means its "long"
* persistence.
*/
private final Stack<String> myPersistentStack;
private final Stack<ToolWindowEntry> myPersistentStack;
/**
* Creates enabled window stack.
@@ -48,7 +48,7 @@ final class ActiveStack {
}
@NotNull
String pop() {
ToolWindowEntry pop() {
return myStack.pop();
}
@@ -57,13 +57,13 @@ final class ActiveStack {
}
@NotNull
private String peek(int i) {
private ToolWindowEntry peek(int i) {
return myStack.get(getSize() - i - 1);
}
@NotNull
String[] getStack() {
String[] result = new String[getSize()];
ToolWindowEntry[] getStack() {
ToolWindowEntry[] result = new ToolWindowEntry[getSize()];
for (int i = 0; i < getSize(); i++) {
result[i] = peek(i);
}
@@ -71,15 +71,15 @@ final class ActiveStack {
}
@NotNull
String[] getPersistentStack() {
String[] result = new String[getPersistentSize()];
ToolWindowEntry[] getPersistentStack() {
ToolWindowEntry[] result = new ToolWindowEntry[getPersistentSize()];
for (int i = 0; i < getPersistentSize(); i++) {
result[i] = peekPersistent(i);
}
return result;
}
void push(@NotNull String id) {
void push(@NotNull ToolWindowEntry id) {
remove(id, true);
myStack.push(id);
myPersistentStack.push(id);
@@ -93,7 +93,7 @@ final class ActiveStack {
* Peeks element at the persistent stack. {@code 0} means the top of the stack.
*/
@NotNull
String peekPersistent(final int index) {
ToolWindowEntry peekPersistent(final int index) {
return myPersistentStack.get(myPersistentStack.size() - index - 1);
}
@@ -104,10 +104,10 @@ final class ActiveStack {
* @param removePersistentAlso if {@code true} then clears last active {@code ID}
* if it's the last active {@code ID}.
*/
void remove(@NotNull String id, boolean removePersistentAlso) {
myStack.removeIf(id::equals);
void remove(@NotNull ToolWindowEntry id, boolean removePersistentAlso) {
myStack.remove(id);
if (removePersistentAlso) {
myPersistentStack.removeIf(id::equals);
myPersistentStack.remove(id);
}
}
}

View File

@@ -1,13 +1,12 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.wm.impl.commands.FinalizableCommand;
import com.intellij.openapi.progress.ProcessCanceledException;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.ArrayList;
import java.util.ArrayDeque;
import java.util.Deque;
import java.util.List;
import java.util.function.BooleanSupplier;
@@ -15,10 +14,17 @@ public final class CommandProcessor implements Runnable {
private static final Logger LOG = Logger.getInstance(CommandProcessor.class);
private final Object myLock = new Object();
private final List<CommandGroup> commandGroups = new ArrayList<>();
private final Deque<List<Runnable>> commandGroups = new ArrayDeque<>();
@NotNull
private final BooleanSupplier isDisposedCondition;
private int myCommandCount;
private boolean myFlushed;
public CommandProcessor(@NotNull BooleanSupplier isDisposedCondition) {
this.isDisposedCondition = isDisposedCondition;
}
public final int getCommandCount() {
synchronized (myLock) {
return myCommandCount;
@@ -32,18 +38,16 @@ public final class CommandProcessor implements Runnable {
}
}
/**
* Executes passed batch of commands. Note, that the processor surround the
* commands with BlockFocusEventsCmd - UnblockFocusEventsCmd. It's required to
* prevent focus handling of events which is caused by the commands to be executed.
*/
public final void execute(@NotNull List<? extends FinalizableCommand> commandList, @NotNull BooleanSupplier expired) {
public final void execute(@NotNull List<Runnable> commands) {
if (commands.isEmpty()) {
return;
}
synchronized (myLock) {
boolean isBusy = myCommandCount > 0 || !myFlushed;
CommandGroup commandGroup = new CommandGroup(commandList, expired);
commandGroups.add(commandGroup);
myCommandCount += commandList.size();
commandGroups.add(commands);
myCommandCount += commands.size();
if (!isBusy) {
run();
@@ -54,81 +58,35 @@ public final class CommandProcessor implements Runnable {
@Override
public final void run() {
synchronized (myLock) {
//noinspection StatementWithEmptyBody
while (runNext()) ;
}
}
while (true) {
List<Runnable> commands = commandGroups.pollFirst();
if (commands == null) {
return;
}
private boolean runNext() {
CommandGroup commandGroup = getNextCommandGroup();
if (commandGroup == null || commandGroup.isEmpty()) {
return false;
}
for (int i = commands.size() - 1; i >= 0; i--) {
Runnable command = commands.get(i);
myCommandCount--;
BooleanSupplier conditionForGroup = commandGroup.getExpireCondition();
if (isDisposedCondition.getAsBoolean()) {
continue;
}
FinalizableCommand command = commandGroup.takeNextCommand();
myCommandCount--;
if (LOG.isDebugEnabled()) {
LOG.debug("CommandProcessor.run " + command);
}
BooleanSupplier expire = command.getExpireCondition() == null ? conditionForGroup : command.getExpireCondition();
if (expire == null ? ApplicationManager.getApplication().isDisposed() : expire.getAsBoolean()) {
return true;
}
if (LOG.isDebugEnabled()) {
LOG.debug("CommandProcessor.run " + command);
}
command.run();
return true;
}
@Nullable
private CommandGroup getNextCommandGroup() {
while (!commandGroups.isEmpty()) {
CommandGroup candidate = commandGroups.get(0);
if (!candidate.isEmpty()) {
return candidate;
try {
command.run();
}
catch (ProcessCanceledException e) {
throw e;
}
catch (Throwable e) {
LOG.error(e);
}
}
}
commandGroups.remove(candidate);
}
return null;
}
private static final class CommandGroup {
private List<? extends FinalizableCommand> myList;
private BooleanSupplier myExpireCondition;
private CommandGroup(@NotNull List<? extends FinalizableCommand> list, @NotNull BooleanSupplier expireCondition) {
myList = list;
myExpireCondition = expireCondition;
}
@NotNull
BooleanSupplier getExpireCondition() {
return myExpireCondition;
}
public boolean isEmpty() {
return myList == null || myList.isEmpty();
}
@NotNull
FinalizableCommand takeNextCommand() {
FinalizableCommand command;
// if singleton list, do not mutate, just get first element and set to null
if (myList.size() == 1) {
command = myList.get(0);
myList = null;
}
else {
command = myList.remove(0);
}
if (isEmpty()) {
// memory leak otherwise
myExpireCondition = () -> true;
}
return command;
}
}
}

View File

@@ -2,7 +2,6 @@
package com.intellij.openapi.wm.impl
import com.intellij.configurationStore.serialize
import com.intellij.ide.ui.UISettings.Companion.instance
import com.intellij.openapi.diagnostic.logger
import com.intellij.openapi.util.JDOMUtil
import com.intellij.openapi.wm.RegisterToolWindowTask
@@ -74,7 +73,7 @@ class DesktopLayout {
* @return all (registered and not unregistered) `WindowInfos` for the specified `anchor`.
* Returned infos are sorted by order.
*/
private fun getAllInfos(anchor: ToolWindowAnchor): List<WindowInfoImpl> {
internal fun getAllInfos(anchor: ToolWindowAnchor): List<WindowInfoImpl> {
val result = mutableListOf<WindowInfoImpl>()
for (info in idToInfo.values) {
if (anchor == info.anchor) {
@@ -190,14 +189,6 @@ class DesktopLayout {
return state
}
fun getVisibleIdsOn(anchor: ToolWindowAnchor, manager: ToolWindowManagerImpl): List<String> {
return getAllInfos(anchor).mapNotNull { each ->
val id = each.id ?: return@mapNotNull null
val window = manager.getToolWindow(id) ?: return@mapNotNull null
if (window.isAvailable || instance.alwaysShowWindowsButton) id else null
}
}
internal inner class MyStripeButtonComparator(anchor: ToolWindowAnchor, manager: ToolWindowManagerImpl) : Comparator<StripeButton> {
private val idToInfo: MutableMap<String?, WindowInfoImpl> = THashMap()

View File

@@ -133,11 +133,11 @@ public final class FloatingDecorator extends JDialog {
if (ScreenUtil.isStandardAddRemoveNotify(getParent())) {
Disposer.dispose(myDelayAlarm);
Disposer.dispose(myDisposable);
} else {
if (isShowing()) {
SwingUtilities.invokeLater(() -> show());
}
}
else if (isShowing()) {
SwingUtilities.invokeLater(() -> show());
}
super.dispose();
}

View File

@@ -11,7 +11,6 @@ import com.intellij.openapi.actionSystem.ex.ActionUtil;
import com.intellij.openapi.keymap.KeymapUtil;
import com.intellij.openapi.project.DumbAware;
import com.intellij.openapi.project.DumbService;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.ui.Queryable;
import com.intellij.openapi.ui.Splitter;
import com.intellij.openapi.util.Disposer;
@@ -24,6 +23,7 @@ import com.intellij.ui.JBColor;
import com.intellij.ui.UIBundle;
import com.intellij.ui.components.panels.NonOpaquePanel;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.impl.ContentManagerImpl;
import com.intellij.ui.paint.LinePainter2D;
import com.intellij.util.ui.JBUI;
import org.jetbrains.annotations.NonNls;
@@ -46,11 +46,9 @@ import java.util.Map;
* @author Vladimir Kondratyev
*/
public final class InternalDecorator extends JPanel implements Queryable, DataProvider, ComponentWithMnemonics {
private final Project myProject;
private WindowInfoImpl myInfo;
private final ToolWindowImpl myToolWindow;
private final ToolWindowImpl toolWindow;
private final MyDivider myDivider;
private final InternalDecoratorListener listener;
private final RemoveStripeButtonAction myRemoveFromSideBarAction;
private ActionGroup myAdditionalGearActions;
@@ -70,18 +68,13 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
private final ToolWindowHeader myHeader;
private final ActionGroup myToggleToolbarGroup;
private final JPanel contentPane;
InternalDecorator(@NotNull Project project,
@NotNull WindowInfoImpl info,
@NotNull ToolWindowImpl toolWindow,
boolean dumbAware,
@NotNull Disposable parentDisposable,
@NotNull InternalDecoratorListener listener) {
InternalDecorator(@NotNull WindowInfoImpl info, @NotNull ToolWindowImpl toolWindow) {
super(new BorderLayout());
myProject = project;
myToolWindow = toolWindow;
myToolWindow.setDecorator(this);
this.toolWindow = toolWindow;
toolWindow.setDecorator(this);
myDivider = new MyDivider();
/*
@@ -89,7 +82,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
*/
ToggleContentUiTypeAction toggleContentUiTypeAction = new ToggleContentUiTypeAction();
myRemoveFromSideBarAction = new RemoveStripeButtonAction();
myToggleToolbarGroup = ToggleToolbarAction.createToggleToolbarGroup(myProject, myToolWindow);
myToggleToolbarGroup = ToggleToolbarAction.createToggleToolbarGroup(toolWindow.getToolWindowManager().getProject(), this.toolWindow);
if (!ToolWindowId.PREVIEW.equals(info.getId())) {
((DefaultActionGroup)myToggleToolbarGroup).addAction(toggleContentUiTypeAction);
}
@@ -100,7 +93,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
myHeader = new ToolWindowHeader(toolWindow, () -> createPopupGroup(true)) {
@Override
protected boolean isActive() {
return myToolWindow.isActive();
return InternalDecorator.this.toolWindow.isActive();
}
@Override
@@ -109,34 +102,41 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
}
};
init(dumbAware, parentDisposable);
enableEvents(AWTEvent.COMPONENT_EVENT_MASK);
contentPane = new JPanel(new BorderLayout());
installFocusTraversalPolicy(contentPane, new LayoutFocusTraversalPolicy());
contentPane.add(myHeader, BorderLayout.NORTH);
add(contentPane, BorderLayout.CENTER);
if (SystemInfo.isMac) {
setBackground(new JBColor(Gray._200, Gray._90));
}
setWindowInfo(info);
this.listener = listener;
}
@Override
public String toString() {
return myToolWindow.getId();
return toolWindow.getId();
}
public boolean isFocused() {
IdeFocusManager focusManager = myToolWindow.getToolWindowManager().getFocusManager();
Component component = focusManager.getFocusedDescendantFor(myToolWindow.getComponent());
IdeFocusManager focusManager = toolWindow.getToolWindowManager().getFocusManager();
Component component = focusManager.getFocusedDescendantFor(toolWindow.getComponent());
if (component != null) {
return true;
}
Component owner = focusManager.getLastFocusedFor(WindowManager.getInstance().getIdeFrame(myProject));
return owner != null && SwingUtilities.isDescendingFrom(owner, myToolWindow.getComponent());
Component owner = focusManager.getLastFocusedFor(WindowManager.getInstance().getIdeFrame(toolWindow.getToolWindowManager().getProject()));
return owner != null && SwingUtilities.isDescendingFrom(owner, toolWindow.getComponent());
}
/**
* Applies specified decoration.
*/
public final void apply(@NotNull WindowInfoImpl info) {
if (myInfo.equals(info) || myProject == null || myProject.isDisposed()) {
if (myInfo.equals(info) || toolWindow.getToolWindowManager().getProject().isDisposed()) {
return;
}
@@ -180,15 +180,15 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
}
}
myToolWindow.getContentUI().setType(myInfo.getContentUiType());
setBorder(new InnerPanelBorder(myToolWindow, myInfo));
toolWindow.getContentUI().setType(myInfo.getContentUiType());
setBorder(new InnerPanelBorder(toolWindow, myInfo));
}
@Nullable
@Override
public Object getData(@NotNull @NonNls String dataId) {
if (PlatformDataKeys.TOOL_WINDOW.is(dataId)) {
return myToolWindow;
return toolWindow;
}
return null;
}
@@ -197,54 +197,40 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
* Fires event that "hide" button has been pressed.
*/
final void fireHidden() {
listener.hidden(this);
toolWindow.getToolWindowManager().hideToolWindow(toolWindow.getId(), false);
}
/**
* Fires event that "hide" button has been pressed.
*/
final void fireHiddenSide() {
listener.hiddenSide(this);
toolWindow.getToolWindowManager().hideToolWindow(toolWindow.getId(), true);
}
/**
* Fires event that user performed click into the title bar area.
*/
final void fireActivated() {
listener.activated(this);
toolWindow.getToolWindowManager().activated(this);
}
final void fireResized() {
listener.resized(this);
toolWindow.getToolWindowManager().resized(this);
}
private void fireContentUiTypeChanges(@NotNull ToolWindowContentUiType type) {
listener.contentUiTypeChanges(this, type);
toolWindow.getToolWindowManager().setContentUiType(toolWindow.getId(), type);
}
private void fireVisibleOnPanelChanged(boolean visibleOnPanel) {
listener.visibleStripeButtonChanged(this, visibleOnPanel);
}
private void init(boolean dumbAware, @NotNull Disposable parentDisposable) {
enableEvents(AWTEvent.COMPONENT_EVENT_MASK);
JPanel contentPane = new JPanel(new BorderLayout());
installFocusTraversalPolicy(contentPane, new LayoutFocusTraversalPolicy());
contentPane.add(myHeader, BorderLayout.NORTH);
void addContentComponent(boolean dumbAware, @NotNull ContentManagerImpl contentManager) {
JPanel innerPanel = new JPanel(new BorderLayout());
JComponent toolWindowComponent = myToolWindow.getComponent();
JComponent toolWindowComponent = contentManager.getComponent();
if (!dumbAware) {
toolWindowComponent = DumbService.getInstance(myProject).wrapGently(toolWindowComponent, parentDisposable);
toolWindowComponent = DumbService.getInstance(toolWindow.getToolWindowManager().getProject()).wrapGently(toolWindowComponent, toolWindow.getDisposable());
}
innerPanel.add(toolWindowComponent, BorderLayout.CENTER);
contentPane.add(new NonOpaquePanel(innerPanel), BorderLayout.CENTER);
add(contentPane, BorderLayout.CENTER);
if (SystemInfo.isMac) {
setBackground(new JBColor(Gray._200, Gray._90));
}
}
@Override
@@ -252,7 +238,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
if (condition == WHEN_ANCESTOR_OF_FOCUSED_COMPONENT && pressed) {
Collection<KeyStroke> keyStrokes = KeymapUtil.getKeyStrokes(ActionManager.getInstance().getAction("FocusEditor").getShortcutSet());
if (keyStrokes.contains(ks)) {
myToolWindow.getToolWindowManager().activateEditorComponent();
toolWindow.getToolWindowManager().activateEditorComponent();
return true;
}
}
@@ -370,7 +356,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
@Nullable
@Override
protected String getHelpId(DataContext dataContext) {
Content content = myToolWindow.getContentManager().getSelectedContent();
Content content = toolWindow.getContentManager().getSelectedContent();
if (content != null) {
String helpId = content.getHelpId();
if (helpId != null) {
@@ -378,7 +364,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
}
}
String id = myToolWindow.getHelpId();
String id = toolWindow.getHelpId();
if (id != null) {
return id;
}
@@ -404,10 +390,10 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
return true;
}
};
resize.add(new ResizeToolWindowAction.Left(myToolWindow, this));
resize.add(new ResizeToolWindowAction.Right(myToolWindow, this));
resize.add(new ResizeToolWindowAction.Up(myToolWindow, this));
resize.add(new ResizeToolWindowAction.Down(myToolWindow, this));
resize.add(new ResizeToolWindowAction.Left(toolWindow, this));
resize.add(new ResizeToolWindowAction.Right(toolWindow, this));
resize.add(new ResizeToolWindowAction.Up(toolWindow, this));
resize.add(new ResizeToolWindowAction.Down(toolWindow, this));
resize.add(ActionManager.getInstance().getAction("MaximizeToolWindow"));
return resize;
}
@@ -468,7 +454,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
*/
@NotNull
final ToolWindowImpl getToolWindow() {
return myToolWindow;
return toolWindow;
}
/**
@@ -496,15 +482,10 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
}
void removeStripeButton() {
fireVisibleOnPanelChanged(false);
toolWindow.getToolWindowManager().setShowStripeButton(toolWindow.getId(), false);
fireHidden();
}
void showStripeButton() {
fireVisibleOnPanelChanged(true);
fireActivated();
}
private final class RemoveStripeButtonAction extends AnAction implements DumbAware {
RemoveStripeButtonAction() {
Presentation presentation = getTemplatePresentation();
@@ -524,26 +505,23 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
}
private final class HideAction extends AnAction implements DumbAware {
@NonNls static final String HIDE_ACTIVE_WINDOW_ACTION_ID = InternalDecorator.HIDE_ACTIVE_WINDOW_ACTION_ID;
HideAction() {
ActionUtil.copyFrom(this, HIDE_ACTIVE_WINDOW_ACTION_ID);
getTemplatePresentation().setText(UIBundle.message("tool.window.hide.action.name"));
}
@Override
public final void actionPerformed(@NotNull final AnActionEvent e) {
public void actionPerformed(@NotNull AnActionEvent e) {
fireHidden();
}
@Override
public final void update(@NotNull final AnActionEvent event) {
final Presentation presentation = event.getPresentation();
public void update(@NotNull final AnActionEvent event) {
Presentation presentation = event.getPresentation();
presentation.setEnabled(myInfo.isVisible());
}
}
private final class ToggleContentUiTypeAction extends ToggleAction implements DumbAware {
private boolean myHadSeveralContents;
@@ -553,7 +531,7 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
@Override
public void update(@NotNull AnActionEvent e) {
myHadSeveralContents = myHadSeveralContents || myToolWindow.getContentManager().getContentCount() > 1;
myHadSeveralContents = myHadSeveralContents || toolWindow.getContentManager().getContentCount() > 1;
super.update(e);
e.getPresentation().setVisible(myHadSeveralContents);
}
@@ -670,9 +648,9 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
@Override
public void putInfo(@NotNull Map<String, String> info) {
info.put("toolWindowTitle", myToolWindow.getTitle());
info.put("toolWindowTitle", toolWindow.getTitle());
final Content selection = myToolWindow.getContentManager().getSelectedContent();
final Content selection = toolWindow.getContentManager().getSelectedContent();
if (selection != null) {
info.put("toolWindowTab", selection.getTabName());
}
@@ -695,8 +673,8 @@ public final class InternalDecorator extends JPanel implements Queryable, DataPr
public String getAccessibleName() {
String name = super.getAccessibleName();
if (name == null) {
String title = StringUtil.defaultIfEmpty(myToolWindow.getTitle(), myToolWindow.getStripeTitle());
title = StringUtil.defaultIfEmpty(title, myToolWindow.getId());
String title = StringUtil.defaultIfEmpty(toolWindow.getTitle(), toolWindow.getStripeTitle());
title = StringUtil.defaultIfEmpty(title, toolWindow.getId());
name = StringUtil.notNullize(title) + " Tool Window";
}
return name;

View File

@@ -1,23 +1,7 @@
/*
* Copyright 2000-2009 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.
*/
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl;
import com.intellij.openapi.wm.ToolWindowAnchor;
import com.intellij.openapi.wm.ToolWindowContentUiType;
import com.intellij.openapi.wm.ToolWindowType;
import org.jetbrains.annotations.NotNull;
import java.util.EventListener;
@@ -26,11 +10,6 @@ import java.util.EventListener;
* @author Vladimir Kondratyev
*/
interface InternalDecoratorListener extends EventListener{
void anchorChanged(@NotNull InternalDecorator source, @NotNull ToolWindowAnchor anchor);
void autoHideChanged(@NotNull InternalDecorator source, boolean autoHide);
void hidden(@NotNull InternalDecorator source);
void hiddenSide(@NotNull InternalDecorator source);
@@ -39,10 +18,6 @@ interface InternalDecoratorListener extends EventListener{
void activated(@NotNull InternalDecorator source);
void typeChanged(@NotNull InternalDecorator source, @NotNull ToolWindowType type);
void sideStatusChanged(@NotNull InternalDecorator source, boolean isSideTool);
void contentUiTypeChanges(@NotNull InternalDecorator sources, @NotNull ToolWindowContentUiType type);
void visibleStripeButtonChanged(@NotNull InternalDecorator source, boolean visible);

View File

@@ -281,9 +281,9 @@ public final class StripeButton extends AnchoredButton implements ActionListener
updateState();
}
private void showPopup(final Component component, final int x, final int y) {
final ActionGroup group = myDecorator.createPopupGroup();
final ActionPopupMenu popupMenu = ActionManager.getInstance().createActionPopupMenu(ActionPlaces.TOOLWINDOW_POPUP, group);
private void showPopup(@Nullable Component component, int x, int y) {
ActionGroup group = myDecorator.createPopupGroup();
ActionPopupMenu popupMenu = ActionManager.getInstance().createActionPopupMenu(ActionPlaces.TOOLWINDOW_POPUP, group);
popupMenu.getComponent().show(component, x, y);
}

View File

@@ -6,7 +6,6 @@ import com.intellij.openapi.ui.popup.Balloon
internal data class ToolWindowEntry(val stripeButton: StripeButton,
val internalDecorator: InternalDecorator,
val watcher: ToolWindowManagerImpl.ToolWindowFocusWatcher,
val disposable: Disposable) {
var floatingDecorator: FloatingDecorator? = null
var windowedDecorator: WindowedDecorator? = null
@@ -14,4 +13,10 @@ internal data class ToolWindowEntry(val stripeButton: StripeButton,
val readOnlyWindowInfo: WindowInfoImpl
get() = internalDecorator.windowInfo
val toolWindow: ToolWindowImpl
get() = internalDecorator.toolWindow
val id: String
get() = toolWindow.id
}

View File

@@ -345,6 +345,7 @@ public final class ToolWindowHeadlessManagerImpl extends ToolWindowManagerEx {
public void installWatcher(ContentManager contentManager) {
}
@NotNull
@Override
public JComponent getComponent() {
return new JLabel();
@@ -355,6 +356,10 @@ public final class ToolWindowHeadlessManagerImpl extends ToolWindowManagerEx {
return myContentManager;
}
@Override
public void addContentManagerListener(@NotNull ContentManagerListener listener) {
}
@Override
public void setDefaultState(@Nullable final ToolWindowAnchor anchor,
@Nullable final ToolWindowType type,

View File

@@ -1,8 +1,6 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl
import com.intellij.ide.UiActivity
import com.intellij.ide.UiActivityMonitor
import com.intellij.ide.impl.ContentManagerWatcher
import com.intellij.notification.EventLog
import com.intellij.openapi.Disposable
@@ -11,71 +9,109 @@ import com.intellij.openapi.actionSystem.ActionManager
import com.intellij.openapi.actionSystem.AnAction
import com.intellij.openapi.actionSystem.impl.ActionManagerImpl
import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.application.ModalityState
import com.intellij.openapi.diagnostic.Logger
import com.intellij.openapi.diagnostic.logger
import com.intellij.openapi.util.ActionCallback
import com.intellij.openapi.util.BusyObject
import com.intellij.openapi.util.Disposer
import com.intellij.openapi.wm.*
import com.intellij.openapi.wm.ToolWindowAnchor
import com.intellij.openapi.wm.ToolWindowContentUiType
import com.intellij.openapi.wm.ToolWindowFactory
import com.intellij.openapi.wm.ToolWindowType
import com.intellij.openapi.wm.ex.ToolWindowEx
import com.intellij.openapi.wm.ex.WindowManagerEx
import com.intellij.openapi.wm.impl.commands.FinalizableCommand
import com.intellij.openapi.wm.impl.content.ToolWindowContentUi
import com.intellij.ui.LayeredIcon
import com.intellij.ui.content.ContentManager
import com.intellij.ui.content.ContentManagerListener
import com.intellij.ui.content.impl.ContentImpl
import com.intellij.ui.content.impl.ContentManagerImpl
import com.intellij.ui.scale.JBUIScale
import com.intellij.util.ObjectUtils
import com.intellij.util.ui.update.Activatable
import com.intellij.util.ui.update.UiNotifyConnector
import java.awt.Component
import java.awt.Rectangle
import java.awt.event.InputEvent
import java.util.*
import javax.swing.Icon
import javax.swing.JComponent
import javax.swing.JLabel
import javax.swing.LayoutFocusTraversalPolicy
import kotlin.math.abs
private val LOG = Logger.getInstance(ToolWindowImpl::class.java)
private val LOG = logger<ToolWindowImpl>()
class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManagerImpl,
val id: String,
canCloseContent: Boolean,
private val canCloseContent: Boolean,
component: JComponent?,
private val parentDisposable: Disposable) : ToolWindowEx {
private val component: JComponent
private var isAvailable = true
private val contentManager: ContentManager
private var icon: Icon? = null
internal var icon: Icon? = null
private var stripeTitle: String? = null
private val contentUi = ToolWindowContentUi(this)
private var decorator: InternalDecorator? = null
private var hideOnEmptyContent = false
var isPlaceholderMode = false
private var contentFactory: ToolWindowFactory? = null
private val pendingContentManagerListeners: List<ContentManagerListener>? = null
private val myShowing = object : BusyObject.Impl() {
override fun isReady() = component != null && component.isShowing
}
private var afterContentManagerCreation: ((ContentManagerImpl) -> Unit)? = null
internal var toolWindowFocusWatcher: ToolWindowManagerImpl.ToolWindowFocusWatcher? = null
private set
fun setAfterContentManagerCreation(value: (ContentManagerImpl) -> Unit) {
if (contentManager.isInitialized()) {
value(contentManager.value)
}
else {
afterContentManagerCreation = value
}
}
private val contentManager = lazy {
val contentManager = ContentManagerImpl(contentUi, canCloseContent, toolWindowManager.project, parentDisposable)
val contentComponent = contentManager.component
InternalDecorator.installFocusTraversalPolicy(contentComponent, LayoutFocusTraversalPolicy())
Disposer.register(parentDisposable, UiNotifyConnector(contentComponent, object : Activatable {
override fun showNotify() {
myShowing.onReady()
}
}))
afterContentManagerCreation?.invoke(contentManager)
toolWindowFocusWatcher = ToolWindowManagerImpl.ToolWindowFocusWatcher(this, contentManager.component)
// after init, as it was before contentManager creation was changed to be lazy
pendingContentManagerListeners?.let { list ->
for (listener in list) {
contentManager.addContentManagerListener(listener)
}
}
contentManager
}
private var helpId: String? = null
init {
contentManager = ContentManagerImpl(contentUi, canCloseContent, toolWindowManager.project, parentDisposable)
if (component != null) {
val content = ContentImpl(component, "", false)
val contentManager = contentManager.value
contentManager.addContent(content)
contentManager.setSelectedContent(content, false)
}
}
this.component = contentManager.component
InternalDecorator.installFocusTraversalPolicy(this.component, LayoutFocusTraversalPolicy())
Disposer.register(parentDisposable, UiNotifyConnector(this.component, object : Activatable {
override fun showNotify() {
myShowing.onReady()
}
}))
fun setFocusedComponent(component: Component) {
toolWindowFocusWatcher?.setFocusedComponentImpl(component)
}
fun getContentUI() = contentUi
@@ -95,14 +131,7 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
}
override fun activate(runnable: Runnable?, autoFocusContents: Boolean, forced: Boolean) {
ApplicationManager.getApplication().assertIsDispatchThread()
val activity = UiActivity.Focus("toolWindow:$id")
UiActivityMonitor.getInstance().addActivity(toolWindowManager.project, activity, ModalityState.NON_MODAL)
toolWindowManager.activateToolWindow(id, forced, autoFocusContents)
toolWindowManager.invokeLater(Runnable {
runnable?.run()
UiActivityMonitor.getInstance().removeActivity(toolWindowManager.project, activity)
})
toolWindowManager.activateToolWindow(id, runnable, autoFocusContents, forced)
}
override fun isActive(): Boolean {
@@ -125,20 +154,14 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
val result = ActionCallback()
myShowing.getReady(this)
.doWhenDone {
val cmd = ArrayList<FinalizableCommand>()
cmd.add(object : FinalizableCommand(null) {
override fun willChangeState(): Boolean {
return false
}
override fun run() {
IdeFocusManager.getInstance(toolWindowManager.project).doWhenFocusSettlesDown {
if (contentManager.isDisposed) return@doWhenFocusSettlesDown
contentManager.getReady(requestor).notify(result)
toolWindowManager.commandProcessor.execute(listOf(Runnable {
toolWindowManager.focusManager.doWhenFocusSettlesDown {
if (contentManager.isInitialized() && contentManager.value.isDisposed) {
return@doWhenFocusSettlesDown
}
contentManager.value.getReady(requestor).notify(result)
}
})
toolWindowManager.execute(cmd)
}))
}
return result
}
@@ -268,19 +291,36 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
* `ContentManager` class. Otherwise it delegates the functionality to the
* passed content manager.
*/
override fun isAvailable(): Boolean {
return isAvailable && component != null
override fun isAvailable() = isAvailable
override fun getComponent(): JComponent {
if (toolWindowManager.project.isDisposed) {
// nullable because of TeamCity plugin
return JLabel("Do not call getComponent() on dispose")
}
return contentManager.value.component
}
override fun getComponent() = component
fun getComponentIfInitialized(): JComponent? {
return if (contentManager.isInitialized()) contentManager.value.component else null
}
fun getContentManagerIfInitialized(): ContentManager? {
return if (contentManager.isInitialized()) contentManager.value else null
}
override fun getContentManager(): ContentManager {
ensureContentInitialized()
return contentManager
return contentManager.value
}
// to avoid ensureContentInitialized call - myContentManager can report canCloseContents without full initialization
fun canCloseContents() = contentManager.canCloseContents()
override fun addContentManagerListener(listener: ContentManagerListener) {
if (contentManager.isInitialized()) {
contentManager.value.addContentManagerListener(listener)
}
}
fun canCloseContents() = canCloseContent
override fun getIcon(): Icon? {
ApplicationManager.getApplication().assertIsDispatchThread()
@@ -289,7 +329,7 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
override fun getTitle(): String? {
ApplicationManager.getApplication().assertIsDispatchThread()
return contentManager.selectedContent?.displayName
return contentManager.value.selectedContent?.displayName
}
override fun getStripeTitle(): String {
@@ -313,7 +353,7 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
override fun setTitle(title: String) {
ApplicationManager.getApplication().assertIsDispatchThread()
val selected = contentManager.selectedContent
val selected = contentManager.value.selectedContent
if (selected != null) {
selected.displayName = title
}
@@ -361,11 +401,11 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
override fun isShowStripeButton() = toolWindowManager.isShowStripeButton(id)
override fun isDisposed() = contentManager.isDisposed
override fun isDisposed() = contentManager.isInitialized() && contentManager.value.isDisposed
fun setContentFactory(value: ToolWindowFactory) {
contentFactory = value
value.init(this)
fun setContentFactory(contentFactory: ToolWindowFactory) {
this.contentFactory = contentFactory
contentFactory.init(this)
}
fun ensureContentInitialized() {
@@ -373,7 +413,9 @@ class ToolWindowImpl internal constructor(val toolWindowManager: ToolWindowManag
if (currentContentFactory != null) {
// clear it first to avoid SOE
this.contentFactory = null
contentManager.removeAllContents(false)
if (contentManager.isInitialized()) {
contentManager.value.removeAllContents(false)
}
currentContentFactory.createToolWindowContent(toolWindowManager.project, this)
}
}

View File

@@ -59,7 +59,7 @@ public final class WindowManagerImpl extends WindowManagerEx implements Persiste
private final EventDispatcher<WindowManagerListener> myEventDispatcher = EventDispatcher.create(WindowManagerListener.class);
private final CommandProcessor myCommandProcessor = new CommandProcessor();
private final CommandProcessor myCommandProcessor = new CommandProcessor(() -> ApplicationManager.getApplication().isDisposed());
private final WindowWatcher myWindowWatcher = new WindowWatcher();
/**

View File

@@ -1,38 +0,0 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl.commands;
import com.intellij.openapi.wm.impl.InternalDecorator;
import com.intellij.openapi.wm.impl.StripeButton;
import com.intellij.openapi.wm.impl.WindowInfoImpl;
import org.jetbrains.annotations.NotNull;
/**
* Apply {@code info} to the corresponded tool button and decorator.
* Command uses freezed copy of passed {@code info} object.
*/
public final class ApplyWindowInfoCmd extends FinalizableCommand {
private final WindowInfoImpl myInfo;
private final StripeButton myButton;
private final InternalDecorator myDecorator;
public ApplyWindowInfoCmd(@NotNull WindowInfoImpl info,
@NotNull StripeButton button,
@NotNull InternalDecorator decorator,
@NotNull Runnable finishCallBack) {
super(finishCallBack);
myInfo = info.copy();
myButton = button;
myDecorator = decorator;
}
@Override
public final void run() {
try {
myButton.apply(myInfo);
myDecorator.apply(myInfo);
}
finally {
finish();
}
}
}

View File

@@ -1,32 +0,0 @@
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl.commands;
import org.jetbrains.annotations.Nullable;
import java.util.function.BooleanSupplier;
/**
* @author Vladimir Kondratyev
*/
public abstract class FinalizableCommand implements Runnable {
private final Runnable myFinishCallBack;
public FinalizableCommand(@Nullable Runnable finishCallBack) {
myFinishCallBack = finishCallBack;
}
public final void finish() {
if (myFinishCallBack != null) {
myFinishCallBack.run();
}
}
@Nullable
public BooleanSupplier getExpireCondition() {
return null;
}
public boolean willChangeState() {
return true;
}
}

View File

@@ -1,49 +0,0 @@
/*
* Copyright 2000-2009 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.openapi.wm.impl.commands;
import com.intellij.util.ui.EdtInvocationManager;
import org.jetbrains.annotations.NotNull;
/**
* @author Vladimir Kondratyev
*/
public final class InvokeLaterCmd extends FinalizableCommand{
private final Runnable myRunnable;
public InvokeLaterCmd(@NotNull Runnable runnable, @NotNull Runnable finishCallBack){
super(finishCallBack);
myRunnable=runnable;
}
@Override
public void run(){
EdtInvocationManager.getInstance().invokeLater(() -> {
try {
myRunnable.run();
}
finally {
finish();
}
});
}
@Override
public boolean willChangeState() {
return false;
}
}

View File

@@ -2,9 +2,7 @@
package com.intellij.openapi.wm.impl.commands;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.wm.FocusWatcher;
import com.intellij.openapi.wm.IdeFocusManager;
import com.intellij.openapi.wm.WindowManager;
import com.intellij.openapi.wm.impl.*;
import com.intellij.util.Alarm;
@@ -13,44 +11,48 @@ import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import java.awt.*;
import java.util.function.BooleanSupplier;
/**
* Requests focus for the specified tool window.
*
* @author Vladimir Kondratyev
*/
public final class RequestFocusInToolWindowCmd extends FinalizableCommand {
public final class RequestFocusInToolWindowCmd implements Runnable {
private static final Logger LOG = Logger.getInstance(RequestFocusInToolWindowCmd.class);
private final ToolWindowImpl myToolWindow;
private final FocusWatcher myFocusWatcher;
private final Project myProject;
public RequestFocusInToolWindowCmd(@NotNull ToolWindowImpl toolWindow, FocusWatcher focusWatcher, @NotNull Runnable finishCallBack, @NotNull Project project) {
super(finishCallBack);
public RequestFocusInToolWindowCmd(@NotNull ToolWindowImpl toolWindow) {
myToolWindow = toolWindow;
myFocusWatcher = focusWatcher;
myProject = project;
}
@Override
public void run() {
try {
if (!myProject.isDisposed()) {
requestFocus();
}
}
finally {
finish();
}
}
Alarm checkerAlarm = new Alarm(myToolWindow.getDisposable());
checkerAlarm.addRequest(new Runnable() {
final long startTime = System.currentTimeMillis();
@NotNull
@Override
public BooleanSupplier getExpireCondition() {
return () -> myProject.isDisposed();
@Override
public void run() {
if (System.currentTimeMillis() - startTime > 10000) {
LOG.debug(myToolWindow.getId(), " tool window - cannot wait for showing component");
return;
}
Component component = getShowingComponentToRequestFocus();
if (component == null) {
checkerAlarm.addRequest(this, 100);
}
else {
Component owner = KeyboardFocusManager.getCurrentKeyboardFocusManager().getPermanentFocusOwner();
ToolWindowManagerImpl manager = myToolWindow.getToolWindowManager();
if (owner != component) {
manager.getFocusManager().requestFocusInProject(component, manager.getProject());
bringOwnerToFront();
}
manager.getFocusManager().doWhenFocusSettlesDown(() -> updateToolWindow(component));
}
}
}, 0);
}
private void bringOwnerToFront() {
@@ -94,7 +96,7 @@ public final class RequestFocusInToolWindowCmd extends FinalizableCommand {
LOG.warn(myToolWindow.getId() + " tool window does not provide focus traversal policy");
return null;
}
Component component = IdeFocusManager.getInstance(myProject).getFocusTargetFor(container);
Component component = myToolWindow.getToolWindowManager().getFocusManager().getFocusTargetFor(container);
if (component == null || !component.isShowing()) {
LOG.debug(myToolWindow.getId(), " tool window - default component is hidden: ", container);
return null;
@@ -102,49 +104,20 @@ public final class RequestFocusInToolWindowCmd extends FinalizableCommand {
return component;
}
private void requestFocus() {
Alarm checkerAlarm = new Alarm(myProject);
checkerAlarm.addRequest(new Runnable() {
final long startTime = System.currentTimeMillis();
@Override
public void run() {
if (System.currentTimeMillis() - startTime > 10000) {
LOG.debug(myToolWindow.getId(), " tool window - cannot wait for showing component");
return;
}
Component c = getShowingComponentToRequestFocus();
if (c == null) {
checkerAlarm.addRequest(this, 100);
}
else {
Component owner = KeyboardFocusManager.getCurrentKeyboardFocusManager().getPermanentFocusOwner();
ToolWindowManagerImpl manager = myToolWindow.getToolWindowManager();
if (owner != c) {
manager.getFocusManager().requestFocusInProject(c, myProject);
bringOwnerToFront();
}
manager.getFocusManager().doWhenFocusSettlesDown(() -> updateToolWindow(c));
}
}
}, 0);
}
private void updateToolWindow(Component c) {
if (c.isFocusOwner()) {
myFocusWatcher.setFocusedComponentImpl(c);
private void updateToolWindow(@NotNull Component component) {
if (component.isFocusOwner()) {
myToolWindow.setFocusedComponent(component);
if (myToolWindow.isAvailable() && !myToolWindow.isActive()) {
myToolWindow.activate(null, true, false);
}
}
updateFocusedComponentForWatcher(c);
updateFocusedComponentForWatcher(component);
}
private static void updateFocusedComponentForWatcher(final Component c) {
final WindowWatcher watcher = ((WindowManagerImpl)WindowManager.getInstance()).getWindowWatcher();
final FocusWatcher focusWatcher = watcher.getFocusWatcherFor(c);
private static void updateFocusedComponentForWatcher(@NotNull Component c) {
WindowWatcher watcher = ((WindowManagerImpl)WindowManager.getInstance()).getWindowWatcher();
FocusWatcher focusWatcher = watcher.getFocusWatcherFor(c);
if (focusWatcher != null && c.isFocusOwner()) {
focusWatcher.setFocusedComponentImpl(c);
}
@@ -154,7 +127,7 @@ public final class RequestFocusInToolWindowCmd extends FinalizableCommand {
* @return first active window from hierarchy with specified roots. Returns {@code null}
* if there is no active window in the hierarchy.
*/
private static Window getActiveWindow(final Window[] windows) {
private static Window getActiveWindow(@NotNull Window[] windows) {
for (Window window : windows) {
if (window.isShowing() && window.isActive()) {
return window;

View File

@@ -1,4 +1,4 @@
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl.content;
import com.intellij.ide.ui.AntialiasingType;
@@ -8,11 +8,11 @@ import com.intellij.ui.EngravedTextGraphics;
import com.intellij.ui.JBColor;
import com.intellij.ui.OffsetIcon;
import com.intellij.ui.content.Content;
import com.intellij.ui.tabs.TabsUtil;
import com.intellij.util.ui.GraphicsUtil;
import com.intellij.util.ui.JBUI;
import com.intellij.util.ui.UIUtil;
import com.intellij.util.ui.WatermarkIcon;
import org.jetbrains.annotations.Nullable;
import javax.accessibility.AccessibleContext;
import javax.swing.*;
@@ -142,6 +142,7 @@ public class BaseLabel extends JLabel {
}
}
@Nullable
public Content getContent() {
return null;
}

View File

@@ -4,16 +4,14 @@ package com.intellij.openapi.wm.impl.content;
import com.intellij.openapi.ui.popup.ListPopup;
import com.intellij.ui.ColorUtil;
import com.intellij.ui.awt.RelativePoint;
import com.intellij.ui.awt.RelativeRectangle;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.ContentManager;
import com.intellij.ui.content.ContentManagerEvent;
import com.intellij.util.ui.JBUI;
import com.intellij.util.ui.UIUtil;
import java.awt.*;
class ComboContentLayout extends ContentLayout {
final class ComboContentLayout extends ContentLayout {
ContentComboLabel myComboLabel;
ComboContentLayout(ToolWindowContentUi ui) {
@@ -93,7 +91,8 @@ class ComboContentLayout extends ContentLayout {
}
boolean isToDrawCombo() {
return myUi.myManager.getContentCount() > 1;
ContentManager manager = myUi.myManager;
return manager != null && manager.getContentCount() > 1;
}
@Override
@@ -111,16 +110,6 @@ class ComboContentLayout extends ContentLayout {
listPopup.show(new RelativePoint(myComboLabel, new Point(0, myComboLabel.getHeight())));
}
@Override
public RelativeRectangle getRectangleFor(Content content) {
return null;
}
@Override
public Component getComponentFor(Content content) {
return null;
}
@Override
public String getCloseActionName() {
return "Close View";

View File

@@ -1,18 +1,4 @@
/*
* Copyright 2000-2013 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.
*/
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl.content;
import com.intellij.ui.Gray;
@@ -20,6 +6,7 @@ import com.intellij.ui.content.Content;
import com.intellij.util.ui.JBUI;
import com.intellij.util.ui.UIUtil;
import com.intellij.util.ui.accessibility.ScreenReader;
import org.jetbrains.annotations.Nullable;
import javax.accessibility.AccessibleAction;
import javax.accessibility.AccessibleContext;
@@ -118,9 +105,10 @@ public class ContentComboLabel extends BaseLabel {
}
}
@Nullable
@Override
public Content getContent() {
return myUi.myManager.getSelectedContent();
return myUi.myManager == null ? null : myUi.myManager.getSelectedContent();
}
@Override

View File

@@ -2,36 +2,23 @@
package com.intellij.openapi.wm.impl.content;
import com.intellij.openapi.ui.popup.ListPopup;
import com.intellij.ui.Gray;
import com.intellij.ui.awt.RelativeRectangle;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.ContentManager;
import com.intellij.ui.content.ContentManagerEvent;
import com.intellij.util.ui.JBUI;
import com.intellij.util.ui.UIUtil;
import org.jetbrains.annotations.Nls;
import org.jetbrains.annotations.NotNull;
import javax.swing.*;
import java.awt.*;
abstract class ContentLayout {
static final Color TAB_BORDER_ACTIVE_WINDOW = new Color(38, 63, 106);
static final Color TAB_BORDER_PASSIVE_WINDOW = new Color(130, 120, 111);
static final Color TAB_BG_ACTIVE_WND_SELECTED_FROM = Gray._111;
static final Color TAB_BG_ACTIVE_WND_SELECTED_TO = Gray._164;
static final Color TAB_BG_ACTIVE_WND_UNSELECTED_FROM = Gray._130;
static final Color TAB_BG_ACTIVE_WND_UNSELECTED_TO = Gray._85;
static final Color TAB_BG_PASSIVE_WND_FROM = new Color(152, 143, 134);
static final Color TAB_BG_PASSIVE_WND_TO = new Color(165, 157, 149);
static final int TAB_ARC = 2;
static final int TAB_SHIFT = 2;
ToolWindowContentUi myUi;
BaseLabel myIdLabel;
ContentLayout(ToolWindowContentUi ui) {
ContentLayout(@NotNull ToolWindowContentUi ui) {
myUi = ui;
}
@@ -67,15 +54,16 @@ abstract class ContentLayout {
}
private String getTitleSuffix() {
switch (myUi.myManager.getContentCount()) {
ContentManager manager = myUi.myManager;
switch (manager == null ? 0 : manager.getContentCount()) {
case 0:
return null;
case 1:
Content content = myUi.myManager.getContent(0);
Content content = manager.getContent(0);
if (content == null) return null;
final String text = content.getDisplayName();
if (text != null && text.trim().length() > 0 && myUi.myManager.canCloseContents()) {
if (text != null && text.trim().length() > 0 && manager.canCloseContents()) {
return ":";
}
return null;
@@ -84,30 +72,8 @@ abstract class ContentLayout {
}
}
protected void fillTabShape(Graphics2D g2d, Shape shape, boolean isSelected, Rectangle bounds) {
if (myUi.myWindow.isActive()) {
if (isSelected) {
g2d.setPaint(UIUtil.getGradientPaint(bounds.x, bounds.y, TAB_BG_ACTIVE_WND_SELECTED_FROM, bounds.x, (float)bounds.getMaxY(),
TAB_BG_ACTIVE_WND_SELECTED_TO));
}
else {
g2d.setPaint(UIUtil.getGradientPaint(bounds.x, bounds.y, TAB_BG_ACTIVE_WND_UNSELECTED_FROM, bounds.x, (float)bounds.getMaxY(), TAB_BG_ACTIVE_WND_UNSELECTED_TO));
}
}
else {
g2d.setPaint(
UIUtil.getGradientPaint(bounds.x, bounds.y, TAB_BG_PASSIVE_WND_FROM, bounds.x, (float)bounds.getMaxY(), TAB_BG_PASSIVE_WND_TO));
}
g2d.fill(shape);
}
public abstract void showContentPopup(ListPopup listPopup);
public abstract RelativeRectangle getRectangleFor(Content content);
public abstract Component getComponentFor(Content content);
@Nls(capitalization = Nls.Capitalization.Title)
public abstract String getCloseActionName();
@@ -121,7 +87,7 @@ abstract class ContentLayout {
public abstract String getNextContentActionName();
protected boolean shouldShowId() {
final JComponent component = myUi.myWindow.getComponent();
JComponent component = myUi.myWindow.getComponentIfInitialized();
return component != null && !"true".equals(component.getClientProperty(ToolWindowContentUi.HIDE_ID_LABEL));
}

View File

@@ -23,6 +23,7 @@ import com.intellij.util.ui.TimedDeadzone;
import com.intellij.util.ui.UIUtilities;
import gnu.trove.THashMap;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import javax.swing.*;
import javax.swing.border.EmptyBorder;
@@ -69,7 +70,12 @@ class ContentTabLabel extends BaseLabel {
@NotNull
@Override
public Runnable getAction() {
return () -> contentManager().removeContent(getContent(), true);
return () -> {
ContentManager contentManager = myUi.myWindow.getContentManagerIfInitialized();
if (contentManager != null) {
contentManager.removeContent(getContent(), true);
}
};
}
@Override
@@ -238,9 +244,9 @@ class ContentTabLabel extends BaseLabel {
}
protected void selectContent() {
final ContentManager mgr = contentManager();
if (mgr.getIndexOfContent(myContent) >= 0) {
mgr.setSelectedContent(myContent, true);
ContentManager manager = getContentManager();
if (manager.getIndexOfContent(myContent) >= 0) {
manager.setSelectedContent(myContent, true);
}
}
@@ -253,7 +259,6 @@ class ContentTabLabel extends BaseLabel {
updateTextAndIcon(myContent, isSelected());
}
@Override
public Dimension getPreferredSize() {
final Dimension size = super.getPreferredSize();
@@ -302,7 +307,8 @@ class ContentTabLabel extends BaseLabel {
@Override
protected Color getActiveFg(boolean selected) {
if (contentManager().getContentCount() > 1) {
ContentManager contentManager = myUi.myWindow.getContentManagerIfInitialized();
if (contentManager != null && contentManager.getContentCount() > 1) {
return selected ? JBUI.CurrentTheme.ToolWindow.underlinedTabForeground() : JBUI.CurrentTheme.Label.foreground(false);
}
@@ -311,14 +317,15 @@ class ContentTabLabel extends BaseLabel {
@Override
protected Color getPassiveFg(boolean selected) {
if (contentManager().getContentCount() > 1) {
ContentManager contentManager = myUi.myWindow.getContentManagerIfInitialized();
if (contentManager != null && contentManager.getContentCount() > 1) {
return selected ? JBUI.CurrentTheme.ToolWindow.underlinedTabInactiveForeground() : JBUI.CurrentTheme.Label.foreground(false);
}
return super.getPassiveFg(selected);
}
private void paintIcons(final Graphics g) {
private void paintIcons(@NotNull Graphics g) {
for (AdditionalIcon icon : myAdditionalIcons) {
if (icon.getAvailable()) {
icon.paintIcon(this, g);
@@ -327,13 +334,14 @@ class ContentTabLabel extends BaseLabel {
}
@Override
protected void paintComponent(final Graphics g) {
protected void paintComponent(@NotNull Graphics g) {
super.paintComponent(g);
paintIcons(g);
}
public boolean isSelected() {
return contentManager().isSelected(myContent);
ContentManager contentManager = myUi.myWindow.getContentManagerIfInitialized();
return contentManager != null && contentManager.isSelected(myContent);
}
public boolean isHovered() {
@@ -342,18 +350,18 @@ class ContentTabLabel extends BaseLabel {
@Override
protected Graphics _getGraphics(Graphics2D g) {
if (isSelected() && contentManager().getContentCount() > 1) {
if (isSelected() && getContentManager().getContentCount() > 1) {
return new EngravedTextGraphics(g, 1, 1, Gray._0.withAlpha(myUi.myWindow.isActive() ? 120 : 130));
}
return super._getGraphics(g);
}
private ContentManager contentManager() {
@NotNull
private ContentManager getContentManager() {
return myUi.myWindow.getContentManager();
}
@NotNull
@Nullable
@Override
public Content getContent() {
return myContent;

View File

@@ -9,7 +9,6 @@ import com.intellij.openapi.ui.popup.ListPopup;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.ui.UIBundle;
import com.intellij.ui.awt.RelativePoint;
import com.intellij.ui.awt.RelativeRectangle;
import com.intellij.ui.content.Content;
import com.intellij.ui.content.ContentManager;
import com.intellij.ui.content.ContentManagerEvent;
@@ -371,17 +370,6 @@ class TabContentLayout extends ContentLayout {
}
}
@Override
public RelativeRectangle getRectangleFor(Content content) {
ContentTabLabel label = myContent2Tabs.get(content);
return new RelativeRectangle(label.getParent(), label.getBounds());
}
@Override
public Component getComponentFor(Content content) {
return myContent2Tabs.get(content);
}
@Override
public String getCloseActionName() {
return UIBundle.message("tabbed.pane.close.tab.action.name");

View File

@@ -1,4 +1,4 @@
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.openapi.wm.impl.content;
import com.intellij.ide.IdeEventQueue;
@@ -99,7 +99,7 @@ public class TabbedContentTabLabel extends ContentTabLabel {
}
}
@NotNull
@Nullable
@Override
public TabbedContent getContent() {
return myContent;

View File

@@ -69,7 +69,7 @@ public final class ToolWindowContentUi extends JPanel implements ContentUI, Prop
public Predicate<Point> isResizableArea = p -> true;
public ToolWindowContentUi(ToolWindowImpl window) {
public ToolWindowContentUi(@NotNull ToolWindowImpl window) {
myWindow = window;
myContent.setOpaque(false);
myContent.setFocusable(false);
@@ -79,30 +79,29 @@ public final class ToolWindowContentUi extends JPanel implements ContentUI, Prop
// InternalDecorator adds myContent right after "this" (via ToolWindowHeader)
// also myContent is never removed (can be invisible due to DumbAwareHider)
UIUtil.putClientProperty(
myContent, UIUtil.NOT_IN_HIERARCHY_COMPONENTS, new Iterable<JComponent>() {
@Override
public Iterator<JComponent> iterator() {
if (myManager == null || myManager.getContentCount() == 0) {
return Collections.emptyIterator();
}
return JBIterable.of(myManager.getContents())
.map(content -> {
JComponent last = null;
for (Component c : UIUtil.uiParents(content.getComponent(), false)) {
if (c == myManager.getComponent() || !(c instanceof JComponent)) return null;
last = (JComponent)c;
}
return last;
})
.filter(Conditions.notNull())
.iterator();
UIUtil.putClientProperty(myContent, UIUtil.NOT_IN_HIERARCHY_COMPONENTS, new Iterable<JComponent>() {
@Override
public Iterator<JComponent> iterator() {
if (myManager == null || myManager.getContentCount() == 0) {
return Collections.emptyIterator();
}
});
return JBIterable.of(myManager.getContents())
.map(content -> {
JComponent last = null;
for (Component c : UIUtil.uiParents(content.getComponent(), false)) {
if (c == myManager.getComponent() || !(c instanceof JComponent)) return null;
last = (JComponent)c;
}
return last;
})
.filter(Conditions.notNull())
.iterator();
}
});
ApplicationManager.getApplication().getMessageBus().connect(this).subscribe(UISettingsListener.TOPIC, uiSettings -> {
revalidate();
repaint();
ApplicationManager.getApplication().getMessageBus().connect(window.getDisposable()).subscribe(UISettingsListener.TOPIC, uiSettings -> {
revalidate();
repaint();
});
}
@@ -149,7 +148,6 @@ public final class ToolWindowContentUi extends JPanel implements ContentUI, Prop
}
private ContentLayout getCurrentLayout() {
assert myManager != null;
return myType == ToolWindowContentUiType.TABBED ? myTabsLayout : myComboLayout;
}
@@ -239,7 +237,7 @@ public final class ToolWindowContentUi extends JPanel implements ContentUI, Prop
revalidate();
repaint();
if (myManager.getContentCount() == 0 && myWindow.isToHideOnEmptyContent()) {
if (myManager != null && myManager.getContentCount() == 0 && myWindow.isToHideOnEmptyContent()) {
myWindow.hide(null);
}
}
@@ -648,11 +646,6 @@ public final class ToolWindowContentUi extends JPanel implements ContentUI, Prop
}
}
@Override
public void dispose() {
myContent.removeAll();
}
boolean isCurrent(ContentLayout layout) {
return getCurrentLayout() == layout;
}

View File

@@ -342,7 +342,4 @@ public final class TabbedPaneContentUI implements ContentUI, PropertyChangeListe
return "Select Next Tab";
}
@Override
public void dispose() {
}
}

View File

@@ -70,7 +70,9 @@ public class ContentManagerImpl implements ContentManager, PropertyChangeListene
// for which com.intellij.psi.impl.smartPointers.SelfElementInfo.restoreFileFromVirtual() must be able to work
// for which the findFile() must access fileManager for which it must be alive
Disposer.register(parentDisposable, this);
Disposer.register(this, contentUI);
if (contentUI instanceof Disposable) {
Disposer.register(this, (Disposable)contentUI);
}
}
@Override
@@ -548,7 +550,6 @@ public class ContentManagerImpl implements ContentManager, PropertyChangeListene
myDispatcher.removeListener(l);
}
private void fireContentAdded(@NotNull Content content, int newIndex) {
ContentManagerEvent e = new ContentManagerEvent(this, content, newIndex, ContentManagerEvent.ContentOperation.add);
myDispatcher.getMulticaster().contentAdded(e);

View File

@@ -63,7 +63,7 @@ final class ProjectData {
ToolWindowData toolWindowData = new ToolWindowData(toolWindow, id);
myToolWindows.put(toolWindow, toolWindowData);
// System.out.println("register tool-window: " + id);
toolWindow.getContentManager().addContentManagerListener(toolWindowData);
toolWindow.addContentManagerListener(toolWindowData);
}
@Override

View File

@@ -152,8 +152,7 @@ public final class IconLoader {
@NotNull
public static Icon getIcon(@NonNls @NotNull final String path) {
Class callerClass = ReflectionUtil.getGrandCallerClass();
Class<?> callerClass = ReflectionUtil.getGrandCallerClass();
assert callerClass != null : path;
return getIcon(path, callerClass);
}