1 /*---------------------------------------------------------------------------*
2   Project:  Horizon
3   File:     LineSimple.cpp
4 
5   Copyright (C)2009-2012 Nintendo Co., Ltd.  All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law.  They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Rev: 47228 $
14  *---------------------------------------------------------------------------*/
15 
16 /*
17  *------------------------------------------------------------
18  * Copyright(c) 2009-2010 by Digital Media Professionals Inc.
19  * All rights reserved.
20  *------------------------------------------------------------
21  * This source code is the confidential and proprietary
22  * of Digital Media Professionals Inc.
23  *------------------------------------------------------------
24  */
25 #include <string.h>
26 
27 #include <nn/gx.h>
28 #include <nn/math.h>
29 #include <nn/fs.h>
30 #include <nn/os.h>
31 #include <nn/init.h>
32 #include <nn/applet.h>
33 #include <nn/fnd/fnd_ExpHeap.h>
34 
35 #include "demo.h"
36 
37 /* buffer id */
38 GLuint s_ArrayBufferID;
39 GLuint s_ElementArrayBufferID;
40 
41 /* program id */
42 GLuint s_PgID;
43 
44 /* shader id */
45 GLuint s_ShID[2];
46 
47 /* ExpHeap for app. */
48 nn::fnd::ExpHeap s_AppHeap;
49 uptr s_HeapForGx;
50 const u32 s_GxHeapSize = 0x400000;
51 
52 demo::RenderSystem s_RenderSystem;
53 
54 /* generate simple object */
LoadObjects(void)55 static void LoadObjects(void)
56 {
57     GLfloat coords[] = {
58          0.5f, 0.0f, 0.f, 1.f,
59         -0.5f, 0.5f, 0.f, 1.f,
60         -0.5f,-0.5f, 0.f, 1.f
61     };
62     GLfloat color[] = {
63         1.f, 0.0f, 0.0f,
64         0.f, 1.0f, 0.0f,
65         0.f, 0.0f, 1.0f
66     };
67 
68     GLushort idxs[] = {0, 1, 2, 0};
69 
70     glGenBuffers(1, &s_ArrayBufferID);
71     glBindBuffer(GL_ARRAY_BUFFER, s_ArrayBufferID);
72     glBufferData(GL_ARRAY_BUFFER, sizeof(coords) + sizeof(color), 0, GL_STATIC_DRAW);
73     glBufferSubData(GL_ARRAY_BUFFER, 0, sizeof(coords), coords);
74     glBufferSubData(GL_ARRAY_BUFFER, sizeof(coords), sizeof(color), color);
75 
76     glGenBuffers(1, &s_ElementArrayBufferID);
77     glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, s_ElementArrayBufferID);
78     glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(idxs), idxs, GL_STATIC_DRAW);
79 
80     glEnableVertexAttribArray(0);
81     glEnableVertexAttribArray(1);
82 
83     glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 0, 0) ;
84     glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 0, (GLvoid*)sizeof(coords));
85 }
86 
DrawFrame(void)87 int DrawFrame(void)
88 {
89     static int f = 0;
90 
91     s_RenderSystem.SetRenderTarget(NN_GX_DISPLAY0);
92     s_RenderSystem.Clear();
93 
94     nn::math::Matrix44 proj;
95     nn::math::MTX44Frustum(&proj, -0.02f, 0.02f, -0.02f * nn::gx::DISPLAY0_HEIGHT / nn::gx::DISPLAY0_WIDTH,
96                  0.02f * nn::gx::DISPLAY0_HEIGHT / nn::gx::DISPLAY0_WIDTH, 0.1f, 100.f);
97     glUniformMatrix4fv(glGetUniformLocation(s_PgID, "uProjection"), 1, GL_TRUE, static_cast<f32*>(proj));
98 
99     nn::math::Matrix34 eye, rot;
100     nn::math::Vector3 camPos(0.f, 0.4f, 7.5f);
101     nn::math::Vector3 camUp(0.f, 1.f, 0.f);
102     nn::math::Vector3 target(0.f, 0.f, 0.f);
103     nn::math::MTX34LookAt(&eye, &camPos, &camUp, &target);
104     nn::math::MTX34RotXYZDeg(&rot, 0.f, -6.f*f, 0.f);
105 
106     nn::math::MTX34Mult(&eye, &eye, &rot);
107     nn::math::Matrix44 mv(eye);
108     glUniformMatrix4fv(glGetUniformLocation(s_PgID, "uModelView"), 1, GL_TRUE, static_cast<f32*>(mv));
109 
110     glDrawElements(GL_GEOMETRY_PRIMITIVE_DMP, 4, GL_UNSIGNED_SHORT, 0);
111     glFinish();
112 
113     s_RenderSystem.SwapBuffers();
114 
115     s_RenderSystem.SetRenderTarget(NN_GX_DISPLAY1);
116     s_RenderSystem.Clear();
117     s_RenderSystem.SwapBuffers();
118 
119     s_RenderSystem.WaitVsync(NN_GX_DISPLAY_BOTH);
120 
121     f++;
122 
123     return !glGetError();
124 }
125 
126 /* initialization */
Initialize(void)127 static int Initialize(void)
128 {
129     // fs initialization
130     nn::fs::Initialize();
131 
132     const size_t ROMFS_BUFFER_SIZE = 1024 * 64;
133     static char buffer[ROMFS_BUFFER_SIZE];
134     NN_UTIL_PANIC_IF_FAILED(
135         nn::fs::MountRom(16, 16, buffer, ROMFS_BUFFER_SIZE));
136 
137     s_AppHeap.Initialize(nn::os::GetDeviceMemoryAddress(), nn::os::GetDeviceMemorySize() );
138     s_HeapForGx = reinterpret_cast<uptr>(s_AppHeap.Allocate(s_GxHeapSize));
139     /* Initialize display */
140     s_RenderSystem.Initialize(s_HeapForGx, s_GxHeapSize);
141 
142     s_PgID = glCreateProgram();
143     s_ShID[0] = glCreateShader(GL_VERTEX_SHADER);
144     s_ShID[1] = glCreateShader(GL_GEOMETRY_SHADER_DMP);
145 
146     nn::fs::FileReader file(L"rom:/shader.shbin");
147     size_t fileSize = file.GetSize();
148     void* buf = s_AppHeap.Allocate(fileSize);
149 
150     s32 read = file.Read(buf, fileSize);
151     glShaderBinary(2, s_ShID, GL_PLATFORM_BINARY_DMP, buf, read);
152     file.Finalize();
153     s_AppHeap.Free(buf);
154 
155     glAttachShader(s_PgID, s_ShID[0]);
156     glAttachShader(s_PgID, s_ShID[1]);
157     glAttachShader(s_PgID, GL_DMP_FRAGMENT_SHADER_DMP);
158 
159     glBindAttribLocation(s_PgID, 0, "aPosition");
160     glBindAttribLocation(s_PgID, 1, "aColor");
161 
162     glLinkProgram(s_PgID);
163     glValidateProgram(s_PgID);
164     glUseProgram(s_PgID);
165 
166     glClearColor(0.36f, 0.42f, 0.5f, 1.0f);
167     glClearDepthf(1.f);
168 
169     glEnable(GL_DEPTH_TEST);
170     glDepthFunc(GL_LESS);
171     glEnable(GL_CULL_FACE);
172     glFrontFace(GL_CCW);
173     glCullFace(GL_BACK);
174 
175     LoadObjects();
176 
177     /* set line width */
178     GLfloat v[4];
179     GLfloat lwidth = 1.f;
180     v[0] = (GLfloat)nn::gx::DISPLAY0_WIDTH / lwidth;
181     v[1] = (GLfloat)nn::gx::DISPLAY0_HEIGHT / lwidth;
182     v[2] = (GLfloat)nn::gx::DISPLAY0_WIDTH * nn::gx::DISPLAY0_HEIGHT;
183     v[3] = 2.f / lwidth;
184     glUniform4fv(glGetUniformLocation(s_PgID, "dmp_Line.width"), 1, v);
185 
186     glUniform3i(glGetUniformLocation(s_PgID, "dmp_TexEnv[0].srcRgb"), GL_PRIMARY_COLOR, GL_PRIMARY_COLOR, GL_PRIMARY_COLOR);
187     glUniform3i(glGetUniformLocation(s_PgID, "dmp_TexEnv[0].srcAlpha"), GL_PRIMARY_COLOR, GL_PRIMARY_COLOR, GL_PRIMARY_COLOR);
188 
189     return 0;
190 }
191 
nnMain(void)192 void nnMain(void)
193 {
194     // Call only nn::applet::Enable to also allow execution from the HOME Menu
195     // HOME Menu transitions, POWER Button presses, and sleep are all unsupported
196     nn::applet::Enable();
197 
198     /* initialization */
199     if (Initialize() >= 0)
200     {
201         while (1)
202         {
203             (void)DrawFrame();
204         }
205     }
206 
207     /* shutdown_display */
208     s_RenderSystem.Finalize();
209     s_AppHeap.Free(reinterpret_cast<void*>(s_HeapForGx));
210     s_AppHeap.Finalize();
211 }
212