首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Wii / GameCube上的Tron游戏

Wii / GameCube上的Tron游戏
EN

Code Review用户
提问于 2020-03-22 13:43:01
回答 2查看 259关注 0票数 8

我实现了下面的Tron循环游戏,以便它可以在GameCube / Wii设备上运行(隔离.)。事实上,有很多工具(我依赖于devkitPPC),我认为Tron游戏对于这种开发来说是一个简单的起点。

我没有C方面的经验,也没有在C中执行“类”的经验,也没有在游戏开发方面的经验(命名可能很可怕),因此,任何帮助都将受到欢迎!

目录结构如下:

代码语言:javascript
复制
├── Makefile
├── source
│   └── tron.c
└── textures
    ├── ballsprites.png
    └── textures.scf

下面列出了不同的文件(我编写的唯一文件是tron.c和精灵,其余的都归功于devkit后面的团队!)

Wall walls[NUM_PLAYERS][NUM_WALLS];是一个全局变量,而不是VersusEngineManager类的属性,因为模拟器总是触发奇怪的内存错误。在这一点上的任何帮助都会很棒!

文本.

代码语言:javascript
复制

tron.c

代码语言:javascript
复制
#include 
#include 
#include 
#include 
#include 
#include 

#include 

#include "textures_tpl.h"
#include "textures.h"

#define DEFAULT_FIFO_SIZE   (256*1024)

static void *frameBuffer[2] = { NULL, NULL};
static GXRModeObj *rmode;

#define NUM_PLAYERS 2
#define NUM_WALLS 20000
#define SPEED 0x200
#define SPRITE_SIZE 4

#define WIDTH 640
#define HEIGHT 480
#define UPPER_MARGIN 20
#define TV_MARGIN 50

typedef struct 
{
    int x, y;
} Point;

bool Point_CheckInRectangle(Point *self, int xmin, int xmax, int ymin, int ymax);
bool Point_CheckCollision(Point *self, Point *other);


typedef struct 
{
    int x, y;
    int dx, dy;
    int image;
} Player;

int Player_init(Player *self, int x, int y, int dx, int dy, int image);
void Player_UpdatePosition(Player *self);

typedef struct
{
    int x, y;
    int image;
} Wall;

int playerLossesCount[NUM_PLAYERS];
Wall walls[NUM_PLAYERS][NUM_WALLS];

typedef struct
{
    int speed;
    int nPlayers;
    int wallIndex;
    Player players[NUM_PLAYERS];
} VersusEngineManager;

int VersusEngineManager_init(VersusEngineManager *self, int speed, int nPlayers);
bool VersusEngineManager_CheckPlayersCollision(VersusEngineManager *self);
bool VersusEngineManager_CheckWallCollision(VersusEngineManager *self, int playerId);
int VersusEngineManager_UpdateGameState(VersusEngineManager *self);
void VersusEngineManager_UpdatePlayerDirectionFromPAD(VersusEngineManager *self, int pad, int playerId);
void VersusEngineManager_UpdatePlayersDirectionFromPADs(VersusEngineManager *self);
void VersusEngineManager_UpdatePlayersDirectionFromPADs(VersusEngineManager *self)
{
    VersusEngineManager_UpdatePlayerDirectionFromPAD(self, 0, 0); 
    VersusEngineManager_UpdatePlayerDirectionFromPAD(self, 1, 1);
}

typedef struct 
{
    int spriteSize;
} SpriteDrawer;

int SpriteDrawer_init(SpriteDrawer *self, int spriteSize);
void SpriteDrawer_Rectangle(SpriteDrawer *self, int x, int y, int width, int height, int image);
void SpriteDrawer_SpriteTex(SpriteDrawer *self, int x, int y, int width, int height, int image);
void SpriteDrawer_AllSprites(SpriteDrawer *self);
void SpriteDrawer_Sprites(SpriteDrawer *self, VersusEngineManager *versusEngineManager);
void SpriteDrawer_Scores(SpriteDrawer *self, VersusEngineManager *versusEngineManager);
void SpriteDrawer_ArenaSprites(SpriteDrawer *self);

