Subversion Repositories svn.mios

Rev

Rev 721 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
213 tk 1
/*
628 adamjking 2
 * @(#)MidiDeviceRoutingGUI.java    beta8   2006/04/23
213 tk 3
 *
628 adamjking 4
 * Copyright (C) 2008    Adam King (adamjking@optusnet.com.au)
213 tk 5
 *
6
 * This application is free software; you can redistribute it and/or modify
7
 * it under the terms of the GNU General Public License as published by
8
 * the Free Software Foundation; either version 2 of the License, or
9
 * (at your option) any later version.
10
 *
11
 * This application is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this application; if not, write to the Free Software
18
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19
 */
20
 
21
package org.midibox.midi.gui;
22
 
628 adamjking 23
import java.awt.BasicStroke;
213 tk 24
import java.awt.BorderLayout;
25
import java.awt.Color;
26
import java.awt.Component;
27
import java.awt.Dimension;
628 adamjking 28
import java.awt.Graphics;
29
import java.awt.Graphics2D;
213 tk 30
import java.awt.GridBagConstraints;
31
import java.awt.GridBagLayout;
32
import java.awt.Insets;
628 adamjking 33
import java.awt.Point;
34
import java.awt.Rectangle;
35
import java.awt.RenderingHints;
36
import java.awt.datatransfer.DataFlavor;
37
import java.awt.datatransfer.Transferable;
213 tk 38
import java.awt.event.ActionEvent;
39
import java.awt.event.ActionListener;
628 adamjking 40
import java.awt.event.MouseEvent;
41
import java.awt.event.MouseListener;
42
import java.awt.event.WindowAdapter;
43
import java.awt.event.WindowEvent;
213 tk 44
import java.util.Hashtable;
45
import java.util.Iterator;
46
import java.util.Observable;
47
import java.util.Observer;
628 adamjking 48
import java.util.Vector;
213 tk 49
 
50
import javax.sound.midi.MidiDevice;
808 adamjking 51
import javax.sound.midi.Receiver;
213 tk 52
import javax.swing.BorderFactory;
53
import javax.swing.DefaultListCellRenderer;
54
import javax.swing.DefaultListModel;
55
import javax.swing.Icon;
628 adamjking 56
import javax.swing.JButton;
57
import javax.swing.JCheckBoxMenuItem;
58
import javax.swing.JComponent;
59
import javax.swing.JDialog;
213 tk 60
import javax.swing.JLabel;
61
import javax.swing.JList;
628 adamjking 62
import javax.swing.JMenu;
63
import javax.swing.JMenuItem;
213 tk 64
import javax.swing.JPanel;
628 adamjking 65
import javax.swing.JPopupMenu;
213 tk 66
import javax.swing.JScrollPane;
628 adamjking 67
import javax.swing.JToggleButton;
213 tk 68
import javax.swing.ListSelectionModel;
69
import javax.swing.SwingConstants;
70
import javax.swing.event.ChangeEvent;
71
import javax.swing.event.ChangeListener;
72
import javax.swing.event.ListSelectionEvent;
73
import javax.swing.event.ListSelectionListener;
74
 
75
import org.midibox.midi.MidiDeviceRouting;
808 adamjking 76
import org.midibox.midi.VirtualMidiDevice;
628 adamjking 77
import org.midibox.utils.gui.DialogOwner;
213 tk 78
import org.midibox.utils.gui.GuiUtils;
79
import org.midibox.utils.gui.ImageLoader;
628 adamjking 80
import org.midibox.utils.gui.SimpleTransferHandler;
213 tk 81
 
