blob: 713a8d85448c49137af996ee2d5e10d96a802be2 [file] [log] [blame]
/*
* Copyright 2000-2012 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.ui.tabs;
import com.intellij.ui.FileColorManager;
import com.intellij.ui.table.JBTable;
import com.intellij.util.ui.EditableModel;
import com.intellij.util.ui.EmptyIcon;
import com.intellij.util.ui.UIUtil;
import org.jetbrains.annotations.NotNull;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.table.AbstractTableModel;
import javax.swing.table.TableCellRenderer;
import javax.swing.table.TableColumn;
import javax.swing.table.TableColumnModel;
import java.awt.*;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.EventObject;
import java.util.List;
/**
* @author spleaner
* @author Konstantin Bulenkov
*/
public abstract class FileColorSettingsTable extends JBTable {
private static final int NAME_COLUMN = 0;
private static final int COLOR_COLUMN = 1;
private final List<FileColorConfiguration> myOriginal;
@NotNull private final FileColorManager myManager;
public FileColorSettingsTable(@NotNull final FileColorManager manager, @NotNull final List<FileColorConfiguration> configurations) {
super(new ModelAdapter(manager, copy(configurations)));
myManager = manager;
setStriped(true);
myOriginal = configurations;
setAutoResizeMode(AUTO_RESIZE_LAST_COLUMN);
final TableColumnModel columnModel = getColumnModel();
final TableColumn nameColumn = columnModel.getColumn(NAME_COLUMN);
nameColumn.setCellRenderer(new ScopeNameRenderer());
final TableColumn colorColumn = columnModel.getColumn(COLOR_COLUMN);
colorColumn.setCellRenderer(new ColorCellRenderer(manager));
}
private static List<FileColorConfiguration> copy(@NotNull final List<FileColorConfiguration> configurations) {
final List<FileColorConfiguration> result = new ArrayList<FileColorConfiguration>();
for (FileColorConfiguration c : configurations) {
try {
result.add(c.clone());
}
catch (CloneNotSupportedException e) {
assert false : "Should not happen!";
}
}
return result;
}
protected abstract void apply(@NotNull final List<FileColorConfiguration> configurations);
@Override
public ModelAdapter getModel() {
return (ModelAdapter) super.getModel();
}
@Override
public boolean editCellAt(int row, int column, EventObject e) {
if (e == null || (e instanceof MouseEvent && ((MouseEvent)e).getClickCount() == 1)) return false;
final Object at = getModel().getValueAt(row, column);
final FileColorConfigurationEditDialog dialog = new FileColorConfigurationEditDialog(myManager, ((FileColorConfiguration)at));
dialog.getScopeComboBox().setEnabled(false);
dialog.show();
return false;
}
public boolean isModified() {
final List<FileColorConfiguration> current = getModel().getConfigurations();
if (myOriginal.size() != current.size()) {
return true;
}
for (int i = 0; i < current.size(); i++) {
if (!myOriginal.get(i).equals(current.get(i))) {
return true;
}
}
return false;
}
public void reset() {
getModel().setConfigurations(myOriginal);
}
public void performRemove() {
final int rowCount = getSelectedRowCount();
if (rowCount > 0) {
final int[] rows = getSelectedRows();
for (int i = rows.length - 1; i >= 0; i--) {
removeConfiguration(rows[i]);
}
}
}
public void moveUp() {
final int rowCount = getSelectedRowCount();
if (rowCount == 1) {
final int index = getModel().moveUp(getSelectedRows()[0]);
if (index > -1) {
getSelectionModel().setSelectionInterval(index, index);
}
}
}
public void moveDown() {
final int rowCount = getSelectedRowCount();
if (rowCount == 1) {
final int index = getModel().moveDown(getSelectedRows()[0]);
if (index > -1) {
getSelectionModel().setSelectionInterval(index, index);
}
}
}
public void apply() {
if (isModified()) {
apply(getModel().getConfigurations());
}
}
public FileColorConfiguration removeConfiguration(final int index) {
final FileColorConfiguration removed = getModel().remove(index);
final int rowCount = getRowCount();
if (rowCount > 0) {
if (index > rowCount - 1) {
getSelectionModel().setSelectionInterval(rowCount - 1, rowCount - 1);
} else {
getSelectionModel().setSelectionInterval(index, index);
}
}
return removed;
}
public void addConfiguration(@NotNull final FileColorConfiguration configuration) {
getModel().add(configuration);
}
private static class ModelAdapter extends AbstractTableModel implements EditableModel {
private final FileColorManager myManager;
private List<FileColorConfiguration> myConfigurations;
private ModelAdapter(FileColorManager manager, final List<FileColorConfiguration> configurations) {
myManager = manager;
myConfigurations = configurations;
}
@Override
public String getColumnName(int column) {
return column == NAME_COLUMN ? "Scope" : "Color";
}
@Override
public int getRowCount() {
return myConfigurations.size();
}
@Override
public int getColumnCount() {
return 2;
}
@Override
public Object getValueAt(int rowIndex, int columnIndex) {
return myConfigurations.get(rowIndex);
}
@NotNull
public List<FileColorConfiguration> getConfigurations() {
return myConfigurations;
}
public FileColorConfiguration remove(int index) {
final FileColorConfiguration removed = myConfigurations.remove(index);
fireTableRowsDeleted(index, index);
return removed;
}
public void add(@NotNull final FileColorConfiguration configuration) {
myConfigurations.add(configuration);
fireTableRowsInserted(myConfigurations.size() - 1, myConfigurations.size() - 1);
}
public void setConfigurations(List<FileColorConfiguration> original) {
myConfigurations = copy(original);
fireTableDataChanged();
}
public int moveUp(int index) {
if (index > 0) {
final FileColorConfiguration configuration = myConfigurations.get(index);
myConfigurations.remove(index);
myConfigurations.add(index - 1, configuration);
fireTableRowsUpdated(index - 1, index);
return index - 1;
}
return -1;
}
public int moveDown(int index) {
if (index < getRowCount() - 1) {
final FileColorConfiguration configuration = myConfigurations.get(index);
myConfigurations.remove(index);
myConfigurations.add(index + 1, configuration);
fireTableRowsUpdated(index, index + 1);
return index + 1;
}
return -1;
}
@Override
public void addRow() {
final FileColorConfigurationEditDialog dialog = new FileColorConfigurationEditDialog((FileColorManagerImpl)myManager, null);
dialog.show();
if (dialog.getExitCode() == 0) {
myConfigurations.add(dialog.getConfiguration());
}
}
@Override
public void removeRow(int index) {
myConfigurations.remove(index);
}
@Override
public void exchangeRows(int oldIndex, int newIndex) {
myConfigurations.add(newIndex, myConfigurations.remove(oldIndex));
fireTableRowsUpdated(Math.min(oldIndex, newIndex), Math.max(oldIndex, newIndex));
}
@Override
public boolean canExchangeRows(int oldIndex, int newIndex) {
return true;
}
}
private static class ScopeNameRenderer extends JLabel implements TableCellRenderer {
private static final Border NO_FOCUS_BORDER = BorderFactory.createEmptyBorder(1, 1, 1, 1);
private ScopeNameRenderer() {
setOpaque(true);
}
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
if (!(value instanceof FileColorConfiguration)) {
return this;
}
preinit(table, isSelected, hasFocus);
final FileColorConfiguration configuration = (FileColorConfiguration)value;
setText(FileColorManagerImpl.getAlias(configuration.getScopeName()));
return this;
}
protected void preinit(JTable table, boolean isSelected, boolean hasFocus) {
setBackground(isSelected ? table.getSelectionBackground() : table.getBackground());
setForeground(isSelected ? table.getSelectionForeground() : table.getForeground());
setBorder(hasFocus ? UIUtil.getTableFocusCellHighlightBorder()
: NO_FOCUS_BORDER);
}
}
private static class ColorCellRenderer extends ScopeNameRenderer {
private Color myColor;
private final FileColorManager myManager;
private ColorCellRenderer(final FileColorManager manager) {
setOpaque(true);
myManager = manager;
setIcon(EmptyIcon.ICON_16);
}
private void setIconColor(final Color color) {
myColor = color;
}
@Override
public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
if (!(value instanceof FileColorConfiguration)) {
return this;
}
preinit(table, isSelected, hasFocus);
final FileColorConfiguration configuration = (FileColorConfiguration)value;
setIconColor(myManager.getColor(configuration.getColorName()));
setText(FileColorManagerImpl.getAlias(configuration.getColorPresentableName()));
return this;
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
if (myColor != null) {
final Icon icon = getIcon();
final int width = icon.getIconWidth();
final int height = icon.getIconHeight();
final Color old = g.getColor();
g.setColor(myColor);
g.fillRect(0, 0, width, height);
g.setColor(old);
}
}
}
}