/[svn]/jsampler/trunk/src/org/jsampler/view/fantasia/Channel.java
ViewVC logotype

Annotation of /jsampler/trunk/src/org/jsampler/view/fantasia/Channel.java

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1743 - (hide annotations) (download)
Sat May 31 23:04:01 2008 UTC (15 years, 11 months ago) by iliev
File size: 28801 byte(s)
* Renamed the column labels in the Channel Routing dialog: The column
  representing the sampler channel's audio channels is "Audio In" and
  the column representing the audio device's channels is "Audio Out"
* Remember the last used tab in the Preferences dialog
* Fantasia: The sampler channels are now referenced by their position
  in the list, not by their ID
* Fantasia: Implemented options to show the channel number and/or the MIDI
  input port/channel on the sampler channel screen when using Small View
  (choose Edit/Preferences, then click the `Channels' tab)
* Fantasia: Migrated to substance 5

1 iliev 912 /*
2     * JSampler - a java front-end for LinuxSampler
3     *
4 iliev 1688 * Copyright (C) 2005-2008 Grigor Iliev <grigor@grigoriliev.com>
5 iliev 912 *
6     * This file is part of JSampler.
7     *
8     * JSampler is free software; you can redistribute it and/or modify
9     * it under the terms of the GNU General Public License version 2
10     * as published by the Free Software Foundation.
11     *
12     * JSampler is distributed in the hope that it will be useful,
13     * but WITHOUT ANY WARRANTY; without even the implied warranty of
14     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15     * GNU General Public License for more details.
16     *
17     * You should have received a copy of the GNU General Public License
18     * along with JSampler; if not, write to the Free Software
19     * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
20     * MA 02111-1307 USA
21     */
22    
23     package org.jsampler.view.fantasia;
24    
25 iliev 1467 import java.awt.Container;
26 iliev 1732 import java.awt.Dimension;
27 iliev 1467 import java.awt.Rectangle;
28 iliev 912
29     import java.awt.event.ActionEvent;
30     import java.awt.event.ActionListener;
31 iliev 1732 import java.awt.event.MouseAdapter;
32     import java.awt.event.MouseEvent;
33 iliev 912
34 iliev 1285 import java.beans.PropertyChangeEvent;
35     import java.beans.PropertyChangeListener;
36    
37 iliev 1732 import java.text.NumberFormat;
38    
39     import javax.swing.AbstractAction;
40     import javax.swing.Action;
41 iliev 912 import javax.swing.BoxLayout;
42 iliev 1732 import javax.swing.ButtonGroup;
43 iliev 912 import javax.swing.DefaultListCellRenderer;
44 iliev 1732 import javax.swing.ImageIcon;
45 iliev 912 import javax.swing.JButton;
46 iliev 1540 import javax.swing.JComponent;
47 iliev 1732 import javax.swing.JLabel;
48     import javax.swing.JMenuItem;
49 iliev 912 import javax.swing.JPanel;
50 iliev 1732 import javax.swing.JPopupMenu;
51     import javax.swing.JRadioButtonMenuItem;
52 iliev 1467 import javax.swing.JScrollPane;
53 iliev 912 import javax.swing.JToggleButton;
54 iliev 1732 import javax.swing.JToolBar;
55 iliev 912
56 iliev 1732 import net.sf.juife.InformationDialog;
57 iliev 912 import net.sf.juife.TitleBar;
58    
59 iliev 1285 import org.jdesktop.swingx.JXCollapsiblePane;
60    
61 iliev 912 import org.jsampler.CC;
62 iliev 1540 import org.jsampler.HF;
63 iliev 912 import org.jsampler.SamplerChannelModel;
64    
65     import org.jsampler.event.SamplerChannelEvent;
66 iliev 1285 import org.jsampler.event.SamplerChannelListEvent;
67     import org.jsampler.event.SamplerChannelListListener;
68 iliev 912 import org.jsampler.event.SamplerChannelListener;
69    
70 iliev 1734 import org.jsampler.view.JSChannel;
71 iliev 1737 import org.jsampler.view.JSChannelsPane;
72 iliev 1734
73 iliev 1732 import org.jsampler.view.std.JSChannelOutputRoutingDlg;
74 iliev 1743 import org.jsampler.view.std.JSFxSendsDlg;
75 iliev 1732 import org.jsampler.view.std.JSFxSendsPane;
76     import org.jsampler.view.std.JSInstrumentChooser;
77     import org.jsampler.view.std.JSVolumeEditorPopup;
78    
79     import org.linuxsampler.lscp.SamplerChannel;
80    
81     import static org.jsampler.view.fantasia.FantasiaI18n.i18n;
82 iliev 1285 import static org.jsampler.view.fantasia.FantasiaPrefs.*;
83 iliev 1732 import static org.jsampler.view.fantasia.FantasiaUtils.*;
84     import static org.jsampler.view.std.JSVolumeEditorPopup.VolumeType;
85 iliev 912
86    
87     /**
88     *
89     * @author Grigor Iliev
90     */
91 iliev 1734 public class Channel extends JSChannel {
92 iliev 1285 private final JXCollapsiblePane mainPane;
93 iliev 1730 private final ChannelOptionsPane optionsPane = new ChannelOptionsPane();
94 iliev 912
95 iliev 1734 private final ViewTracker viewTracker;
96    
97 iliev 1743 private JSFxSendsDlg fxSendsDlg = null;
98 iliev 1732
99 iliev 1737 private final ContextMenu contextMenu;
100 iliev 1732
101 iliev 1730 private boolean selected = false;
102 iliev 912
103 iliev 1730 private AnimatedPorpetyListener animatedPorpetyListener = new AnimatedPorpetyListener();
104 iliev 912
105 iliev 1730 class AnimatedPorpetyListener implements PropertyChangeListener {
106     public void
107     propertyChange(PropertyChangeEvent e) {
108     mainPane.setAnimated(preferences().getBoolProperty(ANIMATED));
109     }
110     }
111 iliev 912
112 iliev 1737 ////////////////////////////////
113     // ******* Mouse tracker *******
114     ////////////////////////////////
115     private static int mouseOverChannelId = -1;
116     private static boolean mousePressed = false;
117    
118     private static ActionListener guiListener = null;
119    
120     private static Channel oldMouseOverChannel = null;
121     private static Channel newMouseOverChannel = null;
122    
123    
124     private static void
125     mouseMoved() {
126     //TODO: do this for all channels panes
127     JSChannelsPane cp = CC.getMainFrame().getChannelsPane(0);
128     for(int i = 0; i < cp.getChannelCount(); i++) {
129     mouseMoved((Channel)cp.getChannel(i));
130     }
131    
132     if(oldMouseOverChannel == newMouseOverChannel) return;
133    
134     if(oldMouseOverChannel != null) oldMouseOverChannel.mouseExited();
135    
136     if(newMouseOverChannel != null) {
137     mouseOverChannelId = newMouseOverChannel.getChannelId();
138     newMouseOverChannel.mouseEntered();
139     }
140    
141     oldMouseOverChannel = newMouseOverChannel = null;
142     }
143    
144     private static void
145     mouseMoved(Channel c) {
146     int id = c.getChannelId();
147     if(c.mainPane.getMousePosition(true) != null) {
148     newMouseOverChannel = c;
149     } else if(id == mouseOverChannelId) {
150     oldMouseOverChannel = c;
151     }
152     }
153    
154     ////////////////////////////////
155    
156    
157 iliev 912 /**
158     * Creates a new instance of <code>Channel</code> using the specified
159     * non-<code>null</code> channel model.
160     * @param model The model to be used by this channel.
161     * @throws IllegalArgumentException If the model is <code>null</code>.
162     */
163     public
164     Channel(SamplerChannelModel model) {
165 iliev 1318 this(model, null);
166     }
167    
168     /**
169     * Creates a new instance of <code>Channel</code> using the specified
170     * non-<code>null</code> channel model.
171     * @param model The model to be used by this channel.
172     * @param listener A listener which is notified when the newly created
173     * channel is fully expanded on the screen.
174     * @throws IllegalArgumentException If the model is <code>null</code>.
175     */
176     public
177     Channel(SamplerChannelModel model, final ActionListener listener) {
178 iliev 912 super(model);
179    
180     setLayout(new BoxLayout(this, BoxLayout.Y_AXIS));
181     optionsPane.setAlignmentX(JPanel.CENTER_ALIGNMENT);
182    
183 iliev 1285 mainPane = new JXCollapsiblePane();
184 iliev 1734 viewTracker = new ViewTracker();
185 iliev 1737 contextMenu = new ContextMenu();
186 iliev 1734
187 iliev 1285 mainPane.getContentPane().setLayout (
188     new BoxLayout(mainPane.getContentPane(), BoxLayout.Y_AXIS)
189     );
190 iliev 912
191 iliev 1732 int viewIdx = preferences().getIntProperty(DEFAULT_CHANNEL_VIEW);
192     if(viewIdx == 0) {
193 iliev 1737 viewTracker.setView(new SmallChannelView(Channel.this));
194 iliev 1732 } else if(viewIdx == 1) {
195 iliev 1737 viewTracker.setView(new NormalChannelView(Channel.this));
196 iliev 1732 } else {
197 iliev 1737 viewTracker.setView(new NormalChannelView(Channel.this));
198 iliev 1732 }
199 iliev 1730
200 iliev 1285 setOpaque(false);
201    
202 iliev 912 getModel().addSamplerChannelListener(getHandler());
203    
204     updateChannelInfo();
205 iliev 1285
206     add(mainPane);
207    
208 iliev 1318 if(listener != null) {
209     final String s = JXCollapsiblePane.ANIMATION_STATE_KEY;
210     mainPane.addPropertyChangeListener(s, new PropertyChangeListener() {
211     public void
212     propertyChange(PropertyChangeEvent e) {
213     if(e.getNewValue() == "expanded") {
214 iliev 1467 // TODO: this should be done regardles the listener != null?
215 iliev 1318 mainPane.removePropertyChangeListener(s, this);
216 iliev 1467 ///////
217 iliev 1318 listener.actionPerformed(null);
218 iliev 1467 ensureChannelIsVisible();
219     } else if(e.getNewValue() == "expanding/collapsing") {
220     ensureChannelIsVisible();
221 iliev 1318 }
222     }
223     });
224     }
225    
226 iliev 1285 mainPane.setAnimated(false);
227     mainPane.setCollapsed(true);
228     mainPane.setAnimated(preferences().getBoolProperty(ANIMATED));
229     mainPane.setCollapsed(false);
230    
231 iliev 1730 preferences().addPropertyChangeListener(ANIMATED, animatedPorpetyListener);
232 iliev 1318
233     if(listener != null) {
234     javax.swing.SwingUtilities.invokeLater(new Runnable() {
235     public void
236     run() { listener.actionPerformed(null); }
237     });
238     }
239 iliev 1341
240     CC.getSamplerModel().addSamplerChannelListListener(getHandler());
241 iliev 1737
242     installGuiListener();
243 iliev 912 }
244    
245 iliev 1737 private static void
246     installGuiListener() {
247     if(guiListener != null) return;
248    
249     guiListener = new ActionListener() {
250     public void
251     actionPerformed(ActionEvent e) {
252     mouseMoved();
253     }
254     };
255    
256     ((MainFrame)CC.getMainFrame()).getGuiTimer().addActionListener(guiListener);
257     }
258    
259 iliev 1467 private void
260 iliev 1737 mouseEntered() {
261     viewTracker.mouseEntered();
262     }
263    
264     private void
265     mouseExited() {
266     viewTracker.mouseExited();
267     }
268    
269     private void
270 iliev 1467 ensureChannelIsVisible() {
271     Container p = getParent();
272     JScrollPane sp = null;
273     while(p != null) {
274     if(p instanceof JScrollPane) {
275     sp = (JScrollPane)p;
276     break;
277     }
278     p = p.getParent();
279     }
280     if(sp == null) return;
281     int h = sp.getViewport().getView().getHeight();
282     sp.getViewport().scrollRectToVisible(new Rectangle(0, h - 2, 1, 1));
283     }
284    
285 iliev 912 /**
286     * Determines whether the channel is selected.
287     * @return <code>true</code> if the channel is selected, <code>false</code> otherwise.
288     */
289     public boolean isSelected() { return selected; }
290    
291     /**
292     * Sets the selection state of this channel.
293     * This method is invoked when the selection state of the channel has changed.
294     * @param select Specifies the new selection state of this channel;
295     * <code>true</code> to select the channel, <code>false</code> otherwise.
296     */
297     public void
298     setSelected(boolean select) {
299    
300     selected = select;
301     }
302    
303     /** Shows the channel properties. */
304     public void
305 iliev 1285 expandChannel() { expandChannel(optionsPane.isAnimated()); }
306 iliev 912
307 iliev 1285 /** Shows the channel properties. */
308     public void
309     expandChannel(boolean animated) {
310     boolean b = optionsPane.isAnimated();
311     optionsPane.setAnimated(animated);
312 iliev 1734 viewTracker.getCurrentView().expandChannel();
313 iliev 1285 optionsPane.setAnimated(b);
314     }
315 iliev 912
316     /**
317     * Updates the channel settings. This method is invoked when changes to the
318     * channel were made.
319     */
320     private void
321     updateChannelInfo() {
322 iliev 1734 viewTracker.getCurrentView().updateChannelInfo();
323 iliev 912 }
324    
325 iliev 1732 public void
326     loadInstrument() {
327     JSInstrumentChooser dlg = FantasiaUtils.createInstrumentChooser(CC.getMainFrame());
328     dlg.setVisible(true);
329    
330     if(!dlg.isCancelled()) {
331     SamplerChannelModel m = getModel();
332     m.loadBackendInstrument(dlg.getInstrumentFile(), dlg.getInstrumentIndex());
333     }
334     }
335    
336 iliev 1734 public void
337     fallbackToOriginalView() {
338     viewTracker.fallbackToOriginalView();
339     }
340    
341     public boolean
342     isUsingOriginalView() {
343     return viewTracker.isUsingOriginalView();
344     }
345    
346 iliev 1341 protected void
347     onDestroy() {
348     CC.getSamplerModel().removeSamplerChannelListListener(getHandler());
349 iliev 1730 preferences().removePropertyChangeListener(ANIMATED, animatedPorpetyListener);
350 iliev 1743 if(fxSendsDlg != null) fxSendsDlg.dispose();
351 iliev 1734 viewTracker.onDestroy();
352 iliev 1341 }
353 iliev 1730
354     public void
355     remove() {
356     if(!mainPane.isAnimated()) {
357     CC.getSamplerModel().removeBackendChannel(getChannelId());
358     return;
359     }
360    
361     String s = JXCollapsiblePane.ANIMATION_STATE_KEY;
362     mainPane.addPropertyChangeListener(s, getHandler());
363     mainPane.setCollapsed(true);
364     }
365 iliev 1341
366 iliev 1730 public void
367     showOptionsPane(boolean show) { optionsPane.showOptionsPane(show); }
368    
369 iliev 1732 public void
370     showFxSendsDialog() {
371     if(fxSendsDlg != null && fxSendsDlg.isVisible()) {
372     fxSendsDlg.toFront();
373     return;
374     }
375 iliev 1743
376     fxSendsDlg = new JSFxSendsDlg(new FxSendsPane(getModel()));
377 iliev 1732 fxSendsDlg.setVisible(true);
378     }
379    
380 iliev 912 private final EventHandler eventHandler = new EventHandler();
381    
382     private EventHandler
383     getHandler() { return eventHandler; }
384    
385 iliev 1730 private class EventHandler implements SamplerChannelListener,
386     SamplerChannelListListener, PropertyChangeListener {
387 iliev 912 /**
388     * Invoked when changes are made to a sampler channel.
389     * @param e A <code>SamplerChannelEvent</code> instance
390     * containing event information.
391     */
392     public void
393     channelChanged(SamplerChannelEvent e) { updateChannelInfo(); }
394    
395     /**
396     * Invoked when the number of active disk streams has changed.
397     * @param e A <code>SamplerChannelEvent</code> instance
398     * containing event information.
399     */
400     public void
401     streamCountChanged(SamplerChannelEvent e) {
402 iliev 1734 viewTracker.getCurrentView().updateStreamCount(getModel().getStreamCount());
403 iliev 912 }
404    
405     /**
406     * Invoked when the number of active voices has changed.
407     * @param e A <code>SamplerChannelEvent</code> instance
408     * containing event information.
409     */
410     public void
411     voiceCountChanged(SamplerChannelEvent e) {
412 iliev 1734 viewTracker.getCurrentView().updateVoiceCount(getModel().getVoiceCount());
413 iliev 912 }
414 iliev 1341
415     /**
416     * Invoked when a new sampler channel is created.
417     * @param e A <code>SamplerChannelListEvent</code>
418     * instance providing the event information.
419     */
420     public void
421     channelAdded(SamplerChannelListEvent e) { }
422    
423     /**
424     * Invoked when a sampler channel is removed.
425     * @param e A <code>SamplerChannelListEvent</code>
426     * instance providing the event information.
427     */
428     public void
429     channelRemoved(SamplerChannelListEvent e) {
430     // Some cleanup when the channel is removed.
431     if(e.getChannelModel().getChannelId() == getChannelId()) {
432     onDestroy();
433     }
434     }
435 iliev 1285
436 iliev 912 public void
437 iliev 1285 propertyChange(PropertyChangeEvent e) {
438     if(e.getNewValue() == "collapsed") {
439     CC.getSamplerModel().removeBackendChannel(getChannelId());
440     }
441     }
442 iliev 912 }
443 iliev 1732
444 iliev 1734
445 iliev 1737
446 iliev 1734 class ViewTracker extends MouseAdapter implements PropertyChangeListener {
447     private ChannelView originalView;
448     private ChannelView mouseOverView;
449     private ChannelView currentView;
450    
451 iliev 1737 private ChannelView.Type mouseOverViewType = null;
452 iliev 1734
453     ViewTracker() {
454    
455 iliev 1737
456 iliev 1734 updateMouseOverViewType();
457    
458     String s = DIFFERENT_CHANNEL_VIEW_ON_MOUSE_OVER;
459     preferences().addPropertyChangeListener(s, this);
460    
461     s = CHANNEL_VIEW_ON_MOUSE_OVER;
462     preferences().addPropertyChangeListener(s, this);
463     }
464    
465     public boolean
466     isUsingOriginalView() {
467     return currentView == originalView;
468     }
469    
470     private void
471     installListeners() {
472 iliev 1737
473 iliev 1734 }
474    
475     private void
476     uninstallListeners() {
477 iliev 1737
478 iliev 1734 }
479    
480     private void
481     updateMouseOverViewType() {
482     if(mouseOverView != null) {
483     mouseOverView.removeEnhancedMouseListener(this);
484     }
485    
486 iliev 1737 mouseOverView = null;
487    
488 iliev 1734 boolean b;
489     b = preferences().getBoolProperty(DIFFERENT_CHANNEL_VIEW_ON_MOUSE_OVER);
490     if(!b) {
491 iliev 1737 mouseOverViewType = null;
492 iliev 1734 uninstallListeners();
493     return;
494     }
495    
496     int i = preferences().getIntProperty(CHANNEL_VIEW_ON_MOUSE_OVER);
497    
498     switch(i) {
499 iliev 1737 case 0: mouseOverViewType = ChannelView.Type.SMALL; break;
500     case 1: mouseOverViewType = ChannelView.Type.NORMAL; break;
501     default:mouseOverViewType = null;
502 iliev 1734 }
503    
504 iliev 1737 if(mouseOverViewType != null) {
505 iliev 1734 installListeners();
506 iliev 1737 }
507     }
508    
509     public ChannelView
510     getMouseOverView() {
511     if(mouseOverViewType == null) return null;
512    
513     if(mouseOverView == null) {
514     Channel channel = Channel.this;
515    
516     switch(mouseOverViewType) {
517     case SMALL: mouseOverView = new SmallChannelView(channel); break;
518     case NORMAL: mouseOverView = new NormalChannelView(channel); break;
519     default: mouseOverView = new NormalChannelView(channel);
520     }
521    
522 iliev 1734 mouseOverView.addEnhancedMouseListener(this);
523     }
524 iliev 1737
525     return mouseOverView;
526 iliev 1734 }
527    
528     public ChannelView
529     getCurrentView() { return currentView; }
530    
531 iliev 1737 public ChannelView
532     getOriginalView() { return originalView; }
533    
534 iliev 1734 public void
535     setView(ChannelView view) {
536     setView(view, true);
537     }
538    
539     public void
540     setView(ChannelView view, boolean manual) {
541     boolean selected = false;
542     if(currentView != null) selected = currentView.isOptionsButtonSelected();
543    
544     if(manual) {
545     if(originalView != null) {
546     originalView.removeEnhancedMouseListener(this);
547     }
548    
549     if(originalView != currentView) destroyOriginalView();
550     if(currentView != null && currentView.getType() == view.getType()) {
551     originalView = currentView;
552     originalView.addEnhancedMouseListener(this);
553     destroyView(view);
554     return;
555     }
556    
557     removeCurrentView();
558    
559     originalView = view;
560     originalView.addEnhancedMouseListener(this);
561     currentView = view;
562     } else {
563     if(view.getType() == getCurrentView().getType()) {
564     destroyView(view);
565     return;
566     }
567    
568     removeCurrentView();
569     currentView = view;
570     }
571    
572     currentView.setOptionsButtonSelected(selected);
573    
574     updateView();
575     }
576    
577     private void
578     updateView() {
579 iliev 1737 ChannelOptionsView view = getCurrentView().getChannelOptionsView();
580     if(view != null) optionsPane.setContentPane(view.getComponent());
581 iliev 1734
582     updateChannelInfo();
583    
584     mainPane.add(getCurrentView().getComponent());
585     mainPane.add(optionsPane);
586     mainPane.validate();
587     mainPane.revalidate();
588     mainPane.repaint();
589     }
590    
591     public void
592     fallbackToOriginalView() {
593     if(currentView == originalView) return;
594    
595     boolean selected = false;
596     if(currentView != null) selected = currentView.isOptionsButtonSelected();
597    
598     removeCurrentView();
599     currentView = originalView;
600     currentView.setOptionsButtonSelected(selected);
601    
602     updateView();
603     }
604    
605     private void
606     removeCurrentView() { removeView(currentView); }
607    
608     private void
609     destroyCurrentView() { destroyView(currentView); }
610    
611     private void
612     removeOriginalView() { removeView(originalView); }
613    
614     private void
615     destroyOriginalView() { destroyView(originalView); }
616    
617     private void
618     removeView(ChannelView view) {
619     if(view == null) return;
620    
621     mainPane.remove(view.getComponent());
622     mainPane.remove(optionsPane);
623    
624     destroyView(view);
625     }
626    
627     private void
628     destroyView(ChannelView view) {
629     if(view == null) return;
630    
631     view.uninstallView();
632    
633     view = null;
634     }
635    
636 iliev 1737 public boolean
637     isMouseOverEnabled() { return mouseOverViewType != null; }
638    
639 iliev 1734 private void
640     mouseEntered() {
641 iliev 1737 if(!isMouseOverEnabled()) return;
642     if(getCurrentView().getType() == getMouseOverView().getType()) return;
643 iliev 1734
644     JSChannel[] channels = CC.getMainFrame().getChannelsPane(0).getChannels();
645     for(JSChannel c : channels) {
646     if(c == Channel.this) continue;
647    
648     Channel chn = (Channel)c;
649     if(!(chn).isUsingOriginalView()) chn.fallbackToOriginalView();
650     }
651    
652 iliev 1737 setView(getMouseOverView(), false);
653 iliev 1734 }
654    
655     private void
656     mouseExited() {
657 iliev 1737 if(!isMouseOverEnabled()) return;
658 iliev 1734 if(getCurrentView().getType() == originalView.getType()) return;
659    
660     fallbackToOriginalView();
661     }
662    
663     public void
664     mouseEntered(MouseEvent e) {
665 iliev 1737 guiListener.actionPerformed(null);
666 iliev 1734 }
667    
668     public void
669     mouseExited(MouseEvent e) {
670 iliev 1737 guiListener.actionPerformed(null);
671 iliev 1734 }
672    
673     public void
674     mousePressed(MouseEvent e) {
675 iliev 1737 mousePressed = true;
676 iliev 1734 }
677    
678     public void
679     mouseReleased(MouseEvent e) {
680 iliev 1737 mousePressed = false;
681 iliev 1734 }
682    
683     public void
684     onDestroy() {
685     destroyCurrentView();
686     destroyOriginalView();
687    
688     uninstallListeners();
689    
690     if(currentView != null) {
691     currentView.removeEnhancedMouseListener(this);
692     }
693    
694     if(mouseOverView != null) {
695     mouseOverView.removeEnhancedMouseListener(this);
696     }
697    
698     String s = DIFFERENT_CHANNEL_VIEW_ON_MOUSE_OVER;
699     preferences().removePropertyChangeListener(s, this);
700    
701     s = CHANNEL_VIEW_ON_MOUSE_OVER;
702     preferences().removePropertyChangeListener(s, this);
703     }
704    
705     public void
706     propertyChange(PropertyChangeEvent e) {
707     updateMouseOverViewType();
708     }
709     }
710    
711 iliev 1732 class EditInstrumentAction extends AbstractAction implements SamplerChannelListener {
712     EditInstrumentAction() {
713     super(i18n.getMenuLabel("channels.editInstrument"));
714     channelChanged(null);
715     getModel().addSamplerChannelListener(this);
716     }
717    
718     public void
719     actionPerformed(ActionEvent e) {
720     CC.getSamplerModel().editBackendInstrument(getChannelId());
721     }
722    
723     public void
724     channelChanged(SamplerChannelEvent e) {
725     boolean b = getChannelInfo().getInstrumentStatus() == 100;
726     setEnabled(b);
727     }
728    
729     public void
730     streamCountChanged(SamplerChannelEvent e) { }
731    
732     public void
733     voiceCountChanged(SamplerChannelEvent e) { }
734     }
735    
736     class FxSendsAction extends AbstractAction {
737     FxSendsAction() {
738     super(i18n.getMenuLabel("channels.fxSends"));
739     }
740    
741     public void
742     actionPerformed(ActionEvent e) {
743     showFxSendsDialog();
744     }
745     }
746    
747     class ChannelRoutingAction extends AbstractAction implements SamplerChannelListener {
748     ChannelRoutingAction() {
749     super(i18n.getMenuLabel("channels.channelRouting"));
750     channelChanged(null);
751     getModel().addSamplerChannelListener(this);
752     }
753    
754     public void
755     actionPerformed(ActionEvent e) {
756     SamplerChannel c = getChannelInfo();
757     new JSChannelOutputRoutingDlg(CC.getMainFrame(), c).setVisible(true);
758     }
759    
760     public void
761     channelChanged(SamplerChannelEvent e) {
762     boolean b = getChannelInfo().getAudioOutputDevice() != -1;
763     setEnabled(b);
764     }
765    
766     public void
767     streamCountChanged(SamplerChannelEvent e) { }
768    
769     public void
770     voiceCountChanged(SamplerChannelEvent e) { }
771     }
772    
773     class SetSmallViewAction extends AbstractAction {
774     SetSmallViewAction() {
775     super(i18n.getMenuLabel("channels.smallView"));
776     }
777    
778     public void
779     actionPerformed(ActionEvent e) {
780 iliev 1734 viewTracker.setView(new SmallChannelView(Channel.this));
781 iliev 1732 }
782     }
783    
784     class SetNormalViewAction extends AbstractAction {
785     SetNormalViewAction() {
786     super(i18n.getMenuLabel("channels.normalView"));
787     }
788    
789     public void
790     actionPerformed(ActionEvent e) {
791 iliev 1734 viewTracker.setView(new NormalChannelView(Channel.this));
792 iliev 1732 }
793     }
794    
795     public ContextMenu
796     getContextMenu() { return contextMenu; }
797    
798     class ContextMenu extends MouseAdapter {
799 iliev 1737 private JPopupMenu menu = null;
800 iliev 1732
801 iliev 1737 protected JRadioButtonMenuItem rbmiSmallView;
802     protected JRadioButtonMenuItem rbmiNormalView;
803 iliev 1732
804     ContextMenu() {
805 iliev 1737
806     }
807    
808     private void
809     createMenu() {
810     menu = new JPopupMenu();
811 iliev 1732 menu.add(new JMenuItem(new EditInstrumentAction()));
812     menu.addSeparator();
813    
814     rbmiSmallView = new JRadioButtonMenuItem(new SetSmallViewAction());
815     rbmiNormalView = new JRadioButtonMenuItem(new SetNormalViewAction());
816 iliev 1737 if(viewTracker.getOriginalView() instanceof SmallChannelView) {
817     rbmiSmallView.setSelected(true);
818     } else if(viewTracker.getOriginalView() instanceof NormalChannelView) {
819     rbmiNormalView.setSelected(true);
820     }
821 iliev 1732
822     ButtonGroup group = new ButtonGroup();
823     group.add(rbmiSmallView);
824     group.add(rbmiNormalView);
825    
826     menu.add(rbmiSmallView);
827     menu.add(rbmiNormalView);
828    
829     menu.addSeparator();
830     menu.add(new JMenuItem(new FxSendsAction()));
831     menu.add(new JMenuItem(new ChannelRoutingAction()));
832     }
833    
834 iliev 1737 private JPopupMenu
835     getMenu() {
836     if(menu == null) createMenu();
837     return menu;
838     }
839    
840 iliev 1732 public void
841     mousePressed(MouseEvent e) {
842     if(e.isPopupTrigger()) show(e);
843     }
844    
845     public void
846     mouseReleased(MouseEvent e) {
847     if(e.isPopupTrigger()) show(e);
848     }
849    
850     void
851     show(MouseEvent e) {
852 iliev 1737 getMenu().show(e.getComponent(), e.getX(), e.getY());
853 iliev 1732 }
854     }
855    
856     class FxSendsPane extends JSFxSendsPane {
857     FxSendsPane(SamplerChannelModel model) {
858     super(model);
859    
860     actionAddFxSend.putValue(Action.SMALL_ICON, Res.iconNew16);
861     actionRemoveFxSend.putValue(Action.SMALL_ICON, Res.iconDelete16);
862     }
863    
864     protected JToolBar
865     createToolBar() {
866     JToolBar tb = new JToolBar();
867     Dimension d = new Dimension(Short.MAX_VALUE, tb.getPreferredSize().height);
868     tb.setMaximumSize(d);
869     tb.setFloatable(false);
870     tb.setAlignmentX(JPanel.RIGHT_ALIGNMENT);
871    
872     tb.add(new ToolbarButton(actionAddFxSend));
873     tb.add(new ToolbarButton(actionRemoveFxSend));
874    
875     return tb;
876     }
877     }
878    
879     public static class StreamVoiceCountPane extends JPanel {
880     private final Channel channel;
881    
882     private final JLabel lStreams = createScreenLabel(" --");
883     private final JLabel lSlash = createScreenLabel("/");
884     private final JLabel lVoices = createScreenLabel("-- ");
885    
886     public
887     StreamVoiceCountPane(Channel channel) {
888     this.channel = channel;
889    
890     setOpaque(false);
891     setLayout(new BoxLayout(this, BoxLayout.X_AXIS));
892     lStreams.setFont(Res.fontScreenMono);
893     lStreams.setHorizontalAlignment(JLabel.RIGHT);
894     lStreams.setToolTipText(i18n.getLabel("Channel.streamVoiceCount"));
895    
896     Dimension d = lStreams.getPreferredSize();
897     lStreams.setMinimumSize(d);
898     lStreams.setPreferredSize(d);
899     lStreams.setMaximumSize(d);
900     add(lStreams);
901    
902     lSlash.setFont(Res.fontScreenMono);
903     lSlash.setToolTipText(i18n.getLabel("Channel.streamVoiceCount"));
904     add(lSlash);
905    
906     lVoices.setFont(Res.fontScreenMono);
907     lVoices.setToolTipText(i18n.getLabel("Channel.streamVoiceCount"));
908    
909     d = lStreams.getPreferredSize();
910     lVoices.setMinimumSize(d);
911     lVoices.setPreferredSize(d);
912     lVoices.setMaximumSize(d);
913     add(lVoices);
914    
915     lStreams.addMouseListener(channel.getContextMenu());
916     lSlash.addMouseListener(channel.getContextMenu());
917     lVoices.addMouseListener(channel.getContextMenu());
918     }
919    
920     public void
921     updateStreamCount(int count) {
922     lStreams.setText(count == 0 ? " --" : String.valueOf(count));
923     }
924    
925     public void
926     updateVoiceCount(int count) {
927     lVoices.setText(count == 0 ? "-- " : String.valueOf(count));
928     }
929     }
930    
931     public static class VolumePane extends JPanel {
932     private final Channel channel;
933     private final JButton btnVolume = createScreenButton("");
934     private JSVolumeEditorPopup popupVolume;
935    
936     private static NumberFormat numberFormat = NumberFormat.getInstance();
937     static { numberFormat.setMaximumFractionDigits(1); }
938    
939     public
940     VolumePane(final Channel channel) {
941     this.channel = channel;
942     setOpaque(false);
943     setLayout(new BoxLayout(this, BoxLayout.X_AXIS));
944    
945     btnVolume.setIcon(Res.iconVolume14);
946     btnVolume.setIconTextGap(2);
947     btnVolume.setAlignmentX(RIGHT_ALIGNMENT);
948     btnVolume.setHorizontalAlignment(btnVolume.LEFT);
949     updateVolumeInfo(100);
950     Dimension d = btnVolume.getPreferredSize();
951     d.width = 57;
952     btnVolume.setPreferredSize(d);
953     btnVolume.setMinimumSize(d);
954    
955     add(btnVolume);
956    
957     btnVolume.addActionListener(new ActionListener() {
958     public void
959     actionPerformed(ActionEvent e) {
960     if(popupVolume.isVisible()) {
961     popupVolume.commit();
962     popupVolume.hide();
963     } else {
964     float vol = channel.getModel().getChannelInfo().getVolume();
965     popupVolume.setCurrentVolume(vol);
966     popupVolume.show();
967     }
968     }
969     });
970    
971     popupVolume = new JSVolumeEditorPopup(btnVolume, VolumeType.CHANNEL);
972    
973     popupVolume.addActionListener(new ActionListener() {
974     public void
975     actionPerformed(ActionEvent e) {
976     channel.getModel().setBackendVolume(popupVolume.getVolumeFactor());
977     }
978     });
979    
980     btnVolume.addMouseListener(channel.getContextMenu());
981     }
982    
983     public void
984     updateVolumeInfo(int volume) {
985     if(CC.getViewConfig().isMeasurementUnitDecibel()) {
986     String s = numberFormat.format(HF.percentsToDecibels(volume));
987     btnVolume.setText(s + "dB");
988     } else {
989     btnVolume.setText(String.valueOf(volume) + "%");
990     }
991     }
992     }
993    
994     public static class PowerButton extends PixmapToggleButton implements ActionListener {
995     private final Channel channel;
996    
997     PowerButton(Channel channel) {
998     this(channel, Res.gfxPowerOff, Res.gfxPowerOn);
999     }
1000    
1001     PowerButton(Channel channel, ImageIcon defaultIcon, ImageIcon selectedIcon) {
1002     super(defaultIcon, selectedIcon);
1003    
1004     this.channel = channel;
1005    
1006     setSelected(true);
1007     addActionListener(this);
1008     setToolTipText(i18n.getButtonLabel("Channel.ttRemoveChannel"));
1009     }
1010    
1011     public void
1012     actionPerformed(ActionEvent e) {
1013     boolean b = preferences().getBoolProperty(CONFIRM_CHANNEL_REMOVAL);
1014     if(b) {
1015     String s = i18n.getMessage("Channel.remove?", channel.getChannelId());
1016     if(!HF.showYesNoDialog(channel, s)) {
1017     setSelected(true);
1018     return;
1019     }
1020     }
1021     channel.remove();
1022     }
1023    
1024     public boolean
1025     contains(int x, int y) { return (x - 11)*(x - 11) + (y - 11)*(y - 11) < 71; }
1026     }
1027    
1028 iliev 1737 public static class OptionsButton extends PixmapToggleButton
1029     implements ActionListener, PropertyChangeListener {
1030    
1031 iliev 1732 private final Channel channel;
1032    
1033     OptionsButton(Channel channel) {
1034     super(Res.gfxOptionsOff, Res.gfxOptionsOn);
1035    
1036     this.channel = channel;
1037    
1038     setRolloverIcon(Res.gfxOptionsOffRO);
1039     this.setRolloverSelectedIcon(Res.gfxOptionsOnRO);
1040     addActionListener(this);
1041     setToolTipText(i18n.getButtonLabel("Channel.ttShowOptions"));
1042     }
1043    
1044     public void
1045     actionPerformed(ActionEvent e) {
1046 iliev 1737 ChannelView view = channel.viewTracker.getCurrentView();
1047    
1048     if(isSelected() && view.getChannelOptionsView() == null) {
1049     view.installChannelOptionsView();
1050     JComponent c = view.getChannelOptionsView().getComponent();
1051     channel.optionsPane.setContentPane(c);
1052     }
1053    
1054 iliev 1732 channel.showOptionsPane(isSelected());
1055    
1056     String s;
1057     if(isSelected()) s = i18n.getButtonLabel("Channel.ttHideOptions");
1058     else s = i18n.getButtonLabel("Channel.ttShowOptions");
1059    
1060     setToolTipText(s);
1061 iliev 1737
1062     s = JXCollapsiblePane.ANIMATION_STATE_KEY;
1063     channel.optionsPane.addPropertyChangeListener(s, this);
1064 iliev 1732 }
1065    
1066 iliev 1737 public void
1067     propertyChange(PropertyChangeEvent e) {
1068     if(e.getNewValue() == "collapsed") {
1069     ChannelView view = channel.viewTracker.getCurrentView();
1070     view.uninstallChannelOptionsView();
1071     channel.optionsPane.setContentPane(new JPanel());
1072     }
1073     }
1074    
1075     public void
1076     onDestroy() {
1077     String s = JXCollapsiblePane.ANIMATION_STATE_KEY;
1078     channel.optionsPane.removePropertyChangeListener(s, this);
1079     }
1080    
1081 iliev 1732 public boolean
1082     contains(int x, int y) { return super.contains(x, y) & y < 13; }
1083     }
1084 iliev 912 }
1085    
1086 iliev 1730 class ChannelOptionsPane extends JXCollapsiblePane {
1087     ChannelOptionsPane() {
1088 iliev 1285 setAnimated(false);
1089     setCollapsed(true);
1090     setAnimated(preferences().getBoolProperty(ANIMATED));
1091    
1092     preferences().addPropertyChangeListener(ANIMATED, new PropertyChangeListener() {
1093     public void
1094     propertyChange(PropertyChangeEvent e) {
1095     setAnimated(preferences().getBoolProperty(ANIMATED));
1096     }
1097     });
1098 iliev 912 }
1099    
1100 iliev 1730 public void
1101     showOptionsPane(boolean show) { setCollapsed(!show); }
1102 iliev 912 }

  ViewVC Help
Powered by ViewVC