放大/缩小整个页面布局 [英] Zoom in/out the whole page layout

查看:120
本文介绍了放大/缩小整个页面布局的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试编写用于放大/缩小应用程序整个页面/屏幕的代码。我收到了这个链接

I am trying to write code for zoom in/out the whole page/screen of the app. I was given this link

Android - 放大/缩小RelativeLayout并传播/捏合

但初学者很难理解要遵循的所有程序。

but it's really difficult for a beginner to understand all the procedures to follow.

如果有人可以帮助并提供有关此主题的更清晰的解释,我和其他初学者一定会很感激。

If someone can help and provide clearer explanation on this topic, I and other beginners will surely appreciate it.

到目前为止,我已设置 MainActivity AnswerActivity 片段

So far I have set MainActivity, AnswerActivity and Fragments.

推荐答案

首先,让我们开始吧。缩放比较容易。 (此代码未在其他示例中使用):

First, lets start simple. Scaling is relatively easy. (this code is not used in the further examples):

    TextView rootView;
    rootView.setScaleX(sx);
    rootView.setScaleY(sx);

sx sy 是比例[X / Y]

sx and sy is scale[X/Y]

这是缩放的基础。现在我们来看看困难的部分:捏缩放。这需要用户以触摸事件的形式输入。

That is the fundamentals of scaling. Now we go to the hard part: Pinch zoom. this requires user input in the form of touch events.

如果你不能使用onTouchEvent作为根视图,首先设置一个onTouchListener。 (我不会显示这部分)

Start by setting an onTouchListener if you cannot use onTouchEvent for the root view. (I will not show this part)

在开始之前,声明一个名为scaleFactor的浮点数:

Before you even start, declare a float called scaleFactor:

[ANY-ACCESS-MODIFIER] long scaleFactor = 1f;

首先,我们需要一个ScaleGestureListener。如果需要,这可以是嵌套类:

First, we need a ScaleGestureListener. This can be a nested class if wanted:

class Scaler extends ScaleGestureDetector {
    public Scaler(Context context, OnScaleGestureListener listener) {
        super(context, listener);
    }

    @Override
    public float getScaleFactor() {//Leave this method empty.
        return super.getScaleFactor();
    }
}

其次我们需要OnScaleGestureListener:

Secondly we need the OnScaleGestureListener:

class ScaleListener implements ScaleGestureDetector.OnScaleGestureListener{

    @Override
    public boolean onScale(ScaleGestureDetector detector) {
        scaleFactor *= detector.getScaleFactor();

        if(scaleFactor > 2) scaleFactor = 2;//Limit to your liking
        else if(scaleFactor < 0.3f) scaleFactor = 0.3f;//Limit to your liking
        scaleFactor = (scaleFactor * 100) / 100;//jitter-protection
        //scaleMatrix.setScale(scaleFactor, scaleFactor, detector.getFocusX(), detector.getFocusY());//This is for usage with a Matrix: Good for canvas and other areas where this is usable. This is from my own scaling code, so I keep the matrix around in this example in case it is needed
        tv.setScaleX(scaleFactor);
        tv.setScaleY(scaleFactor);
        tv.setPivotX(detector.getFocusX());
        tv.setPivotY(detector.getFocusY());
        return true;
    }

    @Override
    public boolean onScaleBegin(ScaleGestureDetector detector) {return true;}

    @Override
    public void onScaleEnd(ScaleGestureDetector detector) {}
}

现在,这是分成两部分的地方。如果可能,请使用 onTouchEvent(MotionEvent ev)。如果你不能使用这个方法(当你在它上面添加 @Override 它显示错误时)你必须使用onTouchListener。将它设置在TextView上( tv.setOnTouchListener(this); 。确保该类实现OnTouchListener)

Now, this is where it splits in two. If possible, use onTouchEvent(MotionEvent ev). If you cannot use this method(when you add @Override above it it shows an error) you have to use onTouchListener instead. set it on the TextView(tv.setOnTouchListener(this);. Make sure the class implements OnTouchListener)

现在,无论你选择什么方法,确认它返回 true

Now, whatever method you picked, MAKE SURE IT RETURNS true!

此代码应该适用于这两种方法,并且它不限于特定方法:

This code should work in both methods, and it isn't limited to a specific method:

(ev是MotionEvent)

(ev is MotionEvent)

    int pointers = ev.getPointerCount();

    if(pointers == 2) {

        zoom = true;
        s.onTouchEvent(ev);//pass original motionevent(unscaled) to zoom

    }

现在,基本代码已到位。现在我们需要为 s 创建实例:

