/[svn]/jsampler/trunk/src/org/jsampler/view/std/BasicPianoRollPainter.java
ViewVC logotype

Annotation of /jsampler/trunk/src/org/jsampler/view/std/BasicPianoRollPainter.java

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1778 - (hide annotations) (download)
Sun Sep 28 20:38:36 2008 UTC (15 years, 7 months ago) by iliev
File size: 8093 byte(s)
* Fantasia: Improved look and feel
* Fantasia: Added buttons for increasing/decreasing the key number
  of the MIDI keyboard (Ctrl+Up Arrow/Ctrl+Down Arrow)
* Fantasia: Added buttons for scrolling left/right on the MIDI keyboard
  (Ctrl+Left Arrow/Ctrl+Right Arrow)
* Added key bindings for triggering MIDI notes using the computer keyboard
  (from a to ' for the white keys and from 0 to 7 for changing the octaves)
* Notes are now triggered when dragging the mouse over the MIDI keyboard

1 iliev 1778 /*
2     * JSampler - a java front-end for LinuxSampler
3     *
4     * Copyright (C) 2005-2008 Grigor Iliev <grigor@grigoriliev.com>
5     *
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.std;
24    
25     import java.awt.Font;
26     import java.awt.FontMetrics;
27     import java.awt.Color;
28     import java.awt.Font;
29     import java.awt.FontMetrics;
30     import java.awt.GradientPaint;
31     import java.awt.Graphics2D;
32     import java.awt.Point;
33     import java.awt.Rectangle;
34     import java.awt.RenderingHints;
35    
36     import java.awt.geom.RoundRectangle2D;
37    
38     /**
39     *
40     * @author Grigor Iliev
41     */
42     public class BasicPianoRollPainter implements PianoRollPainter {
43     private PianoRoll pianoRoll;
44    
45     private Color borderColor = Color.BLACK;
46     private Color keyColor = Color.WHITE;
47     private Color disabledKeyColor = new Color(0xaaaaaa);
48     private Color pressedKeyColor = Color.GREEN;
49     private Color keySwitchColor = Color.PINK;
50     private Color blackKeyColor = Color.BLACK;
51    
52     public
53     BasicPianoRollPainter(PianoRoll pianoRoll) {
54     if(pianoRoll == null) {
55     throw new IllegalArgumentException("piano roll must be non-null");
56     }
57     this.pianoRoll = pianoRoll;
58     }
59    
60     @Override
61     public void
62     paint(PianoRoll pianoRoll, Graphics2D g) {
63     double whiteKeyWidth = getWhiteKeyWidth();
64     double whiteKeyHeight = getWhiteKeyHeight();
65     double arcw = whiteKeyWidth/4.0d;
66     double arch = whiteKeyHeight/14.0d;
67    
68     g.setPaint(keyColor);
69    
70     RoundRectangle2D.Double rect;
71    
72     g.setRenderingHint (
73     RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF
74     );
75    
76     int i = 0;
77     for(int j = pianoRoll.getFirstKey(); j <= pianoRoll.getLastKey(); j++) {
78     if(!PianoRoll.isWhiteKey(j)) continue;
79    
80     Color c = getKeyColor(j);
81     if(g.getPaint() != c) g.setPaint(c);
82    
83     rect = new RoundRectangle2D.Double (
84     // If you change this you should also change getKeyRectangle()
85     whiteKeyWidth * i + i, 0,
86     whiteKeyWidth, whiteKeyHeight,
87     arcw, arch
88     );
89    
90     g.fill(rect);
91     i++;
92     }
93    
94     g.setRenderingHint (
95     RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON
96     );
97    
98     g.setStroke(new java.awt.BasicStroke(1.5f));
99     g.setPaint(borderColor);
100    
101     i = 0;
102     for(int j = pianoRoll.getFirstKey(); j <= pianoRoll.getLastKey(); j++) {
103     if(!PianoRoll.isWhiteKey(j)) continue;
104    
105     rect = new RoundRectangle2D.Double (
106     whiteKeyWidth * i + i, 0,
107     whiteKeyWidth, whiteKeyHeight,
108     arcw, arch
109     );
110    
111     g.draw(rect);
112     i++;
113     }
114    
115    
116     g.setStroke(new java.awt.BasicStroke(2.5f));
117     double blackKeyWidth = getBlackKeyWidth();
118     double blackKeyHeight = getBlackKeyHeight();
119    
120     i = 0;
121     for(int j = pianoRoll.getFirstKey(); j <= pianoRoll.getLastKey(); j++) {
122     if(pianoRoll.getOctaveLabelsVisible() && j % 12 == 0) {
123     int octave = j / 12 - 2;
124     paintOctaveLabel(g, octave, i);
125     }
126     if(!PianoRoll.isWhiteKey(j)) continue;
127    
128     int k = (i + PianoRoll.getKeyOctaveIndex(pianoRoll.getFirstKey())) % 7;
129     if(k == 2 || k == 6) { i++; continue; }
130    
131     Color c = (j == pianoRoll.getLastKey()) ? blackKeyColor : getKeyColor(j + 1);
132     if(g.getPaint() != c) g.setPaint(c);
133    
134     // If you change this you should also change getKeyRectangle()
135     double x = blackKeyWidth * (2*(i + 1)) - blackKeyWidth * 0.5d + i;
136     rect = new RoundRectangle2D.Double (
137     // If you change this you should also change getKeyRectangle()
138     x, 0,
139     blackKeyWidth, blackKeyHeight,
140     arcw, arch
141     );
142     ///////
143    
144     boolean pressed = (j == pianoRoll.getLastKey()) ? false : pianoRoll.getKey(j + 1).isPressed();
145     if(!pressed) g.fill(rect);
146    
147     RoundRectangle2D.Double rect2;
148     rect2 = new RoundRectangle2D.Double (
149     x, 0,
150     blackKeyWidth, arch,
151     arcw, arch / 1.8d
152     );
153    
154     g.fill(rect2);
155     g.setPaint(borderColor);
156     g.draw(rect);
157    
158     if(pressed) {
159     GradientPaint gr = new GradientPaint (
160     (float)(x + blackKeyWidth/2), (float)(blackKeyHeight/4), Color.BLACK,
161     (float)(x + blackKeyWidth/2), (float)blackKeyHeight, new Color(0x058a02)
162     );
163     g.setPaint(gr);
164     g.fill(rect);
165     }
166     i++;
167     }
168     }
169    
170     protected void
171     paintOctaveLabel(Graphics2D g, int octave, int whiteKeyIndex) {
172     double h = pianoRoll.getSize().getHeight();
173     double whiteKeyWidth = getWhiteKeyWidth();
174     g.setPaint(Color.BLACK);
175     int fsize = (int) (whiteKeyWidth / (1.5 + whiteKeyWidth / 50));
176     if(fsize < 8) fsize = 8;
177     g.setFont(g.getFont().deriveFont(Font.BOLD, fsize));
178    
179     float x = (float) (whiteKeyWidth * whiteKeyIndex + whiteKeyIndex);
180     float y = (float) (h - 1);
181    
182     String s = String.valueOf(octave);
183     FontMetrics fm = g.getFontMetrics();
184    
185     // center text
186     int i = fm.stringWidth(s);
187     if(i < whiteKeyWidth) {
188     x += (whiteKeyWidth - i) / 2;
189     } else {
190     x += 2;
191     }
192    
193     y -= (h / 12);
194    
195     g.drawString(s, x, y);
196     }
197    
198     private Color
199     getKeyColor(int key) {
200     PianoRoll.Key k = pianoRoll.getKey(key);
201     if(PianoRoll.isWhiteKey(key)) {
202     if(k.isPressed()) return pressedKeyColor;
203     if(k.isKeyswitch()) return keySwitchColor;
204     if(k.isDisabled()) return disabledKeyColor;
205     return keyColor;
206     } else {
207     if(k.isPressed()) return Color.GREEN;
208     return blackKeyColor;
209     }
210     }
211    
212    
213     private double
214     getWhiteKeyWidth() {
215     double w = pianoRoll.getSize().getWidth();
216     return (w - pianoRoll.getWhiteKeyCount()) / pianoRoll.getWhiteKeyCount();
217     }
218    
219     private double
220     getWhiteKeyHeight() {
221     return pianoRoll.getSize().getHeight() - 3.0d;
222     }
223    
224     private double
225     getBlackKeyWidth() {
226     return getWhiteKeyWidth() / 2.0d;
227     }
228    
229     private double
230     getBlackKeyHeight() {
231     return getWhiteKeyHeight() / 1.5d;
232     }
233    
234     /**
235     * Gets the index of the key containing the specified point.
236     * @return Number between 0 and 127 (inclusive) as specified in the MIDI standard.
237     */
238     @Override
239     public int
240     getKeyByPoint(Point p) {
241     double w = getWhiteKeyWidth() + /* space between keys */ 1.0d;
242     if(w == 0) return -1;
243     int whiteKeyNumber = (int) (p.getX() / w);
244     double leftBorder = whiteKeyNumber * w;
245     int key = pianoRoll.getWhiteKeyByNumber(whiteKeyNumber);
246     if(key == -1) return -1;
247    
248     double bh = getBlackKeyHeight();
249     double blackKeyOffset = w / 4.0d;
250     if(p.getY() > bh) return key;
251     if(key != pianoRoll.getFirstKey() && !PianoRoll.isWhiteKey(key - 1)) {
252     if(p.getX() <= leftBorder + blackKeyOffset) return key - 1;
253     }
254     if(key != pianoRoll.getLastKey() && !PianoRoll.isWhiteKey(key + 1)) {
255     if(p.getX() >= leftBorder + 3 * blackKeyOffset - 3) return key + 1;
256     }
257    
258     return key;
259     }
260    
261     @Override
262     public Rectangle
263     getKeyRectangle(int key) {
264     Rectangle r = new Rectangle();
265     if(!pianoRoll.hasKey(key)) return r;
266    
267     int whiteKeyIndex = PianoRoll.getWhiteKeyCount(pianoRoll.getFirstKey(), key) - 1;
268    
269     if(PianoRoll.isWhiteKey(key)) {
270     double whiteKeyWidth = getWhiteKeyWidth();
271     double whiteKeyHeight = getWhiteKeyHeight();
272     double x = whiteKeyWidth * whiteKeyIndex + whiteKeyIndex;
273     r.setRect(x, 0, whiteKeyWidth, whiteKeyHeight);
274     } else {
275     double blackKeyWidth = getBlackKeyWidth();
276     double blackKeyHeight = getBlackKeyHeight();
277     int i = whiteKeyIndex;
278     double x = blackKeyWidth * (2*(i + 1)) - blackKeyWidth * 0.5d + i;
279     r.setRect(x, 0, blackKeyWidth, blackKeyHeight);
280     }
281    
282     return r;
283     }
284    
285     @Override
286     public int
287     getVelocity(Point p, int key) {
288     boolean whiteKey = PianoRoll.isWhiteKey(key);
289     double h = whiteKey ? getWhiteKeyHeight() : getBlackKeyHeight();
290     int velocity = (int) ((p.getY() / h) * 127.0d + 1);
291     if(velocity < 0) velocity = 0;
292     if(velocity > 127) velocity = 127;
293     return velocity;
294     }
295     }

  ViewVC Help
Powered by ViewVC