HUD elements, including the compass, now drawn correctly in all pmodels

This commit is contained in:
Zeno Rogue 2017-11-13 11:08:06 +01:00
parent 672f4d7b9e
commit 19f12e3068
9 changed files with 122 additions and 70 deletions

View File

@ -775,8 +775,12 @@ int rhypot(int a, int b) { return (int) sqrt(a*a - b*b); }
ld realradius() {
ld vradius = vid.radius;
if(sphere && vid.alphax > 1) vradius /= sqrt(vid.alphax*vid.alphax - 1);
if(sphere && vid.alphax <= 1) vradius = 1e12; // use the following
if(sphere) {
if(sphereflipped())
vradius /= sqrt(vid.alphax*vid.alphax - 1);
else
vradius = 1e12; // use the following
}
vradius = min<ld>(vradius, min(vid.xres, vid.yres) / 2);
return vradius;
}

View File

@ -196,7 +196,7 @@ void initConfig() {
addsaver(vid.timeformat, "message log time format", 0);
addsaver(fontscale, "fontscale", 100);
addsaver(vid.mobilecompasssize, "mobile compass size", 30);
addsaver(vid.mobilecompasssize, "mobile compass size", ISMOBILE || ISPANDORA ? 30 : 0);
addsaver(vid.axes, "movement help", 1);
addsaver(vid.shifttarget, "shift-targetting", 2);
addsaver(vid.steamscore, "scores to Steam", 1);
@ -616,9 +616,7 @@ void showGraphConfig() {
dialog::addSelItem(XLAT("sight range"), its(sightrange), 'r');
#if ISMOBILE==1
dialog::addSelItem(XLAT("compass size"), its(vid.mobilecompasssize), 'c');
#endif
dialog::addSelItem(XLAT("aura brightness"), its(vid.aurastr), 'z');
dialog::addSelItem(XLAT("aura smoothening factor"), its(vid.aurasmoothen), 'x');
@ -689,8 +687,11 @@ void showGraphConfig() {
if(xuni == 'w' && vid.usingGL)
dialog::editNumber(vid.linewidth, 0, 10, 0.1, 1, XLAT("line width"), "");
if(xuni == 'c')
if(xuni == 'c') {
dialog::editNumber(vid.mobilecompasssize, 0, 100, 10, 20, XLAT("compass size"), "");
// we need to check the moves
dialog::reaction = checkmove;
}
#if CAP_FRAMELIMIT
if(xuni == 'l')

View File

@ -399,7 +399,9 @@ void handleKeyNormal(int sym, int uni) {
if(!shmup::on)
multi::mousemovement(mouseover);
}
else mousemovement();
else if(handleCompass()) ;
else
mousemovement();
}
if(sym == SDLK_F1) gotoHelp(help);
@ -791,3 +793,32 @@ void gmodekeys(int sym, int uni) {
}
}
bool haveMobileCompass() {
#if CAP_MOBILE
if(andmode || useRangedOrb) return false;
#else
if(forcetarget) return false;
#endif
return canmove && !shmup::on && vid.mobilecompasssize > 0 && size(screens) == 1;
}
bool handleCompass() {
if(!haveMobileCompass()) return false;
using namespace shmupballs;
int dx = mousex - xmove;
int dy = mousey - yb;
int h = hypot(dx, dy);
if(h < rad) {
if(h < rad*SKIPFAC) movepcto(MD_WAIT);
else {
double d = vid.revcontrol ? -1 : 1;
mouseh = hpxy(dx * d / rad, dy * d / rad);
mousemovement();
}
getcstat = 0;
return true;
}
return false;
}

View File

@ -2336,37 +2336,6 @@ void drawMovementArrows(cell *c, transmatrix V) {
}
}
void drawMobileArrow(cell *c, transmatrix V) {
// int col = getcs().uicolor;
// col -= (col & 0xFF) >> 1;
int dir = neighborId(cwt.c, c);
bool invalid = !legalmoves[dir];
int col = cellcolor(c);
if(col == OUTLINE_NONE) col = 0xC0C0C0FF;
col -= (col & 0xFF) >> 1;
if(invalid) col -= (col & 0xFF) >> 1;
if(invalid) col -= (col & 0xFF) >> 1;
poly_outline = OUTLINE_DEFAULT;
transmatrix m2 = Id;
ld scale = vid.mobilecompasssize / 15.;
m2[0][0] = scale; m2[1][1] = scale; m2[2][2] = 1;
transmatrix Centered = rgpushxto0(tC0(cwtV * sphereflip));
transmatrix t = inverse(Centered) * V;
double alpha = atan2(tC0(t)[1], tC0(t)[0]);
using namespace shmupballs;
double dx = xmove + rad*(1+SKIPFAC-.2)/2 * cos(alpha);
double dy = yb + rad*(1+SKIPFAC-.2)/2 * sin(alpha);
queuepolyat(screenpos(dx, dy) * spin(-alpha) * m2, shArrow, col, PPR_MOBILE_ARROW);
}
int celldistAltPlus(cell *c) { return 1000000 + celldistAlt(c); }
bool drawstaratvec(double dx, double dy) {
@ -4721,17 +4690,6 @@ void drawMarkers() {
// process mouse
if(haveMobileCompass()) {
using namespace shmupballs;
calc();
queuecircle(xmove, yb, rad, 0xFF0000FF);
queuecircle(xmove, yb, rad*SKIPFAC,
legalmoves[MAX_EDGE] ? 0xFF0000FF : 0xFF000080
);
forCellAll(c2, cwt.c) IG(c2) drawMobileArrow(c2, Gm(c2));
if(hypot(mousex-xmove, mousey-yb) <= rad) getcstat = '-';
}
if((vid.axes == 4 || (vid.axes == 1 && !mousing)) && !shmup::on) {
if(multi::players == 1) {
forCellAll(c2, cwt.c) IG(c2) drawMovementArrows(c2, Gm(c2));

56
hud.cpp
View File

@ -296,6 +296,37 @@ bool nohud, nomenukey;
hookset<bool()> *hooks_prestats;
void drawMobileArrow(cell *c, transmatrix V) {
// int col = getcs().uicolor;
// col -= (col & 0xFF) >> 1;
int dir = neighborId(cwt.c, c);
bool invalid = !legalmoves[dir];
int col = cellcolor(c);
if(col == OUTLINE_NONE) col = 0xC0C0C0FF;
col -= (col & 0xFF) >> 1;
if(invalid) col -= (col & 0xFF) >> 1;
if(invalid) col -= (col & 0xFF) >> 1;
poly_outline = OUTLINE_DEFAULT;
// transmatrix m2 = Id;
ld scale = vid.mobilecompasssize * 7;
// m2[0][0] = scale; m2[1][1] = scale; m2[2][2] = 1;
transmatrix Centered = rgpushxto0(tC0(cwtV * sphereflip));
transmatrix t = inverse(Centered) * V;
double alpha = atan2(tC0(t)[1], tC0(t)[0]);
using namespace shmupballs;
double dx = xmove + rad*(1+SKIPFAC-.2)/2 * cos(alpha);
double dy = yb + rad*(1+SKIPFAC-.2)/2 * sin(alpha);
queuepolyat(atscreenpos(dx, dy, scale) * spin(-alpha), shArrow, col, PPR_MOBILE_ARROW);
}
void drawStats() {
callhandlers(false, hooks_prestats);
#if CAP_ROGUEVIZ
@ -338,6 +369,27 @@ void drawStats() {
dialog::display();
}
if(sidescreen) return;
{
dynamicval<eModel> pm(pmodel, mdDisk);
dynamicval<ld> va(vid.alpha, 1);
dynamicval<ld> vax(vid.alphax, 1);
dynamicval<videopar> v(vid, vid);
calcparam();
selectEyeGL(0);
if(haveMobileCompass()) {
initquickqueue();
using namespace shmupballs;
calc();
queuecircle(xmove, yb, rad, 0xFF0000FF);
queuecircle(xmove, yb, rad*SKIPFAC,
legalmoves[MAX_EDGE] ? 0xFF0000FF : 0xFF000080
);
forCellEx(c2, cwt.c) if(gmatrix.count(c2)) drawMobileArrow(c2, gmatrix[c2]);
if(hypot(mousex-xmove, mousey-yb) <= rad) getcstat = '-';
quickqueue();
}
if(vid.xres > vid.yres * 85/100 && vid.yres > vid.xres * 85/100) {
int bycorner[4];
@ -496,4 +548,8 @@ XLAT(
callhooks(hooks_stats);
}
calcparam();
selectEyeGL(0);
}

11
hyper.h
View File

@ -1164,6 +1164,7 @@ enum PPR {
PPR_CARRIED, PPR_CARRIEDa, PPR_CARRIEDb,
PPR_PARTICLE, PPR_SWORDMARK, PPR_MAGICSWORD, PPR_MISSILE,
PPR_MINEMARK, PPR_ARROW,
PPR_MOBILE_ARROW,
PPR_LINE, PPR_TEXT, PPR_CIRCLE,
PPR_MAX
};
@ -2110,3 +2111,13 @@ int isLandValid(eLand l);
bool inmirrororwall(eLand l);
extern bool holdmouse;
// what part of the compass does 'skip turn'
static const auto SKIPFAC = .4;
bool haveMobileCompass();
bool handleCompass();
bool sphereflipped() { return sphere && vid.alpha > 1.1; }
int cellcolor(cell *c);
transmatrix screenpos(ld x, ld y);

View File

@ -14,7 +14,7 @@
#define NOLICENSE
#endif
#define VER "10.23"
#define VER "10.2c"
#define VERNUM 10203
#define VERNUM_HEX 0xA093
@ -86,6 +86,10 @@
#define CAP_SDL (!ISMOBILE)
#endif
#ifdef CAP_COMPASS
#define CAP_COMPASS ISMOBILE
#endif
#ifndef CAP_SDLGFX
#define CAP_SDLGFX (CAP_SDL && !ISWEB)
#endif
@ -472,22 +476,7 @@ bool useRangedOrb;
void handleclick(MOBPAR_FORMAL) {
if(!shmup::on && andmode == 0 && size(screens) == 1 && canmove && !useRangedOrb && vid.mobilecompasssize > 0) {
using namespace shmupballs;
int dx = mousex - xmove;
int dy = mousey - yb;
int h = hypot(dx, dy);
if(h < rad) {
if(h < rad*SKIPFAC) movepcto(MD_WAIT);
else {
double d = vid.revcontrol ? -1 : 1;
mouseh = hpxy(dx * d / rad, dy * d / rad);
mousemovement();
}
getcstat = 0;
return;
}
}
if(handleCompass()) return;
if(buttonclicked || mouseout()) {

View File

@ -12,10 +12,11 @@ namespace shmupballs {
int xmove, xfire, yb, rad;
void calc() {
rad = int(realradius() * (vid.mobilecompasssize ? vid.mobilecompasssize : 14) / 100);
xmove = max(vid.xcenter - vid.radius - rad, rad);
xfire = min(vid.xcenter + vid.radius + rad, vid.xres - rad);
yb = vid.ycenter + vid.radius - rad;
int rr = int(realradius());
rad = int(rr * (vid.mobilecompasssize ? vid.mobilecompasssize : 14) / 100);
xmove = max(vid.xcenter - rr - rad, rad);
xfire = min(vid.xcenter + rr + rad, vid.xres - rad);
yb = vid.ycenter + rr - rad;
}
}

View File

@ -272,6 +272,7 @@ void initgame() {
lastsafety = gold();
bfs();
checkmove();
}
bool havesave = true;