src/platform/psp2/main.c (view raw)
1/* Copyright (c) 2013-2015 Jeffrey Pfau
2 *
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6#include "psp2-context.h"
7
8#include <mgba/internal/gba/gba.h>
9#include "feature/gui/gui-runner.h"
10#include <mgba-util/gui.h>
11#include <mgba-util/gui/font.h>
12#include <mgba-util/gui/file-select.h>
13#include <mgba-util/gui/menu.h>
14
15#include <psp2/ctrl.h>
16#include <psp2/display.h>
17#include <psp2/kernel/processmgr.h>
18#include <psp2/kernel/threadmgr.h>
19#include <psp2/power.h>
20#include <psp2/sysmodule.h>
21#include <psp2/touch.h>
22
23#include <vita2d.h>
24
25static void _drawStart(void) {
26 vita2d_set_vblank_wait(false);
27 vita2d_start_drawing();
28 vita2d_clear_screen();
29}
30
31static void _drawEnd(void) {
32 static int vcount = 0;
33 extern bool frameLimiter;
34 int oldVCount = vcount;
35 vita2d_end_drawing();
36 vcount = sceDisplayGetVcount();
37 vita2d_set_vblank_wait(frameLimiter && vcount + 1 >= oldVCount);
38 vita2d_swap_buffers();
39}
40
41static uint32_t _pollInput(const struct mInputMap* map) {
42 SceCtrlData pad;
43 sceCtrlPeekBufferPositive(0, &pad, 1);
44 int input = mInputMapKeyBits(map, PSP2_INPUT, pad.buttons, 0);
45
46 if (pad.buttons & SCE_CTRL_UP || pad.ly < 64) {
47 input |= 1 << GUI_INPUT_UP;
48 }
49 if (pad.buttons & SCE_CTRL_DOWN || pad.ly >= 192) {
50 input |= 1 << GUI_INPUT_DOWN;
51 }
52 if (pad.buttons & SCE_CTRL_LEFT || pad.lx < 64) {
53 input |= 1 << GUI_INPUT_LEFT;
54 }
55 if (pad.buttons & SCE_CTRL_RIGHT || pad.lx >= 192) {
56 input |= 1 << GUI_INPUT_RIGHT;
57 }
58
59 return input;
60}
61
62static enum GUICursorState _pollCursor(unsigned* x, unsigned* y) {
63 SceTouchData touch;
64 sceTouchPeek(SCE_TOUCH_PORT_FRONT, &touch, 1);
65 if (touch.reportNum < 1) {
66 return GUI_CURSOR_NOT_PRESENT;
67 }
68 *x = touch.report[0].x / 2;
69 *y = touch.report[0].y / 2;
70 return GUI_CURSOR_DOWN;
71}
72
73static int _batteryState(void) {
74 int charge = scePowerGetBatteryLifePercent();
75 int adapter = scePowerIsPowerOnline();
76 int state = 0;
77 if (adapter) {
78 state |= BATTERY_CHARGING;
79 }
80 charge /= 25;
81 return state | charge;
82}
83
84int main() {
85 vita2d_init();
86 struct GUIFont* font = GUIFontCreate();
87 struct mGUIRunner runner = {
88 .params = {
89 PSP2_HORIZONTAL_PIXELS, PSP2_VERTICAL_PIXELS,
90 font, "ux0:data", _drawStart, _drawEnd,
91 _pollInput, _pollCursor,
92 _batteryState,
93 0, 0,
94 },
95 .configExtra = (struct GUIMenuItem[]) {
96 {
97 .title = "Screen mode",
98 .data = "screenMode",
99 .submenu = 0,
100 .state = 0,
101 .validStates = (const char*[]) {
102 "With Background",
103 "Without Background",
104 "Stretched",
105 "Fit Aspect Ratio",
106 },
107 .nStates = 4
108 }
109 },
110 .keySources = (struct GUIInputKeys[]) {
111 {
112 .name = "Vita Input",
113 .id = PSP2_INPUT,
114 .keyNames = (const char*[]) {
115 "Select",
116 0,
117 0,
118 "Start",
119 "Up",
120 "Right",
121 "Down",
122 "Left",
123 "L",
124 "R",
125 0, // L2?
126 0, // R2?
127 "\1\xC",
128 "\1\xA",
129 "\1\xB",
130 "\1\xD"
131 },
132 .nKeys = 16
133 },
134 { .id = 0 }
135 },
136 .nConfigExtra = 1,
137 .setup = mPSP2Setup,
138 .teardown = mPSP2Teardown,
139 .gameLoaded = mPSP2LoadROM,
140 .gameUnloaded = mPSP2UnloadROM,
141 .prepareForFrame = mPSP2PrepareForFrame,
142 .drawFrame = mPSP2Draw,
143 .drawScreenshot = mPSP2DrawScreenshot,
144 .paused = mPSP2Paused,
145 .unpaused = mPSP2Unpaused,
146 .incrementScreenMode = mPSP2IncrementScreenMode,
147 .setFrameLimiter = mPSP2SetFrameLimiter,
148 .pollGameInput = mPSP2PollInput
149 };
150
151 sceTouchSetSamplingState(SCE_TOUCH_PORT_FRONT, SCE_TOUCH_SAMPLING_STATE_START);
152 sceCtrlSetSamplingMode(SCE_CTRL_MODE_ANALOG_WIDE);
153 sceSysmoduleLoadModule(SCE_SYSMODULE_PHOTO_EXPORT);
154
155 mGUIInit(&runner, "psvita");
156
157 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_CROSS, GUI_INPUT_SELECT);
158 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_CIRCLE, GUI_INPUT_BACK);
159 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_TRIANGLE, GUI_INPUT_CANCEL);
160 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_UP, GUI_INPUT_UP);
161 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_DOWN, GUI_INPUT_DOWN);
162 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_LEFT, GUI_INPUT_LEFT);
163 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_RIGHT, GUI_INPUT_RIGHT);
164 mPSP2MapKey(&runner.params.keyMap, SCE_CTRL_SQUARE, mGUI_INPUT_SCREEN_MODE);
165
166 mGUIRunloop(&runner);
167
168 vita2d_fini();
169 mGUIDeinit(&runner);
170
171 int pgfLoaded = sceSysmoduleIsLoaded(SCE_SYSMODULE_PGF);
172 if (pgfLoaded != SCE_SYSMODULE_LOADED) {
173 sceSysmoduleLoadModule(SCE_SYSMODULE_PGF);
174 }
175 GUIFontDestroy(font);
176 sceSysmoduleUnloadModule(SCE_SYSMODULE_PGF);
177
178 sceKernelExitProcess(0);
179 return 0;
180}