 Hello to all! I want to share my experience in developing applications for the Marmalade SDK.
 Hello to all! I want to share my experience in developing applications for the Marmalade SDK.#!/usr/bin/env mkb
files {
[Source]
(source)
main.cpp
entity.cpp
entity.h
}
subprojects {
iw2d
}

  #include "iw2d.h" #include "iwArray.h" #include "entity.h" #include "s3eKeyboard.h" #include "s3eDevice.h" #include <time.h> #include <s3e.h> #define FPS 30 #define MOVE_SPEED 100 #define OBJECT_DIMENSION 50 /***************************************************************/ int main(int argc, char* argv[]) { s3eResult result = S3E_RESULT_SUCCESS; /*      2D  */ Iw2DInit(); /*    */ uint32 width = Iw2DGetSurfaceWidth(); uint32 height = Iw2DGetSurfaceHeight(); /*    "" */ int wall_size = MAX(width, height); /*    */ CIwArray<CEntity*> arr_objects; /*  3    */ /*    */ CIwSVec2 m_Verts1[5]; CIwSVec2 m_Verts2[4]; CIwSVec2 m_Verts3[4]; /*  1 */ m_Verts1[0] = CIwVec2(-OBJECT_DIMENSION, -OBJECT_DIMENSION); m_Verts1[1] = CIwVec2(OBJECT_DIMENSION, -OBJECT_DIMENSION); m_Verts1[2] = CIwVec2(OBJECT_DIMENSION, 0); m_Verts1[3] = CIwVec2(0, OBJECT_DIMENSION); m_Verts1[4] = CIwVec2(-OBJECT_DIMENSION, OBJECT_DIMENSION); /*  2 */ m_Verts2[0] = CIwVec2(-OBJECT_DIMENSION/2, OBJECT_DIMENSION + OBJECT_DIMENSION/2); m_Verts2[1] = CIwVec2(OBJECT_DIMENSION/2, OBJECT_DIMENSION/2); m_Verts2[2] = CIwVec2(OBJECT_DIMENSION/2, -OBJECT_DIMENSION/2); m_Verts2[3] = CIwVec2(-OBJECT_DIMENSION/2, -OBJECT_DIMENSION/2); /*  3:  */ m_Verts3[0] = CIwVec2(-5, wall_size/2); m_Verts3[1] = CIwVec2(5, wall_size/2); m_Verts3[2] = CIwVec2(5, -wall_size/2); m_Verts3[3] = CIwVec2(-5, -wall_size/2); /*  ,    */ /*  ,     */ CEntity *main_object = new CEntity(CIwSVec2(width/2, height/2), &m_Verts2[0], 4, 0xFFff0000); arr_objects.append(main_object); /*         ,   . */ CEntity *tmp_object = new CEntity(CIwSVec2(width/2, height/2), &m_Verts1[0], 5, 0xFF0000ff); tmp_object->SetAngle(IW_ANGLE_PI/3); arr_objects.append(tmp_object); tmp_object = new CEntity(CIwSVec2(50, 50), &m_Verts1[0], 5, 0xFF0000ff); tmp_object->SetAngle(IW_ANGLE_PI/2); arr_objects.append(tmp_object); /*  4 "" */ tmp_object = new CEntity(CIwSVec2(0, height/2), &m_Verts3[0], 4, 0xFFff0000); arr_objects.append(tmp_object); tmp_object = new CEntity(CIwSVec2(width, height/2), &m_Verts3[0], 4, 0xFFff0000); arr_objects.append(tmp_object); tmp_object = new CEntity(CIwSVec2(width/2, 0), &m_Verts3[0], 4, 0xFFff0000); tmp_object->SetAngle(IW_ANGLE_PI/2); arr_objects.append(tmp_object); tmp_object = new CEntity(CIwSVec2(width/2, height), &m_Verts3[0], 4, 0xFFff0000); tmp_object->SetAngle(IW_ANGLE_PI/2); arr_objects.append(tmp_object); /*     */ int time_between_frames = 1000/FPS; /*    */ uint32 timer = (uint32)s3eTimerGetMs(); while(result == S3E_RESULT_SUCCESS) { /*    */ s3eKeyboardUpdate(); /*     .    . */ if (s3eDeviceCheckQuitRequest()) break; /*       .      */ uint32 now_time = (uint32)s3eTimerGetMs(); int delta = now_time - timer; if (delta < 0) delta = 0; /*        */ main_object->Move(CIwSVec2::g_Zero); main_object->Rotate(0); /*             */ if ( (s3eKeyboardGetState(s3eKeyLeft) & S3E_KEY_STATE_DOWN) ) { main_object->Move(CIwSVec2(-MOVE_SPEED, 0)); } else if ( (s3eKeyboardGetState(s3eKeyRight) & S3E_KEY_STATE_DOWN) ) { main_object->Move(CIwSVec2(MOVE_SPEED, 0)); } else if ( (s3eKeyboardGetState(s3eKeyUp) & S3E_KEY_STATE_DOWN) ) { main_object->Move(CIwSVec2(0, -MOVE_SPEED)); } else if ( (s3eKeyboardGetState(s3eKeyDown) & S3E_KEY_STATE_DOWN) ) { main_object->Move(CIwSVec2(0, MOVE_SPEED)); } if ( (s3eKeyboardGetState(s3eKey1) & S3E_KEY_STATE_DOWN) ) { main_object->Rotate(-IW_ANGLE_PI / 2); } else if ( (s3eKeyboardGetState(s3eKey2) & S3E_KEY_STATE_DOWN) ) { main_object->Rotate(IW_ANGLE_PI / 2); } /*    */ Iw2DSurfaceClear(0xffffffff); /*    */ for(int i=0; i < (int)arr_objects.size(); ++i) { arr_objects[i]->Update(delta); } /*     ().      . */ main_object->SetColour(0xff00ff00); /*      ,   . */ int try_count = 10; bool b_collide; do{ b_collide = false; /*      */ for(int i = 0; i < (int)arr_objects.size(); ++i) { /*       */ if(arr_objects[i] != main_object){ /*  .  vec_reaction  ,   . */ CIwVec2 vec_reaction = main_object->CollideRect(arr_objects[i], true); if(!vec_reaction.IsZero()){ main_object->SetColour(0xff000000); b_collide = true; } } } --try_count; /*      ,   ""  ,      . */ } while(b_collide && try_count > 0); /*    */ for(int i=0; i < (int)arr_objects.size(); ++i) { arr_objects[i]->Render(); } /*     */ Iw2DSurfaceShow(); /*        . */ int32 wait_time = (uint32)time_between_frames - ((uint32)s3eTimerGetMs() - now_time); if(wait_time<0)wait_time = 0; timer = now_time; s3eDeviceYield(wait_time); } /*      */ for(int i=0; i < (int)arr_objects.size(); ++i) { delete arr_objects[i]; } /*   */ arr_objects.clear_optimised(); /*       2d . */ Iw2DTerminate(); return 0; }   #pragma once #include "iw2d.h" #include "iwArray.h" #include "IwMath.h" class CEntity{ private: CIwMat2D m_MatLocal; /*    */ iwangle angle; /*    */ iwangle angle_velocity; /*    */ CIwSVec2 m_MoveVelocity; /*   */ uint32 m_NumPoints; /*   */ CIwSVec2 *m_Points; /*   */ CIwVec2 *m_PointsMod; /*  */ CIwVec2 *m_Axis; /*   */ uint32 colour; public: /*  */ CEntity(CIwSVec2 position, CIwSVec2 *verts, int num_verts, uint32 colour = 0xff000000); /*  */ virtual ~CEntity(); /*   */ void Update(int speed); /*   */ void Render(); /*     */ void SetAngle(iwangle angle) {this->angle = angle % IW_ANGLE_PI;}; /*     */ void Rotate(iwangle rot_angle) { angle_velocity = rot_angle; } /*     */ void Move(CIwSVec2 move_velocity) { m_MoveVelocity = move_velocity; } /*    */ void SetColour(int colour){this->colour = colour;} /*      */ const CIwVec2 *GetVerts(){ return m_PointsMod; } /*   */ int GetNumVerts() {return m_NumPoints;} /*   .         */ CIwVec2 CollideRect(CEntity *other, bool b_uncollide = false); private: /*    */ void UpdateVerts(); /*      */ /*         */ /* b_revert -   . */ bool TestOverlaps(CEntity *other, CIwVec2 &min_axis, int &min_t, int b_revert); /*          */ void GetInterval(const CIwVec2 *verts, int count, CIwVec2 axis, int &min, int &max); };   #include "entity.h" CEntity::CEntity(CIwSVec2 position, CIwSVec2 *verts, int num_verts, uint32 colour ): m_MatLocal(CIwMat2D::g_Identity), m_MoveVelocity(CIwSVec2::g_Zero), angle(0), angle_velocity(0) { this->colour = colour; this->m_NumPoints = num_verts; m_Points = NULL; m_PointsMod = new CIwVec2[m_NumPoints]; m_Axis = new CIwVec2[num_verts]; m_MatLocal.t = position; m_Points = verts; } CEntity::~CEntity() { if(m_PointsMod)delete m_PointsMod; delete m_Axis; } void CEntity::Update(int speed) { angle += (angle_velocity * speed) / 1000; angle = angle % IW_ANGLE_2PI; m_MatLocal.SetRot(angle, false); if(!m_MoveVelocity.IsZero()) { m_MatLocal.t += ( m_MoveVelocity * speed) / 1000; } UpdateVerts(); } void CEntity::UpdateVerts() { if(!m_Points) return; /*    */ for(uint32 i = 0; i < m_NumPoints; ++i) { m_PointsMod[i] = m_MatLocal.TransformVec(m_Points[i]); } /*   */ for(uint32 i = 0; i < m_NumPoints; ++i) { /*      */ m_Axis[i] = m_PointsMod[(i + 1) % m_NumPoints] - m_PointsMod[i]; /*  */ m_Axis[i].Normalise(); /*     */ m_Axis[i] = CIwVec2(-m_Axis[i].y, m_Axis[i].x); } } void CEntity::Render() { /*    */ Iw2DSetColour(colour); if(!m_Points)return; /*      */ Iw2DSetTransformMatrix(m_MatLocal); /*   */ Iw2DFillPolygon(m_Points, m_NumPoints); /*   */ Iw2DSetColour(0xff00ffff); Iw2DFillArc(CIwSVec2::g_Zero, CIwSVec2(5,5), 0, IW_ANGLE_2PI); } CIwVec2 CEntity::CollideRect(CEntity *other, bool b_uncollide) { /*   ,       */ int min_t(0); CIwVec2 min_axis(CIwFVec2::g_Zero); /*         ,   */ /*   ..      ,      */ /*        ,  ,    . */ if(!TestOverlaps(other, min_axis, min_t, false))return CIwVec2::g_Zero; if(!other->TestOverlaps(this, min_axis, min_t, true))return CIwVec2::g_Zero; /*   ,      */ if(b_uncollide){ CIwVec2 fvec = min_axis * min_t; /*   */ m_MatLocal.t += fvec; /*  . */ UpdateVerts(); } return min_axis * min_t; } bool CEntity::TestOverlaps(CEntity *other, CIwVec2 &min_axis, int &min_t, int b_revert) { /*   ,     */ const CIwVec2 *other_corner = other->GetVerts(); int other_corner_count = other->GetNumVerts(); /*       */ for (uint32 i = 0; i < m_NumPoints; ++i) { int aMin; int aMax; int bMin; int bMax; /*           */ GetInterval(m_PointsMod, m_NumPoints, m_Axis[i], aMin, aMax); GetInterval(other_corner, other_corner_count, m_Axis[i], bMin, bMax); /* ,       */ if ((aMax <= bMin) || (bMax <= aMin)) { /*   .  */ return false; } /*   .  ,   ,      */ /*               */ int t = 0; if(aMax >= bMin) { t = bMin - aMax ; if(min_axis.IsZero() || ABS(min_t) > ABS(t)){ min_t = t * (b_revert?-1:1); min_axis = m_Axis[i]; } } if(bMax >= aMin) { t = bMax - aMin; if(min_axis.IsZero() || ABS(min_t) > ABS(t)){ min_t = t * (b_revert?-1:1); min_axis = m_Axis[i]; } } } return true; } void CEntity::GetInterval(const CIwVec2 *verts, int count, CIwVec2 axis, int &min, int &max) { min = max = axis.Dot(verts[0]); for (int i = 1; i < count; i++) { int value = axis.Dot(verts[i]); min = MIN(min, value); max = MAX(max, value); } } Source: https://habr.com/ru/post/126785/
All Articles