How to use glOrtho() in OpenGL? - Stack Overflow

文章推薦指數: 80 %
投票人數:10人

The glOrtho command produces an "Oblique" projection that you see in the bottom row. No matter how far away vertexes are in the z direction, they will not ... Home Public Questions Tags Users Companies Collectives ExploreCollectives Teams StackOverflowforTeams –Startcollaboratingandsharingorganizationalknowledge. CreateafreeTeam WhyTeams? Teams CreatefreeTeam Collectives™onStackOverflow Findcentralized,trustedcontentandcollaboratearoundthetechnologiesyouusemost. LearnmoreaboutCollectives Teams Q&Aforwork Connectandshareknowledgewithinasinglelocationthatisstructuredandeasytosearch. LearnmoreaboutTeams HowtouseglOrtho()inOpenGL? AskQuestion Asked 12years,6monthsago Modified 1year,9monthsago Viewed 123ktimes 103 50 Ican'tunderstandtheusageofglOrtho.Cansomeoneexplainwhatitisusedfor? Isitusedtosettherangeofxyandzcoordinateslimit? glOrtho(-1.0,1.0,-1.0,1.0,-1.0,1.0); Itmeansthatthex,yandzrangeisfrom-1to1? c++copengl Share Follow editedMar11,2018at10:26 CiroSantilliOurBigBook.com 316k8989goldbadges11251125silverbadges911911bronzebadges askedApr3,2010at13:50 ufkufk 29.5k6161goldbadges224224silverbadges371371bronzebadges 1 1 Thisvideohelpedmealot. – ViniciusArruda Sep14,2017at13:53 Addacomment  |  3Answers 3 Sortedby: Resettodefault Highestscore(default) Trending(recentvotescountmore) Datemodified(newestfirst) Datecreated(oldestfirst) 164 Havealookatthispicture:GraphicalProjections TheglOrthocommandproducesan"Oblique"projectionthatyouseeinthebottomrow.Nomatterhowfarawayvertexesareinthezdirection,theywillnotrecedeintothedistance. IuseglOrthoeverytimeIneedtodo2DgraphicsinOpenGL(suchashealthbars,menusetc) usingthefollowingcodeeverytimethewindowisresized: glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrtho(0.0f,windowWidth,windowHeight,0.0f,0.0f,1.0f); ThiswillremaptheOpenGLcoordinatesintotheequivalentpixelvalues(Xgoingfrom0towindowWidthandYgoingfrom0towindowHeight).NotethatI'veflippedtheYvaluesbecauseOpenGLcoordinatesstartfromthebottomleftcornerofthewindow.Sobyflipping,Igetamoreconventional(0,0)startingatthetopleftcornerofthewindowrather. NotethattheZvaluesareclippedfrom0to1.SobecarefulwhenyouspecifyaZvalueforyourvertex'sposition,itwillbeclippedifitfallsoutsidethatrange.Otherwiseifit'sinsidethatrange,itwillappeartohavenoeffectonthepositionexceptforZtests. Share Follow editedAug13,2019at8:33 answeredApr8,2010at19:12 MikepoteMikepote 5,77522goldbadges3232silverbadges3636bronzebadges 6 2 Note:(onAndroid)evenifthemodelhasonlynegativezvalues,itseemstobenecessarytohaveapositivevalueforthefinal(far)parameter.Ididasimpletriangletest(withcullingdisabled),withverticesatz=-2.ThetrianglewasinvisibleifIusedglOrtho(..,0.0f,-4.0f);,..-1.0f,-3.0f),or..-3.0f,-1.0f).Tobevisible,thefarparameterhadtobePOSITIVE2orgreater;itdidn'tseemtomatterwhatthenearparameterwas.Anyoftheseworked:..0.0f,2.0f),..-1.0f,2.0f),..-3.0f,2.0f),or..0.0f,1000.0f. – ToolmakerSteve Sep9,2014at21:11 15 It'sridiculoustheamountofbadtutorialsonOpenGlthereare. – basickarl Nov9,2014at17:56 1 @Kari,Hopethislinkcouldhelp.>learnopengl.com/#!In-Practice/2D-Game/Rendering-Sprites – huahsin68 Feb5,2016at2:01 Canyouexplainthezrange? – mgouin May30,2017at15:47 2 @mgouinThezrangespecifieswhereyourZ-nearplaneandyourZ-farplaneare.Whenyoudrawyourgeometry,it'sZvaluesmustbeinsidethetwoZplanes.IftheyfalloutsidetheZplanes,yourgeometrywontberendered.Alsoyourrendereronlyhasacertainresolutionfordepth.Ifyouhaveyourfarplanesetto1000unitsawayandyoutrydrawatinymodelwithlittlefaces0.1unitsawayfromeachother,OpenGLwontbeablegiveyouthedepthresolutionyouneedandyou'llgetZ-fighting(flickering)betweenthefaces. – Mikepote May30,2017at17:06  |  Show1morecomment 60 Minimalrunnableexample glOrtho:2Dgames,objectscloseandfarappearthesamesize: glFrustrum:morereal-lifelike3D,identicalobjectsfurtherawayappearsmaller: main.c #include #include #include #include staticintortho=0; staticvoiddisplay(void){ glClear(GL_COLOR_BUFFER_BIT); glLoadIdentity(); if(ortho){ }else{ /*Thisonlyrotatesandtranslatestheworldaroundtolooklikethecameramoved.*/ gluLookAt(0.0,0.0,-3.0,0.0,0.0,0.0,0.0,1.0,0.0); } glColor3f(1.0f,1.0f,1.0f); glutWireCube(2); glFlush(); } staticvoidreshape(intw,inth){ glViewport(0,0,w,h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if(ortho){ glOrtho(-2.0,2.0,-2.0,2.0,-1.5,1.5); }else{ glFrustum(-1.0,1.0,-1.0,1.0,1.5,20.0); } glMatrixMode(GL_MODELVIEW); } intmain(intargc,char**argv){ glutInit(&argc,argv); if(argc>1){ ortho=1; } glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB); glutInitWindowSize(500,500); glutInitWindowPosition(100,100); glutCreateWindow(argv[0]); glClearColor(0.0,0.0,0.0,0.0); glShadeModel(GL_FLAT); glutDisplayFunc(display); glutReshapeFunc(reshape); glutMainLoop(); returnEXIT_SUCCESS; } GitHubupstream. Compile: gcc-ggdb3-O0-omain-std=c99-Wall-Wextra-pedanticmain.c-lGL-lGLU-lglut RunwithglOrtho: ./main1 RunwithglFrustrum: ./main TestedonUbuntu18.10. Schema Ortho:cameraisaplane,visiblevolumearectangle: Frustrum:cameraisapoint,visiblevolumeasliceofapyramid: Imagesource. Parameters Wearealwayslookingfrom+zto-zwith+yupwards: glOrtho(left,right,bottom,top,near,far) left:minimumxwesee right:maximumxwesee bottom:minimumywesee top:maximumywesee -near:minimumzwesee.Yes,thisis-1timesnear.Soanegativeinputmeanspositivez. -far:maximumzwesee.Alsonegative. Schema: Imagesource. Howitworksunderthehood Intheend,OpenGLalways"uses": glOrtho(-1.0,1.0,-1.0,1.0,-1.0,1.0); IfweuseneitherglOrthonorglFrustrum,thatiswhatweget. glOrthoandglFrustrumarejustlineartransformations(AKAmatrixmultiplication)suchthat: glOrtho:takesagiven3Drectangleintothedefaultcube glFrustrum:takesagivenpyramidsectionintothedefaultcube Thistransformationisthenappliedtoallvertexes.ThisiswhatImeanin2D: Imagesource. Thefinalstepaftertransformationissimple: removeanypointsoutsideofthecube(culling):justensurethatx,yandzarein[-1,+1] ignorethezcomponentandtakeonlyxandy,whichnowcanbeputintoa2Dscreen WithglOrtho,zisignored,soyoumightaswellalwaysuse0. Onereasonyoumightwanttousez!=0istomakespriteshidethebackgroundwiththedepthbuffer. Deprecation glOrthoisdeprecatedasofOpenGL4.5:thecompatibilityprofile12.1."FIXED-FUNCTIONVERTEXTRANSFORMATIONS"isinred. Sodon'tuseitforproduction.Inanycase,understandingitisagoodwaytogetsomeOpenGLinsight. ModernOpenGL4programscalculatethetransformationmatrix(whichissmall)ontheCPU,andthengivethematrixandallpointstobetransformedtoOpenGL,whichcandothethousandsofmatrixmultiplicationsfordifferentpointsreallyfastinparallel. Manuallywrittenvertexshadersthendothemultiplicationexplicitly,usuallywiththeconvenientvectordatatypesoftheOpenGLShadingLanguage. Sinceyouwritetheshaderexplicitly,thisallowsyoutotweakthealgorithmtoyourneeds.SuchflexibilityisamajorfeatureofmoremodernGPUs,whichunliketheoldonesthatdidafixedalgorithmwithsomeinputparameters,cannowdoarbitrarycomputations.Seealso:https://stackoverflow.com/a/36211337/895245 WithanexplicitGLfloattransform[]itwouldlooksomethinglikethis: glfw_transform.c #include #include #include #defineGLEW_STATIC #include #include staticconstGLuintWIDTH=800; staticconstGLuintHEIGHT=600; /*ourColorispassedontothefragmentshader.*/ staticconstGLchar*vertex_shader_source= "#version330core\n" "layout(location=0)invec3position;\n" "layout(location=1)invec3color;\n" "outvec3ourColor;\n" "uniformmat4transform;\n" "voidmain(){\n" "gl_Position=transform*vec4(position,1.0f);\n" "ourColor=color;\n" "}\n"; staticconstGLchar*fragment_shader_source= "#version330core\n" "invec3ourColor;\n" "outvec4color;\n" "voidmain(){\n" "color=vec4(ourColor,1.0f);\n" "}\n"; staticGLfloatvertices[]={ /*PositionsColors*/ 0.5f,-0.5f,0.0f,1.0f,0.0f,0.0f, -0.5f,-0.5f,0.0f,0.0f,1.0f,0.0f, 0.0f,0.5f,0.0f,0.0f,0.0f,1.0f }; /*Buildandcompileshaderprogram,returnitsID.*/ GLuintcommon_get_shader_program( constchar*vertex_shader_source, constchar*fragment_shader_source ){ GLchar*log=NULL; GLintlog_length,success; GLuintfragment_shader,program,vertex_shader; /*Vertexshader*/ vertex_shader=glCreateShader(GL_VERTEX_SHADER); glShaderSource(vertex_shader,1,&vertex_shader_source,NULL); glCompileShader(vertex_shader); glGetShaderiv(vertex_shader,GL_COMPILE_STATUS,&success); glGetShaderiv(vertex_shader,GL_INFO_LOG_LENGTH,&log_length); log=malloc(log_length); if(log_length>0){ glGetShaderInfoLog(vertex_shader,log_length,NULL,log); printf("vertexshaderlog:\n\n%s\n",log); } if(!success){ printf("vertexshadercompileerror\n"); exit(EXIT_FAILURE); } /*Fragmentshader*/ fragment_shader=glCreateShader(GL_FRAGMENT_SHADER); glShaderSource(fragment_shader,1,&fragment_shader_source,NULL); glCompileShader(fragment_shader); glGetShaderiv(fragment_shader,GL_COMPILE_STATUS,&success); glGetShaderiv(fragment_shader,GL_INFO_LOG_LENGTH,&log_length); if(log_length>0){ log=realloc(log,log_length); glGetShaderInfoLog(fragment_shader,log_length,NULL,log); printf("fragmentshaderlog:\n\n%s\n",log); } if(!success){ printf("fragmentshadercompileerror\n"); exit(EXIT_FAILURE); } /*Linkshaders*/ program=glCreateProgram(); glAttachShader(program,vertex_shader); glAttachShader(program,fragment_shader); glLinkProgram(program); glGetProgramiv(program,GL_LINK_STATUS,&success); glGetProgramiv(program,GL_INFO_LOG_LENGTH,&log_length); if(log_length>0){ log=realloc(log,log_length); glGetProgramInfoLog(program,log_length,NULL,log); printf("shaderlinklog:\n\n%s\n",log); } if(!success){ printf("shaderlinkerror"); exit(EXIT_FAILURE); } /*Cleanup.*/ free(log); glDeleteShader(vertex_shader); glDeleteShader(fragment_shader); returnprogram; } intmain(void){ GLintshader_program; GLinttransform_location; GLuintvbo; GLuintvao; GLFWwindow*window; doubletime; glfwInit(); window=glfwCreateWindow(WIDTH,HEIGHT,__FILE__,NULL,NULL); glfwMakeContextCurrent(window); glewExperimental=GL_TRUE; glewInit(); glClearColor(0.0f,0.0f,0.0f,1.0f); glViewport(0,0,WIDTH,HEIGHT); shader_program=common_get_shader_program(vertex_shader_source,fragment_shader_source); glGenVertexArrays(1,&vao); glGenBuffers(1,&vbo); glBindVertexArray(vao); glBindBuffer(GL_ARRAY_BUFFER,vbo); glBufferData(GL_ARRAY_BUFFER,sizeof(vertices),vertices,GL_STATIC_DRAW); /*Positionattribute*/ glVertexAttribPointer(0,3,GL_FLOAT,GL_FALSE,6*sizeof(GLfloat),(GLvoid*)0); glEnableVertexAttribArray(0); /*Colorattribute*/ glVertexAttribPointer(1,3,GL_FLOAT,GL_FALSE,6*sizeof(GLfloat),(GLvoid*)(3*sizeof(GLfloat))); glEnableVertexAttribArray(1); glBindVertexArray(0); while(!glfwWindowShouldClose(window)){ glfwPollEvents(); glClear(GL_COLOR_BUFFER_BIT); glUseProgram(shader_program); transform_location=glGetUniformLocation(shader_program,"transform"); /*THISisjustadummytransform.*/ GLfloattransform[]={ 0.0f,0.0f,0.0f,0.0f, 0.0f,0.0f,0.0f,0.0f, 0.0f,0.0f,1.0f,0.0f, 0.0f,0.0f,0.0f,1.0f, }; time=glfwGetTime(); transform[0]=2.0f*sin(time); transform[5]=2.0f*cos(time); glUniformMatrix4fv(transform_location,1,GL_FALSE,transform); glBindVertexArray(vao); glDrawArrays(GL_TRIANGLES,0,3); glBindVertexArray(0); glfwSwapBuffers(window); } glDeleteVertexArrays(1,&vao); glDeleteBuffers(1,&vbo); glfwTerminate(); returnEXIT_SUCCESS; } GitHubupstream. Compileandrun: gcc-ggdb3-O0-oglfw_transform.out-std=c99-Wall-Wextra-pedanticglfw_transform.c-lGL-lGLU-lglut-lGLEW-lglfw-lm ./glfw_transform.out Output: ThematrixforglOrthoisreallysimple,composedonlyofscalingandtranslation: scalex,0,0,translatex, 0,scaley,0,translatey, 0,0,scalez,translatez, 0,0,0,1 asmentionedintheOpenGL2docs. TheglFrustummatrixisnottoohardtocalculatebyhandeither,butstartsgettingannoying.NotehowfrustumcannotbemadeupwithonlyscalingandtranslationslikeglOrtho,moreinfoat:https://gamedev.stackexchange.com/a/118848/25171 TheGLMOpenGLC++mathlibraryisapopularchoiceforcalculatingsuchmatrices.http://glm.g-truc.net/0.9.2/api/a00245.htmldocumentsbothanorthoandfrustumoperations. Share Follow editedDec9,2020at20:50 answeredMar16,2016at21:06 CiroSantilliOurBigBook.comCiroSantilliOurBigBook.com 316k8989goldbadges11251125silverbadges911911bronzebadges 3 1 "whatshouldbeusedinstead?"-constructyourownmatricesandassignthemdirectly. – Kromster Mar23,2016at13:05 I'mhavinghardtimetryingtocompileyourlastcodeexample(transformingtriangle),I'veclonedtherepositorybutIjustgettheerrorcommon.h:19:23:error:‘TIME_UTC’undeclared(firstuseinthisfunction)timespec_get(&ts,TIME_UTC); – user2188550 Dec9,2020at19:11 1 @IvanzinhoIcouldn'treproduceonUbuntu20.04,presumablyhappeningbecausethatisinC11whichyourGCCdoesnotyetimplement.ButnowIminimizedtheexampleonthisanswerwithoutcommon.hasIshouldhavedonebeforesoitshouldwork:-) – CiroSantilliOurBigBook.com Dec9,2020at20:52 Addacomment  |  4 glOrthodescribesatransformationthatproducesaparallelprojection.Thecurrentmatrix(seeglMatrixMode)ismultipliedbythismatrixandtheresultreplacesthecurrentmatrix,asifglMultMatrixwerecalledwiththefollowingmatrixasitsargument: OpenGLdocumentation(mybold) Thenumbersdefinethelocationsoftheclippingplanes(left,right,bottom,top,nearandfar). The"normal"projectionisaperspectiveprojectionthatprovidestheillusionofdepth.Wikipediadefinesaparallelprojectionas: Parallelprojectionshavelinesofprojectionthatareparallelbothinrealityandintheprojectionplane. Parallelprojectioncorrespondstoaperspectiveprojectionwithahypotheticalviewpoint—e.g.,onewherethecameraliesaninfinitedistanceawayfromtheobjectandhasaninfinitefocallength,or"zoom". Share Follow editedJun20,2020at9:12 CommunityBot 111silverbadge answeredApr3,2010at14:03 ChrisF♦ChrisF 132k3030goldbadges252252silverbadges323323bronzebadges 2 hithanksfortheinfo.icouldn'tquiteunderstandthedifferencebetweenparallelandperspectiveprojection.igoogledabitandfoundtheanswerinwiki.answers.com/Q/… – ufk Apr3,2010at15:08 6 Unfortunatelytheinformationyougotfromanswers.comisprettyworthless.Anisometricview,forexample,isvery3-D,yetitisaparallelprojectionwithoutperspective.Seehere,andtherearealsolinkstomanyotherexamplesofprojections:en.wikipedia.org/wiki/Isometric_projection – BenVoigt Apr4,2010at6:41 Addacomment  |  YourAnswer ThanksforcontributingananswertoStackOverflow!Pleasebesuretoanswerthequestion.Providedetailsandshareyourresearch!Butavoid…Askingforhelp,clarification,orrespondingtootheranswers.Makingstatementsbasedonopinion;backthemupwithreferencesorpersonalexperience.Tolearnmore,seeourtipsonwritinggreatanswers. Draftsaved Draftdiscarded Signuporlogin SignupusingGoogle SignupusingFacebook SignupusingEmailandPassword Submit Postasaguest Name Email Required,butnevershown PostYourAnswer Discard Byclicking“PostYourAnswer”,youagreetoourtermsofservice,privacypolicyandcookiepolicy Nottheansweryou'relookingfor?Browseotherquestionstaggedc++copengloraskyourownquestion. TheOverflowBlog StackOverflowtrends:Weekdayvsweekendsiteactivity Fordevelopers,flowstatestartswithyourfingertips  FeaturedonMeta RecentColorContrastChangesandAccessibilityUpdates Revieweroverboard!Orarequesttoimprovetheonboardingguidancefornew... ShouldIexplainotherpeople'scode-onlyanswers? CollectivesUpdate:RecognizedMembers,Articles,andGitLab Linked 30 WhatareshadersinOpenGLandwhatdoweneedthemfor? 9 OpenGL(ES)--What'sthedifferencebetweenfrustumandortho? 7 OpenGLESnotworkingasdesired 1 TransformationsfrompixelstoNDC 2 I'mhavingaproblemwithmovementinopengl3D 0 Finding/RemappingboundsofOpenGLEScoordinateplane 1 OpenGLDisplayError-Incorrectdisplay 0 movingcamerausingglOrtho 1 Howtostopstretchinginopengl -1 openGLresolutionsettings,screenbehavingunexplainably Seemorelinkedquestions Related 3005 HowdoIset,clear,andtoggleasinglebit? 4230 TheDefinitiveC++BookGuideandList 3246 ImproveINSERT-per-secondperformanceofSQLite 1574 WhydoweneedvirtualfunctionsinC++? 1590 Cyclesinfamilytreesoftware 2134 C++11introducedastandardizedmemorymodel.Whatdoesitmean?AndhowisitgoingtoaffectC++programming? 968 WhyshouldC++programmersminimizeuseof'new'? 2293 Whatdoesthe??!??!operatordoinC? 1843 ImageProcessing:AlgorithmImprovementfor'Coca-ColaCan'Recognition 1837 WhyshouldIuseapointerratherthantheobjectitself? HotNetworkQuestions Whatarethethreeorfourholesonthebackofa3.5inchfloppydiskindicatingandusedfor? FindTheRealSolutionsofaCubic HowtosetupWindows1122H2withalocalaccount? 7or8speedcassette? WhyismyDC-DCbuckconverterconsuming8mAofcurrentwithnoloadconnected? Howtoindicatetotheuserthattheyhaven'tcompletedaprerequisite? HowtotypeŬ(Uwithbreve)? Ispassword-unmaskingworththepotentialsecuritydownside? WhydoesScarecrowinTheWizardOfOzgetthePythagoreanTheoremwrong? CouldwelocateSpringfieldusingthecharacters'accents? MSSQLServerDBTransactionLogGrowthRate Isthereanymonsterwithstatblockchangesduringanencounter? Willitgiveanegativeimpressionifaprofessormentionsthathedeclinedagiftcardfrommeinhisreferenceletter? Iftheserieshasalimitof0,CanIconcludethatitisalsothesum? Discoveringgroupingsofdescriptivetagsfrommedia Doesthehumanvoicequalifyasnoise? Islightflickeringonlyoncameraisbad? Howtotellwhenit'stimetogiveupontires? It'sJustRocketScience Isthereafasterwaytosolvethefollowingproblem? HowdoIunlockaMathematicaNotebook? InEarlyModernEnglish,arethereexamplesofthe"a-+gerund"progressiveconstructionwherethegerundbeginswithavowel? ArcanePropulsionArmor—canitgivethewearerlimbstheyneverhad? Whydonet.bridge.bridge-nf-call-{arp,ip,ip6}tablesdefaultto1? morehotquestions Questionfeed SubscribetoRSS Questionfeed TosubscribetothisRSSfeed,copyandpastethisURLintoyourRSSreader. default Yourprivacy Byclicking“Acceptallcookies”,youagreeStackExchangecanstorecookiesonyourdeviceanddiscloseinformationinaccordancewithourCookiePolicy. Acceptallcookies Customizesettings  



請為這篇文章評分?