第9章 Java在多媒体中的应用.ppt

上传人:韩长文 文档编号:5030348 上传时间:2020-01-29 格式:PPT 页数:123 大小:911.50KB
返回 下载 相关 举报
第9章 Java在多媒体中的应用.ppt_第1页
第1页 / 共123页
第9章 Java在多媒体中的应用.ppt_第2页
第2页 / 共123页
第9章 Java在多媒体中的应用.ppt_第3页
第3页 / 共123页
第9章 Java在多媒体中的应用.ppt_第4页
第4页 / 共123页
第9章 Java在多媒体中的应用.ppt_第5页
第5页 / 共123页
点击查看更多>>
资源描述

《第9章 Java在多媒体中的应用.ppt》由会员分享,可在线阅读,更多相关《第9章 Java在多媒体中的应用.ppt(123页珍藏版)》请在三一文库上搜索。

1、第9章 Java在多媒体中的应用,9.1 利用AWT绘图 9.2 Graphics类的使用 9.3 Font类的使用 9.4 图像处理 9.5 动画图像处理,9.1 利用AWT绘图,这一节中我们主要介绍如何使用Java语言提供的AWT包绘图。java.awt包中提供了用于绘图的API,我们通常称之为2D API。不要以为只有设计绘图程序或游戏软件才会用到Java 2D,其实Java 2D的用途可能远比你想象的更广泛。,其实,只要你的程序有GUI,就很可能会用到Java 2D。因为AWT和Swing的组件常常无法完全适合我们,这个时候自己绘制一部分的GUI就有绝对的必要。甚至,我们还可以用Jav

2、a 2D来绘制自己的组件。实际上,AWT和Swing组件都是透过Java 2D来进行绘制的。,Java 2D API增强了AWT的图形、文本和图像功能,可以开发更为强大的用户接口和新型的Java应用程序。除了更为强大的图形、字体和图像API外,Java 2D API还改进了颜色的定义与复合及对任意几何形状和文本的选中检测,并为打印机和显示设备提供了统一的绘制模式。Java 2D API还可以创建高级图形库,并可创建图像和图形文件读/写过滤器。当与Java媒体框架 (JMF) 和其他Java媒体应用程序配合使用时,Java 2D API还可用来创建和显示动画和其他多媒体演示稿。,到底Java 2

3、D API有多强大?这一点我们可以通过SUN JDK包中提供的例程来了解。在命令行窗口下输入: c:cd jdk1.2demojfcJava2D c:jdk1.2demojfcJava2Djava -classpath Java2Demo.jar Java2Demo 或 c:jdk1.2demojfcJava2Dappletviewer java2demo.html 看到了吗?Java 2D神奇的威力!,下面我们来学习如何使用Java 2D绘图。上面看到的例子虽然功能十分强大,但是它的实现非常复杂。下面,我们先从简单一点的入手。 从java.awt.Component类(所有窗口对象的基类)继

4、承的类提供了一个名为paint()的方法,在需要重新绘制组件时,可调用该方法。 paint()方法只有一个参数,该参数是Graphics类的实例。如果在某个继承了Component的类中覆盖了该方法,那么就可以使用该方法来控制在控制区域着何种颜色。例如,下面的类创建了一个带有蓝背景的面板。,例9.1 BluePanel.java import java.awt.*; class BluePanel extends Panel public static void main(String args) Frame f = new Frame(); BluePanel p = new BluePan

5、el(); f.add(p); f.setSize(300,100); f.setVisible(true);,/ Invoked when the panel needs to be repainted public void paint(Graphics g) / Get the rectangle that represents the viewable area / of the panel Rectangle rect = g.getClipBounds(); / Set the context to paint in a pre-defined color g.setColor(C

6、olor.blue); / Fill the rectangle with the current color g.fillRect(rect.x, rect.y, rect.width, rect.height); 程序运行结果如图9.1所示。,图 9.1,9.2 Graphics类的使用,java.awt中提供了一系列的类用于绘制图形。其中,Color类包含了编辑颜色的方法和常量;Font类包含了编辑字体的方法和常量;FontMetrics类包含了获取字体信息的方法;Polygon类包含了创建多边形的方法;Toolkit类提供了从系统获得图形信息的方法,例如可显示的字体集和屏幕分辨率等等;

