- 功能分析
- 功能实现
- 界面与鼠标相应
- 图形绘制
- 图形外轮廓
- 总体展示
- 用鼠标拖动在界面中画出任意大小的矩形和圆形
- 在输入框中输入边数利用鼠标点击画出多边形
- 画出多边形的外轮廓
- 通过按钮实现功能切换
- 生成界面以及添加组件的方法请参考我的另一篇博客吧(^ v ^)
https://blog.csdn.net/G_Y_Chen/article/details/121119768
- 鼠标响应与按键响应的配置是类似的:
- 实例鼠标监听器接口
- 界面添加鼠标监听器
当然二者也是有不同的,关于按键的接口只有一个,鼠标响应的接口有两个:
- MouseListener
这个接口处理的是鼠标点击相关的行为,其包括5个方法:
mouseClicked鼠标点击(按下+抬起)、mousePressed鼠标按下、mouseReleased鼠标抬起、mouseEntered鼠标进入界面、mouseExited鼠标离开界面 - MouseMotionListener
这个接口处理的是鼠标的移动相关的行为,其包括2个方法:
mouseDragged鼠标拖动、mouseMoved鼠标移动
上述方法也获取一个鼠标对象MouseEvent e,可以通过e.getX()、e.getY()获取鼠标执行对应操作时的坐标。
本案例使用了mousePressed、mouseReleased两个方法实现图形的坐标点记,按压鼠标记录第一个点,松开鼠标记录第二个点。
图形绘制Java实现图形渲染需要使用Graphics类。Graphics类实例化对象不能用new,需要通过界面对象调用getGraphics()方法获得Graphics对象。
Jframe jf = new Jframe("图形绘制");
Graphics g = jf.getGraphics ();
Graphics对象能实现图形绘制如:g.drawRect画矩形、g.drawOval画圆形、g.drawLine画直线。
图形外轮廓- 算法概括
- 计算图形重心
- 视重心为坐标轴原点,建立坐标系。将图形的坐标点分为四个象限如图:
- 对各象限的坐标点进行排序,本案例使用各点的X轴坐标进行排序,第一第二象限是降序排列,第三第四象限是升序排列,这样图形坐标点就实现了逆时针排序
- 根据重排列的数组重新画出图形的轮廓
- UI设计
package draw;
import javax.swing.*;
import java.awt.*;
public class DrawUI {
public void initUI(){
Jframe jf = new Jframe("图形绘制");
jf.setSize(1000,1000);
jf.setDefaultCloseOperation (Jframe.EXIT_ON_CLOSE);// 关闭选项- 退出
jf.setLayout(new FlowLayout());
jf.setResizable (false);// 不能最大化 改变尺寸
DrawListener DrawListener = new DrawListener();
JButton bt_Rect = new JButton("方形");
JButton bt_Ovel = new JButton("圆形");
JButton bt_RectTen = new JButton("多边形");
JButton bt_Outline = new JButton("构建外轮廓");
JLabel shapein = new JLabel("边数:");
JTextField namein = new JTextField();
Dimension dim = new Dimension(50, 30);
namein.setPreferredSize(dim);
jf.add(bt_Rect);
jf.add(bt_Ovel);
jf.add(bt_RectTen);
jf.add(shapein);
jf.add(namein);
jf.add(bt_Outline);
jf.setVisible(true);
jf.addMouseListener (DrawListener);
jf.addMouseMotionListener(DrawListener);
Graphics g = jf.getGraphics ();
DrawListener.setG(g);
bt_Rect.addActionListener(DrawListener);
bt_Ovel.addActionListener(DrawListener);
bt_RectTen.addActionListener(DrawListener);
bt_Outline.addActionListener(DrawListener);
DrawListener.setNamein(namein);
}
public static void main(String[] args) {
DrawUI drawui = new DrawUI();
drawui.initUI();
}
}
- 鼠标与按键监听器
package draw;
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import java.util.Arrays;
public class DrawListener implements MouseListener, ActionListener, MouseMotionListener{
int x1,y1,x2,y2;
private Graphics g;
static String bt_name = "";
private JTextField namein;
static int shape;
public void setG(Graphics g) {
this.g = g;
}
public void setNamein(JTextField namein){
this.namein = namein;
}
private void SortDown(int[] Array_x, int[] Array_y, int num){
if (num>1){
for (int i = 0; i < num -1; i++){
if (Array_x[i] < Array_x[i+1]){
int temp = Array_x[i];
Array_x[i] = Array_x[i+1];
Array_x[i+1] = temp;
temp = Array_y[i];
Array_y[i] = Array_y[i+1];
Array_y[i+1] = temp;
}
}
}
}
private void SortUp(int[] Array_x, int[] Array_y, int num){
if (num>1){
for (int i = 0; i < num -1; i++){
if (Array_x[i] > Array_x[i+1]){
int temp = Array_x[i];
Array_x[i] = Array_x[i+1];
Array_x[i+1] = temp;
temp = Array_y[i];
Array_y[i] = Array_y[i+1];
Array_y[i+1] = temp;
}
}
}
}
private void DrawOutline(Integer[] x, Integer[]y){
g.setColor(Color.RED);
for (int i = 0; i < shape -1; i++) {
g.drawLine(x[i], y[i], x[i+1], y[i+1]);
}
g.drawLine(x[x.length-1], y[y.length-1], x[0], y[0]);
g.setColor(Color.black);
}
@Override
public void actionPerformed(ActionEvent e) {
bt_name = e.getActionCommand();
System.out.println(bt_name + "press");
if (bt_name.equals("多边形")){
shape = Integer.parseInt(namein.getText());
System.out.println(shape + "边型");
coordinates.setNum0();
}
else if (bt_name.equals("构建外轮廓")){
shape = Integer.parseInt(namein.getText());
if (shape > 3){
coordinates co = coordinates.getCo();
int sum_x = 0;
int sum_y = 0;
for (int i = 0; i < shape; i++){
sum_x += co.x[i];
sum_y += co.y[i];
}
int center_x = sum_x/shape;
int center_y = sum_y/shape;
System.out.println("centerx:" + center_x);
System.out.println("centery:" + center_y);
int[] rant1_x = new int[10];
int[] rant1_y = new int[10];
int rant1_num = 0;
int[] rant2_x = new int[10];
int[] rant2_y = new int[10];
int rant2_num = 0;
int[] rant3_x = new int[10];
int[] rant3_y = new int[10];
int rant3_num = 0;
int[] rant4_x = new int[10];
int[] rant4_y = new int[10];
int rant4_num = 0;
ArrayList DrawLine_x = new ArrayList<>();
ArrayList DrawLine_y = new ArrayList<>();
for (int i = 0; i < shape; i++){
if (co.x[i] < center_x){
if (co.y[i] > center_y){
//rent3
rant3_x[rant3_num] = co.x[i];
rant3_y[rant3_num] = co.y[i];
rant3_num++;
}
else{
//rent2
rant2_x[rant2_num] = co.x[i];
rant2_y[rant2_num] = co.y[i];
rant2_num++;
}
}
else{
if (co.y[i] > center_y){
//rent4
rant4_x[rant4_num] = co.x[i];
rant4_y[rant4_num] = co.y[i];
rant4_num++;
}
else{
//rent1
rant1_x[rant1_num] = co.x[i];
rant1_y[rant1_num] = co.y[i];
rant1_num++;
}
}
}
System.out.println(rant1_num);
System.out.println(rant2_num);
System.out.println(rant3_num);
System.out.println(rant4_num);
SortDown(rant1_x, rant1_y, rant1_num);
SortDown(rant2_x, rant2_y, rant2_num);
SortUp(rant3_x, rant3_y, rant3_num);
SortUp(rant4_x, rant4_y, rant4_num);
for (int i =0; i < rant1_num; i++){
DrawLine_x.add(rant1_x[i]);
DrawLine_y.add(rant1_y[i]);
}
for (int i =0; i < rant2_num; i++){
DrawLine_x.add(rant2_x[i]);
DrawLine_y.add(rant2_y[i]);
}
for (int i =0; i < rant3_num; i++){
DrawLine_x.add(rant3_x[i]);
DrawLine_y.add(rant3_y[i]);
}
for (int i =0; i < rant4_num; i++){
DrawLine_x.add(rant4_x[i]);
DrawLine_y.add(rant4_y[i]);
}
Integer[] nsx=new Integer[DrawLine_x.size()];
Integer[] nsy=new Integer[DrawLine_x.size()];
DrawLine_x.toArray(nsx);
DrawLine_y.toArray(nsy);
System.out.println(Arrays.toString(nsx));
System.out.println(Arrays.toString(nsy));
DrawOutline(nsx, nsy);
}
}
}
@Override
public void mouseClicked(MouseEvent e) {
}
@Override
public void mousePressed(MouseEvent e) {
//System.out.println("mousePressed");
x1 = e.getX();
y1 = e.getY();
if (bt_name.equals("多边形")){
coordinates co = coordinates.getCo();
// System.out.println(coordinates.getNum());
if (coordinates.getNum() < shape){
co.x[coordinates.getNum()] = e.getX();
System.out.println("x:" + co.x[coordinates.getNum()]);
co.y[coordinates.getNum()] = e.getY();
System.out.println("y:" + co.y[coordinates.getNum()]);
coordinates.setNumadd();
System.out.println(coordinates.getNum());
}
}
}
@Override
public void mouseReleased(MouseEvent e) {
//System.out.println("mouseReleased");
x2 = e.getX();
y2 = e.getY();
switch (bt_name) {
case "方形" -> g.drawRect(Math.min(x1, x2), Math.min(y1, y2), Math.abs(x2 - x1), Math.abs(y2 - y1));
case "圆形" -> g.drawOval(Math.min(x1, x2), Math.min(y1, y2), Math.abs(x2 - x1), Math.abs(y2 - y1));
case "多边形" -> {
coordinates co = coordinates.getCo();
if (coordinates.getNum() == shape) {
for (int i = 0; i < coordinates.getNum(); i++) {
if (i == coordinates.getNum()-1) {
g.drawLine(co.x[i], co.y[i], co.x[0], co.y[0]);
} else {
g.drawLine(co.x[i], co.y[i], co.x[i + 1], co.y[i + 1]);
}
}
coordinates.setNum0();
}
}
}
}
@Override
public void mouseEntered(MouseEvent e) {
}
@Override
public void mouseExited(MouseEvent e) {
}
@Override
public void mouseDragged(MouseEvent e) {
//System.out.println("mouseDragged");
}
@Override
public void mouseMoved(MouseEvent e) {
//System.out.println("mouseMoved");
}
}
- 坐标类
package draw;
public class coordinates {
int[] x = new int[10];
int[] y = new int[10];
static int num = 0;
private static final coordinates co = new coordinates();
public static coordinates getCo() {
return co;
}
public static int getNum() {
return num;
}
public static void setNumadd() {
coordinates.num = coordinates.num + 1;
}
public static void setNum0() {
coordinates.num = 0;
}
}



