Horizontal line crossing a vertical

Ladies/Gentlemen,
Please let me ask your help on creating program for a horizontal line crossing a vertical one. I desire that after crossing line disappear.
My code is following:

#include <GLFW/glfw3.h>
#include <gl/GL.h>
#include <iostream>


void render_loop(float a, float b, float x)
{
glClearColor(0.2, 0.2, 1.0f, 1.0);
glClear(GL_COLOR_BUFFER_BIT |   GL_DEPTH_BUFFER_BIT);
glPointSize(10);
glLineWidth(1.0);
glColor3f(1.0, 1.0, 0.2);
glBegin(GL_LINES);

glVertex2f(100, 1000.0f); glVertex2f(100.0f, 0.0f);
glVertex2f(a + x, 700.0f); glVertex2f(b + x , 700.0f);

glEnd();

}

/* program entry */
int main(int argc, char* argv[])
{
GLFWwindow* window;

if (!glfwInit())
{
	std::cout << "Failed to initialize GLFW\n";
	exit(EXIT_FAILURE);
}

glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
window = glfwCreateWindow(1200, 800, "LearnOpenGL", NULL, NULL);
if (!window)
{
	std::cout << "Failed to open GLFW window\n";
	glfwTerminate();
	exit(EXIT_FAILURE);
}


glfwMakeContextCurrent(window);
glfwSwapInterval(1);

// set up view
glViewport(0, 0, 1200, 800);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();

// see https://www.opengl.org/sdk/docs/man2/xhtml/glOrtho.xml
glOrtho(0.0, 800.0, 0.0, 800.0, 0.0, 1.0); // this creates a canvas you can do 2D drawing on


// Main loop
float x = 0.0f;
float speed = 1.3f;
float a{ 400.0f }; float b{ 480.0f };

while (!glfwWindowShouldClose(window))
{
	x = x - speed;

	// Draw gears
	render_loop(a, b, x);

	// Swap buffers
	glfwSwapBuffers(window);
	glfwPollEvents();
}
// Terminate GLFW
glfwTerminate();

// Exit program
exit(EXIT_SUCCESS);

}
Regards.

Hi George,
I’m not sure that I understand your problem.
Calculating the intersection between two lines is the first thing we learn in math. But I’m not sure that such a function is present in the libraries often used in conjunction with opengl (I use glm). I recall to have made two functions: one for detecting if an intersection occurs between two line-segments, and another for calculating the actual point. A basic function of mine can test if a point is on the left or right side of two points (a line segment) by using basic math-funtions (looking at projections using dot()?). This function is particularly usefull to test all line-segments of a polygon if a cursor is inside it. I detect an intersection by using that function on both point-pairs … Once you’r there you probably have the values needed to calculate the actual point. yes, it’s cumbersome, very basic vector-math … but in the end very slim.
And somewhat off the scoop of openGL.
It has an unrecognized up-side: … it’s a joy to tinker using the tools of your childhood learning ;o)

Dear Mr. CarstenT
Please accept my many thanks for replied my message. I found some solution no sufficient though. It’s following. Could you please suggest some better?

#include <GLFW/glfw3.h>
#include <gl/GL.h>
#include <iostream>