GXTexObj texObj;

int main( int argc, char **argv ){
    u32 fb;     // initial framebuffer index
    u32 first_frame;
    f32 yscale;
    u32 xfbHeight;
    Mtx44 perspective;
    Mtx GXmodelView2D;
    void *gp_fifo = NULL;

    GXColor background = {0, 0, 0, 0xff};

    VIDEO_Init();

    rmode = VIDEO_GetPreferredMode(NULL);

    fb = 0;
    first_frame = 1;
    // allocate 2 framebuffers for double buffering
    frameBuffer[0] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
    frameBuffer[1] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));

    VIDEO_Configure(rmode);
    VIDEO_SetNextFramebuffer(frameBuffer[fb]);
    VIDEO_SetBlack(FALSE);
    VIDEO_Flush();
    VIDEO_WaitVSync();
    if(rmode->viTVMode&VI_NON_INTERLACE) VIDEO_WaitVSync();

    fb ^= 1;

    // setup the fifo and then init the flipper
    gp_fifo = memalign(32,DEFAULT_FIFO_SIZE);
    memset(gp_fifo,0,DEFAULT_FIFO_SIZE);

    GX_Init(gp_fifo,DEFAULT_FIFO_SIZE);

    // clears the bg to color and clears the z buffer
    GX_SetCopyClear(background, 0x00ffffff);

    // other gx setup
    GX_SetViewport(0,0,rmode->fbWidth,rmode->efbHeight,0,1);
    yscale = GX_GetYScaleFactor(rmode->efbHeight,rmode->xfbHeight);
    xfbHeight = GX_SetDispCopyYScale(yscale);
    GX_SetScissor(0,0,rmode->fbWidth,rmode->efbHeight);
    GX_SetDispCopySrc(0,0,rmode->fbWidth,rmode->efbHeight);
    GX_SetDispCopyDst(rmode->fbWidth,xfbHeight);
    GX_SetCopyFilter(rmode->aa,rmode->sample_pattern,GX_TRUE,rmode->vfilter);
    GX_SetFieldMode(rmode->field_rendering,((rmode->viHeight==2*rmode->xfbHeight)?GX_ENABLE:GX_DISABLE));

    if (rmode->aa)
        GX_SetPixelFmt(GX_PF_RGB565_Z16, GX_ZC_LINEAR);
    else
        GX_SetPixelFmt(GX_PF_RGB8_Z24, GX_ZC_LINEAR);


    GX_SetCullMode(GX_CULL_NONE);
    GX_CopyDisp(frameBuffer[fb],GX_TRUE);
    GX_SetDispCopyGamma(GX_GM_1_0);

    // setup the vertex descriptor
    // tells the flipper to expect direct data
    GX_SetVtxAttrFmt(GX_VTXFMT0, GX_VA_POS, GX_POS_XY, GX_F32, 0);
    GX_SetVtxAttrFmt(GX_VTXFMT0, GX_VA_TEX0, GX_TEX_ST, GX_F32, 0);


    GX_SetNumChans(1);
    GX_SetNumTexGens(1);
    GX_SetTevOp(GX_TEVSTAGE0, GX_REPLACE);
    GX_SetTevOrder(GX_TEVSTAGE0, GX_TEXCOORD0, GX_TEXMAP0, GX_COLOR0A0);
    GX_SetTexCoordGen(GX_TEXCOORD0, GX_TG_MTX2x4, GX_TG_TEX0, GX_IDENTITY);


    GX_InvalidateTexAll();

    TPLFile spriteTPL;
    TPL_OpenTPLFromMemory(&spriteTPL, (void *)textures_tpl,textures_tpl_size);
    TPL_GetTexture(&spriteTPL,ballsprites,&texObj);

    GX_LoadTexObj(&texObj, GX_TEXMAP0);

    guOrtho(perspective,0,479,0,639,0,300);
    GX_LoadProjectionMtx(perspective, GX_ORTHOGRAPHIC);

    PAD_Init();

    srand(time(NULL));

    GX_SetViewport(0,0,rmode->fbWidth,rmode->efbHeight,0,1);
    guMtxIdentity(GXmodelView2D);
    guMtxTransApply (GXmodelView2D, GXmodelView2D, 0.0F, 0.0F, -5.0F);
    GX_LoadPosMtxImm(GXmodelView2D,GX_PNMTX0);

    GX_SetZMode(GX_TRUE, GX_LEQUAL, GX_TRUE);
    GX_SetBlendMode(GX_BM_BLEND, GX_BL_SRCALPHA, GX_BL_INVSRCALPHA, GX_LO_CLEAR);
    GX_SetAlphaUpdate(GX_TRUE);
    GX_SetColorUpdate(GX_TRUE);

    VersusEngineManager versusEngineManager;
    VersusEngineManager_init(&versusEngineManager, SPEED, NUM_PLAYERS);

    SpriteDrawer spriteDrawer;
    SpriteDrawer_init(&spriteDrawer, SPRITE_SIZE);

    while(1) {

        GX_InvVtxCache();
        GX_InvalidateTexAll();
        GX_ClearVtxDesc();
        GX_SetVtxDesc(GX_VA_POS, GX_DIRECT);
        GX_SetVtxDesc(GX_VA_TEX0, GX_DIRECT);

        VersusEngineManager_UpdatePlayersDirectionFromPADs(&versusEngineManager);
        int gameState = VersusEngineManager_UpdateGameState(&versusEngineManager);
        if(gameState==1) { VersusEngineManager_init(&versusEngineManager, SPEED, NUM_PLAYERS); }

        SpriteDrawer_Sprites(&spriteDrawer, &versusEngineManager);
        GX_DrawDone();

        GX_CopyDisp(frameBuffer[fb],GX_TRUE);

        VIDEO_SetNextFramebuffer(frameBuffer[fb]);
        if(first_frame) {
            VIDEO_SetBlack(FALSE);
            first_frame = 0;
        }
        VIDEO_Flush();
        VIDEO_WaitVSync();
        fb ^= 1;        // flip framebuffer
    }
    return 0;
}


