/* Chloe Fan's OpenGL Piano and Bench Copyright (c) 2006 Chloe Fan This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. cfan2Piano(twTriple _pianoColor); Draws a black baby grand piano Can be placed in auditorium, living room, etc. Values are scaled based on the width of the piano, or affine transformations can be used to resize piano. The origin is on the bottom of the base of the piano, right above the legs, where the cover also matches up horizontally, and halfway through the width. This way, the legs are located on the negative y-axis, and the piano will be symmetrical. cfan2Bench(twTriple _pianoColor); Creates a matching bench for the piano. Symmetrical, origin under seat above legs, same as piano, and centered. */ void cfan2Piano(twTriple _pianoColor) { twTriple _wheelColor = {0.84, 0.68, 0.05}; // width of piano const GLfloat pWidth = 12; // length of front: keys, stand const GLfloat pFront = pWidth/2; // length of back: strings, curve const GLfloat pBack = pWidth/4*3; //=============== PIANO FRONT: KEYS AND BASE ================// glPushMatrix(); // keys glColor3f(255,255,255); // white glTranslatef(0, pWidth/12*3/2, pFront*5/6-0.75); glScalef(pWidth, pWidth/48, 0.75); glutSolidCube(1); glPopMatrix(); twColor(_pianoColor,0,0); // set color to piano color glPushMatrix(); // below keys glTranslatef(0,pWidth/24,pFront*5/6-0.5); glScalef(pWidth, pWidth/12, pWidth/12); glutSolidCube(1); glPopMatrix(); glBegin(GL_POLYGON); // right keys "cover" { glVertex3f(pWidth/2, 0, pFront); glVertex3f(pWidth/2, 0, pFront*2/3); glVertex3f(pWidth/2, pWidth/6, pFront*2/3); glVertex3f(pWidth/2, pWidth/6, pFront); } glEnd(); glBegin(GL_POLYGON); // left keys "cover" { glVertex3f(-pWidth/2, 0, pFront*2/3); glVertex3f(-pWidth/2, 0, pFront); glVertex3f(-pWidth/2, pWidth/6, pFront); glVertex3f(-pWidth/2, pWidth/6, pFront*2/3); } glEnd(); glBegin(GL_POLYGON); // book stand { glVertex3f(-pWidth/4, pWidth/4, pWidth/6); glVertex3f(pWidth/4, pWidth/4, pWidth/6); glVertex3f(pWidth/4, pWidth*5/12, pWidth/8); glVertex3f(-pWidth/4, pWidth*5/12, pWidth/8); } glEnd(); glBegin(GL_POLYGON); // book stand back { glVertex3f(-pWidth/24, pWidth/4+pWidth/12, pWidth/12+pWidth/16); glVertex3f(pWidth/24, pWidth/4+pWidth/12, pWidth/12+pWidth/16); glVertex3f(pWidth/24, pWidth/4, pWidth/12); glVertex3f(-pWidth/24, pWidth/4, pWidth/12); } glEnd(); glPushMatrix(); // under book stand glTranslatef(0, pWidth/8, pWidth/3/2); glScalef(pWidth, pWidth/4, pWidth/3); glutSolidCube(1); glPopMatrix(); glBegin(GL_POLYGON); // piano curved base { glVertex3f(-pWidth/2, pWidth/12, 0); glVertex3f(-pWidth/2, pWidth/12, -pBack*5/9); glVertex3f(-pWidth*5/12, pWidth/12, -pBack/1.2); glVertex3f(-pWidth/3, pWidth/12, -pBack/12*11); glVertex3f(-pWidth/4, pWidth/12, -pBack/45*44); glVertex3f(-pWidth/6, pWidth/12, -pBack); // top of big curve glVertex3f(-pWidth/12, pWidth/12, -pBack/45*44); glVertex3f(0, pWidth/12, -pBack/12*11); glVertex3f(pWidth/12, pWidth/12, -pBack/1.2); glVertex3f(pWidth/6, pWidth/12, -pBack*5/9); glVertex3f(pWidth/4, pWidth/12, -pBack/18*7); glVertex3f(pWidth/3, pWidth/12, -pBack/3); glVertex3f(pWidth*5/12, pWidth/12, -pBack/3.6); glVertex3f(pWidth/2, pWidth/12, 0); } glEnd(); // glColor3f(255,255,255); // white: testing glBegin(GL_QUAD_STRIP); // piano base wall { glVertex3f(-pWidth/2, pWidth/12, 0); glVertex3f(-pWidth/2, pWidth/4, 0); glVertex3f(-pWidth/2, pWidth/12, -pBack*5/9); glVertex3f(-pWidth/2, pWidth/4, -pBack*5/9); glVertex3f(-pWidth*5/12, pWidth/12, -pBack/1.2); glVertex3f(-pWidth*5/12, pWidth/4, -pBack/1.2); glVertex3f(-pWidth/3, pWidth/12, -pBack/12*11); glVertex3f(-pWidth/3, pWidth/4, -pBack/12*11); glVertex3f(-pWidth/4, pWidth/12, -pBack/45*44); glVertex3f(-pWidth/4, pWidth/4, -pBack/45*44); glVertex3f(-pWidth/6, pWidth/12, -pBack); // top of big curve glVertex3f(-pWidth/6, pWidth/4, -pBack); glVertex3f(-pWidth/12, pWidth/12, -pBack/45*44); glVertex3f(-pWidth/12, pWidth/4, -pBack/45*44); glVertex3f(0, pWidth/12, -pBack/12*11); glVertex3f(0, pWidth/4, -pBack/12*11); glVertex3f(pWidth/12, pWidth/12, -pBack/1.2); glVertex3f(pWidth/12, pWidth/4, -pBack/1.2); glVertex3f(pWidth/6, pWidth/12, -pBack*5/9); glVertex3f(pWidth/6, pWidth/4, -pBack*5/9); glVertex3f(pWidth/4, pWidth/12, -pBack/18*7); glVertex3f(pWidth/4, pWidth/4, -pBack/18*7); glVertex3f(pWidth/3, pWidth/12, -pBack/3); glVertex3f(pWidth/3, pWidth/4, -pBack/3); glVertex3f(pWidth*5/12, pWidth/12, -pBack/3.6); glVertex3f(pWidth*5/12, pWidth/4, -pBack/3.6); glVertex3f(pWidth/2, pWidth/12, 0); glVertex3f(pWidth/2, pWidth/4, 0); } glEnd(); //======================= PIANO COVER =========================// glPushMatrix(); glTranslatef(0.5,3.5,0); glRotatef(30, 0, 0, 1); glBegin(GL_POLYGON); // piano curved cover { glVertex3f(-pWidth/2, pWidth/4, 0); glVertex3f(-pWidth/2, pWidth/4, -pBack*5/9); glVertex3f(-pWidth*5/12, pWidth/4, -pBack/1.2); glVertex3f(-pWidth/3, pWidth/4, -pBack/12*11); glVertex3f(-pWidth/4, pWidth/4, -pBack/45*44); glVertex3f(-pWidth/6, pWidth/4, -pBack); // top of big curve glVertex3f(-pWidth/12, pWidth/4, -pBack/45*44); glVertex3f(0, pWidth/4, -pBack/12*11); glVertex3f(pWidth/12, pWidth/4, -pBack/1.2); glVertex3f(pWidth/6, pWidth/4, -pBack*5/9); glVertex3f(pWidth/4, pWidth/4, -pBack/18*7); glVertex3f(pWidth/3, pWidth/4, -pBack/3); glVertex3f(pWidth*5/12, pWidth/4, -pBack/3.6); glVertex3f(pWidth/2, pWidth/4, 0); } glEnd(); glPopMatrix(); // glColor3f(255,255,255); // white: testing glBegin(GL_POLYGON); // cover prop { glVertex3f(pWidth/12*5, pWidth/4, -pWidth/16); glVertex3f(pWidth/12*5, pWidth/4, -pWidth/48*5); glVertex3f(pWidth/4, pBack-pWidth/24, -pWidth/48*5); glVertex3f(pWidth/4, pBack-pWidth/24, -pWidth/16); } glEnd(); //==================== PIANO LEGS AND PEDALS ======================// glBegin(GL_POLYGON); // right front slanted left { glVertex3f(pWidth/2-pWidth/12, 0, 0); glVertex3f(pWidth/2-pWidth/12, -pWidth/12, pWidth/8); glVertex3f(pWidth/2-pWidth/12, -pWidth/12, pWidth/8+pWidth/12); glVertex3f(pWidth/2-pWidth/12, 0, pWidth/3); } glEnd(); glBegin(GL_POLYGON); // right front slanted right { glVertex3f(pWidth/2, 0, 0); glVertex3f(pWidth/2, -pWidth/12, pWidth/8); glVertex3f(pWidth/2, -pWidth/12, pWidth/8+pWidth/12); glVertex3f(pWidth/2, 0, pWidth/3); } glEnd(); glBegin(GL_POLYGON); // left front slanted right { glVertex3f(-pWidth/2+pWidth/12, 0, 0); glVertex3f(-pWidth/2+pWidth/12, -pWidth/12, pWidth/8); glVertex3f(-pWidth/2+pWidth/12, -pWidth/12, pWidth/8+pWidth/12); glVertex3f(-pWidth/2+pWidth/12, 0, pWidth/3); } glEnd(); glBegin(GL_POLYGON); // left front slanted left { glVertex3f(-pWidth/2, 0, 0); glVertex3f(-pWidth/2, -pWidth/12, pWidth/8); glVertex3f(-pWidth/2, -pWidth/12, pWidth/8+pWidth/12); glVertex3f(-pWidth/2, 0, pWidth/3); } glEnd(); glBegin(GL_POLYGON); // back slanted front { glVertex3f(-pFront/2, pWidth/12, -pBack+pBack/6); glVertex3f(-pFront/2+pWidth/24, 0, -pBack+pBack/6); glVertex3f((-pFront/2+pWidth/24)+pWidth/12, 0, -pBack+pBack/6); glVertex3f(-pFront/2+pWidth/8, pWidth/12, -pBack+pBack/6); } glEnd(); glPushMatrix(); // legs glTranslatef(pWidth/2-pWidth/24, -pWidth*5/24, pWidth/6); glScalef(1, 5, 1); glutSolidCube(1); // right leg glTranslatef(-pWidth+pWidth/12, 0, 0); glutSolidCube(1); // left leg glPopMatrix(); glPushMatrix(); glTranslatef(-pFront/3, -pWidth/6, -pBack+pBack/9); glScalef(1,6,1); glutSolidCube(1); // back leg glPopMatrix(); glPushMatrix(); // wheels twColor(_wheelColor,0,0); // set color to wheel color glTranslatef(-pWidth/12*5-pWidth/24, -pWidth*5/12-0.25, pWidth/6); glScalef(0.5,0.5,0.5); glutSolidSphere(1,20,20); // left wheel glTranslatef((pWidth-pWidth/12)*2, 0, 0); glutSolidSphere(1,20,20); // right wheel glTranslatef((-pWidth*5/8)*2, 0, (-pBack-pBack/9)*2); glutSolidSphere(1,20,20); glPopMatrix(); // pedals: all pedals are supposed to stick out behind past the "box" since they are attached to the bottom of the piano base to control string frames glPushMatrix(); twColor(_pianoColor,0,0); // back to piano color glTranslatef(-pWidth/16, -pWidth/6, pWidth/6); glScalef(pWidth/24, pWidth/3, pWidth/24); glutSolidCube(1); // left supporter glTranslatef(pWidth/4, 0, 0); glutSolidCube(1); // right supporter glPopMatrix(); glPushMatrix(); glTranslatef(0, -pWidth/3, pWidth/6); glScalef(pWidth/4, pWidth/24, 1); glutSolidCube(1); // pedal box twColor(_wheelColor,0,0); // set color to wheel color glTranslatef(0, 0, 0.25); glScalef(pWidth/120, pWidth/48, pWidth/12); glutSolidSphere(1, 20, 20); // middle pedal glPushMatrix(); glTranslatef(-pWidth*5/24, 0, 0); glutSolidSphere(1,20,20); // left pedal glPopMatrix(); glTranslatef(pWidth*5/24, 0, 0); glutSolidSphere(1,20,20); // right pedal glPopMatrix(); } void cfan2Bench(twTriple _pianoColor) { // bench length const GLfloat bLength = 8; // bench width const GLfloat bWidth = 3; // bench depth const GLfloat bDepth = 1; // leg length const GLfloat lLength = 3; twColor(_pianoColor,0,0); // set color to piano color glPushMatrix(); // seat glTranslatef(0, 0.5, 0); glScalef(bLength, bDepth, bWidth); glutSolidCube(1); glPopMatrix(); glPushMatrix(); // legs glTranslatef(-bLength/2+0.5, -lLength/2, 1); glScalef(0.5, lLength, 0.5); glutSolidCube(1); glTranslatef(0, 0, -((bWidth-1)*2)); glutSolidCube(1); glTranslatef((bLength-1)*2, 0, 0); glutSolidCube(1); glTranslatef(0, 0, (bWidth-1)*2); glutSolidCube(1); glPopMatrix(); }