-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathWavePainter.java
132 lines (112 loc) · 3.31 KB
/
WavePainter.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
import javax.swing.*;
import javax.swing.event.MouseInputAdapter;
import java.awt.*;
import java.awt.event.MouseEvent;
public class WavePainter {
private static final int WIDTH = 320;
private static final int HEIGHT = 240;
private static final int NSAMPLES = 256;
private JFrame frame;
private JPanel drawPanel;
private JPanel buttonPanel;
private int[] waveData = new int[WIDTH];
private byte[] data = new byte[NSAMPLES];
private Point lastPos = new Point(0, 0);
private WavePainter() {
for (int i = 0; i < WIDTH; i++) {
waveData[i] = HEIGHT / 2;
}
frame = new JFrame("WavePainter");
frame.setSize(WIDTH, HEIGHT);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLocationRelativeTo(null);
drawPanel = new JPanel() {
@Override
public void paint(Graphics g) {
super.paint(g);
/* Apparently, `Graphics` defines its own `WIDTH` and `HEIGHT` variables
so we have to preface ours with `WavePainter.` */
// draw a zero line
g.setColor(Color.blue);
g.drawLine(0, WavePainter.HEIGHT / 2, WavePainter.WIDTH, WavePainter.HEIGHT / 2);
// draw the waveform
g.setColor(Color.black);
for (int i = 0; i < WavePainter.WIDTH - 1; i++) {
g.drawLine(i, waveData[i], i + 1, waveData[i + 1]);
}
}
};
MouseInputAdapter mia = new MouseInputAdapter() {
@Override
public void mousePressed(MouseEvent e) {
lastPos.x = e.getX();
lastPos.y = e.getY();
}
@Override
public void mouseReleased(MouseEvent e) {
lastPos.x = -1;
lastPos.y = -1;
}
@Override
public void mouseClicked(MouseEvent e) {
int x = e.getX();
int y = e.getY();
if (x >= 0 && x < WIDTH && y >= 0 && y < HEIGHT) {
waveData[x] = y;
}
}
@Override
public void mouseDragged(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.err.println("dragged to " + x + ", " + y);
if (x >= 0 && x < WIDTH && y >= 0 && y < HEIGHT) {
// lerp between the last point we got an event for and this point
if (lastPos.x < x) {
for (int i = lastPos.x; i <= x; i++) {
waveData[i] = lastPos.y + (y - lastPos.y) * (i - lastPos.x) / (x - lastPos.x);
}
} else if (x < lastPos.x) {
for (int i = x; i <= lastPos.x; i++) {
waveData[i] = y + (lastPos.y - y) * (i - x) / (lastPos.x - x);
}
} else {
// avoid a divide-by-zero
waveData[x] = y;
}
lastPos.x = x;
lastPos.y = y;
}
drawPanel.repaint();
}
};
drawPanel.addMouseListener(mia);
drawPanel.addMouseMotionListener(mia);
buttonPanel = new JPanel();
JButton setButton = new JButton("Set Wave");
setButton.addActionListener(e -> sendData());
buttonPanel.add(setButton);
frame.setLayout(new BorderLayout());
frame.add(drawPanel, BorderLayout.CENTER);
frame.add(buttonPanel, BorderLayout.SOUTH);
frame.setVisible(true);
}
private void sendData() {
int max = 0;
for (int i = 0; i < WIDTH; i++) {
int v = Math.abs(waveData[i] - WIDTH / 2);
if (v > max) max = v;
}
for (int i = 0; i < NSAMPLES; i++) {
int x = i * WIDTH / NSAMPLES;
byte val = (byte) ((waveData[x] - WIDTH / 2) * 127 / max);
data[i] = val;
}
System.out.write('s');
System.out.flush();
System.out.write(data, 0, NSAMPLES);
}
public static void main(String[] args) {
new WavePainter();
}
}