7、Graphics类包含了绘制字符串、线条以及各种几何图形的方法。,Graphics是一个抽象类,其作用是定义一个真正的工具,用来接受图形操作。在该类中,有47个公用方法,可以用作显示图像和文本、绘制和填充形状、剪贴图像操作等等。 9.2.1 绘制字符串、字符和字节 用于绘制字符串、字符和字节的方法分别为 public abstract void drawString(String string, int x, int y)在坐标(x,y)处以当前字体和颜色绘制指定的字符串string。, public void drawChars(char chars, int offset, int num

8、ber, int x, int y) 在坐标(x,y)处以当前字体和颜色绘制指定的一系列字符。chars为要绘制的字符组,offset为位置的坐标,number为要绘制的元素个数。 public void drawBytes(byte bytes, int offset, int number, int x, int y) 在坐标(x,y)处以当前字体和颜色绘制指定的一系列字节。bytes为要绘制的字节数组,offset为位置的坐标,number为要绘制的元素个数。,下面的例子展示了如何使用了drawString(),drawChars()和drawBytes()三个方法: 例9.2 Draw

9、SCB.java import java.awt.*; public class DrawSCB extends Frame String s = “Using drawString!“; char c = c, h, a, r, s, , 8; byte b = b, y, t, e, 1, 2, 3;,public static void main(String args) DrawSCB frame = new DrawSCB(); frame.setSize(300, 100); frame.setVisible(true); public void paint(Graphics g)

10、 g.drawString(s, 100, 40); g.drawChars(c, 0, 7, 100, 65); g.drawBytes(b, 0, 5, 100, 90); 程序运行结果如图9.2所示。,图 9.2,9.2.2 颜色控制 Color类定义了颜色常量和方法。每种颜色都是从RGB(红/绿/蓝)值创建出来的。一个RGB值有三部分,都是从0255的整数值,分别代表着三种颜色的含量。因此,实际上我们可以使用256256256种颜色,即224种颜色。这就是我们常说的24位真彩色。但不是任何计算机都可以显示所有的颜色,就目前来说,大部分计算机都可以显示24位甚至超过24位的彩色。显然,我

11、们很难记住一种颜色的RGB值,因而,Color类将一些最常用的颜色预定义为常量以方便我们使用。表9.1列出了预定义的颜色常量。,表9.1 Color类中定义的颜色常量,Color类中常用的一些方法如下: public Color(int r, int g, int b):创建指定RGB值的颜色。 public int getRed():返回红色含量的值。 public int getBlue():返回蓝色含量的值。 public int getGreen():返回绿色含量的值。 Graphics类与Color类相关的常用方法有: public abstact Color getColor():

12、返回图形上下文的当前颜色。 public abstract void setColor(Color c):设置图形上下文的当前颜色。,下面来看一个颜色控制的实例。 例9.3 ShowColor.java import java.awt.*; public class ShowColor extends Frame int red, green, blue; public static void main(String args) ShowColor frame = new ShowColor(); frame.setSize(300, 100); frame.setVisible(true);