628 adamjking 82
public class MidiDeviceRoutingGUI extends JPanel implements MouseListener,
83
        ChangeListener, ListSelectionListener, ActionListener, Observer {
213 tk 84
 
85
    private MidiDeviceRouting midiDeviceRouting;
86
 
87
    private static Icon openIcon = ImageLoader.getImageIcon("midiPortOpen.png");
88
 
628 adamjking 89
    private static Icon closedIcon = ImageLoader
90
            .getImageIcon("midiPortClosed.png");
213 tk 91
 
92
    private Hashtable icons = new Hashtable();
93
 
94
    private DefaultListModel midiReadDevicesListModel;
95
 
96
    private JList midiReadDevicesList;
97
 
98
    private JScrollPane midiReadDevicesScroller;
99
 
100
    private DefaultListModel midiWriteDevicesListModel;
101
 
102
    private JList midiWriteDevicesList;
103
 
104
    private JScrollPane midiWriteDevicesScroller;
105
 
628 adamjking 106
    private JPopupMenu connectionMenu;
107
 
108
    private JButton connectButton;
109
 
110
    private JButton disconnectButton;
111
 
112
    private JButton disconnectallButton;
113
 
114
    private JToggleButton releaseButton;
115
 
116
    private JPanel wirePanel;
117
 
118
    /*
119
     * private JDialog midiMapManagerDialog;
120
     */
121
 
122
    private Hashtable midiDevicePropertiesDialogs;
123
 
213 tk 124
    public MidiDeviceRoutingGUI(MidiDeviceRouting midiDeviceRouting) {
125
        super(new BorderLayout());
126
 
127
        this.midiDeviceRouting = midiDeviceRouting;
128
        midiDeviceRouting.addObserver(this);
129
 
628 adamjking 130
        midiDevicePropertiesDialogs = new Hashtable();
131
 
132
        addMouseListener(this);
133
 
213 tk 134
        midiReadDevicesListModel = new DefaultListModel();
135
        midiWriteDevicesListModel = new DefaultListModel();
136
 
137
        midiReadDevicesList = new JList(midiReadDevicesListModel);
628 adamjking 138
        midiReadDevicesList
139
                .setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
213 tk 140
        midiReadDevicesList.setLayoutOrientation(JList.VERTICAL);
628 adamjking 141
        midiReadDevicesList.setVisibleRowCount(6);
213 tk 142
        midiReadDevicesList.setCellRenderer(new MyListCellRenderer());
628 adamjking 143
        midiReadDevicesList.addMouseListener(this);
213 tk 144
        midiReadDevicesList.setBackground(Color.WHITE);
145
        midiWriteDevicesList = new JList(midiWriteDevicesListModel);
628 adamjking 146
        midiWriteDevicesList
147
                .setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
213 tk 148
        midiWriteDevicesList.setLayoutOrientation(JList.VERTICAL);
628 adamjking 149
        midiWriteDevicesList.setVisibleRowCount(6);
213 tk 150
        midiWriteDevicesList.setCellRenderer(new MyListCellRenderer());
628 adamjking 151
        midiWriteDevicesList.addMouseListener(this);
213 tk 152
        midiWriteDevicesList.setBackground(Color.WHITE);
153
 
154
        JPanel listPane = new JPanel(new GridBagLayout());
155
 
156
        GridBagConstraints gbc = new GridBagConstraints();
157
        gbc.gridx = 1;
158
        gbc.gridy = 1;
159
        gbc.gridwidth = 1;
160
        gbc.gridheight = 1;
161
        gbc.insets = new Insets(2, 0, 2, 0);
162
        gbc.fill = GridBagConstraints.HORIZONTAL;
163
        gbc.weightx = 1.0;
164
        gbc.weighty = 0.0;
165
 
166
        listPane.setOpaque(false);
167
 
628 adamjking 168
        listPane.add(new JLabel("MIDI Devices - Readable",
169
                SwingConstants.CENTER), gbc);
213 tk 170
        gbc.gridy++;
171
 
172
        midiReadDevicesScroller = new JScrollPane(midiReadDevicesList);
173
        midiReadDevicesScroller.getViewport().addChangeListener(this);
174
        midiReadDevicesScroller
175
                .setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
176
        midiReadDevicesScroller
177
                .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
178
 
179
        gbc.fill = GridBagConstraints.BOTH;
180
        gbc.weighty = 1.0;
181
        gbc.weighty = 1.0;
182
 
183
        listPane.add(midiReadDevicesScroller, gbc);
184
        gbc.gridx++;
185
 
628 adamjking 186
        wirePanel = new JPanel() {
187
 
188
            public void paintComponent(Graphics g) {
189
                super.paintComponent(g);
190
                Graphics2D g2d = (Graphics2D) g;
191
                g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
192
                        RenderingHints.VALUE_ANTIALIAS_ON);
193
 
194
                Iterator it = getMidiDeviceRouting().getMidiReadDevices()
195
                        .iterator();
196
 
197
                int i = 0;
198
 
199
                while (it.hasNext()) {
200
 
201
                    MidiDevice transmittingDevice = (MidiDevice) it.next();
202
 
203
                    Iterator it2 = getMidiDeviceRouting().getMidiWriteDevices()
204
                            .iterator();
205
 
206
                    int o = 0;
207
                    while (it2.hasNext()) {
208
                        MidiDevice receivingDevice = (MidiDevice) it2.next();
209
 
210
                        int connected = getMidiDeviceRouting()
211
                                .devicesConnected(transmittingDevice,
212
                                        receivingDevice);
213
 
214
                        if (connected != MidiDeviceRouting.DISCONNECTED) {
215
 
216
                            Rectangle rec1 = midiReadDevicesList.getCellBounds(
217
                                    i, i);
218
                            Point p1 = new Point(0,
219
                                    ((rec1.height / 2) + rec1.y)
220
                                            + midiReadDevicesScroller.getY()
221
                                            - midiReadDevicesScroller
222
                                                    .getVerticalScrollBar()
223
                                                    .getValue()
224
                                            - wirePanel.getY());
225
 
226
                            Rectangle rec2 = midiWriteDevicesList
227
                                    .getCellBounds(o, o);
228
                            Point p2 = new Point(getWidth(),
229
                                    ((rec2.height / 2) + rec2.y)
230
                                            + midiReadDevicesScroller.getY()
231
                                            - midiWriteDevicesScroller
232
                                                    .getVerticalScrollBar()
233
                                                    .getValue()
234
                                            - wirePanel.getY());
235
 
236
                            if (connected == MidiDeviceRouting.LOGICALLY_CONNECTED) {
237
                                g2d.setStroke(new BasicStroke(2f,
238
                                        BasicStroke.CAP_BUTT,
239
                                        BasicStroke.JOIN_ROUND, 1f,
240
                                        new float[] { 3f, 6f }, 0f));
241
                            } else {
242
                                g2d.setStroke(new BasicStroke(2));
243
                            }
244
                            g2d.drawLine(p1.x, p1.y, p2.x, p2.y);
245
                        }
246
                        o++;
247
                    }
248
                    i++;
249
                }
250
            }
251
        };
252
 
253
        wirePanel.setOpaque(false);
254
 
255
        listPane.add(wirePanel, gbc);
256
 
257
        GuiUtils.setComponentSize(wirePanel, 80, 80);
258
 
213 tk 259
        gbc.gridx++;
260
        gbc.gridy--;
261
 
262
        gbc.fill = GridBagConstraints.HORIZONTAL;
263
        gbc.weightx = 1.0;
264
        gbc.weighty = 0.0;
265
 
628 adamjking 266
        listPane.add(new JLabel("MIDI Devices - Writeable",
213 tk 267
                SwingConstants.CENTER), gbc);
268
        gbc.gridy++;
269
 
270
        midiWriteDevicesScroller = new JScrollPane(midiWriteDevicesList);
271
        midiWriteDevicesScroller
272
                .setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS);