float texCoords[] = {
    0.0 ,0.0 , 0.5, 0.0, 0.5, 0.5, 0.0, 0.5,
    0.5 ,0.0 , 1.0, 0.0, 1.0, 0.5, 0.5, 0.5,
    0.0 ,0.5 , 0.5, 0.5, 0.5, 1.0, 0.0, 1.0,
    0.5 ,0.5 , 1.0, 0.5, 1.0, 1.0, 0.5, 1.0
};


int SpriteDrawer_init(SpriteDrawer *self, int spriteSize)
{
    self->spriteSize = spriteSize;
    return 0;
}


void SpriteDrawer_Sprites(SpriteDrawer *self, VersusEngineManager *versusEngineManager) {
    int spriteSize = self->spriteSize;
    for(int playerId=0;playerIdplayers[playerId].x >> 8, 
            versusEngineManager->players[playerId].y >> 8, 
            spriteSize, 
            spriteSize, 
            versusEngineManager->players[playerId].image);
        for(int wallId=0; wallId < NUM_WALLS; wallId++) {
            SpriteDrawer_SpriteTex(self, 
                walls[playerId][wallId].x >> 8, 
                walls[playerId][wallId].y >> 8, 
                spriteSize, 
                spriteSize, 
                walls[playerId][wallId].image);
        }
    }
    SpriteDrawer_ArenaSprites(self);
    SpriteDrawer_Scores(self, versusEngineManager);
};

void SpriteDrawer_ArenaSprites(SpriteDrawer *self) {
    int spriteSize = self->spriteSize;
    SpriteDrawer_Rectangle(self, TV_MARGIN,UPPER_MARGIN+TV_MARGIN, WIDTH-2*TV_MARGIN-spriteSize, HEIGHT - 2*TV_MARGIN - spriteSize,3);
};