13、 public ShowColor(), red = 200; green = 100; blue = 0; public void paint(Graphics g) g.setColor(new Color(red, green, blue); g.drawString(“Draw color string.“, 50, 40); Color color = g.getColor();,g.drawString(“Red:“+color.getRed(), 10, 70); g.drawString(“Green:“+color.getGreen(), 100, 70); g.drawSt

14、ring(“Blue:“+color.getBlue(), 200, 70); 程序运行结果如图9.3所示。,图 9.3,9.2.3 绘制几何图形 Graphics类中用于绘制几何图形的方法如下: public abstract void drawLine(int x1, int y1, int x2, int y2) 在点(x1,y1)和(x2,y2)之间用当前颜色绘制线段。 public void drawRect(int x, int y, int width, int height) 以点(x,y)为左上角坐标,width和height为宽度和高度,用当前颜色画矩形。 public a

15、bstact void fillRect(int x, int y, int width, int height),以点(x,y)为左上角坐标,width和height为宽度和高度,用当前颜色画一个实心的矩形。 public abstact void clearRect(int x, int y, int width, int height) 以点(x,y)为左上角坐标,width和height为宽度和高度,用当前背景颜色画一个实心的矩形。此方法用于清除某个矩形显示区域。 public abstact void drawRoundRect(int x, int y, int width, in

16、t height, int arcWidth, int arcHeight) 以点(x,y)为左上角坐标,width和height为宽度和高度,用当前颜色画圆角矩形。, public abstact void fillRoundRect(int x, int y, int width, int height, int arcWidth, int arcHeight) 以点(x,y)为左上角坐标,width和height为宽度和高度,用当前颜色画一个实心的圆角矩形。 public void draw3Drect(int x, int y, int width, int height, boole

17、an b) 用指定的width和height,以当前颜色画一个三维矩形。矩形的左上角坐标为(x,y)。当b为true时,矩形为凸的;b为false时,矩形为凹的。, public void fill3Drect(int x, int y, int width, int height, boolean b) 用指定的width和height,以当前颜色画一个填充的三维矩形。矩形的左上角坐标为(x,y)。当b为true时,矩形为凸的;b为false时,矩形为凹的。 public abstract void drawOval(int x, int y, int width, int height)

18、用指定的width和height,以当前颜色画椭圆。外切矩形的左上角坐标为(x,y)。 public abstract void fillOval(int x, int y, int width, int height) 用指定的width和height,以当前颜色画实心椭圆。外切矩形的左上角坐标为(x,y)。, public abstract void drawArc(int x, int y, int width, int height, int startAngle, int arcAngle) 参考外切矩形的左上角坐标(x,y),用指定的width和height,以当前颜色绘制一段弧。

19、弧段从起始角startAngle开始一直到张角arcAngle。 public abstract void fillArc(int x, int y, int width, int height, int startAngle, int arcAngle) 参考外切矩形的左上角坐标(x,y),用指定的width和height,以当前颜色绘制一段实心的弧。弧段从起始角startAngle开始一直到张角arcAngle。, public abstract void drawPolygon(int xPoints, int yPoints, int points) 以当前颜色画一个具有points个

20、顶点的多边形。xPoint和yPoint数组分别指定了每个顶点的x和y坐标。 public void drawPolygon(Polygon p) 以当前颜色画指定的多边形。, public abstract void fillPolygon(int xPoints, int, yPoints, int points) 以当前颜色画一个具有points个顶点的填充多边形。xPoint和yPoint数组分别指定了每个顶点的x和y坐标。 下面我们通过一个例子来学习这些方法。,例9.4 DrawDemo.java import java.awt.*; public class DrawDemo ex

21、tends Frame public static void main(String args) DrawDemo frame = new DrawDemo(); frame.setSize(400, 500); frame.setVisible(true); public void paint(Graphics g), / draw a line g.drawLine(10, 30, 200, 40); / draw a rectangle g.drawRect(10, 50, 100, 50); / draw a filled rectangle g.fillRect(150, 50, 1

22、00, 50); / draw a rounded rectangle g.drawRoundRect(10, 120, 50, 50, 10, 20); / draw a filled rounded rectangle g.fillRoundRect(80, 120, 50, 50, 40, 20); / draw a ellipse,g.drawRoundRect(150, 130, 80, 20, 70, 70); / draw a filled square g.drawRoundRect(250, 120, 50, 50, 0, 0); / draw a circle g.draw

23、RoundRect(330, 120, 50, 50, 50, 50); g.setColor(Color.yellow); / draw a raised 3D rectangle g.draw3DRect(10, 190, 50, 50, true); / draw a sunk 3D rectangle g.draw3DRect(100, 190, 50, 50, false);,/ draw a filled raised 3D rectangle g.fill3DRect(200, 190, 50, 50, true); / draw a filled sunk 3D rectang

24、le g.fill3DRect(300, 190, 50, 50, false); g.setColor(Color.black); / draw an oval g.drawOval(10, 260, 70, 50); / draw an filled oval g.fillOval(200, 260, 50, 70); / draw an arc g.drawArc(10, 350, 60, 60, 0, 180);,/ draw solid arc g.fillArc(100, 350, 50, 60, 0, 270); g.fillArc(200, 350, 50, 60, 0, -1

25、10); g.fillArc(300, 350, 40, 60, 0, -360); / draw a polygon int xPoints1 = 10, 30, 40, 20, 10, 5, 10; int yPoints1 = 430, 430, 440, 460, 460, 440, 430; g.drawPolygon(xPoints1, yPoints1, 7);,/ draw a filled polygon int xPoints2 = 100, 120, 130, 110, 100, 95, 90, 100; int yPoints2 = 430, 430, 440, 460

26、, 460, 440, 420, 430; g.fillPolygon(xPoints2, yPoints2, 8); 程序运行结果如图9.4所示。,图 9.4,9.2.4 屏幕操作 本节介绍一种实现屏幕操作的Graphics方法copyArea()。copyArea()方法用于复制屏幕的一个区域,并将它放置在屏幕的另一个位置上。copyArea方法的定义如下:public abstract void copyArea(int x, int y, int width, int height, int dx, int dy)其中,参数x和y指定了复制区域的左上角坐标;width和height为区

27、域的宽和高;dx和dy指定了与点(x,y)的水平和垂直偏移量,复制的区域放置在该偏移量相对于(x,y)的位置上。,例9.5 CopyAreaDemo.java import java.awt.*; public class CopyAreaDemo extends Frame public static void main(String args) CopyAreaDemo frame = new CopyAreaDemo(); frame.setSize(300, 200); frame.setVisible(true); public void paint(Graphics g), g.d

28、rawRect(20, 30, 50, 50); g.fillOval(50, 100, 50, 70); g.copyArea(20, 30, 100, 170, 150, 20); 程序运行结果如图9.5所示。,图 9.5,9.2.5 绘图模式 绘图模式(paint mode)用于描述如何绘图。默认的绘图模式是覆盖模式(overwrite),当一个图形画在另一个图形上面时,旧的图形将被覆盖,看到的将只是新的图形。另外,还有一种异或绘图模式(XOR),使用这种模式可以看到互相重叠的所有图形。使用异或绘图模式可以通过调用Graphics的方法: public abstract void set

29、XORMode(Color c),来实现。该方法的参数为一个Color对象。这个颜色称作XORMode颜色。由于XOR绘图模式实际上是对新旧两种颜色的二进制值做异或操作,所以当重叠的部分颜色相同时,将恢复为背景颜色。这时候可以通过设置XORMode颜色,指定用某颜色来替代。例如: 例9.6 XORModeDemo.java import java.awt.*; public class XORModeDemo extends Frame public static void main(String args) XORModeDemo frame = new XORModeDemo();,fra

30、me.setSize(300, 100); frame.setVisible(true); public void paint(Graphics g) / draw a pink oval g.setColor(Color.pink); g.fillOval(20, 30, 100, 50); / draw a yellow rectangle over part of the oval g.setColor(Color.yellow); g.fillRect(100, 30, 100, 50); / draw an orange rectangle g.setColor(Color.oran

31、ge);,g.fillOval(190, 30, 80, 50); / set XOR mode to yellow g.setXORMode(Color.yellow); g.fillOval(180, 45, 60, 20); / draw a blue arc g.setColor(Color.blue); g.fillArc(150, 40, 20, 20, 0, 360); / draw a red square g.setColor(Color.red); g.fillRect(120, 45, 20, 20); ,程序绘制了六种不同的形状,前三种为覆盖模式,后三种为异或模式。大家

32、可以通过运行结果中图形重叠部分看出两种不同绘图模式的效果。程序运行结果如图9.6所示。,图 9.6,9.3 Font类的使用,Java 2D具有复杂文本的输出能力。Java 2D和一个重新设计的字体引擎支持使用属性集对字符串的单个字符进行操作。 9.3.1 字体 字体是一套具有一个点尺寸和外观的字符类型集合,例如,所有10点Helvetica英文字符和符号组成一个字体。文本所使用的字体定义特定的外观、大小和式样(黑体、斜体或者普通体)。,字体如何定义特定外观呢?字体是从字形(glyphs)创建的,一个字形是一个位映像图像,它定义字体中的字符和符号的外观。同一字体家族的字体都有相似的外观,因为他

33、们使用同一个字形创建。同样的,不同的字体家族使用不同的字形得到相互区分的外观。 一个字体家族不但由具有相似外观的字体组成,还包括不同的大小和式样。Helvetica 10 point黑体和Helvetica 12 point斜体是同一家族中的两个不同字体,而Times Roman 8 point黑体和Times Roman 10 point普通体是另一个家族的两个不同字体。,为了使用一个字体,需要创建一个Font对象,而为了做到这个,则需要知道系统中有什么字体可用以及它们的名字。字体有逻辑名、家族名和字体名。 逻辑名是被映射到平台上,可用的特定字体的名字。调用java.awt.Font.get

34、Name类可以得到一个Font对象的逻辑名。,家族名是字体家族的名字,它通过不同的外观决定排版图案,例如,Helvetica或者Times New Roman。要得到一个Font对象的家族名,须调用java.awt.Font.getFamily类。 字体名代表家族中的特定字体,例如Helvetica Bold。要得到一个Font对象的字体名,须调用java.awt.Font.getFontName类。要决定系统上哪些字体可用,须调用java.awt.GraphicsEnvironment.getAllFonts类。,9.3.2 创建和派生字体 创建一个字体的最简单的方法是指定字体名、大小和式样

35、。一旦你有一个Font对象,你就可以通过调用Font.deriveFont方法在存在的字体上派生任意个新Font对象,并指定新的大小、样式、变换(位置、倾斜、缩放或者旋转)或者属性映射。例如 Font boldFont = new Font(“Helvetica“, Font.BOLD, 12); Font italicDerived = boldFont.deriveFont(Font.ITALIC, 12); Font plainDerived = boldFont.deriveFont(Font.PLAIN, 14);,一旦你有一个字体,你就可以用它创建一个TextLayout对象并绘制

36、艺术字。java.awt.Font.TextLayout类可以让你使用字符、字体和属性集创建艺术字。一旦被创建,TextLayout对象就不可编辑,但是它的方法可以让你访问布局、字体、脱字符,选择和点击测试信息。 下面的代码使用Font,TextLayout和 FontRenderContext 对象绘制了一个简单的文本,使用的是24 point Times黑体。,例9.7 TimesB.java import java.awt.*; import java.awt.event.*; import java.awt.geom.*; import java.awt.Font.*; public

37、class TimesB extends Canvas private Image img; publicc TimesB() setBackground(Color.white); public void paint(Graphics g), Graphics2D g2; g2 = (Graphics2D)g; g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); ontRenderContext frc = g2.getFontRenderContext(); Fon