273
        midiWriteDevicesScroller
274
                .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
275
        midiWriteDevicesScroller.getViewport().addChangeListener(this);
276
 
277
        gbc.fill = GridBagConstraints.BOTH;
278
        gbc.weightx = 1.0;
279
        gbc.weighty = 1.0;
280
 
281
        listPane.add(midiWriteDevicesScroller, gbc);
282
 
283
        int maxPreferredWidth = Math.max(midiReadDevicesScroller
284
                .getPreferredSize().width, midiWriteDevicesScroller
285
                .getPreferredSize().width);
286
        int maxPreferredHeight = Math.max(midiReadDevicesScroller
287
                .getPreferredSize().height, midiWriteDevicesScroller
288
                .getPreferredSize().height);
289
 
290
        GuiUtils.setComponentSize(midiReadDevicesScroller, maxPreferredWidth,
291
                maxPreferredHeight);
292
        GuiUtils.setComponentSize(midiWriteDevicesScroller, maxPreferredWidth,
293
                maxPreferredHeight);
294
 
628 adamjking 295
        midiReadDevicesList.setDragEnabled(true);
296
        midiWriteDevicesList.setDragEnabled(true);
297
        midiReadDevicesList.setTransferHandler(new MidiDevicesTransferHandler(
298
                false));
299
        midiWriteDevicesList.setTransferHandler(new MidiDevicesTransferHandler(
300
                true));
213 tk 301
        midiReadDevicesList.addListSelectionListener(this);
302
        midiWriteDevicesList.addListSelectionListener(this);
303
 