void render_loop(float a, float b)
{
glClearColor(0.2, 0.2, 1.0f, 1.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPointSize(10);
glLineWidth(1.0);
glColor3f(1.0, 1.0, 0.2);
glBegin(GL_LINES);

glVertex2f(100, 1000.0f); glVertex2f(100.0f, 0.0f);
glVertex2f(a, 700.0f); glVertex2f(b, 700.0f);

glEnd();

}

/* program entry */
int main(int argc, char* argv[])
{
GLFWwindow* window;

if (!glfwInit())
{
	std::cout << "Failed to initialize GLFW\n";
	exit(EXIT_FAILURE);
}

glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
window = glfwCreateWindow(1200, 800, "LearnOpenGL", NULL, NULL);
if (!window)
{
	std::cout << "Failed to open GLFW window\n";
	glfwTerminate();
	exit(EXIT_FAILURE);
}


glfwMakeContextCurrent(window);
glfwSwapInterval(1);

// set up view
glViewport(0, 0, 1200, 800);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();

// see https://www.opengl.org/sdk/docs/man2/xhtml/glOrtho.xml
glOrtho(0.0, 800.0, 0.0, 800.0, 0.0, 1.0); // this creates a canvas you can do 2D drawing on


// Main loop
float x = 0.0f;
float speed = 1.3f;

while (!glfwWindowShouldClose(window))
{
	float a{ 400.0f + x }; float b{ 480.0f + x };
	if (a > 100.0)
	{
		x = x - speed;

		// Draw gears
		render_loop(a, b);

		// Swap buffers
		glfwSwapBuffers(window);
		glfwPollEvents();
	}
	else if (b > 100.0)
	{
		a = 100.0;
		x = x - speed;

		// Draw gears
		render_loop(a, b);

		// Swap buffers
		glfwSwapBuffers(window);
		glfwPollEvents();
	}
	else
	{
		a = 100.0;
	}
		
	render_loop(a, b);

	// Swap buffers
	glfwSwapBuffers(window);
	glfwPollEvents();
}
// Terminate GLFW
glfwTerminate();

// Exit program
exit(EXIT_SUCCESS);

}

Regards.

Georges,
You have to explain what you expect to achieve. I “see” a long vertical line at x=100 and a minor horizontal line at y=700, 80 pixels long at start moving toward the long vertical. It looks as if the if(), else_if() & else() makes the line collaps at the foot of the long vertical when it has moved there. If that’s not what you want … then … what is it that you want to achieve?

Dear Mr. CarstenT,
Please accept my thanks for you continue be interested in my issue. I’m interested in create a project for chanters and singers see in real time their voice pitch error (interval) in respect to note they should sing. Horizontal line represent note, height the frequency and wide the duration. At left to vertical line some arrow (indicator) should show the interval pitch - note. Pitch is characterized by voice fundamental frequency. So singer can see in real time his voice’s pitch error and so be able to minimize it.
Indeed Project should be composed of two main parts. One to work with a digital processing kit and other with main PC. Latter should be graphics project. Regards.

Hi Georges,
Ok, the setup and major intend makes sense. I still do not grasp your first input:

The point a vertical line (x=100) intersecting a horizontal line (y=200) makes at intersection at (x,y)=(100,200). That should be obvious to you.
If you have a constant vertical line at y=100 and a moving graph, then run through the graph-data-points and pick the line, or two points where p1.y<100 && 100<p2.y. Once you have the two points and their .x-values too, you pick pen and paper to figure out the final calculation of the point somewhere between the two .x-values and y=100.
… the intersection is a moving point too.
But, Georges, this is just my guessing of your specific needs.
I have assumed that you get a stream of data-points. If it’s a dense set of points you could do with approximating the intersection to the point above or below. Do you grasp what I mean by saying that the intersection is a weighted mean of the two neighbors (weighted with y_above-100 & y_below-100). If everything fails … Pythagoras ;o)

I hope this inspires you to find what you need.

Georges,
you’ll need to look up the dot()-function and figure out the phytagoras-prone vector-length() function it you’ll skip the glm math library. It’s a header-only and no problem to implement into your programming. Be chritical about the code. I think that distSignValue() and vecProjOnVec() is plain dot()

 int distSignValue(const glm::dvec2 &aa0,  const glm::dvec2 &aa1,  const glm::dvec2 &pp ){
                    double sd =  (aa0.y - aa1.y)*pp.x + (aa1.x - aa0.x)*pp.y + aa0.x*aa1.y - aa1.x*aa0.y   ;
                    if(sd>=0.0d){ return (int) 1; }
                    else{return (int) -1; }
                }
		

bool doIntersect(const glm::dvec2& a1 , const glm::dvec2& a2 ,const glm::dvec2& b1 ,const glm::dvec2& b2){
         if( (distSignValue(a1,a2,b1)*distSignValue(a1,a2,b2)<0)&&(distSignValue(b1,b2,a1)*distSignValue(b1,b2,a2)<0 ) )
                 {return true;}
                 else{ return false;}
            }


glm::dvec2 vecProjOnVec( const glm::dvec2 & project, const glm::dvec2 & onto){
                glm::dvec2 res;
                double dt = glm::dot( project , onto );
                double lenOnto = glm::length(onto) ;
                res.x = ((dt/lenOnto)*onto.x)/lenOnto;
                res.y = ((dt/lenOnto)*onto.y)/lenOnto;endl;
                return res;
            }

pair<glm::dvec2,bool> intersection( const glm::dvec2& a1 , const glm::dvec2& a2 ,const glm::dvec2& b1 ,const glm::dvec2& b2  ){
                    pair<glm::dvec2,bool> result;
                    if(doIntersect(a1 ,a2 ,b1 ,b2) ){
                        glm::dvec2 a1a2 = glm::dvec2( a2.x - a1.x , a2.y - a1.y ) ; // ab
                        glm::dvec2 a1b1 = glm::dvec2( b1.x - a1.x , b1.y - a1.y ) ; // ac
                        glm::dvec2 b1b2 = glm::dvec2( b2.x - b1.x , b2.y - b1.y ) ; // cd
                        glm::dvec2 a1a2_hat = glm::dvec2( - a1a2.y, a1a2.x ) ; //
                        glm::dvec2 a1b1_proj = vecProjOnVec(a1b1,a1a2_hat); // projected onto hat
                        glm::dvec2 b1b2_proj = vecProjOnVec(b1b2,a1a2_hat);

                        double r_tio;
                        if(glm::length(b1b2_proj)!=0.0d){ r_tio = glm::length(a1b1_proj)/glm::length(b1b2_proj) ; }
                        else{ r_tio = 500.0d; }
                        result.first=glm::dvec2( r_tio*b1b2.x  + b1.x , r_tio*b1b2.y  + b1.y ) ;
                        result.second=true;
                    }
                    else{
                        result.first = glm::dvec2(0.0d, 0.0d) ;
                        result.second = false;
                    }
                    return result;
                }

