Effect of the source code

Finally to the end of the year, in two days I also want to go home for Chinese New Year, think about it! Today I will bring you a canvas price selection effect based on mobile terminal. The design effect is like this.



The main function is to drag the ruler to change the price. And pay treasure and jingdong finance in also have such effect (as expected the world design is you copy I copy you 😁).

1. Implementation idea

The heart of the whole effect is the ruler drawn on canvas. It includes the ruler body, numbers and the fixed calibration axis in the middle, all of which are drawn with canvas. The large price text at the top, because it will be needed elsewhere to calculate the relevant returns. So, we’ll use a DOM to render it, so it’s easy to get.

There is a mapping relationship between the distance dragged by the ruler and the price, which is the most difficult part to deal with in the whole effect. We are doing analysis when dealing with related problems. Now, let’s implement the basic ruler drawing.

2. Ruler attribute definition

Let’s start by defining a class called rule-js with the following properties.

Now let’s look at what each property means:

1) X, y: coordinate position of the ruler

2) Vx: the moving speed of the ruler

3) AX: the moving acceleration of the ruler

4) color: draw the color of the ruler line and the color of the text

5) scaleX, scaleY: scale ratio

6) markShort, markLong: the length of the ruler’s long and short lines

7) textHeight: the height of the text from the ruler body

8) min, Max: maximum and minimum values to be displayed

9) width: pixel width of the ruler

10) Step

11) SEG: segment number

12) pxStep: actual step size on canvas (unit: px)

13) minPxStep: Each pxStep is divided into 10 segments without the actual pixel width of the segments

14) lineBottom: the bottom line parameter

15) lineRed: calibration axis parameters

There are a lot of arguments, but there aren’t that many that really need to be passed in. Here I will explain the ideas of the parameters (8) ~ (15).

The min and Max parameters set the maximum and minimum amounts to be displayed. This number is passed in from the outside, such as setting the user to save a minimum of 100 yuan and a maximum of 100,000 yuan. So min and Max correspond to 100 and 100000 respectively.

Width is the actual screen length of the entire ruler. For example, if you want the ruler to draw 1000px, you can pass 1000.

For example, if we set the maximum amount of money as 10000 yuan, then setting step as 1000 yuan means that every 1000 yuan represents a small section, which is also the data to be drawn on the ruler scale on canvas.

Seg segment number is equal to total amount Max divided by step.

PxStep is the pixel step that is really insinuated to the canvas.

MiniPxStep Each pxStep is divided into 10 segments with no pixel distance between the segments.

The lineBottom is separate from the scale of the ruler, so I’m thinking of drawing the bottom line of the ruler. The width of the bottom line is actually the width of the canvas. There is no need to draw the ruler from the beginning to the end. And for the user experience, the scale starts and ends in the center of the canvas. So, if you draw them all together, you have to draw an ungraduated line first, then a graduated line, and then an ungraduated line at the end. This undoubtedly makes drawing and subsequent ruler movement quite troublesome. So IF I pull it out, it’s just a normal line running through the canvas.

The lineRed calibration axis, always in the middle of the canvas, is also drawn independently of the ruler scale.

Now that we have the properties, let’s add a draw method to draw our ruler.

2. Ruler drawing

A) Draw the scale part of the ruler



There is a screenshot error herei+=this.miniPxStep. It shouldn’t be hard to understand, but every other timeminiPxStepDraw a line segment, line segment type according tonThis variable to determine.

B) Draw the text part of the ruler

Text cannot be drawn in terms of actual screen pixels, but must be mapped to the amount, so the number drawn here is (n/10) * this.step. At the same time, there is a special treatment, which is that the initial value is 1, not 0. Because, our amount does not allow to enter 0 yuan. If you don’t need this, just comment it out.

C) Draw the bottom line

D) Draw the calibration axis

This completes the entire ruler, the rule-js file, on Github at the top. Now let’s call this file and see what it looks like.

Here we set the minimum amount to 100000 yuan and the minimum amount to 500 yuan. The length of the ruler is 5000px and the step is 1000 yuan. The renderings are as follows:

