PDA

View Full Version : Scaling i want to add scaling to my codeould someone advise me how



cloudracer
04-25-2014, 11:46 AM
I want to add scaling to my code but im not sure how to do it.

I want to make it so that the position is stored in (x_mouse, y_mouse) when the middle button is clicked and When mouse is in motion with middle button pressed down it's recorded its position in (x_mouse_cur, y_mouse_cur); Thank you



#include "stdafx.h"
#include <Windows.h>
#include <iostream>
#include <fstream>
#include <math.h>
#include <gl\GL.h>
#include <gl\GLU.h>
#include "glut.h"

using namespace std;

void display();
void reshape(int w, int h);
void idle();
void mouse_click(int button, int state, int x, int y);
void mouse_motion(int x, int y);
void cal_vertices();
void read_vertices();
void init();

// global var, rotation angle
float angle = 0.0;
float vertices[5][2]; // 5 vertices, and x, y coordinates
GLuint listname = 1;
float dx = 0.0;
float dy = 0.0;
float dz = 0.0;
float scale = 1.0;

// mouse click
int x_click, y_click;
int button;

int main(int argc, char* argv[])
{
// initialize glut
glutInit(&argc, argv);

// initialize window position
glutInitWindowPosition(10, 10);

// window size
glutInitWindowSize(1200, 600);

// display mode
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);

// create a window
glutCreateWindow("A simple glut window");

glutDisplayFunc(display);
glutReshapeFunc(reshape);
glutIdleFunc(idle);
glutMouseFunc(mouse_click);
glutMotionFunc(mouse_motion);

init();

// glut main loop
glutMainLoop();

return 0;
}

void display(){
glClearColor(0.0, 0.0, 0.0, 1.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

//glPushMatrix();
// glRotatef(angle, 0.0, 1.0, 0.0);
// glRotatef(angle, 1.0, 0.0, 0.0);
// glutSolidTeapot(0.5);
//glPopMatrix();

glPushMatrix();
glTranslatef(dx, dy, dz);
glRotatef(angle, 0.0, 0.0, 1.0);
glScalef(scale, scale, scale);
glCallList(listname);
glPopMatrix();

glutSwapBuffers();
}

void reshape(int w, int h) {

// Prevent a divide by zero, when window is too short
// (you cant make a window of zero width).
if(h == 0)
h = 1;

float ratio = 1.0* w / h;

// Reset the coordinate system before modifying
glMatrixMode(GL_PROJECTION);
glLoadIdentity();

// Set the viewport to be the entire window
glViewport(0, 0, w, h);

// Set the correct perspective.
gluPerspective(45,ratio,1,1000);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(0.0,0.0,5.0, // eye's position
0.0,0.0,1.0, // center of interest
0.0f,1.0f,0.0f); // up direction

}

void idle()
{
angle = angle + 0.5;
glutPostRedisplay();
}

void mouse_click(int button, int state, int x, int y)
{
if (state == GLUT_DOWN) {
x_click = x;
y_click = y;
::button = button; // button = GLUT_LEFT_BUTTON, GLUT_RIGHT_BUTTON, GLUT_MIDDLE_BUTTON
}else {
::button = -1;
}
}

void mouse_motion(int x, int y)
{
switch (button){
case GLUT_LEFT_BUTTON:
dx -= (x_click - x) * 0.01;
dy += (y_click - y) * 0.01;
break;
case GLUT_RIGHT_BUTTON:
angle -=(x_click - x);
break;
case GLUT_MIDDLE_BUTTON:
scale -= (x_click - x) * 0.02;
break;
}
x_click = x;
y_click = y;
}

void cal_vertices()
{
// open a file for writing pentagen vertices
ofstream outfile("vertices.txt");
float a = 2 * 3.1415926 / 5.0;
float x1 = 0.0, y1 = 1.0;
outfile << x1 << " " << y1 << endl;;
float x, y;
for (int i = 1; i < 5; i++) {
x = x1 * cos(a * i) - y1 * sin(a * i);
y = y1 * cos(a * i) + x1 * sin(a * i);
outfile << x << " " << y << endl;;
}
outfile.close();
}

void read_vertices()
{
ifstream infile("vertices.txt");
for (int i = 0; i < 5; i++){
infile >> vertices[i][0];
infile >> vertices[i][1];
cout << vertices[i][0] << " " << vertices[i][1] << endl;
}
}

void init()
{
cal_vertices();
read_vertices();

glNewList(listname, GL_COMPILE);
glBegin(GL_LINE_LOOP);
for(int i = 0; i < 5; i++){
glVertex3f(vertices[i][0], vertices[i][1], 0.0);
}
glEnd();
glEndList();
}

The Little Body
04-27-2014, 01:34 PM
The problem seem only to be generated by the sign you use into the GLUT_MIDDLE_BUTTON in your mouse_motion() func
=> only use += instead -= and this seem to work fine



void mouse_motion(int x, int y)
{
switch (button){

case GLUT_LEFT_BUTTON:
dx -= (x_click - x) * 0.01;
dy += (y_click - y) * 0.01;
break;

case GLUT_RIGHT_BUTTON:
angle -=(x_click - x);
break;

case GLUT_MIDDLE_BUTTON:
scale += (x_click - x) * 0.02;
break;
}
x_click = x;
y_click = y;
}

(the figure grow when the mouse goes to right and the figure narrow when the mouse goes to left)
[while the middle button is always pressed of course]


I have a very little transform your code for to can compile it on a linux box and add an exit key to it
(you now quit the program when you hit the Escape key)



#ifdef WINDOWS
#include "stdafx.h"
#include <Windows.h>
#include <gl\GL.h>
#include <gl\GLU.h>
#endif

#include <math.h>
#include <fstream>
#include <iostream>
#include <GL/glut.h>


using namespace std;

void display();
void reshape(int w, int h);
void idle();
void mouse_click(int button, int state, int x, int y);
void mouse_motion(int x, int y);
void keyboard( unsigned char key, int x, int y);
void cal_vertices();
void read_vertices();
void init();

// global var, rotation angle
float angle = 0.0;
float vertices[5][2]; // 5 vertices, and x, y coordinates
GLuint listname = 1;
float dx = 0.0;
float dy = 0.0;
float dz = 0.0;
float scale = 1.0;

// mouse click
int x_click, y_click;
int button;

// OpenGL window handle
int win;

int main(int argc, char* argv[])
{
// initialize glut
glutInit(&argc, argv);

// initialize window position
glutInitWindowPosition(10, 10);

// window size
glutInitWindowSize(1200, 600);

// display mode
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);

// create a window
win = glutCreateWindow("A simple glut window");

glutDisplayFunc(display);
glutReshapeFunc(reshape);
glutIdleFunc(idle);
glutMouseFunc(mouse_click);
glutMotionFunc(mouse_motion);
glutKeyboardFunc(keyboard);

init();

// glut main loop
glutMainLoop();

return 0;
}

