android字体渐变仿音乐歌词

来源:互联网 发布:实时荧光定量pcr数据分析 编辑:程序博客网 时间:2024/06/03 17:22

 

package com.example.colorText;

import android.animation.ObjectAnimator;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;

public class MainActivity extends Activity {

 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  setContentView(R.layout.activity_main);
  final View view=findViewById(R.id.id_changeTextColorView);
  findViewById(R.id.btn).setOnClickListener(new OnClickListener() {
   
   @SuppressLint("NewApi")
   @Override
   public void onClick(View v) {
    //对象要有set get方法
    ObjectAnimator.ofFloat(view, "progress", 0,1).setDuration(3000).start();
        
    
   }
  });
  
 }

 
}

 

package com.example.colorText;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Rect;
import android.graphics.Paint.FontMetrics;
import android.graphics.Paint.Style;
import android.util.AttributeSet;
import android.util.Log;
import android.util.TypedValue;
import android.view.View;
import android.view.View.MeasureSpec;
import android.widget.TextView;

public class myView extends View {
 private static final String TAG = "myView";
 private float progress = 0;
 private String text = "橘子群岛";
 private int mWidth;
 private int mHeight;
 private Rect mbounds;
 private int textWidth;
 private int textHeight;
 private int startX;
 private int startY;
 private Paint paint;
 private Paint oriPain;
 private boolean isStart = true;

 public myView(Context context) {
  this(context, null);

 }

 public myView(Context context, AttributeSet attrs) {
  this(context, attrs, 0);

 }

 public myView(Context context, AttributeSet attrs, int defStyle) {
  super(context, attrs, defStyle);
  paint = new Paint(Paint.ANTI_ALIAS_FLAG);
  oriPain = new Paint(Paint.ANTI_ALIAS_FLAG);
  oriPain.setColor(0xffff0000);
  oriPain.setDither(true);
  paint.setTextSize(sp2px(30));
  oriPain.setTextSize(sp2px(30));
  paint.setStyle(Style.FILL);
  // oriPain.setStyle(Style.STROKE);//空心字
  oriPain.setStyle(Style.FILL);

  paint.setColor(0xff0000ff);
  mbounds = new Rect();

  TypedArray ta = context.obtainStyledAttributes(attrs,
    R.styleable.ColorTrackView);
  
  progress = ta.getFloat(R.styleable.ColorTrackView_progress, 0);
        ta.recycle();

  
 }

 @Override
 protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
  measureText();
  int width = getWidthMeasure(widthMeasureSpec);
  int height = getHeightMeasure(heightMeasureSpec);

  setMeasuredDimension(width, height);
  startX = getMeasuredWidth() / 2 - textWidth / 2;
  startY = getMeasuredHeight() / 2 + textHeight / 2;
  super.onMeasure(widthMeasureSpec, heightMeasureSpec);

 }

 private void measureText() {
  textWidth = (int) oriPain.measureText(text);
  FontMetrics fm = oriPain.getFontMetrics();
  textHeight = (int) (fm.descent + fm.ascent);
        oriPain.getTextBounds(text, 0, text.length(), mbounds);


 }

 private int getHeightMeasure(int heights) {
  int mode = MeasureSpec.getMode(heights);
  int val = MeasureSpec.getSize(heights);

  int result = 0;
  switch (mode) {
  case MeasureSpec.EXACTLY:

   result = val;
   break;
  case MeasureSpec.AT_MOST:
   // break;//不要break 就可以 把上面的 result = textWidth; 注掉;
  case MeasureSpec.UNSPECIFIED:
   result = textHeight + getPaddingTop() + getPaddingBottom();
   break;
  }

  // EXACTLY的值 是精确的 最大也是屏幕大小 AT_MOST warp_content 动态大小 不会超过屏幕
  result = mode == MeasureSpec.AT_MOST ? Math.min(result, val) : result;
  return result;
 }

 private int getWidthMeasure(int widths) {
  int mode = MeasureSpec.getMode(widths);
  int width = MeasureSpec.getSize(widths);
  int result = 0;
  if (mode == MeasureSpec.EXACTLY) {
   // 精确值
   result = width;

  } else if (mode == MeasureSpec.UNSPECIFIED) {
  
   result = textWidth;
  }
  if (mode == MeasureSpec.AT_MOST) {
   result = textWidth + getPaddingLeft() + getPaddingRight();

  }
  // EXACTLY的值 是精确的 最大也是屏幕大小 AT_MOST warp_content 动态大小 不会超过屏幕
  result = mode == MeasureSpec.AT_MOST ? Math.min(result, width) : result;
  // 如果这个模式 就会取到 result = textWidth;不会取到超过 math_content
  return result;
 }

 @Override
 protected void onDraw(Canvas canvas) {

  super.onDraw(canvas);
  int l = (int) (startX + progress * mbounds.width());

  canvas.drawColor(0xaa11ff11);

  canvasDrawLeft(canvas, l);

 }

 private void canvasDrawOriginal(Canvas canvas) {
  //textHeight是负值,getMeasuredHeight() / 2字体的底部在控件中间,要加上字体的一半
 canvas.drawText(text,startX ,getMeasuredHeight() / 2-(textHeight) / 2, oriPain);

  // 高度一半 减去字体descent()+ ascent()=字体高度 的一半 让字体一半在上面 一半在下面

 }

 private void canvasDrawLeft(Canvas canvas, int l) {
  canvas.save();
  canvasDrawOriginal(canvas);

  canvas.clipRect(startX, 0, l, getMeasuredHeight());

  canvas.drawText(
    text,
    startX,
    getMeasuredHeight() / 2
      - ((oriPain.descent() + oriPain.ascent()) / 2), paint);
  canvas.restore();

 }

 public float getProgress() {
  return progress;
 }

 public void setProgress(float progress) {
  this.progress = progress;
  invalidate();// 必须 构造 get set 方法不然 接收不到 外面穿进来的值
 }

 private int sp2px(float dpVal) {
  return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP,
    dpVal, getResources().getDisplayMetrics());
 }

}

 


 

0 0