Offset the ruler by 200px, such as x: rulex-200, to look like this:

Set step size to 500, the effect is as follows:

Ok, now that the static ruler is drawn, the next step is to complete the interactive function so that the ruler can scroll with us and show the amount of money currently dragged.

3. Drag the ruler

Now let’s implement the ruler drag. Ruler drag, its principle is very simple, is to let the ruler position follow the mouse move. For the sake of demonstration, I’ve changed the mouse event to the touch event on the mobile side.

Let’s start with our utility functionsutils.jsFile and then define a few variables.

IsMouseDown is used to determine whether the mouse is up, oldX is used to record the position of the last drag, and mouse is an object returned using captureMouse that returns information about the current position of the mouse on the canvas.

Then, listen for the Canvas mouse events mousedown, Mouseup, mousemove. And change the position of the rule.

IsMouseDown becomes true when the mouse is pressed down. OffsetX, which I forgot to write above, records the offset between the mouse position and the ruler position. Then rule. X = mouse.x-offsetx as the mouse moves. If you don’t do this, as soon as you click on the canvas and drag the ruler, you will find that the initial position of the ruler will move to the mouse click position, which is a bad experience. We need to move the ruler in the existing position with the mouse wherever we click. If you can’t feel it, try it out.

OldX is also very easy to understand, which is to record the last position of the ruler, and I haven’t used it here, but I might use it later. Now we write the ruler drawing into the animation function

Let’s see what the animation looks like.

Ok, now we have the ruler to follow the mouse drag. Next, we’ll display the amount of money we dragged.

4. Amount display

First, add an input field and then get it.

Here I set the minimum value of the input field to be the minimum size of the ruler, so I can leave that alone. We’re going to focus on the onMouseMove function

Note the calculated value of money, which is (centerx-rule-.x)* rule-.ratioscale. (Centerx-rule-x) is easier to understand because our ruler is drawn from the center point of the canvas. But rule. RatioScale is not defined in the original constructor. Here we need to add in the constructor, which means how much money per pixel, think of it as graph scale.

RatioScale = math.floor (this.max/this.width) // ratioScale = math.floor (this.max/this.width) // ratioScale = math.floor (this.max/this.width) //Copy the code

So naturally, the distance traveled times the scale gives you the money. Let’s see what happens.

Notice that the amount shown above is negative, so we need to limit the range of movement. Make it move only between a limited maximum and minimum amount.

5. Limit the movement range

The limitation of a certain range can be divided into two parts. One, the limit of the ruler range. 2. Restrictions on the amount displayed. Let’s do these two parts together.

1) Reset the initial position of the ruler assuming that the minimum amount we set is 500 yuan, then the position of the initial calibration axis should be 500 yuan. So after initializing the position of the ruler, we reset it to the position of the minimum amount. This is the time to convert the amount.

rule.x = centerX - rule.min / rule.ratioScale;Copy the code

Is the amount of money worth counting down.

2) Limit the movement range of the ruler

Here a detection boundary value function is defined. When the amount is less than the minimum investment amount, the ruler position is the initial position start(note that the initial position has been reset), and the amount is set to the minimum amount. The maximum position is the same. And then we call it in onMouseMove.

Look at the renderings.

6. Enter the amount to move the ruler

In addition to dragging, we also want to move the ruler through the amount input box. Enter the amount and the ruler moves to the target amount.

At the same time, we also made the boundary limit, when the input amount is less than or greater than the set value, set the ruler position and input box display as the boundary value, see the effect.

7. Speed it up

It’s still a little bit unnatural, but we want it to keep moving after the finger goes away, until it slows down to zero. To do this, create two new variables.

Var speed = 0, fl = 0.95; // Initial velocity, friction coefficientCopy the code

Create a new move function and call it in the animation loop.

At this point, the core function of dragging input is developed. Another thing to be aware of if you want to use it in your project is the blurring of canvas on mobile. There are already many solutions for this, you just need to be patient with debugging. Finally, I wish you all a happy New Year, source code in the head address oh.