Java实现窗体中角色逐渐风化效果

本文介绍了一种使用Java实现的图片风化效果方法。通过分解图片像素并模拟碎片运动来达到视觉上的破碎与还原效果。文章提供了完整的代码示例,并展示了如何通过按钮触发图片的破碎和复原。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

效果图如下:


源码:
AirslakeImage.java
packageorg.test;

importjava.awt.Button;
importjava.awt.Color;
importjava.awt.Frame;
importjava.awt.Graphics;
importjava.awt.Image;
importjava.awt.Panel;
importjava.awt.event.ActionEvent;
importjava.awt.event.ActionListener;
importjava.awt.event.WindowAdapter;
importjava.awt.event.WindowEvent;
importjava.awt.image.PixelGrabber;
importjava.util.Random;

importorg.loon.framework.game.image.Bitmap;
importorg.loon.framework.game.image.LColor;
/***//**
*<p>Title:LoonFramework</p>
*<p>Description:java实现图片风化效果</p>
*<p>Copyright:Copyright(c)2007</p>
*<p>Company:LoonFramework</p>
*
@authorchenpeng
*@email:ceponline@yahoo.com.cn
*
@version0.1
*/

publicclassAirslakeImageextendsPanelimplementsRunnable,ActionListener...{

/***//**
*
*/

privatestaticfinallongserialVersionUID=1L;

staticfinalpublicint_WIDTH=400;

staticfinalpublicint_HEIGHT=400;

privateboolean_isRun=false;

privateImage_img;

privateImage_screen;

privateGraphics_back;

privateint_imgWidth;
privateint_imgHeight;

privateFraction[]_fractions;

privateThread_timer;

privateButton_meganteButton;
privateButton_revivalButton;


privateRandom_rand=newRandom();

publicAirslakeImage()...{

_screen
=newBitmap(_WIDTH,_HEIGHT).getImage();

_back
=_screen.getGraphics();

setSize(_WIDTH,_HEIGHT);

_meganteButton
=newButton("破碎图片");
_meganteButton.addActionListener(
this);
add(_meganteButton);

_revivalButton
=newButton("还原图片");
_revivalButton.addActionListener(
this);
add(_revivalButton);
_revivalButton.setEnabled(
false);

loadImage(
"role.png");

init(_img);
}


/***//**
*初始化image图像,分解其中像素
*
@param_img
*/

privatevoidinit(Image_img)...{
if(_timer!=null)...{
_timer
=null;
_isRun
=false;
}

_fractions
=newFraction[_imgWidth*_imgHeight];
PixelGrabberpg
=newPixelGrabber(_img,0,0,_imgWidth,_imgHeight,true);
try...{
pg.grabPixels();
}
catch(InterruptedExceptione)...{
e.printStackTrace();
}

intpixel[]=(int[])pg.getPixels();

//重新封装像素
for(inty=0;y<_imgHeight;y++)...{
for(intx=0;x<_imgWidth;x++)...{
intn=y*_imgWidth+x;
_fractions[n]
=newFraction();
doubleangle=_rand.nextInt(360);
doublespeed=10.0/_rand.nextInt(30);
_fractions[n].x
=x+90;
_fractions[n].y
=y+20;
_fractions[n].vx
=Math.cos(angle*Math.PI/180)*speed;
_fractions[n].vy
=Math.sin(angle*Math.PI/180)*speed;
_fractions[n].color
=pixel[n];
_fractions[n].countToCrush
=x/6+_rand.nextInt(10);
}

}

}


publicvoidupdate(Graphicsg)...{
paint(g);
}


publicvoidpaint(Graphicsg)...{
//变更背景色
_back.setColor(Color.WHITE);
//清空背景
_back.fillRect(0,0,_WIDTH,_HEIGHT);

for(intn=0;n<_imgWidth*_imgHeight;n++)...{
intx=(int)_fractions[n].x;
inty=(int)_fractions[n].y;
LColorcolor
=LColor.getLColor(_fractions[n].color);
//纯黑色区域不读取
if(!LColor.equals(color,LColor.fromArgb(0,0,0)))...{
//获得rgb三色
intred=color.R;
intgreen=color.G;
intblue=color.B;
_back.setColor(
newColor(red,green,blue));
//绘制
_back.drawLine(x,y,x,y);
}

}

g.drawImage(_screen,
0,0,this);
}


publicvoidactionPerformed(ActionEvente)...{
if(e.getSource()==_meganteButton)...{
execute();
_meganteButton.setEnabled(
false);
_revivalButton.setEnabled(
true);
}
elseif(e.getSource()==_revivalButton)...{
init(_img);
repaint();
_meganteButton.setEnabled(
true);
_revivalButton.setEnabled(
false);
}

}




/***//**
*加载图像
*
@paramfilename
*/

privatevoidloadImage(Stringfilename)...{
Bitmapbitmap
=newBitmap(("./image/"+filename).intern());
//替换透明区域颜色(象素化后,转为rgb形式的透明区域色值将显示为r=0,g=0,b=0),可以直接用pixel识别透明区域,也可以替换或跳过该区域)
_img=bitmap.getImage();
_imgWidth
=_img.getWidth(this);
_imgHeight
=_img.getHeight(this);
}




/***//**
*执行操作
*
*/

privatevoidexecute()...{
_timer
=newThread(this);
_timer.start();
_isRun
=true;
}


classFraction...{
//图片在窗体中x
publicdoublex;
//图片在窗体中y
publicdoubley;
//显示图x
publicdoublevx;
//显示图y
publicdoublevy;
//color
publicintcolor;
//变形颗粒数量
publicintcountToCrush;
}


publicvoidrun()...{
while(_isRun)...{
for(intn=0;n<_imgWidth*_imgHeight;n++)...{
if(_fractions[n].countToCrush<=0)...{
_fractions[n].x
+=_fractions[n].vx;
_fractions[n].y
+=_fractions[n].vy;
_fractions[n].vy
+=0.1;
}
else...{
_fractions[n].countToCrush
--;
}


}

//间隔
try...{
Thread.sleep(
60);
}
catch(InterruptedExceptione)...{
e.printStackTrace();
}

repaint();
}

}



publicstaticvoidmain(String[]args)...{
java.awt.EventQueue.invokeLater(
newRunnable()...{
publicvoidrun()...{
Framefrm
=newFrame("java实现图片风化效果");
frm.add(
newAirslakeImage());
frm.setResizable(
false);
frm.setSize(_WIDTH,_HEIGHT);
frm.addWindowListener(
newWindowAdapter()...{
publicvoidwindowClosing(WindowEvente)...{
System.exit(
0);
}

}
);
frm.setLocationRelativeTo(
null);
frm.setVisible(
true);
}

}
);
}

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值