先看ANDROID QQ截图:
再看DEMO截图:
直接看代码:
public class test3 extends Activity {
private NewLayOut layout;
private myThread mThread;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
LayoutInflater inflater = (LayoutInflater)getSystemService(LAYOUT_INFLATER_SERVICE);
layout = (NewLayOut) inflater.inflate(R.layout.move, null);
ImageView button = (ImageView)layout.findViewById(R.id.ImageView01);
button.setOnClickListener(mClickListener);
ImageView button2 = (ImageView)layout.findViewById(R.id.ImageView02);
button2.setOnClickListener(mClickListener);
ImageView button3 = (ImageView)layout.findViewById(R.id.ImageView03);
button3.setOnClickListener(mClickListener);
this.setContentView(layout);
}
private View.OnClickListener mClickListener = new View.OnClickListener() {
public void onClick(View v) {
startMove(v);
}
};
private void startMove(View v)
{
stopThread();//停止之前的线程
mThread = new myThread(v);
mThread.start();
}
private void stopThread()
{
if (mThread != null)
{
try
{
layout.mIsStop = true;
mThread.join();
}
catch(Exception e)
{
e.printStackTrace();
}
}
}
class myThread extends Thread
{
private View mView;
public myThread(View v){ this.mView = v; }
public void run() {
layout.doWork(this.mView);
}
}
}
NewLayOut 类 继承 LinearLayout,因为需要在LinearLayout里面画图
package test3.program;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Rect;
import android.graphics.BitmapFactory;
import android.graphics.drawable.BitmapDrawable;
import android.util.AttributeSet;
import android.view.View;
import android.widget.LinearLayout;
public class NewLayOut extends LinearLayout {
private static final short SPEED = 15;
private Context mContext;
private Rect mNowRect;//当前的区域
private Rect mEndRect;//结束的区域
private BitmapDrawable mSelecter;//移动的半透明背景bitmaip
private boolean mSyn = false;//循环和onDraw同步
public boolean mIsStop = false;//是否到达指定区域
public NewLayOut(Context context) {
super(context);
init(context);
}
public NewLayOut(Context context, AttributeSet attrs) {
super(context, attrs);
init(context);
}
private void init(Context context)
{
mContext = context;
mSelecter = new BitmapDrawable(
BitmapFactory.decodeResource(mContext.getResources(),
R.drawable.topbar_select));
mNowRect = new Rect();
mEndRect = new Rect();
}
protected void onLayout(boolean paramBoolean, int paramInt1, int paramInt2, int paramInt3, int paramInt4)
{
super.onLayout(paramBoolean, paramInt1, paramInt2, paramInt3, paramInt4);
this.getChildAt(0).getHitRect(mNowRect);//取得第一个控制区域作为起始区域
}
/**
*
* @param v 目标控件
*/
public void doWork(View v)
{
v.getHitRect(this.mEndRect);
if (this.mNowRect.right < this.mEndRect.right)
{
work(new RunForword()
{
public void run()
{
mNowRect.left += SPEED;//每次左边移动15格
mNowRect.right += SPEED;//每次右边移动15格
System.out.println("is run run run");
if (mNowRect.right >= mEndRect.right)//如果移动超出或等于目标区域
ReachRect();
}
});
}
else if(this.mNowRect.right > this.mEndRect.right)
{
work(new RunForword()
{
public void run()
{
mNowRect.left -= SPEED;//每次左边移动15格
mNowRect.right -= SPEED;//每次右边移动15格
if (mNowRect.right <= mEndRect.right)//如果移动超出或等于目标区域
ReachRect();
}
});
}
}
private void work(RunForword run)
{
this.mIsStop = false;
while(!this.mIsStop)
{
if(this.mSyn)//画图与循环同步
{
run.run();
System.out.println("is running!");
this.mSyn = false;
this.postInvalidate();
//Thread.sleep(35);
}
}
}
/**
* 到达目的地
*/
private void ReachRect()
{
mNowRect.left = mEndRect.left;
mNowRect.right = mEndRect.right;
mIsStop = true;
}
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
mSelecter.setBounds(mNowRect);
mSelecter.draw(canvas);
this.mSyn = true;
System.out.println("is ondraw");
}
public interface RunForword
{
void run();
}
}
编写的过程中发现一点问题:
第一:画图与循环同步的问题
private void work(RunForword run)
{
this.mIsStop = false;
while(!this.mIsStop)
{
if(this.mSyn)//画图与循环同步
{
run.run();
System.out.println("is running!");
this.mSyn = false;
this.postInvalidate();
//Thread.sleep(35);
}
}
}
如果把
if(this.mSyn) 这段去掉 看图:
就是while循环好多次之后,onDraw才执行一次。猜想onDraw在上一次未执行完之前是不会被执行第二次的(onDraw好像开了一个新线程画图,但看SDK源码实现没看出个端儿。),所以需要做一个这样的同步。这里是继承LinearLayout的,不知道直接继承View会不会出现这种情况。上面的程序,onDraw执行完的时间大概在Thread.sleep(35)这么多时间。
看看把
if(this.mSyn) 加上去后的打印数据 看图:
第二:把移动的运算部份run.run();的方法直接放到onDraw里面运算
private void work(RunForword run)
{
this.mIsStop = false;
while(!this.mIsStop)
{
if(this.mSyn)//画图与循环同步
{
System.out.println("is running!");
this.mSyn = false;
this.postInvalidate();
//Thread.sleep(35);
}
}
}
protected void onDraw(Canvas canvas)
{
super.onDraw(canvas);
run.run();//大概时这个意思。。当实这样实写是不行的。
mSelecter.setBounds(mNowRect);
mSelecter.draw(canvas);
this.mSyn = true;
System.out.println("is ondraw");
}
这样做的话,发觉移动的侦数比较底下,分析了一下原因。首先上面讲的,因为onDraw在上一次未画完图之前,第二次是不会运行的。而while循环又无视onDraw方法未执行完毕。所以在onDraw未执行完毕的过程中。运行run.run(),把下一次移动的数据准备好了。所以侦数就稍有上升了。
最后附上DEMO的源码:
test3.rar
如上描述,有不正确的地方,请指教。谢谢。。
完毕。
有关ANDROID QQ的一些实现方法,请听下回分解。
- 大小: 15.2 KB
- 大小: 5.4 KB
- 大小: 5.3 KB
- 大小: 2.9 KB
- 大小: 3.1 KB
分享到:
相关推荐
通过以上步骤,我们可以成功地在Android应用中实现类似QQ顶栏的椭圆透明背景移动效果。这不仅提升了应用的视觉效果,也为用户带来了更丰富的交互体验。在实际开发中,开发者应根据项目需求灵活运用这些技术,创造出...
- **实例说明**:为工具栏添加背景色或背景图片,使其更加美观。 - **技术要点**: - 设置工具栏的背景属性。 - 可能需要处理图像的裁剪和缩放。 **实例008 带浮动工具栏** - **实例说明**:允许工具栏从固定...
2、工具栏应用实例,包括:带背景的工具栏、带图标的工具栏、带下拉菜单的工具栏、可调整按钮位置的工具栏、浮动工具栏、根据表中数据动态生成工具栏、具有提示功能的工具栏。3、状态栏应用实例,包括:带进度条的...
首先,我们需要理解放大镜效果的基本原理:在原始图片上覆盖一个透明的小窗口,当用户移动鼠标时,这个小窗口会显示被鼠标覆盖部分的放大图像。这种效果通常通过CSS创建一个具有透明度的遮罩层,并利用JavaScript...
实例008 带背景的工具栏 实例009 带图标的工具栏 实例010 带下拉菜单的工具栏 实例011 可调整按钮位置的工具栏 实例012 浮动工具栏 实例013 根据表中数据动态生成工具栏 实例014 具有提示功能的工具栏 1.4 ...
实例008 带背景的工具栏 实例009 带图标的工具栏 实例010 带下拉菜单的工具栏 实例011 可调整按钮位置的工具栏 实例012 浮动工具栏 实例013 根据表中数据动态生成工具栏 实例014 具有提示功能的工具栏 1.4 ...
- 使用`ToolStrip`类的`BackgroundImage`属性来设置工具栏的背景图片。 - 使用`BackgroundImageLayout`属性来控制背景图片的显示方式。 **实例008:带浮动工具栏** - **实例说明**:创建一个可以自由浮动的工具...
cc实例017 滚动字幕的状态栏 1.5 导航界面应用实例 cc实例018 Outlook导航界面 cc实例019 树状导航界面 cc实例020 按钮导航界面 cc实例021 类QQ导航菜单 1.6 界面窗体应用实例 cc实例022 背景为渐变...
cc实例008 带背景的工具栏 cc实例009 带图标的工具栏 cc实例010 带下拉菜单的工具栏 cc实例011 可调整按钮位置的工具栏 cc实例012 浮动工具栏 cc实例013 根据表中数据动态生成工具栏 ...
cc实例008 带背景的工具栏 cc实例009 带图标的工具栏 cc实例010 带下拉菜单的工具栏 cc实例011 可调整按钮位置的工具栏 cc实例012 浮动工具栏 cc实例013 根据表中数据动态生成工具栏 ...
5 实例006 菜级联菜单 7 1.2 工具栏设计 7 实例007 带背景的工具栏 7 实例008 浮动工具栏 8 实例009 带下拉菜单的工具栏 9 实例010 具有提示功能的工具栏 9 1.3 状态栏设计 10...
实例078 尝试制作一个半透明渐显窗体 实例079 使窗体标题栏文字右对齐 实例080 窗口间移动按钮 实例081 窗体中滚动的字幕 实例082 使用任意组件拖动窗体 实例083 窗体换肤程序 第9章 windows应用程序常用控件 实例...
util实现Java图片水印添加功能,有添加图片水印和文字水印,可以设置水印位置,透明度、设置对线段锯齿状边缘处理、水印图片的路径,水印一般格式是gif,png,这种图片可以设置透明度、水印旋转等,可以参考代码...
MFC实现绘图软件功能如下:绘制 直线(移动,选中,拉伸,线条类型,颜色,粗细)绘制椭圆(Ctrl按住即为圆形,填充色选择边框色选择粗细透明色等等)矩形,四边随意拉伸效果,画笔实现直线同样功能(选中续画),...