void SpriteDrawer_Rectangle(SpriteDrawer *self, int x,int y,int width,int height,int sprite) {
    int spriteSize = self->spriteSize;
    for(int i=x; i < x+width;i+=spriteSize){ 
        SpriteDrawer_SpriteTex(self, i,y,spriteSize, spriteSize, sprite); 
    }
    for(int i=x; i < x+width+spriteSize;i+=spriteSize){ 
        SpriteDrawer_SpriteTex(self, i,y+height,spriteSize, spriteSize, sprite);
    }
    for(int i=y; i < y+height;i+=spriteSize){ 
        SpriteDrawer_SpriteTex(self, x,i,spriteSize, spriteSize, sprite); 
    }
    for(int i=y; i < y+height;i+=spriteSize){ 
        SpriteDrawer_SpriteTex(self, x+width,i,spriteSize, spriteSize, sprite);
    }
};


void SpriteDrawer_Scores(SpriteDrawer *self, VersusEngineManager *versusEngineManager) {
    int spriteSize = self->spriteSize;
    for(int playerId=0;playerId> 8),  TV_MARGIN + 2* SPEED * (1 + playerId) >> 8, spriteSize, spriteSize, versusEngineManager->players[playerId].image);
        }
    }
};

void SpriteDrawer_SpriteTex(SpriteDrawer *self, int x, int y, int width, int height, int image ) {
    int texIndex = image * 8;

    GX_Begin(GX_QUADS, GX_VTXFMT0, 4);          // Draw A Quad
    GX_Position2f32(x, y);                  // Top Left
    GX_TexCoord2f32(texCoords[texIndex],texCoords[texIndex+1]);
    texIndex+=2;
    GX_Position2f32(x+width-1, y);          // Top Right
    GX_TexCoord2f32(texCoords[texIndex],texCoords[texIndex+1]);
    texIndex+=2;
    GX_Position2f32(x+width-1,y+height-1);  // Bottom Right
    GX_TexCoord2f32(texCoords[texIndex],texCoords[texIndex+1]);
    texIndex+=2;
    GX_Position2f32(x,y+height-1);          // Bottom Left
    GX_TexCoord2f32(texCoords[texIndex],texCoords[texIndex+1]);
    GX_End();                                   // Done Drawing The Quad 

}

int Player_init(Player *self, int x, int y, int dx, int dy, int image)
{
    self->x = x;
    self->y = y;
    self->dx = dx;
    self->dy = dy;
    self->image = image;
    return 0;
}

void Player_UpdatePosition(Player *self)
{
        self->x += self->dx; 
        self->y += self->dy; 
}

bool Point_CheckInRectangle(Point *self, int xmin, int xmax, int ymin, int ymax) 
{
    return self->x < xmin || self->x > xmax || self->y < ymin || self->y > ymax;
}

bool Point_CheckCollision(Point *self, Point *other)
{
    return self->x == other->x && self->y==other->y;
}

int VersusEngineManager_init(VersusEngineManager *self, int speed, int nPlayers)
{
    self->speed = speed;
    self->nPlayers = nPlayers;
    self->wallIndex = 0;

    Player player0, player1;
    Player_init(&player0, ((WIDTH - SPRITE_SIZE ) / 2 ) << 8,100 << 8,0, SPEED, 0);
    Player_init(&player1, ((WIDTH - SPRITE_SIZE ) / 2 ) << 8,400 << 8,0, -SPEED, 1);

    self->players[0] = player0; 
    self->players[1] = player1; 

    for(int playerId=0;playerIdnPlayers;playerId++){
        for(int wallId=0; wallId < NUM_WALLS; wallId++) {
            walls[playerId][wallId].x = 0; 
            walls[playerId][wallId].y = 0; 
            walls[playerId][wallId].image = 2; 
        }
    }
    return 0;
}

bool VersusEngineManager_CheckPlayersCollision(VersusEngineManager *self)
{
    for(int i=0; i < self->nPlayers; i++)
    {
        for(int j=i+1; j < self->nPlayers; j++)
        {
            if(Point_CheckCollision(&self->players[i], &self->players[j]) ) {
                return true; }
        }
    }
    return false;
};