38、t f = new Font(“Times“,Font.BOLD, 24); String s = new String(“24 Point Times Bold“); TextLayout tl = new TextLayout(s, f, frc); Dimension theSize= getSize();,g2.setColor(Color.green); tl.draw(g2, theSize.width/30, theSize.height/2); public static void main(String s) WindowListener l = new WindowAdap

39、ter() public void windowClosing(WindowEvent e) System.exit(0); public void windowClosed(WindowEvent e) System.exit(0); ;,Frame f = new Frame(“2D Text“); f.addWindowListener(l); f.add(“Center“, new TimesB(); f.pack(); f.setSize(new Dimension(400, 300); f.show(); 程序运行结果如图9.7所示。,图 9.7,程序中,java.awt.Font

40、代表系统中可用字体的一个实例;java.awt.TextLayout代表不可变的艺术字数据;java.awt.Font.FontRenderContext包含绘制文本时需要的正确测量和定位的信息。,9.4 图 像 处 理,正如上一节所介绍的,Graphics类中确实提供了不少绘制图形的方法,但如果用它们在Applet运行过程中实时地绘制一幅较复杂的图形,就好比是在用斧头和木块去制造航天飞机。因此,对于复杂图形,一般都事先用专用的绘图软件将其绘制好,或者是用其他截取图像的工具(如扫描仪、视效卡等)获取图像的数据信息,再将它们按一定的格式存入图像文件中。程序运行时,只要找到图像文件存贮的位置,将它

41、装载到内存里,然后在适当的时机将它显示在屏幕上就可以了。,9.4.1 加载和显示图像 在AWT中,java.awt.image类用于描述图像,它通过传递一个Image类对象的引用给Graphics.drawImage(Image, int, int, ImageObserver)方法,就可以将图像在画布(Canvas)或是其他可视组件中显示出来。,Java目前所支持的图像文件格式只有两种,分别是GIF和JPEG格式(带有 .GIF、.JPG、.JPEG后缀名的文件)。因此,若图像文件是其他格式,就须先将它们转换为这两种格式。 java.awt.image是一个抽象类,它定义的方法提供对图像信息

42、的访问。下面通过一个例子来看看如何利用Image类来显示一幅图像。,例9.8 ImageTestApplication.java import java.awt.*; import java.awt.event.*; public class ImageTestApplication extends Frame Insets insets; Image im; static public void main(String args) ImageTestApplication app = new ImageTestApplication();,app.show(); public ImageTe

43、stApplication() super(“Image Test“); im = Toolkit.getDefaultToolkit().getImage(“tiger.gif“); addWindowListener(new WindowAdapter() public void windowClosing(WindowEvent event) dispose(); System.exit(0); ); ,public void addNotify() super.addNotify(); / peer is created here insets = getInsets(); setBo

44、unds(100, 100, 217 + insets.left, 321 + insets.top); public void paint(Graphics g) g.drawImage(im, insets.left, insets.top, this); System.out.println(“drawing image.“); System.out.println(g.drawImage(im, insets.left, insets.top, this); ,在应用程序中加载图像必须调用Toolkit类的静态方法getImage(),该方法返回一个指定图像文件的Image对象描述,然

45、后在paint()方法中调用Graphics类的drawImage()方法,就可以将图片显示在当前容器中。,需要注意的是addNotify()方法,覆盖这个方法是为了得到框架窗口空白区域的引用,并用它来设置框架窗口的大小。这样做是因为框架窗口的左上角(0,0)坐标是从标题栏开始计算的,如果将图从(0,0)开始画,空白区域以外(即标题栏覆盖的部分)将会被裁减,所以必须从坐标(insets.left,insets.top)的位置开始画图。程序的运行结果如图9.8所示。,图 9.8,在上面的例子中,查看控制台会发现,paint()方法被调用了很多次,这是因为getImage()方法是启动一个线程来加

46、载图像的,所以paint()方法被调用的时候不一定已经载入了整张图片,每次只绘出已经加载的部分。,Java这样采用线程的做法虽然会提高性能,但是也为编程带来了一些问题。例如,上例中的setBounds()方法中的尺寸是硬编码(直接写入数值)的,这种方法缺乏通用性,是明确不被推荐的做法。较好的方法是直接取图像的尺寸,通过调用Image.getWidth()和Image.getHeight()方法可以做到。因为在图像被完全加载以前,它们的返回值都是-1,所以要等到图像加载完才能调用它们。,如何知道图像有没有被加载完呢?AWT包为此提供了MediaTracker类用于监控图像的加载过程。使用Medi

47、aTracker类分为三步: (1) 创建MediaTracker对象。 (2) 使用MediaTracker.addImage()指明要监控的图像对象。 (3) 创建try/catch块,等待和指定与ID相关的图像被完全加载。 现在采用MediaTracker类来改写上面的例子。,例9.9 ImageTestApplication.java import java.awt.*; import java.awt.event.*; public class ImageTestApplication extends Frame Insets insets; Image im; int width,

48、 height; static public void main(String args) ImageTestApplication app = new ImageTestApplication();,app.show(); public ImageTestApplication() super(“Image Test“); MediaTracker tracker = new MediaTracker(this); im = Toolkit.getDefaultToolkit().getImage(“tiger.gif“); tracker.addImage(im, 0); try tracker.waitForID(0); catch (InterruptedException e) e.printStackTrace(); width = im.getWidth(this); height = im.getHeight(this);,addWindowListener(new WindowAdapter() public void windowClosing(WindowEvent event) dispose(); System.exit(0); ); public void addNotify() super.addNot

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 研究报告 > 商业贸易


经营许可证编号:宁ICP备18001539号-1