304
        listPane.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
305
        listPane.setOpaque(false);
294 rutgerv 306
        add(listPane, BorderLayout.CENTER);
628 adamjking 307
 
308
        JPanel buttonPane = new JPanel(new GridBagLayout());
309
        gbc = new GridBagConstraints();
310
 
311
        gbc.gridx = 0;
312
        gbc.gridy = 0;
313
        gbc.gridwidth = 1;
314
        gbc.fill = GridBagConstraints.BOTH;
315
 
641 adamjking 316
        gbc.insets = new Insets(5, 5, 10, 5);
628 adamjking 317
 
318
        connectButton = new JButton("Connect");
319
        connectButton.setToolTipText("Connect Selected Devices");
320
        connectButton.addActionListener(this);
321
        buttonPane.add(connectButton, gbc);
322
        gbc.gridx++;
323
 
324
        disconnectButton = new JButton("Disconnect");
325
        disconnectButton.setToolTipText("Disconnect Selected Devices");
326
        disconnectButton.addActionListener(this);
327
        buttonPane.add(disconnectButton, gbc);
328
        gbc.gridx++;
329
 
330
        disconnectallButton = new JButton("Disconnect All");
331
        disconnectallButton.setToolTipText("Disconnect All Devices");
332
        disconnectallButton.addActionListener(this);
333
        buttonPane.add(disconnectallButton, gbc);
641 adamjking 334
        gbc.gridx++;
628 adamjking 335
 
336
        releaseButton = new JToggleButton("Release Ports", midiDeviceRouting
721 adamjking 337
                .isPortsReleased());
628 adamjking 338
        releaseButton.setToolTipText("Release MIDI Ports");
339
        releaseButton.addActionListener(this);
340
        buttonPane.add(releaseButton, gbc);
341
 
342
        buttonPane.setOpaque(false);
343
        add(buttonPane, BorderLayout.SOUTH);
213 tk 344
        populateTrees();
345
    }
346
 
347
    public MidiDeviceRouting getMidiDeviceRouting() {
348
        return midiDeviceRouting;
349
    }
350
 
628 adamjking 351
    public void addMidiDeviceIcon(Object object, Icon icon) {
352
        icons.put(object, icon);
353
    }
354
 
213 tk 355
    public Icon getMidiDeviceIcon(MidiDevice md) {
808 adamjking 356
 
357
        if (md instanceof VirtualMidiDevice) {
358
 
359
            Receiver receiver = ((VirtualMidiDevice) md).getMidiInReceiver();
360
 
361
            if (icons.containsKey(receiver)) {
362
                return (Icon) icons.get(receiver);
363
            }
364
 
365
            if (icons.containsKey(receiver.getClass())) {
366
                return (Icon) icons.get(receiver.getClass());
367
            }
368
        }
369
 
213 tk 370
        if (icons.containsKey(md)) {
371
            return (Icon) icons.get(md);
372
        }
373
 
374
        if (icons.containsKey(md.getClass())) {
375
            return (Icon) icons.get(md.getClass());
376
        }
377
 
378
        try {
379
            if (md.isOpen()) {
380
                return openIcon;
381
            }
382
 
383
            return closedIcon;
384
 
385
        } catch (Exception e) {
386
            return closedIcon;
387
        }
388
    }
389
 
390
    public void redrawAll() {
391
        midiReadDevicesList.repaint();
628 adamjking 392
        midiWriteDevicesList.repaint();
393
        wirePanel.repaint();
394
        setButtonStates();
213 tk 395
    }
396
 