bool VersusEngineManager_CheckWallCollision(VersusEngineManager *self, int playerId)
{
    if(Point_CheckInRectangle(&self->players[playerId], 
            TV_MARGIN<<8,
            WIDTH-SPRITE_SIZE-TV_MARGIN << 8,
            (UPPER_MARGIN + TV_MARGIN) <<8 ,
            (HEIGHT+UPPER_MARGIN-SPRITE_SIZE-TV_MARGIN) << 8)) 
    {return true;}

    for(int i=0;iwallIndex; wallId++) {
            if(self->players[playerId].x == walls[i][wallId].x && self->players[playerId].y == walls[i][wallId].y) {
                return true;
            }   
        }
    }
    return false;

}

int VersusEngineManager_UpdateGameState(VersusEngineManager *self)
{
    for(int playerId=0;playerIdnPlayers;playerId++){
        Player_UpdatePosition(&self->players[playerId]);

        bool collision = false;
        if (VersusEngineManager_CheckPlayersCollision(self)) {
            collision = true;
        }
        else if(VersusEngineManager_CheckWallCollision(self, playerId)) {
            playerLossesCount[playerId] += 1;
            collision = true;
        }

        walls[playerId][self->wallIndex].x = self->players[playerId].x;
        walls[playerId][self->wallIndex].y = self->players[playerId].y;
        walls[playerId][self->wallIndex].image = playerId;

        if(collision) {return 1;} ;
    }
    self->wallIndex += 1;
    return 0;
};

void VersusEngineManager_UpdatePlayerDirectionFromPAD(VersusEngineManager *self, int pad, int playerId)
{
    PAD_ScanPads();

    if (PAD_ButtonsDown(pad) & PAD_BUTTON_LEFT) {
        if (self->players[playerId].dx ==0) {
            self->players[playerId].dx = -self->speed;
            self->players[playerId].dy = 0;
            return;
        }
    }

    if (PAD_ButtonsDown(pad) & PAD_BUTTON_RIGHT) {
        if (self->players[playerId].dx ==0) {
            self->players[playerId].dx = self->speed;
            self->players[playerId].dy = 0;
            return;
        }
    }

    if (PAD_ButtonsDown(pad) & PAD_BUTTON_UP) {
        if (self->players[playerId].dy ==0) {
            self->players[playerId].dx = 0;
            self->players[playerId].dy = -self->speed;
            return;
        }
    }

    if (PAD_ButtonsDown(pad) & PAD_BUTTON_DOWN) {
        if (self->players[playerId].dy ==0) {
            self->players[playerId].dx = 0;
            self->players[playerId].dy = self->speed; 
            return;
        }
    }
}

Makefile

代码语言:javascript
复制
#---------------------------------------------------------------------------------
# Clear the implicit built in rules
#---------------------------------------------------------------------------------
.SUFFIXES:
.SECONDARY:
#---------------------------------------------------------------------------------
ifeq ($(strip $(DEVKITPPC)),)
$(error "Please set DEVKITPPC in your environment. export DEVKITPPC=devkitPPC")
endif

include $(DEVKITPPC)/wii_rules

#---------------------------------------------------------------------------------
# TARGET is the name of the output
# BUILD is the directory where object files & intermediate files will be placed
# SOURCES is a list of directories containing source code
# INCLUDES is a list of directories containing extra header files
#---------------------------------------------------------------------------------
TARGET      :=  $(notdir $(CURDIR))
BUILD       :=  build
SOURCES     :=  source
DATA        :=
TEXTURES    :=  textures 
INCLUDES    :=

#---------------------------------------------------------------------------------
# options for code generation
#---------------------------------------------------------------------------------

CFLAGS  = -g -O2 -Wall $(MACHDEP) $(INCLUDE)
CXXFLAGS    =   $(CFLAGS)

LDFLAGS =   -g $(MACHDEP) -Wl,-Map,$(notdir $@).map

#---------------------------------------------------------------------------------
# any extra libraries we wish to link with the project
#---------------------------------------------------------------------------------
LIBS    :=  -logc -lm

#---------------------------------------------------------------------------------
# list of directories containing libraries, this must be the top level containing
# include and lib
#---------------------------------------------------------------------------------
LIBDIRS :=

