JFrame 不规则窗体
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JFrame 不规则窗体相关的知识,希望对你有一定的参考价值。
效果截图:
这几天静心学java,由于学的不是很好,也没有什么有什么可以作品,但是毕竟也算刚开始认真学,也遇到了好多问题;
首先
1. JFrame的无边框设置:JFrame.setUndecorated(true);这个属性网上提到的很多;是在JFrame在显示情况下(JFrame.setVisible(true);)能去掉JFrame默认的标题和边框。
2.背景图形设置:com.sun.awt.AWTUtilities.setWindowShape(Window w,Shape s);这个是jre里面自带的一个rt.jar包,但说有查到说使用这个包之后程序就不会有跨平台性,但是也可以引用第三方库 jna.jar + platform.jar 提供的WindowUtils类可以实现快平台,以后我试试吧。
3.背景图形的绘制:这个很感谢那个大神,我搜了很久终于搜到了这个算法:
1 package object; 2 3 import java.awt.Image; 4 import java.awt.Rectangle; 5 import java.awt.Shape; 6 import java.awt.geom.Area; 7 import java.awt.image.PixelGrabber; 8 import java.util.ArrayList; 9 10 public class getImage { 11 public Shape getImageShape(Image img) { 12 ArrayList<Integer> x = new ArrayList<Integer>(); 13 ArrayList<Integer> y = new ArrayList<Integer>(); 14 int width = img.getWidth(null);//图像宽度 15 int height = img.getHeight(null);//图像高度 16 17 //筛选像素 18 //首先获取图像所有的像素信息 19 PixelGrabber pgr = new PixelGrabber(img, 0, 0, -1, -1, true); 20 try { 21 pgr.grabPixels(); 22 } catch (InterruptedException ex) { 23 ex.getStackTrace(); 24 } 25 int pixels[] = (int[]) pgr.getPixels(); 26 for (int i = 0; i < pixels.length; i++) { 27 //筛选,将不透明的像素的坐标加入到坐标ArrayList x和y中 28 int alpha = getAlpha(pixels[i]); 29 if (alpha == 0) { 30 continue; 31 } else { 32 x.add(i % width > 0 ? i % width - 1 : 0); 33 y.add(i % width == 0 ? (i == 0 ? 0 : i / width - 1) : i / width); 34 } 35 } 36 int[][] matrix = new int[height][width]; 37 for (int i = 0; i < height; i++) { 38 for (int j = 0; j < width; j++) { 39 matrix[i][j] = 0; 40 } 41 } 42 43 //导入坐标ArrayList中的不透明坐标信息 44 for (int c = 0; c < x.size(); c++) { 45 matrix[y.get(c)][x.get(c)] = 1; 46 } 47 48 Area rec = new Area(); 49 int temp = 0; 50 51 for (int i = 0; i < height; i++) { 52 for (int j = 0; j < width; j++) { 53 if (matrix[i][j] == 1) { 54 if (temp == 0) { 55 temp = j; 56 } else if (j == width) { 57 if (temp == 0) { 58 Rectangle rectemp = new Rectangle(j, i, 1, 1); 59 rec.add(new Area(rectemp)); 60 } else { 61 Rectangle rectemp = new Rectangle(temp, i, j - temp, 1); 62 rec.add(new Area(rectemp)); 63 temp = 0; 64 } 65 } 66 } else { 67 if (temp != 0) { 68 Rectangle rectemp = new Rectangle(temp, i, j - temp, 1); 69 rec.add(new Area(rectemp)); 70 temp = 0; 71 } 72 } 73 } 74 temp = 0; 75 } 76 return rec; 77 } 78 79 private int getAlpha(int pixel) { 80 return (pixel >> 24) & 0xff; 81 } 82 }
这个算法可以将图片alpha=0的部位直接剔除掉并得到一个新的图形,使用com.sun.awt.AWTUtilities.setWindowShape感觉是拿这个图形对窗体背景进行遮罩:
因此,还要将想要的背景图重新添加到窗体上【注:高宽位置正好要对准】。
好了,然后直接在这个窗体上添加所需要的控件。
4.窗体的拖动:
拖动的话我是在当前Frame顶部添加了一个JLabel:然后添加拖动事件:
1 //... 2 3 this.dragbar.addMouseListener(new MouseAdapter() { 4 @Override 5 public void mousePressed(MouseEvent e) { 6 getlocationPoint(e); 7 } 8 }); 9 10 this.dragbar.addMouseMotionListener(new MouseAdapter() { 11 @Override 12 public void mouseDragged(MouseEvent e) { 13 dragwindow(e); 14 } 15 }); 16 17 //... 18 19 protected void getlocationPoint(MouseEvent e) { 20 this.px1=e.getX(); 21 this.py1=e.getY(); 22 23 } 24 protected void dragwindow(MouseEvent e) { 25 JLabel bar=(JLabel)e.getSource(); 26 int xx=this.jf.getX()+e.getX()-this.px1; 27 int yy=this.jf.getY()+e.getY()-this.py1; 28 this.jf.setLocation(xx, yy); 29 30 }
以上是关于JFrame 不规则窗体的主要内容,如果未能解决你的问题,请参考以下文章