【问题标题】:Android restrict the size when text sizing with pinch zoom and temp imageAndroid在使用捏缩放和临时图像调整文本大小时限制大小
【发布时间】:2020-06-01 13:31:13
【问题描述】:

我的静态布局上有文本,布局是 Recyclerview 中的一个项目。 Recyclerview 类的触摸事件使用 ScaleGestureDetector 控制对文本的捏合缩放。缩放场景是,当用户动作移动 Recyclerview 的屏幕时,获取 recyclerview 的屏幕截图并在 Recyclerview 上显示图像,然后用户缩放到图像。当动作开始时,将来自缩放的新文本大小应用于项目。新的文本大小应该与缩放到显示文本大小的图像时相同。为此,我使用 RelativeSizeSpan 和浮点缩放器值。我想限制总文本大小的变化,但它没有发生。

真正的问题是,捏缩放可以多次执行,并且有必要收集它们中的每一个的缩放比例,因为捏缩放会重置每个动作指针。 (mScaleFactor = 1.0f) 并且所有的缩放不应该超过指定的限制。 (MAX_ZOOM 和 MIN_ZOOM)

Recyclerview:

private ScaleListener mScaleListener;
private ScaleGestureDetector mScaleGestureDetector;

@Override
public boolean onTouchEvent(MotionEvent event) {
    int action = event.getAction() & MotionEvent.ACTION_MASK;

    if(event.getPointerCount() == 2 && (action == MotionEvent.ACTION_MOVE || action == MotionEvent.ACTION_POINTER_UP)) {
        if(mScaleGestureDetector == null){
            mScaleListener = new ScaleListener(mRecyclerview, mContext);
            mScaleGestureDetector = new ScaleGestureDetector(mContext, mScaleListener);
        } return mScaleGestureDetector.onTouchEvent(event);

    }

}

适配器:

private void changeTextSize(float mScaleFactor){
    ...
    float newFontSize = (relativeSizeSpan.getSizeChange() * mScaleFactor);
    ...
}

比例监听器:

public class ScaleListener extends ScaleGestureDetector.SimpleOnScaleGestureListener {

    private static final float MAX_ZOOM = 2.5f;
    private static final float MIN_ZOOM = 0.5f;
    private float mScaleFactor = 1.0f;
    private ImageView mScreenShotView;
    private Context mContext; 
    private View mView;

    public ScaleListener(View mView, Context mContext) {
        this.mView = mView;
        this.mContext = mContext;
        init();
    }

    private void init(){
        int mWidth = mView.getWidth();
        int mHeight = mView.getHeight();
        if(mWidth == 0 || mHeight == 0) return;

        mScreenShotView = new ImageView(mContext);
        mScreenShotView.setLayoutParams(new ViewGroup.LayoutParams(mWidth, mHeight));

        ViewGroup mPhysicalParentLayout = (ViewGroup) mView.getParent();
        mPhysicalParentLayout.addView(mScreenShotView, mPhysicalParentLayout.indexOfChild(mView));
    }

    @Override
    public boolean onScaleBegin(ScaleGestureDetector detector) {
        mScreenShotView.setBackgroundDrawable(new BitmapDrawable(Kit.getScreenshot(mView)));
        mScreenShotView.setAlpha(1f); mView.setAlpha(0f);
        return true;
    }

    @Override
    public boolean onScale(ScaleGestureDetector scaleGestureDetector){
        mScaleFactor *= scaleGestureDetector.getScaleFactor();

        mScaleFactor = Math.max(MIN_ZOOM, Math.min(mScaleFactor, MAX_ZOOM));

        mScreenShotView.setScaleX(mScaleFactor);
        mScreenShotView.setScaleY(mScaleFactor);

        return true;
    }

    @Override
    public void onScaleEnd(ScaleGestureDetector detector) {

        ((ReadBookRcAdapter)Objects.requireNonNull(((RecyclerView)mView).getAdapter())).changeTextSize(mScaleFactor);

        mScreenShotView.animate().alpha(0f).setDuration(300).setListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationStart(Animator animation) { 
                mView.animate().alpha(1f).setDuration(300).setListener(null); 
            }
            @Override
            public void onAnimationEnd(Animator animation) {
                mScreenShotView.setScaleX(1.0f);
                mScreenShotView.setScaleY(1.0f);
                mScaleFactor = 1.0f;
            }
        });

    }


}

【问题讨论】:

  • 什么是 relativeSizeSpan?
  • 这是一个相对大小跨度 :) developer.android.com/reference/android/text/style/…
  • 是的,我经历过...你能发布一种 Gif 或视频,你究竟得到了什么?缩放时
  • 用 gif 更新了问题。
  • 我已经厌倦了很多次这样的条件,但是我的 recyclerview 项目发生了不止一次合并的可跨字符串,有

    ...

    和更大的尺寸跨度。这些项目只有一个标题及其段落,并且未指定运行时哪种样式,因此常量限制会破坏我的样式层次结构。

标签: java android android-layout android-recyclerview


【解决方案1】:

解决了限制 TextView.setTextSize() 值的问题。这是我的适配器类:

public class ReadBookRcAdapter extends RecyclerView.Adapter<ReadBookRcAdapter.ReadBookViewHolder> {

    private Context mContext;
    private ArrayList<ReadBookTextBlockModel> mTextViewBlocks;
    private float mTextSize;

    public ReadBookRcAdapter(Context context) {
        this.mContext = context;
        this.mTextViewBlocks = new ReadBookTextBlockModel(context).getTextBlocks();
        mTextSize = 15.0f;
    }

    class ReadBookViewHolder extends RecyclerView.ViewHolder {
        TextView mTextViewItem;

        ReadBookViewHolder(@NonNull View itemView) {
            super(itemView);
            this.mTextViewItem = itemView.findViewById(R.id.readBookTextRow);
        }

        void bind(ReadBookTextBlockModel dataList){
            if (mTextSize != 15.0f) mTextViewItem.setTextSize(mTextSize);
            mTextViewItem.setText(dataList.getBlockText());
        }

    }

    @NonNull
    @Override
    public ReadBookViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.rc_item_read_book, parent, false);
        return new ReadBookViewHolder(view);
    }

    @Override
    public void onBindViewHolder(@NonNull ReadBookViewHolder holder, int position) {
        ReadBookTextBlockModel model = mTextViewBlocks.get(position);
        holder.bind(model);
    }

    public void setTextSize(float scale){

        float maxTextSize = 37.5f;
        float minTextSize = 7.5f;

        if((mTextSize == minTextSize && scale < 1.0f) || (mTextSize == maxTextSize && scale >= 1.0f))
            return;

        float newTextSize = mTextSize * scale;
        newTextSize = Math.max(minTextSize, Math.min(newTextSize, maxTextSize));

        mTextSize = newTextSize;

        Log.e("mTextSize*scale", String.valueOf(mTextSize));

        notifyDataSetChanged();
    }

}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-07-14
    • 2023-01-26
    • 1970-01-01
    • 2014-10-29
    • 2010-12-02
    • 2011-04-20
    相关资源
    最近更新 更多