#---------------------------------------------------------------------------------
# no real need to edit anything past this point unless you need to add additional
# rules for different file extensions
#---------------------------------------------------------------------------------
ifneq ($(BUILD),$(notdir $(CURDIR)))
#---------------------------------------------------------------------------------

export OUTPUT   :=  $(CURDIR)/$(TARGET)

export VPATH    :=  $(foreach dir,$(SOURCES),$(CURDIR)/$(dir)) \
                    $(foreach dir,$(DATA),$(CURDIR)/$(dir)) \
                    $(foreach dir,$(TEXTURES),$(CURDIR)/$(dir))

export DEPSDIR  :=  $(CURDIR)/$(BUILD)

#---------------------------------------------------------------------------------
# automatically build a list of object files for our project
#---------------------------------------------------------------------------------
CFILES      :=  $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.c)))
CPPFILES    :=  $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.cpp)))
sFILES      :=  $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.s)))
SFILES      :=  $(foreach dir,$(SOURCES),$(notdir $(wildcard $(dir)/*.S)))
BINFILES    :=  $(foreach dir,$(DATA),$(notdir $(wildcard $(dir)/*.*)))
SCFFILES    :=  $(foreach dir,$(TEXTURES),$(notdir $(wildcard $(dir)/*.scf)))
TPLFILES    :=  $(SCFFILES:.scf=.tpl)

#---------------------------------------------------------------------------------
# use CXX for linking C++ projects, CC for standard C
#---------------------------------------------------------------------------------
ifeq ($(strip $(CPPFILES)),)
    export LD   :=  $(CC)
else
    export LD   :=  $(CXX)
endif

export OFILES_BIN   :=  $(addsuffix .o,$(BINFILES)) $(addsuffix .o,$(TPLFILES))
export OFILES_SOURCES := $(CPPFILES:.cpp=.o) $(CFILES:.c=.o) $(sFILES:.s=.o) $(SFILES:.S=.o)
export OFILES := $(OFILES_BIN) $(OFILES_SOURCES)

export HFILES := $(addsuffix .h,$(subst .,_,$(BINFILES))) $(addsuffix .h,$(subst .,_,$(TPLFILES)))

#---------------------------------------------------------------------------------
# build a list of include paths
#---------------------------------------------------------------------------------
export INCLUDE  :=  $(foreach dir,$(INCLUDES),-I$(CURDIR)/$(dir)) \
                    $(foreach dir,$(LIBDIRS),-I$(dir)/include) \
                    -I$(CURDIR)/$(BUILD) \
                    -I$(LIBOGC_INC)

#---------------------------------------------------------------------------------
# build a list of library paths
#---------------------------------------------------------------------------------
export LIBPATHS :=  $(foreach dir,$(LIBDIRS),-L$(dir)/lib) \
                    -L$(LIBOGC_LIB)

export OUTPUT   :=  $(CURDIR)/$(TARGET)
.PHONY: $(BUILD) clean

#---------------------------------------------------------------------------------
$(BUILD):
    @[ -d $@ ] || mkdir -p $@
    @$(MAKE) --no-print-directory -C $(BUILD) -f $(CURDIR)/Makefile

#---------------------------------------------------------------------------------
clean:
    @echo clean ...
    @rm -fr $(BUILD) $(OUTPUT).elf $(OUTPUT).dol

#---------------------------------------------------------------------------------
else

#---------------------------------------------------------------------------------
# main targets
#---------------------------------------------------------------------------------
$(OUTPUT).dol: $(OUTPUT).elf
$(OUTPUT).elf: $(OFILES)

$(OFILES_SOURCES) : $(HFILES)

#---------------------------------------------------------------------------------
# This rule links in binary data with the .bin extension
#---------------------------------------------------------------------------------
%.bin.o %_bin.h :   %.bin
#---------------------------------------------------------------------------------
    @echo $(notdir $<)
    @$(bin2o)

#---------------------------------------------------------------------------------
%.tpl.o %_tpl.h :   %.tpl
#---------------------------------------------------------------------------------
    @echo $(notdir $<)
    @$(bin2o)


-include $(DEPSDIR)/*.d

#---------------------------------------------------------------------------------
endif
#---------------------------------------------------------------------------------

<#>球棒.

EN

回答 2

Code Review用户

回答已采纳

发布于 2020-03-23 16:36:23

C中没有类,但是有函数。

关于:

代码语言:javascript
复制
CFLAGS = -g -O2 -Wall $(MACHDEP) $(INCLUDE) 

编译时,始终启用警告,然后修复这些警告。(对于gcc,至少使用:-Wall -Wextra -Wconversion -pedantic -std=gnu11 )

每次引用该宏时,=都会使其重新评估.建议:

代码语言:javascript
复制
CFLAGS := -g -O2 -Wall $(MACHDEP) $(INCLUDE) 

注意:=而不是=

声明的结构不被指定为tag名称。当使用调试器时,这将成为一个问题,因为大多数调试器都需要一个标记名才能显示结构中的各个字段。

票数 2
EN

Code Review用户

发布于 2020-03-22 14:46:27

静力学

您有一个文件程序,所以更多的方法和全局,包括:

代码语言:javascript
复制
int playerLossesCount[NUM_PLAYERS];
Wall walls[NUM_PLAYERS][NUM_WALLS];

GXTexObj texObj;

应该是static

变量的

声明

代码语言:javascript
复制
int main( int argc, char **argv ){
    u32 fb;     // initial framebuffer index
    u32 first_frame;
    f32 yscale;
    u32 xfbHeight;
    Mtx44 perspective;
    Mtx GXmodelView2D;
    void *gp_fifo = NULL;

这种风格是典型的前C99代码,但通常情况下,它更难遵循这样的代码。如果这些变量是在离实际使用的地方更近的地方声明和初始化的,就更容易辨认了。

空间

对于空格,C通常比Python更自由,但如下所示:

代码语言:javascript
复制
GX_SetScissor(0,0,rmode->fbWidth,rmode->efbHeight);

还需要更多。可能每个逗号后面有一个空格,这样才能看得清楚。同时,你的支撑风格也有很大的差异;比较一下

代码语言:javascript
复制
        if(Point_CheckCollision(&self->players[i], &self->players[j]) ) {
            return true; }

使用

代码语言:javascript
复制
if(Point_CheckInRectangle(&self->players[playerId], 
        TV_MARGIN<<8,
        WIDTH-SPRITE_SIZE-TV_MARGIN << 8,
        (UPPER_MARGIN + TV_MARGIN) <<8 ,
        (HEIGHT+UPPER_MARGIN-SPRITE_SIZE-TV_MARGIN) << 8)) 
{return true;}

使用

代码语言:javascript
复制
        if(self->players[playerId].x == walls[i][wallId].x && self->players[playerId].y == walls[i][wallId].y) {
            return true;
        }  

最后一个似乎是最理智的,但无论你做什么,选择一种风格,并坚持它。

坐标

基于对此的解读:

代码语言:javascript
复制
float texCoords[] = {
    0.0 ,0.0 , 0.5, 0.0, 0.5, 0.5, 0.0, 0.5,
// ...
GX_TexCoord2f32(texCoords[texIndex],texCoords[texIndex+1]);

好像你在把一个坐标数组压平,表示为x,y,x,y.如果要使用一个Point结构数组(您甚至自己声明了一个;您也可以使用它),那么您的代码会更容易读懂。

环组合

这是:

代码语言:javascript
复制
for(int i=y; i < y+height;i+=spriteSize){ 
    SpriteDrawer_SpriteTex(self, x,i,spriteSize, spriteSize, sprite); 
}
for(int i=y; i < y+height;i+=spriteSize){ 
    SpriteDrawer_SpriteTex(self, x+width,i,spriteSize, spriteSize, sprite);
}

应该成为等价物

代码语言:javascript
复制
for(int i=y; i < y+height;i+=spriteSize){ 
    SpriteDrawer_SpriteTex(self, x,i,spriteSize, spriteSize, sprite); 
    SpriteDrawer_SpriteTex(self, x+width,i,spriteSize, spriteSize, sprite);
}
票数 7
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/239272

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档