628 adamjking 397
    private void buildConnectionMenu(boolean output) {
398
 
399
        final MidiDevice sourceDevice = (MidiDevice) ((output) ? midiDeviceRouting
400
                .getMidiWriteDevices()
401
                : midiDeviceRouting.getMidiReadDevices())
402
                .elementAt(((output) ? midiWriteDevicesList
403
                        : midiReadDevicesList).getSelectedIndex());
404
        final Vector targetDevices = ((output) ? midiDeviceRouting
405
                .getMidiReadDevices() : midiDeviceRouting.getMidiWriteDevices());
406
 
407
        connectionMenu = new JPopupMenu(sourceDevice.getDeviceInfo().getName());
408
 
409
        JMenu connectMenu = new JMenu("Connect to ...");
410
 
411
        connectionMenu.add(connectMenu);
412
 
413
        connectionMenu.setLabel(sourceDevice.getDeviceInfo().getName());
414
 
415
        Iterator it = targetDevices.iterator();
416
 
417
        while (it.hasNext()) {
418
 
419
            MidiDevice targetDevice = (MidiDevice) it.next();
420
 
421
            final MidiDevice transmittingDevice = ((output) ? targetDevice
422
                    : sourceDevice);
423
            final MidiDevice receivingDevice = ((output) ? sourceDevice
424
                    : targetDevice);
425
            final JCheckBoxMenuItem connect = new JCheckBoxMenuItem(
426
                    targetDevice.getDeviceInfo().getName(),
427
                    midiDeviceRouting.devicesConnected(transmittingDevice,
428
                            receivingDevice) != MidiDeviceRouting.DISCONNECTED);
429
 
430
            connect.addActionListener(new ActionListener() {
431
                public void actionPerformed(ActionEvent ae) {
432
                    if (connect.isSelected()) {
433
                        midiDeviceRouting.connectDevices(transmittingDevice,
434
                                receivingDevice);
435
                    } else {
436
                        midiDeviceRouting.disconnectDevices(transmittingDevice,
437
                                receivingDevice);
438
                    }
439
                }
440
            });
441
            connectMenu.add(connect);
442
        }
443
 
444
        JMenuItem properties = new JMenuItem("MIDI Device Properties");
445
        properties.addActionListener(new ActionListener() {
446
            public void actionPerformed(ActionEvent ae) {
447
                showMidiDevicePropertyDialog(sourceDevice);
448
            }
449
        });
450
        connectionMenu.add(properties);
451
    }
452
 
453
    private void showMidiDevicePropertyDialog(MidiDevice midiDeviceIn) {
454
 
455
        final MidiDevice midiDevice = midiDeviceIn;
456
 
457
        if (!midiDevicePropertiesDialogs.containsKey(midiDevice)) {
458
 
459
            final MidiDeviceProperties midiDeviceProperties = new MidiDeviceProperties(
460
                    midiDevice);
461
 
462
            JDialog midiDevicePropertiesDialog = new JDialog(DialogOwner
463
                    .getFrame(), midiDevice.getDeviceInfo().getName(), false);
464
            midiDevicePropertiesDialog.setContentPane(midiDeviceProperties);
465
            midiDevicePropertiesDialog.pack();
466
            midiDevicePropertiesDialog.setLocationRelativeTo(this);
467
            midiDevicePropertiesDialog.setVisible(true);
468
 
469
            midiDevicePropertiesDialogs.put(midiDevice,
470
                    midiDevicePropertiesDialog);
471
 
472
            midiDevicePropertiesDialog.addWindowListener(new WindowAdapter() {
473
                public void windowClosing(WindowEvent we) {
474
                    midiDevicePropertiesDialogs.remove(midiDevice);
475
                }
476
            });
477
        }
478
        ((JDialog) midiDevicePropertiesDialogs.get(midiDevice)).requestFocus();
479
    }
480
 
213 tk 481
    private void populateTrees() {
628 adamjking 482
 
213 tk 483
        midiReadDevicesListModel.removeAllElements();
628 adamjking 484
 
213 tk 485
        Iterator it = midiDeviceRouting.getMidiReadDevices().iterator();
486
 
487
        while (it.hasNext()) {
488
            midiReadDevicesListModel.addElement(((MidiDevice) it.next())
489
                    .getDeviceInfo().getName());
490
        }
628 adamjking 491
 
213 tk 492
        midiReadDevicesList.setSelectedIndex(0);
628 adamjking 493
 
213 tk 494
        midiWriteDevicesListModel.removeAllElements();
628 adamjking 495
 
213 tk 496
        it = midiDeviceRouting.getMidiWriteDevices().iterator();
628 adamjking 497
 
213 tk 498
        while (it.hasNext()) {
499
            midiWriteDevicesListModel.addElement(((MidiDevice) it.next())
500
                    .getDeviceInfo().getName());
501
        }
628 adamjking 502
 
213 tk 503
        midiWriteDevicesList.setSelectedIndex(0);
628 adamjking 504
 
213 tk 505
        updateUI();
506
    }
507
 
