By default, the Y axis will start from bottom in ZedGraph.
Now, I want to have a chart will look:
y
0 |
10 |
20 |
30 |
40 |--------------x
Is it possible to reverse Y asix?
It can be achieved by setting YAxis.Scale.IsReverse = true;
Related
I have a 3x3 matrix I'm using to track movement in 2D. I need to extract from that the translation, rotation and scale matrices. Can anyone suggest how I would do this? I've had no luck searching online so far (possibly I'm using the wrong terms).
This is just off the top of my head so there may be an error in here, but:
Assuming your matrix is row-major (just transpose everything if you're using column major):
| cos(t) -sin(t) 0 |
| sin(t) cos(t) 0 |
| tx ty 1 |
The translation vector will be the last row in the matrix [tx ty 1]. Extracting scale and rotation in a composed matrix is a bit trickier.
Looking at a 3x3 rotation matrix,
| cos(t) -sin(t) 0 |
| sin(t) cos(t) 0 |
| 0 0 1 |
And a scale matrix
| vx 0 0 |
| 0 vy 0 |
| 0 0 1 |
The combined rotation & scale matrix might look like (ct = cos(t), st = sin(t))
| vx*ct -vx*st 0 |
| vy*st vy*ct 0 |
| 0 0 1 |
For uniform scaling, vx=vy.
| v*ct -v*st 0 |
| v*st v*ct 0 |
| 0 0 1 |
Remembering the trig identity
ct^2 + st^2 = 1
We can see that the
(v*ct)^2 + (v*st)^2 = v^2
or
v^2*ct^2 + v^2*st^2 = v^2
... all the terms of which are in the composite (scale,rotation,translation or SRT for short) matrix,
So,
v = sqrt((v*ct)^2 + (v*st)^2)
or
v = sqrt(M[0,0]^2 + M[0,1]^2);
Theta, then is just
t = acos(vct/v)
or
t = acos(M[0,0]/v)
or, this might work much easier but I haven't tried it:
theta = atan2(vst,vct),
scale = sqrt(vst^2+vct^2)
where ^ is an exponent, not an XOR.
... and you can work out the rest.
It would be wiser to keep your scale, rotation and translation values around and use those values both to build the matrix and for whatever other tasks you require. Relying on the matrix as the only container for that information will eventually lead to compound floating-point errors and other drama.
Some notes:
Theta is an angle. It's a fun, easy-to-draw Greek symbol, and all us engineers love greek characters. It's mostly Stockholm syndrome since some of them look like 5's, and some of them are impossible to draw unless you're Greek.
This works great for 2D, where there is only one possible rotation axis. If you're working in three (or higher! It's a thing now!) dimensions, the concept is the same but the implementation becomes much, much messier.
st, ct, vst, vct, etc. are all contained in the composite matrix you have available. (Composite == concatenated == combined. The terminology in use depends on who you're reading.) The non-intuitive part is extracting the elements that you need from the matrix. This requires understanding what is in the matrix, where, and why.
This is a solvable problem. Normally, I'm a sit-down-and-start-coding kind of guy, and in 25 years of professional development, I'd have to say that it's worked out pretty well so far. But, there are times where a whiteboard or a notebook and a mechanical pencil are better friends than your keyboard.
For a column major matrix, given:
X vector of < Xx, Xy >;
Y vector of < Yx, Yy > and
Translation/position of < Tx, Ty >,
The corresponding column major transformation matrix is:
The translation is:
For the Scaling, the scale factors for the X and Y vectors are:
The scaling transformation is then:
For Rotation, the normalized vectors are:
X Vector: < Xx/Sx, Xy/Sx >
Y Vector: < Yx/Sy, Yy/Sy >
And the rotation transformation "R" is:
RECOMPOSITION:
Given translation "T", rotation "R", and scaling "S" transformation in column major order, the original matrix/transform can be recreated with:
T * R * S
Assumption, the original transformation has X and Y vectors that are:
Not parallel;
Not a length of zero;
Not mirrored; and
Not skewed/sheared.
The rotation can be further decomposed into an angle as described by 3Dave (which is row major, and needs to be transposed to be column major).
Supposing that I have two labels with variable text. Label 1 is in the center of the screen. I can position Label 2 on the right side of Label 1:
label1.Location = (WIDTH / 2, Height / 2)
label2.Location = new Point(label1.Right, label1.Top);
Form output:
_______________
| |
| 100 200 |
|_______________|
Now I want do the same, but position Label 2 on the left side of Label 1. How can I do this?
Form output:
_______________
| |
| 200 100 |
|_______________|
If label2 is already sized correctly, you can just subtract its width from the left side of label1:
label2.Location = new Point(label1.Left - label2.Width, label1.Top)
Diagram:
-----(label1.Left - label2.Width)
|
| -----label1.Left
_|___|_________
| v v |
| +---+---+ <--------label1.Top
| |200|100| |
| +---+---+ |
| '---' |
|___|__________|
|
-----label2.Width
Position the second label starting from the left point of the first label and subtracting the witdh of the one to be placed
label2.Location = new Point(label1.Left - label2.Width, label1.Top);
By the way, the value used for your first label should consider the width and height of the label to be really at the center of the label container.
So assuming you want the first label at the center of its containing form you should use a formula like this
int leftPos = (this.Width / 2) - (label1.Width / 2);
int topPos = (this.Height / 2) - (label1.height / 2);
label1.Location = new Point(leftPos, topPos)
I have a bug somewhere in my code, was wondering if this is incorrect.
I have a 2D view matrix in my code, but to display my world to the screen I need to convert the 2D view matrix to a 3D one. This is the process that I am using:
| a b c | | a b c 0 |
| d e f | => | d e f 0 |
| g h i | | g h i 0 |
| 0 0 0 1 |
It works when I use an identity matrix for the 2D matrix, but as soon as I apply any transforms to the 2D matrix all my objects being drawn disappear.
For drawing in 2D using 3D, I use this projection matrix:
_basicEffect.Projection = Matrix.CreateOrthographicOffCenter(0, graphicsDevice.Viewport.Width, graphicsDevice.Viewport.Height, 0, 0, 1);
What is the correct way to transform the 2D matrix to 3D?
Affine transformations use the extra row/column of the transformation matrix for translation. So I think what you want to do is to move the last row/column down/right and then for the new axis simply insert the identity transformation.
| a b c | | a b 0 c |
| d e f | => | d e 0 f |
| g h i | | 0 0 1 0 |
| g h 0 i |
I'm not sure, but give it a try at least.
I'm looking for a simple algorithm that, given a rectangle with width w and height h, splits the rectangle into n more or less equal sized and shape rectangles and calculates the center of these rectangles.
EDIT: Forgot to mention that the shapes should be as similar as possible to a square.
Any hints how to start?
A simple algorithm is to split vertically into n equal sized strips of height h and width w/n.
If you assume that the initial rectangle has corners (0,0) and (w,h) then using this algorithm the ith rectangle would have center (w / n * (i + ½), h/2), for 0 <= i < n.
Update: try finding all the factorizations of the number n into factor pairs (i, j) such that i * j = n, and find the factor pair such that the ratio of the factors is closest to the ratio of the sides of the rectangle. Then use the two factors to create a regular grid of smaller rectangles.
For example when n is 10, you can choose between (1, 10), (2, 5), (5, 2) and (10, 1). Here is an example grid using the factors (5, 2):
------------------------------------
| | | | | |
| | | | | |
------------------------------------
| | | | | |
| | | | | |
------------------------------------
If your initial rectangle has width 60 and height 20 then using the factor pair (5, 2) will give ten rectangles of size (60/5, 20/2) = (12, 10) which is close to square.
Let's say I have two rectangles overlapping each other like this...
alt text http://filebox.me/files/u8atnxd34_overlap1.png
And I want them to end up like this...
alt text http://filebox.me/files/jt8ef1t44_overlap2.png
How would I calculate the position I need to add so that the rectangles move out of each other?
Note: I did find this question but it doesn't tell me how to actually move the rectangles.
Everyone's assuming I want to move the rectangle downwards, but I actually want the rectangle to move in the direction which would be the most logical. So that if the rectangle is completely to the right of the first rectangle and moves 1 pixel to the left, that it instead of moving downwards, it would move to the right.
__________
| ____|____
| A | | |
|___|____| |
| B |
|_________|
if [
(TopLeftOfA.Y + A.Height - TopLeftOfB.Y)
<
(TopLeftOfA.X + A.Width - TopLeftOfB.X)
]
TopLeftOfB.Y = TopLeftOfA.Y + A.Height
else
TopLeftOfB.X = TopLeftOfA.X + A.Width
Just move first rectangle any direction from second rectangle.
even easier:
set the Y coördinates of the first rectangle's bottom, to the y coördinates of the second rectangle's top
In the exact configuration you have shown:
where a = is the foreground rectangle and b = the background triangle.
a.Top = b.Bottom; // Add +1 to have it just past the bottom.
rectangle2.top = rectangle1.bottom+1 (javascript)