diff --git a/config.cpp b/config.cpp index 2a2330d0..bb427866 100644 --- a/config.cpp +++ b/config.cpp @@ -230,6 +230,8 @@ void initConfig() { addsaver(vid.antialias, "antialias", AA_NOGL | AA_FONT | AA_LINES | AA_LINEWIDTH | AA_VERSION); addsaver(vid.linewidth, "linewidth", 1); addsaver(vid.scale, "scale", 1); + addsaver(vid.xposition, "xposition", 0); + addsaver(vid.yposition, "yposition", 0); addsaver(vid.alpha, "projection", 1); addsaver(vid.sspeed, "scrollingspeed", 0); addsaver(vid.mspeed, "movement speed", 1); @@ -363,6 +365,7 @@ void resetModes(char leave = 'c') { } pmodel = mdDisk; vid.alpha = 1; vid.scale = 1; + vid.xposition = vid.yposition = 0; if(rug::rugged) rug::close(); vid.monmode = DEFAULT_MONMODE; diff --git a/control.cpp b/control.cpp index 38f8bf4f..c5d9be48 100644 --- a/control.cpp +++ b/control.cpp @@ -783,10 +783,10 @@ void displayabutton(int px, int py, string s, int col) { #endif void gmodekeys(int sym, int uni) { - if(uni == '1') { vid.alpha = 999; vid.scale = 998; } - if(uni == '2') { vid.alpha = 1; vid.scale = 0.4; } - if(uni == '3') { vid.alpha = 1; vid.scale = 1; } - if(uni == '4') { vid.alpha = 0; vid.scale = 1; } + if(uni == '1') { vid.alpha = 999; vid.scale = 998; vid.xposition = vid.yposition = 0; } + if(uni == '2') { vid.alpha = 1; vid.scale = 0.4; vid.xposition = vid.yposition = 0; } + if(uni == '3') { vid.alpha = 1; vid.scale = 1; vid.xposition = vid.yposition = 0; } + if(uni == '4') { vid.alpha = 0; vid.scale = 1; vid.xposition = vid.yposition = 0; } if(uni == '5') { vid.wallmode += 60 + (shiftmul > 0 ? 1 : -1); vid.wallmode %= 6; } if(uni == '6') vid.grid = !vid.grid; if(uni == '7') { vid.darkhepta = !vid.darkhepta; } diff --git a/graph.cpp b/graph.cpp index 51614b3a..9b544aae 100644 --- a/graph.cpp +++ b/graph.cpp @@ -5111,6 +5111,9 @@ void calcparam() { } if(dronemode) { vid.ycenter -= vid.radius; vid.ycenter += vid.fsize/2; vid.ycenter += vid.fsize/2; vid.radius *= 2; } + + vid.xcenter += vid.scrsize * vid.xposition; + vid.ycenter += vid.scrsize * vid.yposition; ld eye = vid.eye; if(pmodel || rug::rugged) eye = 0; vid.beta = 1 + vid.alpha + eye; @@ -5248,6 +5251,9 @@ void gamescreen(int _darken) { #endif darken = 0; + + if(texture::tstate == texture::tsAdjusting) + texture::drawRawTexture(); } void normalscreen() { diff --git a/hyper.h b/hyper.h index b1d80de6..1e29e555 100644 --- a/hyper.h +++ b/hyper.h @@ -592,6 +592,8 @@ struct videopar { int xscr, yscr; + ld xposition, yposition; + // paramaters calculated from the above int xcenter, ycenter; int radius; diff --git a/mapeditor.cpp b/mapeditor.cpp index 778bb550..265391b2 100644 --- a/mapeditor.cpp +++ b/mapeditor.cpp @@ -1000,8 +1000,8 @@ namespace mapeditor { } displaymm('g', vid.xres-8, 8+fs*4, 2, vid.fsize, XLAT("g = grid"), 16); - displayButton(vid.xres-8, 8+fs*3, XLAT("z = zoom in"), 'z', 16); - displayButton(vid.xres-8, 8+fs*2, XLAT("o = zoom out"), 'o', 16); + displaymm('z', vid.xres-8, 8+fs*3, 2, vid.fsize, XLAT("z = zoom in"), 16); + displaymm('o', vid.xres-8, 8+fs*2, 2, vid.fsize, XLAT("o = zoom out"), 16); if(intexture) for(int i=0; i<10; i++) { if(8 + fs * (6+i) < vid.yres - 8 - fs * 7) @@ -1320,12 +1320,34 @@ namespace mapeditor { return true; } + void scaleall(ld z) { + + // (mx,my) = (xcb,ycb) + ss * (xpos,ypos) + (mrx,mry) * scale + + // (mrx,mry) * (scale-scale') = + // ss * ((xpos',ypos')-(xpos,ypos)) + + // mx = xb + ssiz*xpos + mrx * scale + // mx = xb + ssiz*xpos' + mrx * scale' + + ld mrx = (.0 + mousex - vid.xcenter) / vid.scale; + ld mry = (.0 + mousey - vid.ycenter) / vid.scale; + + vid.xposition += (vid.scale - vid.scale*z) * mrx / vid.scrsize; + vid.yposition += (vid.scale - vid.scale*z) * mry / vid.scrsize; + + vid.scale *= z; + #if CAP_TEXTURE + texture::itt = xyscale(texture::itt, 1/z); + #endif + } + void drawHandleKey(int sym, int uni) { handlePanning(sym, uni); if(uni == SETMOUSEKEY) { - if(mousekey == 'g' && newmousekey == 'g') + if(mousekey == newmousekey) mousekey = '-'; else mousekey = newmousekey; @@ -1353,22 +1375,16 @@ namespace mapeditor { }; dialog::openColorDialog(gridcolor, grid_colors); } + + char mkuni = uni == '-' ? mousekey : uni; + + bool clickused = false; - if(uni == 'g' || (uni == '-' && mousekey == 'g')) - coldcenter = ccenter, ccenter = mh; + if(mkuni == 'g') + coldcenter = ccenter, ccenter = mh, clickused = true; - if(uni == 'z') { - vid.scale *= 2; - #if CAP_TEXTURE - texture::itt = xyscale(texture::itt, .5); - #endif - } - if(uni == 'o') { - vid.scale /= 2; - #if CAP_TEXTURE - texture::itt = xyscale(texture::itt, 2); - #endif - } + if(mkuni == 'z') scaleall(2), clickused = true; + if(mkuni == 'o') scaleall(.5), clickused = true; if(uni == ' ' && cheater) { popScreen(); @@ -1401,7 +1417,7 @@ namespace mapeditor { #if CAP_TEXTURE if(texture::tstate == texture::tsActive) { - if(uni == '-' && mousekey != 'g') { + if(uni == '-' && !clickused) { if(!holdmouse) texture::undoLock(); texture::drawPixel(mouseover, mouseh, (texture::paint_color >> 8) | ((texture::paint_color & 0xFF) << 24)); holdmouse = true; diff --git a/textures.cpp b/textures.cpp index 18c5e390..23f2422d 100644 --- a/textures.cpp +++ b/textures.cpp @@ -441,8 +441,8 @@ void drawRawTexture() { glBindTexture(GL_TEXTURE_2D, textureid); vector tver, sver; for(int i=0; i<4; i++) { - int cx[4] = {1, -1, -1, 1}; - int cy[4] = {1, 1, -1, -1}; + int cx[4] = {2, -2, -2, 2}; + int cy[4] = {2, 2, -2, -2}; int x = cx[i]; int y = cy[i]; hyperpoint inmodel = hpxyz(x, y, 1); @@ -630,8 +630,10 @@ void init_textureconfig() { addsaver(View[i][j], "viewmatrix_" + its(i) + its(j), i==j ? 1 : 0); addsaverenum(targetgeometry, "geometry", gNormal); - addsaverenum(pmodel, "used model", pmNormal); + addsaverenum(pmodel, "used model", mdDisk); addsaver(vid.yshift, "Y shift", 0); + addsaver(vid.yposition, "Y position", 0); + addsaver(vid.xposition, "X position", 0); addsaver(vid.camera_angle, "camera angle", 0); addsaverenum(target_nontrunc, "chamfering", false); // ... geometry parameters @@ -713,9 +715,6 @@ void showMenu() { cmode = sm::SIDE | sm::MAYDARK | sm::DIALOG_STRICT_X; gamescreen(0); - if(tstate == tsAdjusting) - drawRawTexture(); - if(tstate == tsOff) { dialog::init(XLAT("texture mode (off)")); dialog::addItem(XLAT("select geometry/pattern"), 'r');