628 adamjking 508
    private void setButtonStates() {
509
 
510
        int[] selectedReadIndices = midiReadDevicesList.getSelectedIndices();
511
        int[] selectedWriteIndices = midiWriteDevicesList.getSelectedIndices();
512
 
513
        connectButton.setEnabled(false);
514
        disconnectButton.setEnabled(false);
721 adamjking 515
        releaseButton.setSelected(midiDeviceRouting.isPortsReleased());
628 adamjking 516
 
517
        if (selectedReadIndices.length > 0 && selectedWriteIndices.length > 0) {
518
 
519
            for (int r = 0; r < selectedReadIndices.length; r++) {
520
 
521
                MidiDevice transmittingDevice = (MidiDevice) midiDeviceRouting
522
                        .getMidiReadDevices().elementAt(selectedReadIndices[r]);
523
 
524
                for (int w = 0; w < selectedWriteIndices.length; w++) {
525
 
526
                    MidiDevice receivingDevice = (MidiDevice) midiDeviceRouting
527
                            .getMidiWriteDevices().elementAt(
528
                                    selectedWriteIndices[w]);
529
 
530
                    if (midiDeviceRouting.devicesConnected(transmittingDevice,
531
                            receivingDevice) != MidiDeviceRouting.DISCONNECTED) {
532
                        disconnectButton.setEnabled(true);
533
                    } else {
534
                        connectButton.setEnabled(true);
535
                    }
536
                }
537
            }
538
        }
539
    }
540
 
213 tk 541
    public void valueChanged(ListSelectionEvent lse) {
628 adamjking 542
        setButtonStates();
543
    }
544
 
545
    public void mouseClicked(MouseEvent me) {
546
 
547
    }
548
 
549
    public void mouseReleased(MouseEvent me) {
550
        Object source = me.getSource();
551
 
552
        if (source == midiReadDevicesList || source == midiWriteDevicesList) {
553
            JList source2 = (JList) source;
554
            if (me.getButton() == MouseEvent.BUTTON3) {
555
                int index = source2.locationToIndex(me.getPoint());
556
                source2.setSelectedIndex(index);
557
                buildConnectionMenu((source == midiWriteDevicesList) ? true
558
                        : false);
559
                connectionMenu.show(source2, me.getX(), me.getY());
213 tk 560
            }
628 adamjking 561
        }
213 tk 562
    }
563
 
628 adamjking 564
    public void mousePressed(MouseEvent me) {
565
 
566
    }
567
 
568
    public void mouseEntered(MouseEvent me) {
569
 
570
    }
571
 
572
    public void mouseExited(MouseEvent me) {
573
 
574
    }
575
 
213 tk 576
    public void stateChanged(ChangeEvent ce) {
628 adamjking 577
        wirePanel.repaint();
213 tk 578
    }
579
 
580
    public Dimension getMinimumSize() {
581
        return getPreferredSize();
582
    }
583
 
584
    public void update(Observable observable, Object object) {
585
        if (observable == midiDeviceRouting) {
628 adamjking 586
            if (object == midiDeviceRouting.getMidiReadDevices()
587
                    || object == midiDeviceRouting.getMidiWriteDevices()) {
213 tk 588
                populateTrees();
589
            }
557 rutgerv 590
            redrawAll();
213 tk 591
        }
592
    }
593
 
594
    public void actionPerformed(ActionEvent ae) {
628 adamjking 595
        Object source = ae.getSource();
596
 
597
        if (source == connectButton) {
598
 
599
            int[] selectedReadIndices = midiReadDevicesList
600
                    .getSelectedIndices();
601
            int[] selectedWriteIndices = midiWriteDevicesList
602
                    .getSelectedIndices();
603
 
604
            for (int r = 0; r < selectedReadIndices.length; r++) {
605
 
606
                MidiDevice transmittingDevice = (MidiDevice) midiDeviceRouting
607
                        .getMidiReadDevices().elementAt(selectedReadIndices[r]);
608
 
609
                for (int w = 0; w < selectedWriteIndices.length; w++) {
610
                    MidiDevice receivingDevice = (MidiDevice) midiDeviceRouting
611
                            .getMidiWriteDevices().elementAt(
612
                                    selectedWriteIndices[w]);
613
 
614
                    midiDeviceRouting.connectDevices(transmittingDevice,
615
                            receivingDevice);
616
                }
617
 
618
            }
619
        } else if (source == disconnectButton) {
620
 
621
            int[] selectedReadIndices = midiReadDevicesList
622
                    .getSelectedIndices();
623
            int[] selectedWriteIndices = midiWriteDevicesList
624
                    .getSelectedIndices();
625
 
626
            for (int r = 0; r < selectedReadIndices.length; r++) {
627
 
628
                MidiDevice transmittingDevice = (MidiDevice) midiDeviceRouting
629
                        .getMidiReadDevices().elementAt(selectedReadIndices[r]);
630
 
631
                for (int w = 0; w < selectedWriteIndices.length; w++) {
632
                    MidiDevice receivingDevice = (MidiDevice) midiDeviceRouting
633
                            .getMidiWriteDevices().elementAt(
634
                                    selectedWriteIndices[w]);
635
 
636
                    midiDeviceRouting.disconnectDevices(transmittingDevice,
637
                            receivingDevice);
638
                }
639
            }
640
        } else if (source == disconnectallButton) {
641
            midiDeviceRouting.disconnectAll();
641 adamjking 642
        } else if (source == releaseButton) {
628 adamjking 643
            midiDeviceRouting.setPortsReleased(releaseButton.isSelected());
294 rutgerv 644
        }
213 tk 645
    }
