diff --git a/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkBg.java b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkBg.java new file mode 100644 index 00000000..af69cd0c --- /dev/null +++ b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkBg.java @@ -0,0 +1,88 @@ +package com.bonait.bnframework.common.watermark; + +import android.content.Context; +import android.graphics.Canvas; +import android.graphics.Color; +import android.graphics.ColorFilter; +import android.graphics.Paint; +import android.graphics.PixelFormat; +import android.graphics.drawable.Drawable; + +import androidx.annotation.IntRange; +import androidx.annotation.NonNull; +import androidx.annotation.Nullable; + +import java.util.List; + +public class WaterMarkBg extends Drawable { + private Paint paint = new Paint(); + private List labels; + private Context context; + private int degress;//角度 + private int fontSize;//字体大小 单位sp + + /** + * 初始化构造 + * @param context 上下文 + * @param labels 水印文字列表 多行显示支持 + * @param degress 水印角度 + * @param fontSize 水印文字大小 + */ + public WaterMarkBg(Context context, List labels, int degress, int fontSize) { + this.labels = labels; + this.context = context; + this.degress = degress; + this.fontSize = fontSize; + } + + @Override + public void draw(@NonNull Canvas canvas) { + + + int width = getBounds().right; + int height = getBounds().bottom; + + canvas.drawColor(Color.parseColor("#40F3F5F9")); + paint.setColor(Color.parseColor("#50AEAEAE")); + + paint.setAntiAlias(true); + paint.setTextSize(sp2px(context,fontSize)); + canvas.save(); + canvas.rotate(degress); + float textWidth = paint.measureText(labels.get(0)); + int index = 0; + for (int positionY = height / 10; positionY <= height; positionY += height / 10+80) { + float fromX = -width + (index++ % 2) * textWidth; + for (float positionX = fromX; positionX < width; positionX += textWidth * 2) { + int spacing = 0;//间距 + for(String label:labels){ + canvas.drawText(label, positionX, positionY+spacing, paint); + spacing = spacing+50; + } + + } + } + canvas.restore(); + } + + @Override + public void setAlpha(@IntRange(from = 0, to = 255) int alpha) { + + } + + @Override + public void setColorFilter(@Nullable ColorFilter colorFilter) { + + } + + @Override + public int getOpacity() { + return PixelFormat.UNKNOWN; + } + + + public static int sp2px(Context context, float spValue) { + final float fontScale = context.getResources().getDisplayMetrics().scaledDensity; + return (int) (spValue * fontScale + 0.5f); + } +} \ No newline at end of file diff --git a/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkInfo.java b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkInfo.java new file mode 100644 index 00000000..539a54c9 --- /dev/null +++ b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkInfo.java @@ -0,0 +1,202 @@ +package com.bonait.bnframework.common.watermark; + + +import android.graphics.Color; +import android.graphics.Paint; +public class WaterMarkInfo { + + private int mDegrees; + private int mTextColor; + private int mTextSize; + private boolean mTextBold; + private int mDx; + private int mDy; + private Paint.Align mAlign; + + private WaterMarkInfo(int degrees, int textColor, int textSize, boolean textBold, int dx, int dy, Paint.Align align) { + mDegrees = degrees; + mTextColor = textColor; + mTextSize = textSize; + mTextBold = textBold; + mDx = dx; + mDy = dy; + mAlign = align; + } + + public int getDegrees() { + return mDegrees; + } + + public int getTextColor() { + return mTextColor; + } + + public int getTextSize() { + return mTextSize; + } + + public int getDx() { + return mDx; + } + + public int getDy() { + return mDy; + } + + public Paint.Align getAlign() { + return mAlign; + } + + public int getAlignInt() { + switch (mAlign) { + case LEFT: + return 0; + case RIGHT: + return 2; + default: + return 1; + } + } + + public boolean isTextBold() { + return mTextBold; + } + + void setDegrees(int degrees) { + mDegrees = degrees; + } + + void setTextColor(int textColor) { + mTextColor = textColor; + } + + void setTextSize(int textSize) { + mTextSize = textSize; + } + + void setTextBold(boolean textBold) { + mTextBold = textBold; + } + + void setDx(int dx) { + mDx = dx; + } + + void setDy(int dy) { + mDy = dy; + } + + void setAlign(Paint.Align align) { + this.mAlign = align; + } + + public static Builder create() { + return new Builder(); + } + + public static class Builder { + private int mDegrees; + private int mTextColor; + private int mTextSize; + private boolean mTextBold; + private int mDx; + private int mDy; + private Paint.Align mAlign; + + private Builder() { + mDegrees = -30; + mTextColor = Color.parseColor("#33000000"); + mTextSize = 35; + mTextBold = false; + mDx = 100; + mDy = 240; + mAlign = Paint.Align.CENTER; + } + + /** + * 设置水印文字倾斜度 + * + * @param degrees 文字倾斜度(默认:-30) + * @return Builder + */ + public Builder setDegrees(int degrees) { + mDegrees = degrees; + return this; + } + + /** + * 设置水印文字颜色 + * + * @param textColor 文字颜色(默认:#33000000) + * @return Builder + */ + public Builder setTextColor(int textColor) { + mTextColor = textColor; + return this; + } + + /** + * 设置水印文字大小(单位:px) + * + * @param textSize 文字大小(默认:42px) + * @return Builder + */ + public Builder setTextSize(int textSize) { + mTextSize = textSize; + return this; + } + + /** + * 设置水印文字是否加粗 + * + * @param textBold 文字加粗(默认:false) + * @return Builder + */ + public Builder setTextBold(boolean textBold) { + mTextBold = textBold; + return this; + } + + /** + * 设置水印文字X轴间距(单位:px) + * + * @param dx 文字X轴间距(默认:100px) + * @return Builder + */ + public Builder setDx(int dx) { + mDx = dx; + return this; + } + + /** + * 设置水印文字Y轴间距(单位:px) + * + * @param dy 文字Y轴间距(默认:240px) + * @return Builder + */ + public Builder setDy(int dy) { + mDy = dy; + return this; + } + + /** + * 设置水印文字对齐方式 + * + * @param align 对齐方式(默认:Center) + * @return Builder + */ + public Builder setAlign(Paint.Align align) { + mAlign = align; + return this; + } + + /** + * 生成水印全局配置信息 + * + * @return 配置信息 + */ + public WaterMarkInfo generate() { + return new WaterMarkInfo(mDegrees, mTextColor, mTextSize, mTextBold, mDx, mDy, mAlign); + } + } +} diff --git a/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkManager.java b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkManager.java new file mode 100644 index 00000000..2fa3b49f --- /dev/null +++ b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkManager.java @@ -0,0 +1,187 @@ +package com.bonait.bnframework.common.watermark; + +import android.annotation.SuppressLint; +import android.app.Activity; +import android.graphics.Paint; +import android.view.LayoutInflater; + + +import com.bonait.bnframework.R; + +import java.util.ArrayList; +import java.util.List; +/** + * @author Leon (wshk729@163.com) + * @date 2018/8/24 + *

+ */ +public class WaterMarkManager { + + static WaterMarkInfo INFO = null; + static String[] CONTENT = null; + static List LIST = new ArrayList<>(); + + /** + * 设置水印全局配置信息 + * + * @param info 配置信息 + */ + public static void setInfo(WaterMarkInfo info) { + INFO = info; + } + + /** + * 获取一个满屏水印View + * + * @param activity activity + */ + @SuppressLint("InflateParams") + public static WaterMarkView getView(Activity activity) { + return (WaterMarkView) LayoutInflater.from(activity).inflate(R.layout.view_water_mark, null); + } + + /** + * WaterMarkInfo初始化判断 + */ + private static void assertInitialized() { + if (INFO == null) { + INFO = WaterMarkInfo.create().generate(); + } + } + + /** + * 同步设置全部水印文字信息 + * + * @param content 文字信息 + */ + public static void setText(String... content) { + assertInitialized(); + CONTENT = content; + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncText(content); + } + } + } + } + + /** + * 同步设置全部水印倾斜角度 + * + * @param degrees 倾斜角度(默认:-30) + */ + public static void setDegrees(int degrees) { + assertInitialized(); + INFO.setDegrees(degrees); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncDegrees(degrees); + } + } + } + } + + /** + * 同步设置全部水印字体颜色 + * + * @param textColor 字体颜色(默认:#33000000) + */ + public static void setTextColor(int textColor) { + assertInitialized(); + INFO.setTextColor(textColor); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncTextColor(textColor); + } + } + } + } + + /** + * 同步设置全部水印字体大小(单位:px) + * + * @param textSize 字体大小(默认:42px) + */ + public static void setTextSize(int textSize) { + assertInitialized(); + INFO.setTextSize(textSize); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncTextSize(textSize); + } + } + } + } + + /** + * 同步设置全部水印字体是否粗体 + * + * @param textBold 是否粗体(默认:false) + */ + public static void setTextBold(boolean textBold) { + assertInitialized(); + INFO.setTextBold(textBold); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncTextBold(textBold); + } + } + } + } + + /** + * 同步设置全部水印X轴偏移量(单位:px) + * + * @param dx X轴偏移量(默认:100px) + */ + public static void setDx(int dx) { + assertInitialized(); + INFO.setDx(dx); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSyncDx(dx); + } + } + } + } + + /** + * 同步设置全部水印Y轴偏移量(单位:px) + * + * @param dy Y轴偏移量(默认:240px) + */ + public static void setDy(int dy) { + assertInitialized(); + INFO.setDy(dy); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSignDy(dy); + } + } + } + } + + /** + * 同步设置全部水印对齐方式 + * + * @param align 对齐方式(默认:Center) + */ + public static void setAlign(Paint.Align align) { + assertInitialized(); + INFO.setAlign(align); + if (LIST.size() > 0) { + for (WaterMarkView view : LIST) { + if (view != null) { + view.setSignAlign(align); + } + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkView.java b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkView.java new file mode 100644 index 00000000..1e53db4e --- /dev/null +++ b/app/src/main/java/com/bonait/bnframework/common/watermark/WaterMarkView.java @@ -0,0 +1,335 @@ +package com.bonait.bnframework.common.watermark; + + +import android.annotation.SuppressLint; +import android.content.Context; +import android.content.res.TypedArray; +import android.graphics.Canvas; +import android.graphics.Color; +import android.graphics.Paint; +import android.graphics.Rect; +import android.graphics.Typeface; +import android.text.TextPaint; +import android.util.AttributeSet; +import android.view.MotionEvent; +import android.view.View; + +import com.bonait.bnframework.R; + +public class WaterMarkView extends View { + + private static final String DEFAULT_SEPARATOR = "///"; + private TextPaint mTextPaint = new TextPaint(); + + private String[] mText; + private int mDegrees; + private int mTextColor; + private int mTextSize=35; + private boolean mTextBold; + private int mDx; + private int mDy; + private Paint.Align mAlign; + private boolean mSync; + private int textWidth, textHeight; + + public WaterMarkView(Context context) { + this(context, null); + } + + public WaterMarkView(Context context, AttributeSet attrs) { + super(context, attrs); + TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.WaterMarkView); + mDegrees = typedArray.getInt(R.styleable.WaterMarkView_water_mark_degree, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getDegrees() : -30); + String text = typedArray.getString(R.styleable.WaterMarkView_water_mark_text); + if (text != null) { + mText = text.split(DEFAULT_SEPARATOR); + } + mTextColor = typedArray.getColor(R.styleable.WaterMarkView_water_mark_textColor, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getTextColor() : Color.parseColor("#33000000")); + mTextSize = typedArray.getDimensionPixelSize(R.styleable.WaterMarkView_water_mark_textSize, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getTextSize() : 42); + mTextBold = typedArray.getBoolean(R.styleable.WaterMarkView_water_mark_textBold, WaterMarkManager.INFO != null && WaterMarkManager.INFO.isTextBold()); + mDx = typedArray.getDimensionPixelSize(R.styleable.WaterMarkView_water_mark_dx, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getDx() : 100); + mDy = typedArray.getDimensionPixelSize(R.styleable.WaterMarkView_water_mark_dy, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getDy() : 240); + int align = typedArray.getInt(R.styleable.WaterMarkView_water_mark_align, WaterMarkManager.INFO != null ? WaterMarkManager.INFO.getAlignInt() : 1); + mAlign = align == 0 ? Paint.Align.LEFT : align == 2 ? Paint.Align.RIGHT : Paint.Align.CENTER; + mSync = typedArray.getBoolean(R.styleable.WaterMarkView_water_mark_sync, true); + typedArray.recycle(); + + setBackgroundColor(Color.TRANSPARENT); + mTextPaint.setAntiAlias(true); + mTextPaint.setFlags(Paint.ANTI_ALIAS_FLAG); + mTextPaint.setColor(mTextColor); + mTextPaint.setTextSize(mTextSize); + mTextPaint.setTypeface(mTextBold ? Typeface.DEFAULT_BOLD : Typeface.DEFAULT); + mTextPaint.setTextAlign(mAlign); + + mText = mText == null && mSync ? WaterMarkManager.CONTENT : mText; + + textWidth = 0; + textHeight = 0; + if (mText != null && mText.length > 0) { + for (String s : mText) { + Rect tvRect = new Rect(); + mTextPaint.getTextBounds(s, 0, s.length(), tvRect); + textWidth = textWidth > tvRect.width() ? textWidth : tvRect.width(); + textHeight += (tvRect.height() + 10); + } + } + + if (mSync) { + WaterMarkManager.LIST.add(this); + } + } + + @Override + protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { + super.onMeasure(widthMeasureSpec, heightMeasureSpec); + } + + @Override + protected void onDraw(Canvas canvas) { + super.onDraw(canvas); + + if (mText != null && mText.length > 0) { + int measuredWidth = getMeasuredWidth(); + int measuredHeight = getMeasuredHeight(); + + if (measuredWidth == 0 || measuredHeight == 0) { + return; + } + + int canvasLength = measuredWidth > measuredHeight ? measuredWidth : measuredHeight; + + canvas.save(); + canvas.rotate(mDegrees, measuredWidth / 2, measuredHeight / 2); + + canvas.save(); + int y = 0; + boolean odd = true; + while (y < canvasLength + textHeight) { + int x = odd ? 0 : -(textWidth + mDx) / 2; + while (x < canvasLength + textWidth) { + drawTexts(mText, mTextPaint, canvas, x, y); + x = x + textWidth + mDx; + } + y = y + textHeight + mDy; + odd = !odd; + } + canvas.restore(); + } + } + + private void drawTexts(String[] ss, Paint paint, Canvas canvas, int x, int y) { + Paint.FontMetrics fontMetrics = paint.getFontMetrics(); + float top = fontMetrics.top; + float bottom = fontMetrics.bottom; + int length = ss.length; + float total = (length - 1) * (bottom - top) + (fontMetrics.descent - fontMetrics.ascent); + float offset = total / 2 - bottom; + for (int i = 0; i < length; i++) { + float yAxis = -(length - i - 1) * (bottom - top) + offset; + canvas.drawText(ss[i], x, y + yAxis + 10, paint); + } + } + + /** + * 设置水印文字内容 + * + * @param text 文字内容 + */ + public void setText(String... text) { + mText = text; + + textWidth = 0; + textHeight = 0; + if (mText != null && mText.length > 0) { + for (String s : mText) { + Rect tvRect = new Rect(); + mTextPaint.getTextBounds(s, 0, s.length(), tvRect); + textWidth = textWidth > tvRect.width() ? textWidth : tvRect.width(); + textHeight += (tvRect.height() + 10); + } + } + postInvalidate(); + } + + /** + * 同步设置水印文字内容 + * + * @param text 文字内容 + */ + void setSyncText(String... text) { + if (mSync) { + setText(text); + } + } + + /** + * 设置水印倾斜角度 + * + * @param degrees 倾斜角度(默认:-30) + */ + public void setDegrees(int degrees) { + mDegrees = degrees; + postInvalidate(); + } + + /** + * 同步设置水印倾斜角度 + * + * @param degrees 倾斜角度(默认:-30) + */ + void setSyncDegrees(int degrees) { + if (mSync) { + setDegrees(degrees); + } + } + + /** + * 设置水印字体颜色 + * + * @param textColor 字体颜色(默认:#33000000) + */ + public void setTextColor(int textColor) { + mTextColor = textColor; + mTextPaint.setColor(mTextColor); + postInvalidate(); + } + + /** + * 同步设置水印字体颜色 + * + * @param textColor 字体颜色(默认:#33000000) + */ + void setSyncTextColor(int textColor) { + if (mSync) { + setTextColor(textColor); + } + } + + /** + * 设置水印字体大小(单位:px) + * + * @param textSize 字体大小(默认:42px) + */ + public void setTextSize(int textSize) { + mTextSize = textSize; + mTextPaint.setTextSize(30); + postInvalidate(); + } + + /** + * 同步设置水印字体大小(单位:px) + * + * @param textSize 字体大小(默认:42px) + */ + void setSyncTextSize(int textSize) { + if (mSync) { + setTextSize(30); + } + } + + /** + * 设置水印字体是否粗体 + * + * @param textBold 是否粗体(默认:false) + */ + public void setTextBold(boolean textBold) { + mTextBold = textBold; + mTextPaint.setTypeface(mTextBold ? Typeface.DEFAULT_BOLD : Typeface.DEFAULT); + postInvalidate(); + } + + /** + * 同步设置水印字体是否粗体 + * + * @param textBold 是否粗体(默认:false) + */ + void setSyncTextBold(boolean textBold) { + if (mSync) { + setTextBold(textBold); + } + } + + /** + * 设置水印X轴偏移量(单位:px) + * + * @param dx X轴偏移量(默认:100px) + */ + public void setDx(int dx) { + this.mDx = dx; + postInvalidate(); + } + + /** + * 同步设置水印X轴偏移量(单位:px) + * + * @param dx X轴偏移量(默认:100px) + */ + void setSyncDx(int dx) { + if (mSync) { + setDx(dx); + } + } + + /** + * 设置水印Y轴偏移量(单位:px) + * + * @param dy Y轴偏移量(默认:240px) + */ + public void setDy(int dy) { + this.mDy = dy; + postInvalidate(); + } + + /** + * 同步设置水印Y轴偏移量(单位:px) + * + * @param dy Y轴偏移量(默认:240px) + */ + void setSignDy(int dy) { + if (mSync) { + setDy(dy); + } + } + + /** + * 设置水印对齐方式 + * + * @param align 对齐方式(默认:Center) + */ + public void setAlign(Paint.Align align) { + this.mAlign = align; + postInvalidate(); + } + + /** + * 同步设置水印对齐方式 + * + * @param align 对齐方式(默认:Center) + */ + void setSignAlign(Paint.Align align) { + if (mSync) { + setAlign(align); + } + } + + /** + * 销毁相关页面时调用(切记) + */ + public void onDestroy() { + if (mSync) { + WaterMarkManager.LIST.remove(this); + } + } + + @Override + public boolean dispatchTouchEvent(MotionEvent event) { + return false; + } + + @SuppressLint("ClickableViewAccessibility") + @Override + public boolean onTouchEvent(MotionEvent event) { + return false; + } +} \ No newline at end of file diff --git a/app/src/main/res/layout/activity_bottom_navigation2.xml b/app/src/main/res/layout/activity_bottom_navigation2.xml index aec3204c..73907989 100644 --- a/app/src/main/res/layout/activity_bottom_navigation2.xml +++ b/app/src/main/res/layout/activity_bottom_navigation2.xml @@ -25,4 +25,19 @@ app:labelVisibilityMode="labeled" app:menu="@menu/navigation" /> + + \ No newline at end of file diff --git a/app/src/main/res/layout/item/layout/view_water_mark.xml b/app/src/main/res/layout/item/layout/view_water_mark.xml new file mode 100644 index 00000000..96ebda93 --- /dev/null +++ b/app/src/main/res/layout/item/layout/view_water_mark.xml @@ -0,0 +1,5 @@ + + \ No newline at end of file diff --git a/app/src/main/res/values/attrs.xml b/app/src/main/res/values/attrs.xml index 6267894e..296bd211 100644 --- a/app/src/main/res/values/attrs.xml +++ b/app/src/main/res/values/attrs.xml @@ -21,4 +21,20 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml index 6d923faf..1f74c5c5 100644 --- a/app/src/main/res/values/colors.xml +++ b/app/src/main/res/values/colors.xml @@ -66,6 +66,7 @@ #EEEEEE #004684 #80000000 + #14000000