Now, the base code is in place. Now we need to create the instance for s:

全局声明:

private Scaler s;
private ScaleListener listener;

以及你在布局中膨胀的地方:

and where you inflate the layout:

listener = new ScaleListener();
s = new Scaler(c, listener);//c is a context. 

现在,假设所有组件都已到位,您就拥有了一个有效的放大/缩小系统。请注意,这不包括在缩放视图上滚动。您必须创建一个offsetX / Y变量,并在有一个指针时进行输入并检查您想要移动的距离。

Now, assuming all the components are in place you have a functioning zoom-in/out system. Please note that this does not cover scrolling on the zoomed view. You have to create an offsetX/Y variable, and take input when there is one pointer and check how far a distance you want to move.

使用TextView和触摸事件,您可以使用#setScrollX或#setScrollY以及偏移来设置新的滚动位置。

Using a TextView and touch events, you can use #setScrollX or #setScrollY along with an offset to set the new, scrolled position.

创建自己的自定义文本视图可能会更容易。您可以通过创建一个新类并使其扩展TextView来完成此操作。然后你可以根据需要进行修改。这将允许您将缩放等添加到自定义TextView中。如果您在单个班级中有多个文本视图,或者您有多个具有可缩放和可滚动文本视图的活动,则这是首选方法。

It may though be easier to create your own, custom text view. You do this by creating a new class and making it extend TextView. Then you put modifications as you want into there. This would allow you to add zoom and such into the custom TextView. This is though a prefered way to do it if you have multiple textviews in a single class or you have multiple activities with a zoomable and scrollable textview.

编辑:自定义textview

遗憾的是,很多集成工具都无法运行。 textview上的 android:scrollbars 不适用于实例。所以首先TextView必须有一个ScrolLView:

Sadly, not a lot of the integrated tools does nto work. android:scrollbars on a textview doesn't work for an instance. So first the TextView has to have a ScrolLView around it:

<ScrollView android:id="@+id/textScroll"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <com.package.ZoomableTextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Some hfndusijhgn hgnm hnixjkgbhn fvb uynfv bunfg vbuygn buy hgnyu gnui h  uh nuioiogfej uhud\nfhbnikjhgnuieskhg nmuimjhbnguijhgne \nfuyh ghfuisdghbuisjhgnuie dgjh\nifgb dsauingfbehja kbfiuej ksghbisdjkg nbhni\ngfdfjgdfh hdfh sdfhg sh "/>

</ScrollView>

和ZoomableTextView:

And ZoomableTextView:

你需要这个依赖性优先:

You need this dependency first:

compile 'com.android.support:appcompat-v7:25.3.1'

这是为了获取AppCompat库,以便TextView可以使用新功能,同时保持对早期版本的支持。现在为班级:

This is to get the AppCompat library so the TextView can use new features while maintaining support for earlier versions. now for the class:

public class ZoomableTextView extends AppCompatTextView/*This is why the AppCompat dependency is needed*/ {
    private float textSize,
            textScale;
    private Scaler s;
    private ScaleListener listener;
    public ZoomableTextView(Context context) {
        super(context);
        init();
    }

    public ZoomableTextView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public ZoomableTextView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    public void init(){
        listener = new ScaleListener();
        s = new Scaler(getContext(), listener);
        textSize = getTextSize();
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
    }

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        super.onTouchEvent(ev);
        if(ev.getPointerCount() == 2){
            s.onTouchEvent(ev);
        }
        return true;
    }

    class ScaleListener implements ScaleGestureDetector.OnScaleGestureListener{

        @Override
        public boolean onScale(ScaleGestureDetector detector) {
            textScale *= detector.getScaleFactor();

            if(textScale > 2) textScale = 2;//Limit to your liking
            else if(textScale < 0.3f) textScale = 0.3f;//Limit to your liking
            textScale = (textScale * 100) / 100;//jitter-protection
            if(textScale < 0.3f) textScale = 0.3f;
            if(textScale > 2) textScale = 2;

            setTextSize(textSize * textScale);
            setPivotX(detector.getFocusX());
            setPivotY(detector.getFocusY());
            return true;
        }

        @Override
        public boolean onScaleBegin(ScaleGestureDetector detector) {return true;}

        @Override
        public void onScaleEnd(ScaleGestureDetector detector) {}
    }

    class Scaler extends ScaleGestureDetector {
        public Scaler(Context context, OnScaleGestureListener listener) {
            super(context, listener);
        }

        @Override
        public float getScaleFactor() {//Leave this method empty.
            return super.getScaleFactor();
        }
    }
}

这篇关于放大/缩小整个页面布局的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