646
 
647
    public class MyListCellRenderer extends DefaultListCellRenderer {
648
        public Component getListCellRendererComponent(JList list, Object value,
649
                int index, boolean isSelected, boolean hasFocus) {
650
 
651
            super.getListCellRendererComponent(list, value, index, isSelected,
652
                    hasFocus);
653
 
654
            setIcon(getMidiDeviceIcon(((MidiDevice) ((list == midiWriteDevicesList) ? midiDeviceRouting
655
                    .getMidiWriteDevices()
656
                    : midiDeviceRouting.getMidiReadDevices()).elementAt(index))));
657
 
658
            return this;
659
        }
628 adamjking 660
    }
661
 
662
    public class MidiDevicesTransferHandler extends SimpleTransferHandler {
663
 
664
        private boolean output;
665
 
666
        public MidiDevicesTransferHandler(boolean output) {
667
            super();
668
            this.output = output;
669
            dropOnSelf = false;
670
            supportedDataFlavors = new DataFlavor[] { MidiDeviceTransferable.LOCAL_JVM_MIDI_DEVICE_FLAVOR };
671
        }
672
 
673
        public boolean importData(JComponent c, Transferable t) {
674
 
675
            if (canImport(c, supportedDataFlavors)) {
676
 
677
                int[] indices = ((output) ? midiWriteDevicesList
678
                        : midiReadDevicesList).getSelectedIndices();
679
 
680
                for (int d = 0; d < indices.length; d++) {
681
 
682
                    MidiDevice localDevice = (MidiDevice) ((output) ? midiDeviceRouting
683
                            .getMidiWriteDevices()
684
                            : midiDeviceRouting.getMidiReadDevices())
685
                            .elementAt(indices[d]);
686
 
687
                    try {
688
                        MidiDevice[] remoteDevices = (MidiDevice[]) t
689
                                .getTransferData(MidiDeviceTransferable.LOCAL_JVM_MIDI_DEVICE_FLAVOR);
690
 
691
                        for (int d2 = 0; d2 < remoteDevices.length; d2++) {
692
 
693
                            MidiDevice remoteDevice = remoteDevices[d2];
694
 
695
                            if (output) {
696
                                midiDeviceRouting.connectDevices(remoteDevice,
697
                                        localDevice);
698
                            } else {
699
                                midiDeviceRouting.connectDevices(localDevice,
700
                                        remoteDevice);
701
                            }
702
                        }
703
                    } catch (Exception e) {
704
                        return false;
705
                    }
706
                }
707
                return true;
708
            }
709
            return false;
710
        }
711
 
712
        protected Transferable createTransferable(JComponent c) {
713
            justExported = true;
714
            int[] indices = ((output) ? midiWriteDevicesList
715
                    : midiReadDevicesList).getSelectedIndices();
716
 
717
            MidiDevice[] midiDevices = new MidiDevice[indices.length];
718
 
719
            for (int d = 0; d < midiDevices.length; d++) {
720
                midiDevices[d] = (MidiDevice) ((output) ? midiDeviceRouting
721
                        .getMidiWriteDevices() : midiDeviceRouting
722
                        .getMidiReadDevices()).elementAt(indices[d]);
723
            }
724
            return new MidiDeviceTransferable(midiDevices);
725
        }
726
    }
213 tk 727
}