import java.awt.Container;\r
import java.awt.Cursor;\r
import java.awt.Dimension;\r
+import java.awt.Font;\r
import java.awt.GridBagConstraints;\r
import java.awt.GridBagLayout;\r
import java.awt.GridLayout;\r
import java.io.StringWriter;\r
import java.net.URI;\r
import java.text.MessageFormat;\r
+import java.util.ArrayList;\r
import java.util.Collection;\r
+import java.util.Collections;\r
import java.util.List;\r
import java.util.Map;\r
import java.util.Properties;\r
import javax.swing.Box;\r
import javax.swing.BoxLayout;\r
import javax.swing.ButtonGroup;\r
-import javax.swing.DefaultListCellRenderer;\r
-import javax.swing.DefaultListModel;\r
import javax.swing.InputMap;\r
import javax.swing.JButton;\r
import javax.swing.JCheckBox;\r
import javax.swing.JRadioButton;\r
import javax.swing.JRootPane;\r
import javax.swing.JScrollPane;\r
+import javax.swing.JTable;\r
import javax.swing.JTextArea;\r
import javax.swing.KeyStroke;\r
import javax.swing.ListCellRenderer;\r
import javax.swing.UIManager;\r
import javax.swing.event.ListSelectionEvent;\r
import javax.swing.event.ListSelectionListener;\r
+import javax.swing.table.AbstractTableModel;\r
+import javax.swing.table.TableCellRenderer;\r
+import javax.swing.table.TableColumnModel;\r
\r
import charactermanaj.Main;\r
import charactermanaj.clipboardSupport.ClipboardUtil;\r
/**\r
* プロファイル一覧を表示するリストコンポーネント\r
*/\r
- private JList characterList;\r
+ private JTable characterList;\r
\r
/**\r
* プロファイル一覧のリストモデル\r
*/\r
- private DefaultListModel characterListModel;\r
+ private ProfileSelectorTableModel characterListModel;\r
\r
/**\r
* プロファイルの説明用テキストエリア\r
\r
JPanel pnlProfiles = new JPanel(new BorderLayout());\r
\r
- characterListModel = new DefaultListModel();\r
- for (CharacterData characterData : characterDatas) {\r
- characterListModel.addElement(characterData);\r
- }\r
+ characterListModel = new ProfileSelectorTableModel();\r
+ characterListModel.setModel(characterDatas);\r
\r
- characterList = new JList(characterListModel);\r
- characterList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\r
- characterList.setCellRenderer(new DefaultListCellRenderer() {\r
+ characterList = new JTable(characterListModel) {\r
private static final long serialVersionUID = 1L;\r
+\r
@Override\r
- public Component getListCellRendererComponent(JList list,\r
- Object value, int index, boolean isSelected,\r
- boolean cellHasFocus) {\r
- CharacterData characterData = (CharacterData) value;\r
- StringBuilder displayNameBuf = new StringBuilder();\r
- displayNameBuf.append(characterData.getName());\r
- if (ProfileListManager.isUsingCharacterData(characterData)) {\r
- displayNameBuf.append(strings.getProperty("profile.opend"));\r
+ public Component prepareRenderer(TableCellRenderer renderer,\r
+ int row, int column) {\r
+\r
+ CharacterData cd = characterListModel.getRow(row);\r
+\r
+ Component comp = super.prepareRenderer(renderer, row, column);\r
+ if (ProfileListManager.isUsingCharacterData(cd)) {\r
+ // 使用中のものは太字で表示\r
+ Font f = comp.getFont();\r
+ comp.setFont(f.deriveFont(Font.BOLD));\r
}\r
- if (!characterData.canWrite()) {\r
- displayNameBuf.append(strings.getProperty("profile.noteditable"));\r
+\r
+ if (!cd.canWrite()) {\r
+ // 書き込み不可のものはイタリックで表示\r
+ Font f = comp.getFont();\r
+ comp.setFont(f.deriveFont(Font.ITALIC));\r
}\r
- return super.getListCellRendererComponent(list, displayNameBuf\r
- .toString(), index, isSelected, cellHasFocus);\r
+ return comp;\r
}\r
- });\r
- characterList.addListSelectionListener(new ListSelectionListener() {\r
+ };\r
+ characterList.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);\r
+ characterList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\r
+\r
+ characterListModel.adjustColumnModel(characterList.getColumnModel());\r
+\r
+ characterList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\r
+ characterList.getSelectionModel().addListSelectionListener(\r
+ new ListSelectionListener() {\r
public void valueChanged(ListSelectionEvent e) {\r
if (!e.getValueIsAdjusting()) {\r
updateUIState();\r
\r
JScrollPane characterListSP = new JScrollPane(characterList);\r
characterListSP.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);\r
+ characterListSP\r
+ .setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);\r
pnlProfiles.add(characterListSP, BorderLayout.CENTER);\r
\r
actProfileNew = new AbstractAction(strings.getProperty("profile.new")) {\r
* キャラクターデータの選択変更に伴い、ボタンやサンプルピクチャなどを切り替える.\r
*/\r
protected void updateUIState() {\r
- CharacterData characterData = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData characterData = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ characterData = characterListModel.getRow(selRow);\r
+ }\r
\r
final Properties strings = LocalizedResourcePropertyLoader\r
.getInstance().getLocalizedProperties(STRINGS_RESOURCE);\r
* サンプルピクチャのファイルを削除し、表示されている画像をクリップボードに保存する\r
*/\r
protected void onSamplePictureCut() {\r
- CharacterData characterData = (CharacterData) characterList.getSelectedValue();\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow < 0) {\r
+ return;\r
+ }\r
+ CharacterData characterData = characterListModel.getRow(selRow);\r
+\r
BufferedImage img = sampleImgPanel.getSamplePictrue();\r
\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
* サンプルピクチャをクリップボードから貼り付け、それをファイルに保存する\r
*/\r
protected void onSamplePicturePaste() {\r
- CharacterData characterData = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData characterData = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ characterData = characterListModel.getRow(selRow);\r
+ }\r
+\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
if (characterData == null || !characterData.isValid() || !canWriteSamplePicture) {\r
tk.beep();\r
* ドロップイベント\r
*/\r
protected void onDrop(Collection<File> dropFiles) {\r
+ CharacterData characterData = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ characterData = characterListModel.getRow(selRow);;\r
+ }\r
+\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
- CharacterData characterData = (CharacterData) characterList.getSelectedValue();\r
if (dropFiles == null || dropFiles.isEmpty()\r
|| !canWriteSamplePicture || characterData == null\r
|| !characterData.isValid() || !canWriteSamplePicture) {\r
* OKボタン押下\r
*/\r
protected void onOK() {\r
- selectedCharacterData = (CharacterData) characterList.getSelectedValue();\r
+ selectedCharacterData = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ selectedCharacterData = characterListModel.getRow(selRow);\r
+ }\r
if (selectedCharacterData == null) {\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
tk.beep();\r
* デフォルトのプロファイルで作成する場合\r
*/\r
protected void onProfileNew(boolean makeDefault) {\r
- CharacterDataPersistent persist = CharacterDataPersistent.getInstance();\r
+ CharacterData cd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ cd = characterListModel.getRow(selRow);\r
+ }\r
\r
- CharacterData cd = (CharacterData) characterList.getSelectedValue();\r
+ CharacterDataPersistent persist = CharacterDataPersistent.getInstance();\r
\r
if (makeDefault || cd == null) {\r
try {\r
}\r
\r
// 作成されたプロファイルを一覧に追加する.\r
- characterListModel.addElement(newCd);\r
+ characterListModel.add(newCd);\r
}\r
\r
/**\r
* プロファィルの編集\r
*/\r
protected void onProfileEdit() {\r
- CharacterData cd = (CharacterData) characterList.getSelectedValue();\r
- int rowIndex = characterList.getSelectedIndex();\r
- if (cd == null || !cd.isValid() || rowIndex < 0) {\r
+ CharacterData cd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ cd = characterListModel.getRow(selRow);\r
+ }\r
+ if (cd == null || !cd.isValid()) {\r
return;\r
}\r
\r
MainFrame.notifyChangeCharacterData(cd, newCd, this);\r
\r
// プロファイル一覧画面も更新する.\r
- characterListModel.set(rowIndex, newCd);\r
+ characterListModel.set(selRow, newCd);\r
characterList.repaint();\r
\r
} catch (Exception ex) {\r
* プロファイルの削除\r
*/\r
protected void onProfileRemove() {\r
- CharacterData cd = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData cd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ cd = characterListModel.getRow(selRow);\r
+ }\r
if (cd == null || !cd.isValid() || ProfileListManager.isUsingCharacterData(cd) || !cd.canWrite()) {\r
// 無効なキャラクター定義であるか、使用中であるか、書き込み不可であれば削除は実行できない.\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
}\r
\r
// モデルから該当キャラクターを削除して再描画\r
- characterListModel.removeElement(cd);\r
+ characterListModel.remove(selRow);\r
characterList.repaint();\r
updateUIState();\r
}\r
* 場所を開く\r
*/\r
protected void onProfileBrowse() {\r
- CharacterData cd = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData cd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ cd = characterListModel.getRow(selRow);\r
+ }\r
if (cd == null || !cd.isValid()) {\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
tk.beep();\r
*/\r
protected void onProfileImport() {\r
try {\r
- CharacterData selCd = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData selCd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ selCd = characterListModel.getRow(selRow);\r
+ }\r
\r
// 選択したプロファイルを更新するか、新規にプロファイルを作成するか選択できるようにする\r
if (selCd != null) {\r
if (importWizDialog.getExitCode() == ImportWizardDialog.EXIT_PROFILE_CREATED) {\r
\r
// 作成されたプロファイルを一覧に追加する.\r
- characterListModel.addElement(newCd);\r
+ characterListModel.add(newCd);\r
\r
} else if (importWizDialog.getExitCode() == ImportWizardDialog.EXIT_PROFILE_UPDATED) {\r
\r
* エクスポート\r
*/\r
protected void onProfileExport() {\r
- CharacterData cd = (CharacterData) characterList.getSelectedValue();\r
+ CharacterData cd = null;\r
+ int selRow = characterList.getSelectedRow();\r
+ if (selRow >= 0) {\r
+ cd = characterListModel.getRow(selRow);\r
+ }\r
if (cd == null || !cd.isValid()) {\r
Toolkit tk = Toolkit.getDefaultToolkit();\r
tk.beep();\r
}\r
}\r
}\r
+\r
+/**\r
+ * プロファイル一覧リストのモデル\r
+ */\r
+class ProfileSelectorTableModel extends AbstractTableModel {\r
+\r
+ private static final long serialVersionUID = 1L;\r
+\r
+ private enum Columns {\r
+ NAME("profile.column.name") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getName();\r
+ }\r
+ },\r
+ ID("profile.column.id") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getId();\r
+ }\r
+ },\r
+ REVISION("profile.column.revision") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getRev();\r
+ }\r
+ },\r
+ DESCRIPTION("profile.column.description") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getDescription();\r
+ }\r
+ },\r
+ AUTHOR("profile.column.author") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getAuthor();\r
+ }\r
+ },\r
+ LOCATION("profile.column.location") {\r
+ @Override\r
+ public String getValue(CharacterData cd) {\r
+ return cd.getDocBase().toString();\r
+ }\r
+ };\r
+\r
+ private final String columnName;\r
+\r
+ private String displayName;\r
+\r
+ private int width;\r
+\r
+ private Columns(String columnName) {\r
+ this.columnName = columnName;\r
+ }\r
+\r
+ public String getDisplayName() {\r
+ loadProperty();\r
+ return displayName;\r
+ }\r
+\r
+ public int getWidth() {\r
+ loadProperty();\r
+ return width;\r
+ }\r
+\r
+ private void loadProperty() {\r
+ if (displayName != null) {\r
+ return;\r
+ }\r
+ final Properties strings = LocalizedResourcePropertyLoader\r
+ .getInstance().getLocalizedProperties(\r
+ ProfileSelectorDialog.STRINGS_RESOURCE);\r
+ displayName = strings.getProperty(columnName);\r
+ width = Integer\r
+ .parseInt(strings.getProperty(columnName + ".width"));\r
+ }\r
+\r
+ public abstract String getValue(CharacterData cd);\r
+ }\r
+\r
+ private List<CharacterData> rows = Collections\r
+ .emptyList();\r
+\r
+ public void setModel(List<CharacterData> rows) {\r
+ if (rows == null) {\r
+ throw new IllegalArgumentException();\r
+ }\r
+ this.rows = new ArrayList<CharacterData>(rows);\r
+ fireTableDataChanged();\r
+ }\r
+\r
+ public void add(CharacterData cd) {\r
+ if (cd == null) {\r
+ throw new IllegalArgumentException();\r
+ }\r
+ this.rows.add(cd);\r
+ int lastRow = this.rows.size() - 1;\r
+ fireTableRowsInserted(lastRow, lastRow);\r
+ }\r
+\r
+ public void set(int selRow, CharacterData cd) {\r
+ this.rows.set(selRow, cd);\r
+ fireTableRowsDeleted(selRow, selRow);\r
+ }\r
+\r
+ public void remove(int selRow) {\r
+ this.rows.remove(selRow);\r
+ fireTableRowsDeleted(selRow, selRow);\r
+ }\r
+\r
+ public List<CharacterData> getModel() {\r
+ return rows;\r
+ }\r
+\r
+ public CharacterData getRow(int rowIndex) {\r
+ CharacterData cd = rows.get(rowIndex);\r
+ return cd;\r
+ }\r
+\r
+ public int getColumnCount() {\r
+ return Columns.values().length;\r
+ }\r
+\r
+ public int getRowCount() {\r
+ return rows.size();\r
+ }\r
+\r
+ public void adjustColumnModel(TableColumnModel columnModel) {\r
+ Columns[] columns = Columns.values();\r
+ for (int idx = 0; idx < columns.length; idx++) {\r
+ columnModel.getColumn(idx).setPreferredWidth(\r
+ columns[idx].getWidth());\r
+ }\r
+ }\r
+\r
+ @Override\r
+ public String getColumnName(int column) {\r
+ return Columns.values()[column].getDisplayName();\r
+ }\r
+\r
+ public Object getValueAt(int rowIndex, int columnIndex) {\r
+ CharacterData cd = getRow(rowIndex);\r
+ Columns column = Columns.values()[columnIndex];\r
+ return column.getValue(cd);\r
+ }\r
+\r
+ @Override\r
+ public boolean isCellEditable(int rowIndex, int columnIndex) {\r
+ return false;\r
+ }\r
+\r
+ @Override\r
+ public void setValueAt(Object aValue, int rowIndex, int columnIndex) {\r
+ // なにもしない.\r
+ }\r
+}\r