void display(){
glClearColor(0.0, 0.0, 0.0, 1.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

//glPushMatrix();
// glRotatef(angle, 0.0, 1.0, 0.0);
// glRotatef(angle, 1.0, 0.0, 0.0);
// glutSolidTeapot(0.5);
//glPopMatrix();

glPushMatrix();
glTranslatef(dx, dy, dz);
glRotatef(angle, 0.0, 0.0, 1.0);
glScalef(scale, scale, scale);
glCallList(listname);
glPopMatrix();

glutSwapBuffers();
}

void reshape(int w, int h) {

// Prevent a divide by zero, when window is too short
// (you cant make a window of zero width).
if(h == 0)
h = 1;

float ratio = 1.0* w / h;

// Reset the coordinate system before modifying
glMatrixMode(GL_PROJECTION);
glLoadIdentity();

// Set the viewport to be the entire window
glViewport(0, 0, w, h);

// Set the correct perspective.
gluPerspective(45,ratio,1,1000);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(0.0,0.0,5.0, // eye's position
0.0,0.0,1.0, // center of interest
0.0f,1.0f,0.0f); // up direction

}

void idle()
{
angle = angle + 0.5;
glutPostRedisplay();
}

void mouse_click(int button, int state, int x, int y)
{
if (state == GLUT_DOWN) {
x_click = x;
y_click = y;
::button = button; // button = GLUT_LEFT_BUTTON, GLUT_RIGHT_BUTTON, GLUT_MIDDLE_BUTTON
}else {
::button = -1;
}
}

void mouse_motion(int x, int y)
{
switch (button){

case GLUT_LEFT_BUTTON:
dx -= (x_click - x) * 0.01;
dy += (y_click - y) * 0.01;
break;

case GLUT_RIGHT_BUTTON:
angle -=(x_click - x);
break;

case GLUT_MIDDLE_BUTTON:
scale += (x_click - x) * 0.02;
break;
}
x_click = x;
y_click = y;
}

void keyboard( unsigned char key, int x, int y)
{
if ( key == 27 )
{
glutDestroyWindow(win);
}
}


void cal_vertices()
{
// open a file for writing pentagen vertices
ofstream outfile("vertices.txt");
float a = 2 * 3.1415926 / 5.0;
float x1 = 0.0, y1 = 1.0;
outfile << x1 << " " << y1 << endl;;
float x, y;
for (int i = 1; i < 5; i++) {
x = x1 * cos(a * i) - y1 * sin(a * i);
y = y1 * cos(a * i) + x1 * sin(a * i);
outfile << x << " " << y << endl;;
}
outfile.close();
}

void read_vertices()
{
ifstream infile("vertices.txt");
for (int i = 0; i < 5; i++){
infile >> vertices[i][0];
infile >> vertices[i][1];
cout << vertices[i][0] << " " << vertices[i][1] << endl;
}
}

void init()
{
cal_vertices();
read_vertices();

glNewList(listname, GL_COMPILE);
glBegin(GL_LINE_LOOP);
for(int i = 0; i < 5; i++){
glVertex3f(vertices[i][0], vertices[i][1], 0.0);
}
glEnd();
glEndList();
}


This compile fine on a linux box using only this :


g++ scaling.c -o scaling -lm -lglut -lGL -lGLU

The Little Body
04-27-2014, 02:07 PM
This is exactely the same thing, only inverse the grow vs narrow action :(

=> I have reread your initial post and look about the needed transformation for to handle updates of x_move_cur and y_mov_cur
(I think this need only to differentiate GLUT_*_BUTTON cases on the mouse_click() function)