Dear Mr. CarstenT,
Please let me express my glad for you are still interested in helping me. I explain my intention little further.
Arrow (pointer) I expect to create at left of vertical line moves up-down and represents voice’s pitch. So its vertical distance from line segment represents the interval pitch-note that is pitch’s error. User should regulate his/her voice pitch in order to minimize this distance. It’s necessary line-segment does appear at the left of vertical line. However if it appears isn’t problem.
Indeed many line segments are included in project one after the other but at different height (for represent different notes) and usually different length (wide).
I’m beginner in graphics programming and in programming in general. So your instructions are all Greek to me.
My better approach is following. I’m satisfied with it.
Regards.

#include <GLFW/glfw3.h>
#include <gl/GL.h>
#include <iostream>


void render_loop(float a, float b)
 {
glClearColor(0.2, 0.2, 1.0f, 1.0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPointSize(10);
glLineWidth(1.0);
glColor3f(1.0, 1.0, 0.2);
glBegin(GL_LINES);

glVertex2f(100, 1000.0f); glVertex2f(100.0f, 0.0f);
glVertex2f(a, 700.0f); glVertex2f(b, 700.0f);

glEnd();

 }

 /* program entry */
int main(int argc, char* argv[])
{
GLFWwindow* window;

if (!glfwInit())
{
	std::cout << "Failed to initialize GLFW\n";
	exit(EXIT_FAILURE);
}

glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
window = glfwCreateWindow(1400, 800, "LearnOpenGL", NULL, NULL);
if (!window)
{
	std::cout << "Failed to open GLFW window\n";
	glfwTerminate();
	exit(EXIT_FAILURE);
}


glfwMakeContextCurrent(window);
glfwSwapInterval(1);

// set up view
glViewport(0, 0, 1400, 800);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();

// see https://www.opengl.org/sdk/docs/man2/xhtml/glOrtho.xml
glOrtho(0.0, 1400.0, 0.0, 800.0, 0.0, 1.0); // this creates a canvas you can do 2D drawing on


// Main loop
float speed = 1.3f;
float a{ 400.0f };
float b{ 480.0f };

while (!glfwWindowShouldClose(window))
{
	if (a > 100.0)
	{
		a = a - speed;
		b = b - speed;
		// Draw gears
		render_loop(a, b);

		// Swap buffers
		glfwSwapBuffers(window);
		glfwPollEvents();
	}
	else if (b > 100.0)
	{
		a = 100.0;
		b = b - speed;

		// Draw gears
		render_loop(a, b);

		// Swap buffers
		glfwSwapBuffers(window);
		glfwPollEvents();
	}
	else
	{
		a = 100.0;


		render_loop(a, b);

		// Swap buffers
		glfwSwapBuffers(window);
		glfwPollEvents();
	}
}
// Terminate GLFW
glfwTerminate();

// Exit program
exit(EXIT_SUCCESS);

}

;o) I’ll take that as a compliment.

Dear Mr. CarstenT
Please let me answer: That’s right. However I hope that when I learn enough graphics I can ask your help.
Regards.

hi Georges,
I saw your post in “Square is not moving”. There’s a lot of things that I don’t understand about old style openGL, so I’ll just comment on the type question:

int my_int = 5;
float my_float = glFloat(my_int ) ;
This is a valid and precise conversion.

my_float = 1.5f ;
int anInt = int(my_float ); will not throw an error, but it can be problematic that it looses the 0.5 part and is rounded off.

Mr. CarstenT,
Please accept my many thanks for you replied my message. Then, do you think float variables a and b in my second program in present topic, are rounded off and represent pixels?
Regards.

Hi Georges,
The position value needs not be an int. It sort of belongs to the abstract consept ‘space’ where you just needs all the precition that you can find for the calculations that happens here. In the end … as an output, the float will be approximated to a pixel-position. The opengl mashinery has inner calculations before a point appears as a read pixel-dot.
You have a problem in that the questions you put is not really related to glfw or opengl. I’m an old geeser like you with no formal programming-learning, but 20 years of experience. I’ll make an exception and invite you to look me up on facebook as Carsten Troelsgaard (the version with the big grin) and stand up to support you on those things. Be warned: opengl & C++ programming in one go is a heavy packet to lift.

Dr. Mr. CarstenT,
Please accept my many thanks for you replied my message though not answered my question. I need be sure that function’s parameters represent pixels. I have to find out that myself though.
Also let me express my glad for you invited me to look you up on Facebook.
Regards.

Hi Georges,
I believe they do, but take my advice on early gl with a pinch of salt.
Do you have any indicators that they are not?
You have scaled the output through glViewport and the projection as an ortho appropriately. Do the two lines appear properly on the screen?

Mr. CarstenT,

Please let me express my glad for you replied my message and my sorrow for the delay in my response. I have not indications that parameters do not represent pixels, but that ought be integers. Two lines appear properly on screen. I’m interested in 2D graphics with opengl.

Regards.

Hi Georges,
The problems you’ve presented so far seems small compared to the hassle you could meet when it comes to ‘drawing’ the voice-graph.