package com.auto.lyric.widgets;
|
|
import android.content.Context;
|
import android.graphics.Canvas;
|
import android.graphics.Color;
|
import android.graphics.Paint;
|
import android.util.AttributeSet;
|
import android.util.Log;
|
|
import com.auto.lyric.data.LyricObject;
|
import com.auto.lyric.data.LyricServer;
|
import com.auto.lyric.util.DeviceUtil;
|
|
/**
|
* 歌词
|
* Created by Runt (qingingrunt2010@qq.com) on 2022/4/30.
|
*/
|
public class LyricView extends androidx.appcompat.widget.AppCompatTextView {
|
|
|
private float mX; //屏幕X轴的中点,此值固定,保持歌词在X中间显示
|
private float offsetY; //歌词在Y轴上的偏移量,此值会根据歌词的滚动变小
|
private int lrcIndex=0; //保存歌词TreeMap的下标
|
private int SIZEWORD=0;//显示歌词文字的大小值
|
private int INTERVAL=45;//歌词每行的间隔
|
Paint paint=new Paint();//画笔,用于画不是高亮的歌词
|
Paint paintHL=new Paint(); //画笔,用于画高亮的歌词,即当前唱到这句歌词
|
|
public LyricView(Context context){
|
super(context);
|
init();
|
}
|
|
public LyricView(Context context, AttributeSet attrs) {
|
super(context, attrs);
|
init();
|
}
|
|
/* (non-Javadoc)
|
* @see android.view.View#onDraw(android.graphics.Canvas)
|
*/
|
@Override
|
protected void onDraw(Canvas canvas) {
|
if(LyricServer.getLrc_map().size() > 0){
|
paintHL.setTextSize(SIZEWORD);
|
paint.setTextSize(SIZEWORD);
|
LyricObject temp= LyricServer.getLrc_map().get(lrcIndex);
|
canvas.drawText(temp.lrc, mX, offsetY+(SIZEWORD+INTERVAL)*lrcIndex, paintHL);
|
// 画当前歌词之前的歌词
|
for(int i=lrcIndex-1;i>=0;i--){
|
temp=LyricServer.getLrc_map().get(i);
|
if(offsetY+(SIZEWORD+INTERVAL)*i<0){
|
break;
|
}
|
canvas.drawText(temp.lrc, mX, offsetY+(SIZEWORD+INTERVAL)*i, paint);
|
}
|
// 画当前歌词之后的歌词
|
for(int i=lrcIndex+1;i<LyricServer.getLrc_map().size();i++){
|
temp=LyricServer.getLrc_map().get(i);
|
if(offsetY+(SIZEWORD+INTERVAL)*i>600){
|
break;
|
}
|
canvas.drawText(temp.lrc, mX, offsetY+(SIZEWORD+INTERVAL)*i, paint);
|
}
|
}
|
else{
|
paint.setTextSize(25);
|
canvas.drawText("找不到歌词", mX, 310, paint);
|
}
|
super.onDraw(canvas);
|
}
|
|
public void init(){
|
offsetY=320;
|
|
paint=new Paint();
|
paint.setTextAlign(Paint.Align.CENTER);
|
paint.setColor(Color.GREEN);
|
paint.setAntiAlias(true);
|
paint.setDither(true);
|
paint.setAlpha(180);
|
|
|
paintHL=new Paint();
|
paintHL.setTextAlign(Paint.Align.CENTER);
|
|
paintHL.setColor(Color.RED);
|
paintHL.setAntiAlias(true);
|
paintHL.setAlpha(255);
|
}
|
|
/**
|
* 根据歌词里面最长的那句来确定歌词字体的大小
|
*/
|
public void setTextSize(){
|
if(LyricServer.getLrc_map().size() == 0){
|
return;
|
}
|
int max=LyricServer.getLrc_map().get(0).lrc.length();
|
for(int i=1;i<LyricServer.getLrc_map().size();i++){
|
LyricObject lrcStrLength=LyricServer.getLrc_map().get(i);
|
if(max<lrcStrLength.lrc.length()){
|
max=lrcStrLength.lrc.length();
|
}
|
}
|
SIZEWORD = DeviceUtil.convertDpToPixel(320/max,getContext());
|
|
}
|
|
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
|
mX = w * 0.5f;
|
super.onSizeChanged(w, h, oldw, oldh);
|
}
|
|
/**
|
* 歌词滚动的速度
|
*
|
* @return 返回歌词滚动的速度
|
*/
|
public Float SpeedLrc(){
|
float speed=0;
|
if(offsetY+(SIZEWORD+INTERVAL)*lrcIndex>220){
|
speed=((offsetY+(SIZEWORD+INTERVAL)*lrcIndex-220)/20);
|
|
} else if(offsetY+(SIZEWORD+INTERVAL)*lrcIndex < 120){
|
Log.i("speed", "speed is too fast!!!");
|
speed = 0;
|
}
|
// if(speed<0.2){
|
// speed=0.2f;
|
// }
|
return speed;
|
}
|
|
/**
|
* 按当前的歌曲的播放时间,从歌词里面获得那一句
|
* @param time 当前歌曲的播放时间
|
* @return 返回当前歌词的索引值
|
*/
|
public int getIndex(int time){
|
int index=0;
|
for(int i=0;i<LyricServer.getLrc_map().size();i++){
|
LyricObject temp=LyricServer.getLrc_map().get(i);
|
if(temp.begintime<time){
|
++index;
|
}
|
}
|
lrcIndex = index-1;
|
if(lrcIndex<0){
|
lrcIndex=0;
|
}
|
return lrcIndex;
|
}
|
|
public void setIndex(int lrcIndex) {
|
this.lrcIndex = lrcIndex;
|
}
|
|
/**
|
* @return the offsetY
|
*/
|
public float getOffsetY() {
|
return offsetY;
|
}
|
|
/**
|
* @param offsetY the offsetY to set
|
*/
|
public void setOffsetY(float offsetY) {
|
this.offsetY = offsetY;
|
}
|
|
/**
|
* @return 返回歌词文字的大小
|
*/
|
public int getSIZEWORD() {
|
return SIZEWORD;
|
}
|
|
/**
|
* 设置歌词文字的大小
|
* @param sIZEWORD the sIZEWORD to set
|
*/
|
public void setSIZEWORD(int sIZEWORD) {
|
SIZEWORD = sIZEWORD;
|
}
|
|
public int getIndexFromOffsetY(float offsetY){
|
//220 - index * (binding.lyric.getSIZEWORD() + 44)
|
int index = (int) ((220 - offsetY) / (SIZEWORD + 44));
|
Log.i("LyricView", "getIndexFromOffsetY index:"+index);
|
if(index < 0){
|
return 0;
|
}else if(LyricServer.getLrc_map().keySet().size()>index){
|
return index;
|
}else {
|
return LyricServer.getLrc_map().keySet().size() -1;
|
}
|
}
|
}
|