control.x += 1;
break;
case SDLK_z:
- cam.DoubleZoom();
+ cam.StartZoom();
break;
case SDLK_x:
- cam.HalfZoom();
+ cam.StartShrink();
break;
default:
break;
case SDLK_d:
control.x -= 1;
break;
+ case SDLK_z:
+ cam.StopZoom();
+ break;
+ case SDLK_x:
+ cam.StopShrink();
+ break;
default:
break;
}
SDL_Surface *dst = screen.Screen();
const Vector<int> begin = cam.ToScreen(Vector<float>(0, 0));
const Vector<int> end =
- cam.ToScreen((univ.size * univ.secSize * univ.areaSize)) + Vector<int>(1, 1);;
+ cam.ToScreen((univ.size * univ.secSize * univ.areaSize))
+ + Vector<int>(1, 1);
Fill(dst, background);
- Grid(dst, begin, end, cam.ToScale(univ.areaSize), secGrid);
- Grid(dst, begin, end, cam.ToScale(univ.secSize * univ.areaSize), univGrid);
+ Grid2(dst, begin, end, cam.ToScale(univ.areaSize), univ.secSize, secGrid, univGrid);
Cross(dst, cam.ToScreen(focus.Pos()), 15, focusColor);
for (const Entity &e : univ.Entities()) {
Camera::Camera(int w, int h, const Vector<float> &t)
: target(&t)
, offset(w/2, h/2)
-, zoom(0) {
+, zoom(1) {
}
}
void Camera::Update(float delta) {
+ zoom += zoom * zoomAcc * delta;
+ if (zoom < 0.0001) zoom = 0.0001;
+}
+
+void Camera::StartZoom() {
+ zoomAcc += 1;
+}
+void Camera::StopZoom() {
+ zoomAcc -= 1;
}
-void Camera::DoubleZoom() {
- zoom += 1;
+void Camera::StartShrink() {
+ zoomAcc -= 1;
}
-void Camera::HalfZoom() {
- zoom -= 1;
+void Camera::StopShrink() {
+ zoomAcc += 1;
}
}
void Resize(int w, int h);
void Update(float deltaT);
- void DoubleZoom();
- void HalfZoom();
+ void StartZoom();
+ void StopZoom();
+ void StartShrink();
+ void StopShrink();
Vector<int> ToScreen(Vector<float> v) const {
return Vector<int>(OffsetOf(v));
return ToScale(v - *target) + offset;
}
Vector<float> ToScale(Vector<float> v) const {
- if (zoom == 0) {
- return v;
- } else if (zoom > 0) {
- return v * float(1 << zoom);
- } else {
- return v / float(1 << -zoom);
- }
+ return v * zoom;
}
private:
const Vector<float> *target;
Vector<float> offset;
- int zoom;
+ float zoom;
+ int zoomAcc;
};
}
}
+void Grid2(
+ SDL_Surface *dst,
+ Vector<int> first,
+ Vector<int> second,
+ Vector<int> size,
+ Vector<int> n,
+ Color color1,
+ Color color2) {
+ Uint32 c1 = color1.MapRGBA(dst);
+ Uint32 c2 = color2.MapRGBA(dst);
+
+ Vector<int> from = min(first, second);
+ Vector<int> to = max(first, second);
+
+ if (size.x <= 1 || size.y <= 1) {
+ FillRect(dst, from, to - from, c1);
+ Grid(dst, from, to, size * n, color2);
+ return;
+ }
+
+ if (from.x > dst->w || from.y > dst->h || to.x < 0 || to.y < 0) {
+ return;
+ }
+
+ Vector<int> i(0, 0);
+ while (from.x < -size.x) { from.x += size.x; ++i.x; }
+ while (from.y < -size.y) { from.y += size.y; ++i.y; }
+ while (to.x > dst->w + size.x) to.x -= size.x;
+ while (to.y > dst->h + size.y) to.y -= size.y;
+
+ int width = to.x - from.x;
+ int height = to.y - from.y;
+
+ for (Vector<int> pos(from); pos.x <= to.x; pos.x += size.x) {
+ VLine(dst, pos, height, (i.x++ % n.x) ? c1 : c2);
+ }
+ for (Vector<int> pos(from); pos.y <= to.y; pos.y += size.y) {
+ HLine(dst, pos, width, (i.y++ % n.y) ? c1 : c2);
+ }
+}
+
+void Grid2(
+ SDL_Surface *dst,
+ Vector<int> first,
+ Vector<int> second,
+ Vector<float> size,
+ Vector<int> n,
+ Color color1,
+ Color color2) {
+ Uint32 c1 = color1.MapRGBA(dst);
+ Uint32 c2 = color2.MapRGBA(dst);
+
+ Vector<int> from = min(first, second);
+ Vector<int> to = max(first, second);
+
+ if (size.x <= 1 || size.y <= 1) {
+ FillRect(dst, from, to - from, c1);
+ Grid(dst, from, to, size * Vector<float>(n), color2);
+ return;
+ }
+
+ if (from.x > dst->w || from.y > dst->h || to.x < 0 || to.y < 0) {
+ return;
+ }
+
+ Vector<int> i(0, 0);
+ while (from.x < -size.x) { from.x += size.x; ++i.x; }
+ while (from.y < -size.y) { from.y += size.y; ++i.y; }
+ while (to.x > dst->w + size.x) to.x -= size.x;
+ while (to.y > dst->h + size.y) to.y -= size.y;
+
+ float width = to.x - from.x;
+ float height = to.y - from.y;
+
+ for (Vector<float> pos(from); pos.x <= to.x; pos.x += size.x) {
+ VLine(dst, pos, height, (i.x++ % n.x) ? c1 : c2);
+ }
+ for (Vector<float> pos(from); pos.y <= to.y; pos.y += size.y) {
+ HLine(dst, pos, width, (i.y++ % n.y) ? c1 : c2);
+ }
+}
+
}