initial commit
This commit is contained in:
+16
@@ -0,0 +1,16 @@
|
||||
*.d
|
||||
*.o
|
||||
*.a
|
||||
*.lib
|
||||
*.dll
|
||||
*.so
|
||||
*.so.*
|
||||
*.dylib
|
||||
*.exe
|
||||
*.out
|
||||
*.dSYM/
|
||||
*.su
|
||||
*.idb
|
||||
*.pdb
|
||||
obj/
|
||||
bin/
|
||||
@@ -0,0 +1,373 @@
|
||||
Mozilla Public License Version 2.0
|
||||
==================================
|
||||
|
||||
1. Definitions
|
||||
--------------
|
||||
|
||||
1.1. "Contributor"
|
||||
means each individual or legal entity that creates, contributes to
|
||||
the creation of, or owns Covered Software.
|
||||
|
||||
1.2. "Contributor Version"
|
||||
means the combination of the Contributions of others (if any) used
|
||||
by a Contributor and that particular Contributor's Contribution.
|
||||
|
||||
1.3. "Contribution"
|
||||
means Covered Software of a particular Contributor.
|
||||
|
||||
1.4. "Covered Software"
|
||||
means Source Code Form to which the initial Contributor has attached
|
||||
the notice in Exhibit A, the Executable Form of such Source Code
|
||||
Form, and Modifications of such Source Code Form, in each case
|
||||
including portions thereof.
|
||||
|
||||
1.5. "Incompatible With Secondary Licenses"
|
||||
means
|
||||
|
||||
(a) that the initial Contributor has attached the notice described
|
||||
in Exhibit B to the Covered Software; or
|
||||
|
||||
(b) that the Covered Software was made available under the terms of
|
||||
version 1.1 or earlier of the License, but not also under the
|
||||
terms of a Secondary License.
|
||||
|
||||
1.6. "Executable Form"
|
||||
means any form of the work other than Source Code Form.
|
||||
|
||||
1.7. "Larger Work"
|
||||
means a work that combines Covered Software with other material, in
|
||||
a separate file or files, that is not Covered Software.
|
||||
|
||||
1.8. "License"
|
||||
means this document.
|
||||
|
||||
1.9. "Licensable"
|
||||
means having the right to grant, to the maximum extent possible,
|
||||
whether at the time of the initial grant or subsequently, any and
|
||||
all of the rights conveyed by this License.
|
||||
|
||||
1.10. "Modifications"
|
||||
means any of the following:
|
||||
|
||||
(a) any file in Source Code Form that results from an addition to,
|
||||
deletion from, or modification of the contents of Covered
|
||||
Software; or
|
||||
|
||||
(b) any new file in Source Code Form that contains any Covered
|
||||
Software.
|
||||
|
||||
1.11. "Patent Claims" of a Contributor
|
||||
means any patent claim(s), including without limitation, method,
|
||||
process, and apparatus claims, in any patent Licensable by such
|
||||
Contributor that would be infringed, but for the grant of the
|
||||
License, by the making, using, selling, offering for sale, having
|
||||
made, import, or transfer of either its Contributions or its
|
||||
Contributor Version.
|
||||
|
||||
1.12. "Secondary License"
|
||||
means either the GNU General Public License, Version 2.0, the GNU
|
||||
Lesser General Public License, Version 2.1, the GNU Affero General
|
||||
Public License, Version 3.0, or any later versions of those
|
||||
licenses.
|
||||
|
||||
1.13. "Source Code Form"
|
||||
means the form of the work preferred for making modifications.
|
||||
|
||||
1.14. "You" (or "Your")
|
||||
means an individual or a legal entity exercising rights under this
|
||||
License. For legal entities, "You" includes any entity that
|
||||
controls, is controlled by, or is under common control with You. For
|
||||
purposes of this definition, "control" means (a) the power, direct
|
||||
or indirect, to cause the direction or management of such entity,
|
||||
whether by contract or otherwise, or (b) ownership of more than
|
||||
fifty percent (50%) of the outstanding shares or beneficial
|
||||
ownership of such entity.
|
||||
|
||||
2. License Grants and Conditions
|
||||
--------------------------------
|
||||
|
||||
2.1. Grants
|
||||
|
||||
Each Contributor hereby grants You a world-wide, royalty-free,
|
||||
non-exclusive license:
|
||||
|
||||
(a) under intellectual property rights (other than patent or trademark)
|
||||
Licensable by such Contributor to use, reproduce, make available,
|
||||
modify, display, perform, distribute, and otherwise exploit its
|
||||
Contributions, either on an unmodified basis, with Modifications, or
|
||||
as part of a Larger Work; and
|
||||
|
||||
(b) under Patent Claims of such Contributor to make, use, sell, offer
|
||||
for sale, have made, import, and otherwise transfer either its
|
||||
Contributions or its Contributor Version.
|
||||
|
||||
2.2. Effective Date
|
||||
|
||||
The licenses granted in Section 2.1 with respect to any Contribution
|
||||
become effective for each Contribution on the date the Contributor first
|
||||
distributes such Contribution.
|
||||
|
||||
2.3. Limitations on Grant Scope
|
||||
|
||||
The licenses granted in this Section 2 are the only rights granted under
|
||||
this License. No additional rights or licenses will be implied from the
|
||||
distribution or licensing of Covered Software under this License.
|
||||
Notwithstanding Section 2.1(b) above, no patent license is granted by a
|
||||
Contributor:
|
||||
|
||||
(a) for any code that a Contributor has removed from Covered Software;
|
||||
or
|
||||
|
||||
(b) for infringements caused by: (i) Your and any other third party's
|
||||
modifications of Covered Software, or (ii) the combination of its
|
||||
Contributions with other software (except as part of its Contributor
|
||||
Version); or
|
||||
|
||||
(c) under Patent Claims infringed by Covered Software in the absence of
|
||||
its Contributions.
|
||||
|
||||
This License does not grant any rights in the trademarks, service marks,
|
||||
or logos of any Contributor (except as may be necessary to comply with
|
||||
the notice requirements in Section 3.4).
|
||||
|
||||
2.4. Subsequent Licenses
|
||||
|
||||
No Contributor makes additional grants as a result of Your choice to
|
||||
distribute the Covered Software under a subsequent version of this
|
||||
License (see Section 10.2) or under the terms of a Secondary License (if
|
||||
permitted under the terms of Section 3.3).
|
||||
|
||||
2.5. Representation
|
||||
|
||||
Each Contributor represents that the Contributor believes its
|
||||
Contributions are its original creation(s) or it has sufficient rights
|
||||
to grant the rights to its Contributions conveyed by this License.
|
||||
|
||||
2.6. Fair Use
|
||||
|
||||
This License is not intended to limit any rights You have under
|
||||
applicable copyright doctrines of fair use, fair dealing, or other
|
||||
equivalents.
|
||||
|
||||
2.7. Conditions
|
||||
|
||||
Sections 3.1, 3.2, 3.3, and 3.4 are conditions of the licenses granted
|
||||
in Section 2.1.
|
||||
|
||||
3. Responsibilities
|
||||
-------------------
|
||||
|
||||
3.1. Distribution of Source Form
|
||||
|
||||
All distribution of Covered Software in Source Code Form, including any
|
||||
Modifications that You create or to which You contribute, must be under
|
||||
the terms of this License. You must inform recipients that the Source
|
||||
Code Form of the Covered Software is governed by the terms of this
|
||||
License, and how they can obtain a copy of this License. You may not
|
||||
attempt to alter or restrict the recipients' rights in the Source Code
|
||||
Form.
|
||||
|
||||
3.2. Distribution of Executable Form
|
||||
|
||||
If You distribute Covered Software in Executable Form then:
|
||||
|
||||
(a) such Covered Software must also be made available in Source Code
|
||||
Form, as described in Section 3.1, and You must inform recipients of
|
||||
the Executable Form how they can obtain a copy of such Source Code
|
||||
Form by reasonable means in a timely manner, at a charge no more
|
||||
than the cost of distribution to the recipient; and
|
||||
|
||||
(b) You may distribute such Executable Form under the terms of this
|
||||
License, or sublicense it under different terms, provided that the
|
||||
license for the Executable Form does not attempt to limit or alter
|
||||
the recipients' rights in the Source Code Form under this License.
|
||||
|
||||
3.3. Distribution of a Larger Work
|
||||
|
||||
You may create and distribute a Larger Work under terms of Your choice,
|
||||
provided that You also comply with the requirements of this License for
|
||||
the Covered Software. If the Larger Work is a combination of Covered
|
||||
Software with a work governed by one or more Secondary Licenses, and the
|
||||
Covered Software is not Incompatible With Secondary Licenses, this
|
||||
License permits You to additionally distribute such Covered Software
|
||||
under the terms of such Secondary License(s), so that the recipient of
|
||||
the Larger Work may, at their option, further distribute the Covered
|
||||
Software under the terms of either this License or such Secondary
|
||||
License(s).
|
||||
|
||||
3.4. Notices
|
||||
|
||||
You may not remove or alter the substance of any license notices
|
||||
(including copyright notices, patent notices, disclaimers of warranty,
|
||||
or limitations of liability) contained within the Source Code Form of
|
||||
the Covered Software, except that You may alter any license notices to
|
||||
the extent required to remedy known factual inaccuracies.
|
||||
|
||||
3.5. Application of Additional Terms
|
||||
|
||||
You may choose to offer, and to charge a fee for, warranty, support,
|
||||
indemnity or liability obligations to one or more recipients of Covered
|
||||
Software. However, You may do so only on Your own behalf, and not on
|
||||
behalf of any Contributor. You must make it absolutely clear that any
|
||||
such warranty, support, indemnity, or liability obligation is offered by
|
||||
You alone, and You hereby agree to indemnify every Contributor for any
|
||||
liability incurred by such Contributor as a result of warranty, support,
|
||||
indemnity or liability terms You offer. You may include additional
|
||||
disclaimers of warranty and limitations of liability specific to any
|
||||
jurisdiction.
|
||||
|
||||
4. Inability to Comply Due to Statute or Regulation
|
||||
---------------------------------------------------
|
||||
|
||||
If it is impossible for You to comply with any of the terms of this
|
||||
License with respect to some or all of the Covered Software due to
|
||||
statute, judicial order, or regulation then You must: (a) comply with
|
||||
the terms of this License to the maximum extent possible; and (b)
|
||||
describe the limitations and the code they affect. Such description must
|
||||
be placed in a text file included with all distributions of the Covered
|
||||
Software under this License. Except to the extent prohibited by statute
|
||||
or regulation, such description must be sufficiently detailed for a
|
||||
recipient of ordinary skill to be able to understand it.
|
||||
|
||||
5. Termination
|
||||
--------------
|
||||
|
||||
5.1. The rights granted under this License will terminate automatically
|
||||
if You fail to comply with any of its terms. However, if You become
|
||||
compliant, then the rights granted under this License from a particular
|
||||
Contributor are reinstated (a) provisionally, unless and until such
|
||||
Contributor explicitly and finally terminates Your grants, and (b) on an
|
||||
ongoing basis, if such Contributor fails to notify You of the
|
||||
non-compliance by some reasonable means prior to 60 days after You have
|
||||
come back into compliance. Moreover, Your grants from a particular
|
||||
Contributor are reinstated on an ongoing basis if such Contributor
|
||||
notifies You of the non-compliance by some reasonable means, this is the
|
||||
first time You have received notice of non-compliance with this License
|
||||
from such Contributor, and You become compliant prior to 30 days after
|
||||
Your receipt of the notice.
|
||||
|
||||
5.2. If You initiate litigation against any entity by asserting a patent
|
||||
infringement claim (excluding declaratory judgment actions,
|
||||
counter-claims, and cross-claims) alleging that a Contributor Version
|
||||
directly or indirectly infringes any patent, then the rights granted to
|
||||
You by any and all Contributors for the Covered Software under Section
|
||||
2.1 of this License shall terminate.
|
||||
|
||||
5.3. In the event of termination under Sections 5.1 or 5.2 above, all
|
||||
end user license agreements (excluding distributors and resellers) which
|
||||
have been validly granted by You or Your distributors under this License
|
||||
prior to termination shall survive termination.
|
||||
|
||||
************************************************************************
|
||||
* *
|
||||
* 6. Disclaimer of Warranty *
|
||||
* ------------------------- *
|
||||
* *
|
||||
* Covered Software is provided under this License on an "as is" *
|
||||
* basis, without warranty of any kind, either expressed, implied, or *
|
||||
* statutory, including, without limitation, warranties that the *
|
||||
* Covered Software is free of defects, merchantable, fit for a *
|
||||
* particular purpose or non-infringing. The entire risk as to the *
|
||||
* quality and performance of the Covered Software is with You. *
|
||||
* Should any Covered Software prove defective in any respect, You *
|
||||
* (not any Contributor) assume the cost of any necessary servicing, *
|
||||
* repair, or correction. This disclaimer of warranty constitutes an *
|
||||
* essential part of this License. No use of any Covered Software is *
|
||||
* authorized under this License except under this disclaimer. *
|
||||
* *
|
||||
************************************************************************
|
||||
|
||||
************************************************************************
|
||||
* *
|
||||
* 7. Limitation of Liability *
|
||||
* -------------------------- *
|
||||
* *
|
||||
* Under no circumstances and under no legal theory, whether tort *
|
||||
* (including negligence), contract, or otherwise, shall any *
|
||||
* Contributor, or anyone who distributes Covered Software as *
|
||||
* permitted above, be liable to You for any direct, indirect, *
|
||||
* special, incidental, or consequential damages of any character *
|
||||
* including, without limitation, damages for lost profits, loss of *
|
||||
* goodwill, work stoppage, computer failure or malfunction, or any *
|
||||
* and all other commercial damages or losses, even if such party *
|
||||
* shall have been informed of the possibility of such damages. This *
|
||||
* limitation of liability shall not apply to liability for death or *
|
||||
* personal injury resulting from such party's negligence to the *
|
||||
* extent applicable law prohibits such limitation. Some *
|
||||
* jurisdictions do not allow the exclusion or limitation of *
|
||||
* incidental or consequential damages, so this exclusion and *
|
||||
* limitation may not apply to You. *
|
||||
* *
|
||||
************************************************************************
|
||||
|
||||
8. Litigation
|
||||
-------------
|
||||
|
||||
Any litigation relating to this License may be brought only in the
|
||||
courts of a jurisdiction where the defendant maintains its principal
|
||||
place of business and such litigation shall be governed by laws of that
|
||||
jurisdiction, without reference to its conflict-of-law provisions.
|
||||
Nothing in this Section shall prevent a party's ability to bring
|
||||
cross-claims or counter-claims.
|
||||
|
||||
9. Miscellaneous
|
||||
----------------
|
||||
|
||||
This License represents the complete agreement concerning the subject
|
||||
matter hereof. If any provision of this License is held to be
|
||||
unenforceable, such provision shall be reformed only to the extent
|
||||
necessary to make it enforceable. Any law or regulation which provides
|
||||
that the language of a contract shall be construed against the drafter
|
||||
shall not be used to construe this License against a Contributor.
|
||||
|
||||
10. Versions of the License
|
||||
---------------------------
|
||||
|
||||
10.1. New Versions
|
||||
|
||||
Mozilla Foundation is the license steward. Except as provided in Section
|
||||
10.3, no one other than the license steward has the right to modify or
|
||||
publish new versions of this License. Each version will be given a
|
||||
distinguishing version number.
|
||||
|
||||
10.2. Effect of New Versions
|
||||
|
||||
You may distribute the Covered Software under the terms of the version
|
||||
of the License under which You originally received the Covered Software,
|
||||
or under the terms of any subsequent version published by the license
|
||||
steward.
|
||||
|
||||
10.3. Modified Versions
|
||||
|
||||
If you create software not governed by this License, and you want to
|
||||
create a new license for such software, you may create and use a
|
||||
modified version of this License if you rename the license and remove
|
||||
any references to the name of the license steward (except to note that
|
||||
such modified license differs from this License).
|
||||
|
||||
10.4. Distributing Source Code Form that is Incompatible With Secondary
|
||||
Licenses
|
||||
|
||||
If You choose to distribute Source Code Form that is Incompatible With
|
||||
Secondary Licenses under the terms of this version of the License, the
|
||||
notice described in Exhibit B of this License must be attached.
|
||||
|
||||
Exhibit A - Source Code Form License Notice
|
||||
-------------------------------------------
|
||||
|
||||
This Source Code Form is subject to the terms of the Mozilla Public
|
||||
License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
file, You can obtain one at https://mozilla.org/MPL/2.0/.
|
||||
|
||||
If it is not possible or desirable to put the notice in a particular
|
||||
file, then You may include the notice in a location (such as a LICENSE
|
||||
file in a relevant directory) where a recipient would be likely to look
|
||||
for such a notice.
|
||||
|
||||
You may add additional accurate notices of copyright ownership.
|
||||
|
||||
Exhibit B - "Incompatible With Secondary Licenses" Notice
|
||||
---------------------------------------------------------
|
||||
|
||||
This Source Code Form is "Incompatible With Secondary Licenses", as
|
||||
defined by the Mozilla Public License, v. 2.0.
|
||||
@@ -0,0 +1,178 @@
|
||||
CLOCK_SRC = src/platform/clock/posix.c
|
||||
INPUT_SRC = src/platform/client/input/sdl.c
|
||||
|
||||
.include "config.mk"
|
||||
|
||||
ENGINE_SRCS = src/skele.c ${CLOCK_SRC}
|
||||
SOFT_PLAT_SRCS = src/platform/client/video/sdl.c ${INPUT_SRC}
|
||||
GL_PLAT_SRCS = src/platform/client/video/gl.c ${INPUT_SRC}
|
||||
SOFT_CLIENT_SRCS = example/client/main.c
|
||||
GL_CLIENT_SRCS = example/gl_client/main.c
|
||||
SERVER_EXAMPLE = example/server/main.c
|
||||
|
||||
LIBSKELE_SRCS = ${ENGINE_SRCS} ${SOFT_PLAT_SRCS}
|
||||
LIBGLSKELE_SRCS = ${ENGINE_SRCS} ${GL_PLAT_SRCS}
|
||||
LIBSKELE_SRV_SRCS = ${ENGINE_SRCS}
|
||||
|
||||
LIBSKELE = ${BIN_DIR}/debug/libskele.a
|
||||
LIBGLSKELE = ${BIN_DIR}/debug/libglskele.a
|
||||
LIBSKELE_SRV = ${BIN_DIR}/debug/libskeleserver.a
|
||||
SKELE_BIN = ${BIN_DIR}/debug/skele_client
|
||||
GLSKELE_BIN = ${BIN_DIR}/debug/glskele_client
|
||||
SERVER_BIN = ${BIN_DIR}/debug/skele_server
|
||||
|
||||
LIBSKELE_R = ${BIN_DIR}/release/libskele.a
|
||||
LIBGLSKELE_R = ${BIN_DIR}/release/libglskele.a
|
||||
LIBSKELE_SRV_R = ${BIN_DIR}/release/libskeleserver.a
|
||||
SKELE_BIN_R = ${BIN_DIR}/release/skele_client
|
||||
GLSKELE_BIN_R = ${BIN_DIR}/release/glskele_client
|
||||
SERVER_BIN_R = ${BIN_DIR}/release/skele_server
|
||||
|
||||
LDFLAGS_PLAT = -L/usr/local/lib
|
||||
CFLAGS_PLAT = -I/usr/local/include
|
||||
CFLAGS_BASE = -Wall -Wpedantic -I${.CURDIR}/${INC_DIR} -std=c99 ${CFLAGS_PLAT} ${DEBUG_FLAGS} \
|
||||
-DGL_MAJOR=${GL_MAJOR} -DGL_MINOR=${GL_MINOR}
|
||||
LINK_STK = -Wl,-Bstatic -lstk -Wl,-Bdynamic
|
||||
|
||||
LIBSKELE_DEBUG_OBJS = ${LIBSKELE_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/soft\//}
|
||||
LIBGLSKELE_DEBUG_OBJS = ${LIBGLSKELE_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/gl\//}
|
||||
LIBSKELE_SRV_DEBUG_OBJS = ${LIBSKELE_SRV_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/server\//}
|
||||
SOFT_CLIENT_DEBUG_OBJS = ${SOFT_CLIENT_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/soft\//}
|
||||
GL_CLIENT_DEBUG_OBJS = ${GL_CLIENT_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/gl\//}
|
||||
SERVER_DEBUG_OBJS = ${SERVER_EXAMPLE:S/.c$/.o/:S/^/${.CURDIR}\/obj\/debug\/server\//}
|
||||
|
||||
LIBSKELE_RELEASE_OBJS = ${LIBSKELE_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/soft\//}
|
||||
LIBGLSKELE_RELEASE_OBJS = ${LIBGLSKELE_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/gl\//}
|
||||
LIBSKELE_SRV_RELEASE_OBJS = ${LIBSKELE_SRV_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/server\//}
|
||||
SOFT_CLIENT_RELEASE_OBJS = ${SOFT_CLIENT_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/soft\//}
|
||||
GL_CLIENT_RELEASE_OBJS = ${GL_CLIENT_SRCS:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/gl\//}
|
||||
SERVER_RELEASE_OBJS = ${SERVER_EXAMPLE:S/.c$/.o/:S/^/${.CURDIR}\/obj\/release\/server\//}
|
||||
|
||||
ALL_SOFT_SRCS = ${LIBSKELE_SRCS} ${SOFT_CLIENT_SRCS}
|
||||
ALL_GL_SRCS = ${LIBGLSKELE_SRCS} ${GL_CLIENT_SRCS}
|
||||
ALL_SERVER_SRCS = ${LIBSKELE_SRV_SRCS} ${SERVER_EXAMPLE}
|
||||
|
||||
PREFIX ?= /usr/local
|
||||
GL_MAJOR ?= 3
|
||||
GL_MINOR ?= 3
|
||||
|
||||
.PHONY: all debug release skele glskele server libs install uninstall clean run run_gl
|
||||
|
||||
all: debug
|
||||
|
||||
debug: ${.CURDIR}/${LIBSKELE} ${.CURDIR}/${LIBGLSKELE} ${.CURDIR}/${LIBSKELE_SRV} \
|
||||
${.CURDIR}/${SKELE_BIN} ${.CURDIR}/${GLSKELE_BIN} ${.CURDIR}/${SERVER_BIN}
|
||||
|
||||
release: ${.CURDIR}/${LIBSKELE_R} ${.CURDIR}/${LIBGLSKELE_R} ${.CURDIR}/${LIBSKELE_SRV_R} \
|
||||
${.CURDIR}/${SKELE_BIN_R} ${.CURDIR}/${GLSKELE_BIN_R} ${.CURDIR}/${SERVER_BIN_R}
|
||||
|
||||
libs: ${.CURDIR}/${LIBSKELE} ${.CURDIR}/${LIBGLSKELE} ${.CURDIR}/${LIBSKELE_SRV}
|
||||
skele: ${.CURDIR}/${LIBSKELE} ${.CURDIR}/${SKELE_BIN}
|
||||
glskele: ${.CURDIR}/${LIBGLSKELE} ${.CURDIR}/${GLSKELE_BIN}
|
||||
server: ${.CURDIR}/${LIBSKELE_SRV} ${.CURDIR}/${SERVER_BIN}
|
||||
|
||||
run: skele
|
||||
${.CURDIR}/${SKELE_BIN}
|
||||
|
||||
run_gl: glskele
|
||||
${.CURDIR}/${GLSKELE_BIN}
|
||||
|
||||
${.CURDIR}/${LIBSKELE}: ${LIBSKELE_DEBUG_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${LIBGLSKELE}: ${LIBGLSKELE_DEBUG_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${LIBSKELE_SRV}: ${LIBSKELE_SRV_DEBUG_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${LIBSKELE_R}: ${LIBSKELE_RELEASE_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${LIBGLSKELE_R}: ${LIBGLSKELE_RELEASE_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${LIBSKELE_SRV_R}: ${LIBSKELE_SRV_RELEASE_OBJS}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
ar rcs ${.TARGET} ${.ALLSRC}
|
||||
|
||||
${.CURDIR}/${SKELE_BIN}: ${SOFT_CLIENT_DEBUG_OBJS} ${.CURDIR}/${LIBSKELE}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -o ${.TARGET} ${SOFT_CLIENT_DEBUG_OBJS} -L${.CURDIR}/${BIN_DIR}/debug -lskele ${LINK_STK} -lSDL3 ${LDFLAGS_PLAT}
|
||||
|
||||
${.CURDIR}/${GLSKELE_BIN}: ${GL_CLIENT_DEBUG_OBJS} ${.CURDIR}/${LIBGLSKELE}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -o ${.TARGET} ${GL_CLIENT_DEBUG_OBJS} -L${.CURDIR}/${BIN_DIR}/debug -lglskele ${LINK_STK} -lSDL3 -lGL ${LDFLAGS_PLAT}
|
||||
|
||||
${.CURDIR}/${SERVER_BIN}: ${SERVER_DEBUG_OBJS} ${.CURDIR}/${LIBSKELE_SRV}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -o ${.TARGET} ${SERVER_DEBUG_OBJS} -L${.CURDIR}/${BIN_DIR}/debug -lskeleserver ${LINK_STK} ${LDFLAGS_PLAT}
|
||||
|
||||
${.CURDIR}/${SKELE_BIN_R}: ${SOFT_CLIENT_RELEASE_OBJS} ${.CURDIR}/${LIBSKELE_R}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -s -o ${.TARGET} ${SOFT_CLIENT_RELEASE_OBJS} -L${.CURDIR}/${BIN_DIR}/release -lskele ${LINK_STK} -lSDL3 ${LDFLAGS_PLAT}
|
||||
|
||||
${.CURDIR}/${GLSKELE_BIN_R}: ${GL_CLIENT_RELEASE_OBJS} ${.CURDIR}/${LIBGLSKELE_R}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -s -o ${.TARGET} ${GL_CLIENT_RELEASE_OBJS} -L${.CURDIR}/${BIN_DIR}/release -lglskele ${LINK_STK} -lSDL3 -lGL ${LDFLAGS_PLAT}
|
||||
|
||||
${.CURDIR}/${SERVER_BIN_R}: ${SERVER_RELEASE_OBJS} ${.CURDIR}/${LIBSKELE_SRV_R}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} -s -o ${.TARGET} ${SERVER_RELEASE_OBJS} -L${.CURDIR}/${BIN_DIR}/release -lskeleserver ${LINK_STK} ${LDFLAGS_PLAT}
|
||||
|
||||
.for _src in ${ALL_SOFT_SRCS}
|
||||
${.CURDIR}/obj/debug/soft/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -g -O0 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
${.CURDIR}/obj/release/soft/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -O2 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
.endfor
|
||||
|
||||
.for _src in ${ALL_GL_SRCS}
|
||||
${.CURDIR}/obj/debug/gl/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -g -O0 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
${.CURDIR}/obj/release/gl/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -O2 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
.endfor
|
||||
|
||||
.for _src in ${ALL_SERVER_SRCS}
|
||||
${.CURDIR}/obj/debug/server/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -g -O0 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
${.CURDIR}/obj/release/server/${_src:S/.c$/.o/}: ${_src}
|
||||
@mkdir -p ${.TARGET:H}
|
||||
${CC} ${CFLAGS_BASE} -O2 -MMD -MP -MT ${.TARGET} -MF ${.TARGET:S/.o$/.d/} -c ${.ALLSRC} -o ${.TARGET}
|
||||
.endfor
|
||||
|
||||
.-include "obj/debug/soft/*.d"
|
||||
.-include "obj/debug/gl/*.d"
|
||||
.-include "obj/debug/server/*.d"
|
||||
.-include "obj/release/soft/*.d"
|
||||
.-include "obj/release/gl/*.d"
|
||||
.-include "obj/release/server/*.d"
|
||||
|
||||
install: release
|
||||
install -d ${PREFIX}/lib
|
||||
install -d ${PREFIX}/include/skele
|
||||
install -m 644 ${.CURDIR}/${LIBSKELE_R} ${PREFIX}/lib/libskele.a
|
||||
install -m 644 ${.CURDIR}/${LIBGLSKELE_R} ${PREFIX}/lib/libglskele.a
|
||||
install -m 644 ${.CURDIR}/${LIBSKELE_SRV_R} ${PREFIX}/lib/libskeleserver.a
|
||||
cp -r ${.CURDIR}/include/ ${PREFIX}/include/skele/
|
||||
install -d ${PREFIX}/bin
|
||||
|
||||
uninstall:
|
||||
rm -f ${PREFIX}/lib/libskele.a
|
||||
rm -f ${PREFIX}/lib/libglskele.a
|
||||
rm -f ${PREFIX}/lib/libskeleserver.a
|
||||
rm -rf ${PREFIX}/include/skele
|
||||
|
||||
clean:
|
||||
rm -rf ${.CURDIR}/${OBJ_DIR} ${.CURDIR}/${BIN_DIR}
|
||||
@@ -0,0 +1,10 @@
|
||||
@echo off
|
||||
if "%1"=="run" (
|
||||
if "%2"=="" (
|
||||
make -f gmake.mk run MODE=debug
|
||||
) else (
|
||||
make -f gmake.mk run MODE=%2
|
||||
)
|
||||
) else (
|
||||
make -f gmake.mk %*
|
||||
)
|
||||
@@ -0,0 +1,51 @@
|
||||
#!/bin/sh
|
||||
|
||||
OS=$(uname -s | tr '[:upper:]' '[:lower:]')
|
||||
|
||||
if [ "$OS" = "freebsd" ]; then
|
||||
MK_FILE="bmake.mk"
|
||||
else
|
||||
MK_FILE="gmake.mk"
|
||||
fi
|
||||
|
||||
if grep -q "Raspberry Pi 5" /proc/device-tree/model 2>/dev/null; then
|
||||
GL_MAJOR=3
|
||||
GL_MINOR=1
|
||||
else
|
||||
GL_MAJOR=3
|
||||
GL_MINOR=3
|
||||
fi
|
||||
|
||||
HAS_INSTALL=0
|
||||
HAS_UNINSTALL=0
|
||||
for arg in "$@"; do
|
||||
case "$arg" in
|
||||
install) HAS_INSTALL=1 ;;
|
||||
uninstall) HAS_UNINSTALL=1 ;;
|
||||
esac
|
||||
done
|
||||
|
||||
if [ "$HAS_INSTALL" = "1" ] || [ "$HAS_UNINSTALL" = "1" ]; then
|
||||
if [ "$HAS_INSTALL" = "1" ]; then
|
||||
make -f "$MK_FILE" release GL_MAJOR=$GL_MAJOR GL_MINOR=$GL_MINOR
|
||||
fi
|
||||
|
||||
if [ "$(id -u)" = "0" ]; then
|
||||
PRIV=""
|
||||
elif command -v doas > /dev/null 2>&1; then
|
||||
PRIV="doas"
|
||||
elif command -v sudo > /dev/null 2>&1; then
|
||||
PRIV="sudo"
|
||||
else
|
||||
echo "error: install requires root. neither doas nor sudo found." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
$PRIV make -f "$MK_FILE" "$@" GL_MAJOR=$GL_MAJOR GL_MINOR=$GL_MINOR
|
||||
elif [ "$1" = "run" ]; then
|
||||
make -f "$MK_FILE" run GL_MAJOR=$GL_MAJOR GL_MINOR=$GL_MINOR
|
||||
elif [ "$1" = "run_gl" ]; then
|
||||
make -f "$MK_FILE" run_gl GL_MAJOR=$GL_MAJOR GL_MINOR=$GL_MINOR
|
||||
else
|
||||
make -f "$MK_FILE" "$@" GL_MAJOR=$GL_MAJOR GL_MINOR=$GL_MINOR
|
||||
fi
|
||||
@@ -0,0 +1,6 @@
|
||||
-std=c99
|
||||
-Wall
|
||||
-Wpedantic
|
||||
-Iinclude
|
||||
-I/usr/local/include
|
||||
-I/usr/include
|
||||
@@ -0,0 +1,13 @@
|
||||
SRC_DIR = src
|
||||
INC_DIR = include
|
||||
OBJ_DIR = obj
|
||||
BIN_DIR = bin
|
||||
|
||||
GL_MAJOR ?= 3
|
||||
GL_MINOR ?= 3
|
||||
|
||||
ENGINE_SRCS = \
|
||||
src/skele.c \
|
||||
$(CLOCK_SRC)
|
||||
|
||||
DEBUG_FLAGS ?=
|
||||
@@ -0,0 +1,82 @@
|
||||
#include "client/blit.h"
|
||||
#include "client/input.h"
|
||||
#include "client/video.h"
|
||||
#include "clock.h"
|
||||
#include "skele.h"
|
||||
#include <stdlib.h>
|
||||
#include <stk/stk.h>
|
||||
#include <string.h>
|
||||
|
||||
static uint8_t running = 1;
|
||||
|
||||
static void on_signal(void) { running = 0; }
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
skele_video_config_t video_cfg;
|
||||
uint64_t last, now, elapsed;
|
||||
uint8_t *pixels;
|
||||
uint32_t total;
|
||||
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
|
||||
skele_clock_init(on_signal);
|
||||
|
||||
if (skele_stk_setup() != SKELE_INIT_SUCCESS)
|
||||
return 1;
|
||||
|
||||
if (skele_init() != SKELE_INIT_SUCCESS) {
|
||||
skele_stk_teardown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
video_cfg.render_width = SKELE_DEFAULT_RENDER_WIDTH;
|
||||
video_cfg.render_height = SKELE_DEFAULT_RENDER_HEIGHT;
|
||||
video_cfg.window_width = 0;
|
||||
video_cfg.window_height = 0;
|
||||
video_cfg.flags = 0;
|
||||
|
||||
if (skele_video_init(video_cfg) != SKELE_INIT_SUCCESS) {
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
total = (uint32_t)(video_cfg.render_width * video_cfg.render_height);
|
||||
pixels = malloc(total);
|
||||
if (!pixels) {
|
||||
skele_video_shutdown();
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
memset(pixels, 0, total);
|
||||
|
||||
last = skele_time_ns();
|
||||
|
||||
while (running) {
|
||||
if (!skele_input_poll())
|
||||
break;
|
||||
|
||||
stk_poll();
|
||||
|
||||
now = skele_time_ns();
|
||||
elapsed = now - last;
|
||||
|
||||
if (elapsed >= skele_tick_ns) {
|
||||
skele_tick();
|
||||
last = now;
|
||||
}
|
||||
|
||||
skele_video_blit(pixels);
|
||||
skele_video_present();
|
||||
}
|
||||
|
||||
free(pixels);
|
||||
skele_video_shutdown();
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
#include "client/input.h"
|
||||
#include "client/video.h"
|
||||
#include "clock.h"
|
||||
#include "skele.h"
|
||||
#include <SDL3/SDL.h>
|
||||
#include <SDL3/SDL_opengl.h>
|
||||
#include <stk/stk.h>
|
||||
|
||||
static uint8_t running = 1;
|
||||
|
||||
static void on_signal(void) { running = 0; }
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
skele_video_config_t video_cfg;
|
||||
uint64_t last;
|
||||
uint64_t now;
|
||||
uint64_t elapsed;
|
||||
|
||||
skele_clock_init(on_signal);
|
||||
|
||||
if (skele_stk_setup() != SKELE_INIT_SUCCESS)
|
||||
return 1;
|
||||
|
||||
if (skele_init() != SKELE_INIT_SUCCESS) {
|
||||
skele_stk_teardown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
video_cfg.render_width = SKELE_DEFAULT_RENDER_WIDTH;
|
||||
video_cfg.render_height = SKELE_DEFAULT_RENDER_HEIGHT;
|
||||
video_cfg.window_width = 0;
|
||||
video_cfg.window_height = 0;
|
||||
video_cfg.flags = 0;
|
||||
|
||||
if (skele_video_init(video_cfg) != SKELE_INIT_SUCCESS) {
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
last = skele_time_ns();
|
||||
|
||||
while (running) {
|
||||
if (!skele_input_poll())
|
||||
break;
|
||||
|
||||
stk_poll();
|
||||
|
||||
now = skele_time_ns();
|
||||
elapsed = now - last;
|
||||
|
||||
if (elapsed >= skele_tick_ns) {
|
||||
skele_tick();
|
||||
last = now;
|
||||
}
|
||||
|
||||
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
|
||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
skele_video_present();
|
||||
}
|
||||
|
||||
skele_video_shutdown();
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
#include "clock.h"
|
||||
#include "skele.h"
|
||||
#include <stk/stk.h>
|
||||
|
||||
static uint8_t running = 1;
|
||||
|
||||
static void on_signal(void) { running = 0; }
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
uint64_t tick_start;
|
||||
uint64_t elapsed;
|
||||
|
||||
skele_clock_init(on_signal);
|
||||
|
||||
if (skele_stk_setup() != SKELE_INIT_SUCCESS)
|
||||
return 1;
|
||||
|
||||
if (skele_init() != SKELE_INIT_SUCCESS) {
|
||||
skele_stk_teardown();
|
||||
return 1;
|
||||
}
|
||||
|
||||
while (running) {
|
||||
tick_start = skele_time_ns();
|
||||
|
||||
stk_poll();
|
||||
skele_tick();
|
||||
|
||||
elapsed = skele_time_ns() - tick_start;
|
||||
if (elapsed < skele_tick_ns)
|
||||
skele_sleep_ns(skele_tick_ns - elapsed);
|
||||
}
|
||||
|
||||
skele_stk_teardown();
|
||||
skele_shutdown();
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,222 @@
|
||||
ifeq ($(OS),Windows_NT)
|
||||
CLOCK_SRC := src/platform/clock/win32.c
|
||||
INPUT_SRC := src/platform/client/input/sdl.c
|
||||
else
|
||||
CLOCK_SRC := src/platform/clock/posix.c
|
||||
INPUT_SRC := src/platform/client/input/sdl.c
|
||||
endif
|
||||
|
||||
include config.mk
|
||||
|
||||
ENGINE_SRCS := src/skele.c $(CLOCK_SRC)
|
||||
SOFT_PLAT_SRCS := src/platform/client/video/sdl.c $(INPUT_SRC)
|
||||
GL_PLAT_SRCS := src/platform/client/video/gl.c $(INPUT_SRC)
|
||||
SOFT_CLIENT_SRCS := example/client/main.c
|
||||
GL_CLIENT_SRCS := example/gl_client/main.c
|
||||
SERVER_EXAMPLE := example/server/main.c
|
||||
|
||||
LIBSKELE_SRCS := $(ENGINE_SRCS) $(SOFT_PLAT_SRCS)
|
||||
LIBGLSKELE_SRCS := $(ENGINE_SRCS) $(GL_PLAT_SRCS)
|
||||
LIBSKELE_SRV_SRCS := $(ENGINE_SRCS)
|
||||
|
||||
ifeq ($(OS),Windows_NT)
|
||||
SHELL := cmd.exe
|
||||
LIBSKELE := $(BIN_DIR)/debug/libskele.a
|
||||
LIBGLSKELE := $(BIN_DIR)/debug/libglskele.a
|
||||
LIBSKELE_SRV := $(BIN_DIR)/debug/libskeleserver.a
|
||||
SKELE_BIN := $(BIN_DIR)/debug/skele_client.exe
|
||||
GLSKELE_BIN := $(BIN_DIR)/debug/glskele_client.exe
|
||||
SERVER_BIN := $(BIN_DIR)/debug/skele_server.exe
|
||||
LIBSKELE_R := $(BIN_DIR)/release/libskele.a
|
||||
LIBGLSKELE_R := $(BIN_DIR)/release/libglskele.a
|
||||
LIBSKELE_SRV_R := $(BIN_DIR)/release/libskeleserver.a
|
||||
SKELE_BIN_R := $(BIN_DIR)/release/skele_client.exe
|
||||
GLSKELE_BIN_R := $(BIN_DIR)/release/glskele_client.exe
|
||||
SERVER_BIN_R := $(BIN_DIR)/release/skele_server.exe
|
||||
LDFLAGS_PLAT :=
|
||||
CFLAGS_PLAT :=
|
||||
MKDIR = if not exist $(subst /,\,$(1)) mkdir $(subst /,\,$(1))
|
||||
RMDIR = if exist $(subst /,\,$(1)) rd /s /q $(subst /,\,$(1))
|
||||
else
|
||||
LIBSKELE := $(BIN_DIR)/debug/libskele.a
|
||||
LIBGLSKELE := $(BIN_DIR)/debug/libglskele.a
|
||||
LIBSKELE_SRV := $(BIN_DIR)/debug/libskeleserver.a
|
||||
SKELE_BIN := $(BIN_DIR)/debug/skele_client
|
||||
GLSKELE_BIN := $(BIN_DIR)/debug/glskele_client
|
||||
SERVER_BIN := $(BIN_DIR)/debug/skele_server
|
||||
LIBSKELE_R := $(BIN_DIR)/release/libskele.a
|
||||
LIBGLSKELE_R := $(BIN_DIR)/release/libglskele.a
|
||||
LIBSKELE_SRV_R := $(BIN_DIR)/release/libskeleserver.a
|
||||
SKELE_BIN_R := $(BIN_DIR)/release/skele_client
|
||||
GLSKELE_BIN_R := $(BIN_DIR)/release/glskele_client
|
||||
SERVER_BIN_R := $(BIN_DIR)/release/skele_server
|
||||
LDFLAGS_PLAT :=
|
||||
CFLAGS_PLAT :=
|
||||
MKDIR = mkdir -p $(1)
|
||||
RMDIR = rm -rf $(1)
|
||||
endif
|
||||
|
||||
ifeq ($(OS),Windows_NT)
|
||||
GL_LIB := -lopengl32
|
||||
LDFLAGS_PLAT :=
|
||||
CFLAGS_PLAT :=
|
||||
else ifeq ($(shell uname),FreeBSD)
|
||||
GL_LIB := -lGL
|
||||
LDFLAGS_PLAT := -L/usr/local/lib
|
||||
CFLAGS_PLAT := -I/usr/local/include
|
||||
else
|
||||
GL_LIB := -lGL
|
||||
LDFLAGS_PLAT :=
|
||||
CFLAGS_PLAT :=
|
||||
endif
|
||||
LINK_STK := -Wl,-Bstatic -lstk -Wl,-Bdynamic
|
||||
RELEASE_LDFLAGS := -s
|
||||
CFLAGS_BASE := -Wall -Wpedantic -I$(INC_DIR) -std=c99 $(CFLAGS_PLAT) $(DEBUG_FLAGS) \
|
||||
-DGL_MAJOR=$(GL_MAJOR) -DGL_MINOR=$(GL_MINOR)
|
||||
|
||||
LIBSKELE_DEBUG_OBJS := $(LIBSKELE_SRCS:%.c=obj/debug/soft/%.o)
|
||||
LIBGLSKELE_DEBUG_OBJS := $(LIBGLSKELE_SRCS:%.c=obj/debug/gl/%.o)
|
||||
LIBSKELE_SRV_DEBUG_OBJS := $(LIBSKELE_SRV_SRCS:%.c=obj/debug/server/%.o)
|
||||
SOFT_CLIENT_DEBUG_OBJS := $(SOFT_CLIENT_SRCS:%.c=obj/debug/soft/%.o)
|
||||
GL_CLIENT_DEBUG_OBJS := $(GL_CLIENT_SRCS:%.c=obj/debug/gl/%.o)
|
||||
SERVER_DEBUG_OBJS := $(SERVER_EXAMPLE:%.c=obj/debug/server/%.o)
|
||||
|
||||
LIBSKELE_RELEASE_OBJS := $(LIBSKELE_SRCS:%.c=obj/release/soft/%.o)
|
||||
LIBGLSKELE_RELEASE_OBJS := $(LIBGLSKELE_SRCS:%.c=obj/release/gl/%.o)
|
||||
LIBSKELE_SRV_RELEASE_OBJS := $(LIBSKELE_SRV_SRCS:%.c=obj/release/server/%.o)
|
||||
SOFT_CLIENT_RELEASE_OBJS := $(SOFT_CLIENT_SRCS:%.c=obj/release/soft/%.o)
|
||||
GL_CLIENT_RELEASE_OBJS := $(GL_CLIENT_SRCS:%.c=obj/release/gl/%.o)
|
||||
SERVER_RELEASE_OBJS := $(SERVER_EXAMPLE:%.c=obj/release/server/%.o)
|
||||
|
||||
PREFIX ?= /usr
|
||||
MODE ?= debug
|
||||
|
||||
.PHONY: all debug release skele glskele server libs \
|
||||
install uninstall clean run run_gl
|
||||
|
||||
all: debug
|
||||
|
||||
debug: \
|
||||
$(LIBSKELE) \
|
||||
$(LIBGLSKELE) \
|
||||
$(LIBSKELE_SRV) \
|
||||
$(SKELE_BIN) \
|
||||
$(GLSKELE_BIN) \
|
||||
$(SERVER_BIN)
|
||||
|
||||
release: \
|
||||
$(LIBSKELE_R) \
|
||||
$(LIBGLSKELE_R) \
|
||||
$(LIBSKELE_SRV_R) \
|
||||
$(SKELE_BIN_R) \
|
||||
$(GLSKELE_BIN_R) \
|
||||
$(SERVER_BIN_R)
|
||||
|
||||
libs: $(LIBSKELE) $(LIBGLSKELE) $(LIBSKELE_SRV)
|
||||
skele: $(LIBSKELE) $(SKELE_BIN)
|
||||
glskele: $(LIBGLSKELE) $(GLSKELE_BIN)
|
||||
server: $(LIBSKELE_SRV) $(SERVER_BIN)
|
||||
|
||||
run: skele
|
||||
$(SKELE_BIN)
|
||||
|
||||
run_gl: glskele
|
||||
$(GLSKELE_BIN)
|
||||
|
||||
$(LIBSKELE): $(LIBSKELE_DEBUG_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(LIBGLSKELE): $(LIBGLSKELE_DEBUG_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(LIBSKELE_SRV): $(LIBSKELE_SRV_DEBUG_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(LIBSKELE_R): $(LIBSKELE_RELEASE_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(LIBGLSKELE_R): $(LIBGLSKELE_RELEASE_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(LIBSKELE_SRV_R): $(LIBSKELE_SRV_RELEASE_OBJS)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(AR) rcs $@ $^
|
||||
|
||||
$(SKELE_BIN): $(SOFT_CLIENT_DEBUG_OBJS) $(LIBSKELE)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) -o $@ $(SOFT_CLIENT_DEBUG_OBJS) -L$(BIN_DIR)/debug -lskele $(LINK_STK) -lSDL3 $(LDFLAGS_PLAT)
|
||||
|
||||
$(GLSKELE_BIN): $(GL_CLIENT_DEBUG_OBJS) $(LIBGLSKELE)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) -o $@ $(GL_CLIENT_DEBUG_OBJS) -L$(BIN_DIR)/debug -lglskele $(LINK_STK) -lSDL3 $(GL_LIB) $(LDFLAGS_PLAT)
|
||||
|
||||
$(SERVER_BIN): $(SERVER_DEBUG_OBJS) $(LIBSKELE_SRV)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) -o $@ $(SERVER_DEBUG_OBJS) -L$(BIN_DIR)/debug -lskeleserver $(LINK_STK) $(LDFLAGS_PLAT)
|
||||
|
||||
$(SKELE_BIN_R): $(SOFT_CLIENT_RELEASE_OBJS) $(LIBSKELE_R)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(RELEASE_LDFLAGS) -o $@ $(SOFT_CLIENT_RELEASE_OBJS) -L$(BIN_DIR)/release -lskele $(LINK_STK) -lSDL3 $(LDFLAGS_PLAT)
|
||||
|
||||
$(GLSKELE_BIN_R): $(GL_CLIENT_RELEASE_OBJS) $(LIBGLSKELE_R)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(RELEASE_LDFLAGS) -o $@ $(GL_CLIENT_RELEASE_OBJS) -L$(BIN_DIR)/release -lglskele $(LINK_STK) -lSDL3 $(GL_LIB) $(LDFLAGS_PLAT)
|
||||
|
||||
$(SERVER_BIN_R): $(SERVER_RELEASE_OBJS) $(LIBSKELE_SRV_R)
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(RELEASE_LDFLAGS) -o $@ $(SERVER_RELEASE_OBJS) -L$(BIN_DIR)/release -lskeleserver $(LINK_STK) $(LDFLAGS_PLAT)
|
||||
|
||||
obj/debug/soft/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -g -O0 -MMD -MP -c $< -o $@
|
||||
|
||||
obj/debug/gl/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -g -O0 -MMD -MP -c $< -o $@
|
||||
|
||||
obj/debug/server/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -g -O0 -MMD -MP -c $< -o $@
|
||||
|
||||
obj/release/soft/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -O2 -MMD -MP -c $< -o $@
|
||||
|
||||
obj/release/gl/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -O2 -MMD -MP -c $< -o $@
|
||||
|
||||
obj/release/server/%.o: %.c
|
||||
@$(call MKDIR,$(@D))
|
||||
$(CC) $(CFLAGS_BASE) -O2 -MMD -MP -c $< -o $@
|
||||
|
||||
-include $(wildcard obj/debug/soft/*.d)
|
||||
-include $(wildcard obj/debug/gl/*.d)
|
||||
-include $(wildcard obj/debug/server/*.d)
|
||||
-include $(wildcard obj/release/soft/*.d)
|
||||
-include $(wildcard obj/release/gl/*.d)
|
||||
-include $(wildcard obj/release/server/*.d)
|
||||
|
||||
install: release
|
||||
install -d $(PREFIX)/lib
|
||||
install -d $(PREFIX)/include/skele
|
||||
install -m 644 $(LIBSKELE_R) $(PREFIX)/lib/libskele.a
|
||||
install -m 644 $(LIBGLSKELE_R) $(PREFIX)/lib/libglskele.a
|
||||
install -m 644 $(LIBSKELE_SRV_R) $(PREFIX)/lib/libskeleserver.a
|
||||
cp -r include/* $(PREFIX)/include/skele/
|
||||
install -d $(PREFIX)/bin
|
||||
|
||||
uninstall:
|
||||
rm -f $(PREFIX)/lib/libskele.a
|
||||
rm -f $(PREFIX)/lib/libglskele.a
|
||||
rm -f $(PREFIX)/lib/libskeleserver.a
|
||||
rm -rf $(PREFIX)/include/skele
|
||||
|
||||
clean:
|
||||
@$(call RMDIR,$(OBJ_DIR))
|
||||
@$(call RMDIR,$(BIN_DIR))
|
||||
@@ -0,0 +1,16 @@
|
||||
#ifndef SKELE_BLIT_H
|
||||
#define SKELE_BLIT_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void skele_video_blit(uint8_t *pixels);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_BLIT_H */
|
||||
@@ -0,0 +1,132 @@
|
||||
#ifndef SKELE_INPUT_H
|
||||
#define SKELE_INPUT_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
SKELE_KEY_UNKNOWN = 0,
|
||||
|
||||
SKELE_KEY_A,
|
||||
SKELE_KEY_B,
|
||||
SKELE_KEY_C,
|
||||
SKELE_KEY_D,
|
||||
SKELE_KEY_E,
|
||||
SKELE_KEY_F,
|
||||
SKELE_KEY_G,
|
||||
SKELE_KEY_H,
|
||||
SKELE_KEY_I,
|
||||
SKELE_KEY_J,
|
||||
SKELE_KEY_K,
|
||||
SKELE_KEY_L,
|
||||
SKELE_KEY_M,
|
||||
SKELE_KEY_N,
|
||||
SKELE_KEY_O,
|
||||
SKELE_KEY_P,
|
||||
SKELE_KEY_Q,
|
||||
SKELE_KEY_R,
|
||||
SKELE_KEY_S,
|
||||
SKELE_KEY_T,
|
||||
SKELE_KEY_U,
|
||||
SKELE_KEY_V,
|
||||
SKELE_KEY_W,
|
||||
SKELE_KEY_X,
|
||||
SKELE_KEY_Y,
|
||||
SKELE_KEY_Z,
|
||||
|
||||
SKELE_KEY_0,
|
||||
SKELE_KEY_1,
|
||||
SKELE_KEY_2,
|
||||
SKELE_KEY_3,
|
||||
SKELE_KEY_4,
|
||||
SKELE_KEY_5,
|
||||
SKELE_KEY_6,
|
||||
SKELE_KEY_7,
|
||||
SKELE_KEY_8,
|
||||
SKELE_KEY_9,
|
||||
|
||||
SKELE_KEY_F1,
|
||||
SKELE_KEY_F2,
|
||||
SKELE_KEY_F3,
|
||||
SKELE_KEY_F4,
|
||||
SKELE_KEY_F5,
|
||||
SKELE_KEY_F6,
|
||||
SKELE_KEY_F7,
|
||||
SKELE_KEY_F8,
|
||||
SKELE_KEY_F9,
|
||||
SKELE_KEY_F10,
|
||||
SKELE_KEY_F11,
|
||||
SKELE_KEY_F12,
|
||||
|
||||
SKELE_KEY_SPACE,
|
||||
SKELE_KEY_ENTER,
|
||||
SKELE_KEY_ESCAPE,
|
||||
SKELE_KEY_TAB,
|
||||
SKELE_KEY_BACKSPACE,
|
||||
SKELE_KEY_LSHIFT,
|
||||
SKELE_KEY_RSHIFT,
|
||||
SKELE_KEY_LCTRL,
|
||||
SKELE_KEY_RCTRL,
|
||||
SKELE_KEY_LALT,
|
||||
SKELE_KEY_RALT,
|
||||
|
||||
SKELE_KEY_UP,
|
||||
SKELE_KEY_DOWN,
|
||||
SKELE_KEY_LEFT,
|
||||
SKELE_KEY_RIGHT,
|
||||
|
||||
SKELE_KEY_COUNT
|
||||
} skele_key_t;
|
||||
|
||||
typedef enum {
|
||||
SKELE_PAD_A,
|
||||
SKELE_PAD_B,
|
||||
SKELE_PAD_X,
|
||||
SKELE_PAD_Y,
|
||||
SKELE_PAD_LB,
|
||||
SKELE_PAD_RB,
|
||||
SKELE_PAD_LT,
|
||||
SKELE_PAD_RT,
|
||||
SKELE_PAD_LSTICK,
|
||||
SKELE_PAD_RSTICK,
|
||||
SKELE_PAD_START,
|
||||
SKELE_PAD_BACK,
|
||||
SKELE_PAD_DPAD_UP,
|
||||
SKELE_PAD_DPAD_DOWN,
|
||||
SKELE_PAD_DPAD_LEFT,
|
||||
SKELE_PAD_DPAD_RIGHT,
|
||||
SKELE_PAD_BUTTON_COUNT
|
||||
} skele_pad_button_t;
|
||||
|
||||
typedef enum {
|
||||
SKELE_PAD_AXIS_LX,
|
||||
SKELE_PAD_AXIS_LY,
|
||||
SKELE_PAD_AXIS_RX,
|
||||
SKELE_PAD_AXIS_RY,
|
||||
SKELE_PAD_AXIS_LT,
|
||||
SKELE_PAD_AXIS_RT,
|
||||
SKELE_PAD_AXIS_COUNT
|
||||
} skele_pad_axis_t;
|
||||
|
||||
#define SKELE_MAX_PADS 4
|
||||
|
||||
uint8_t skele_input_poll(void);
|
||||
|
||||
uint8_t skele_key_down(skele_key_t key);
|
||||
uint8_t skele_key_held(skele_key_t key);
|
||||
|
||||
uint8_t skele_pad_connected(uint8_t pad);
|
||||
uint8_t skele_pad_button_down(uint8_t pad, skele_pad_button_t btn);
|
||||
uint8_t skele_pad_button_held(uint8_t pad, skele_pad_button_t btn);
|
||||
float skele_pad_axis(uint8_t pad, skele_pad_axis_t axis);
|
||||
|
||||
void skele_mouse_delta(int32_t *dx, int32_t *dy);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_INPUT_H */
|
||||
@@ -0,0 +1,21 @@
|
||||
#ifndef SKELE_PALETTE_H
|
||||
#define SKELE_PALETTE_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define SKELE_PALETTE_COLORS 256
|
||||
|
||||
typedef uint32_t skele_palette_t[SKELE_PALETTE_COLORS];
|
||||
|
||||
void skele_palette_set(skele_palette_t pal);
|
||||
void skele_palette_set_index(uint8_t index, uint32_t color);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_PALETTE_H */
|
||||
@@ -0,0 +1,38 @@
|
||||
#ifndef SKELE_VIDEO_H
|
||||
#define SKELE_VIDEO_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define SKELE_VIDEO_FULLSCREEN 0x01
|
||||
#define SKELE_VIDEO_BORDERLESS 0x02
|
||||
#define SKELE_VIDEO_RESIZABLE 0x04
|
||||
#define SKELE_VIDEO_HIGHDPI 0x08
|
||||
|
||||
#define SKELE_DEFAULT_RENDER_WIDTH 320
|
||||
#define SKELE_DEFAULT_RENDER_HEIGHT 200
|
||||
|
||||
typedef struct {
|
||||
uint16_t render_width;
|
||||
uint16_t render_height;
|
||||
uint16_t window_width;
|
||||
uint16_t window_height;
|
||||
uint8_t flags;
|
||||
} skele_video_config_t;
|
||||
|
||||
uint8_t skele_video_init(skele_video_config_t cfg);
|
||||
void skele_video_shutdown(void);
|
||||
void skele_video_present(void);
|
||||
void skele_video_set_title(const char *title);
|
||||
void skele_video_toggle_fullscreen(void);
|
||||
void skele_video_cycle_scale(void);
|
||||
void skele_video_set_mouse_grab(uint8_t grab);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_VIDEO_H */
|
||||
@@ -0,0 +1,18 @@
|
||||
#ifndef SKELE_CLOCK_H
|
||||
#define SKELE_CLOCK_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void skele_clock_init(void (*on_signal)(void));
|
||||
uint64_t skele_time_ns(void);
|
||||
void skele_sleep_ns(uint64_t ns);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_CLOCK_H */
|
||||
@@ -0,0 +1,39 @@
|
||||
#ifndef SKELE_H
|
||||
#define SKELE_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define SKELE_VERSION_MAJOR 0
|
||||
#define SKELE_VERSION_MINOR 0
|
||||
#define SKELE_VERSION_PATCH 0
|
||||
|
||||
#define SKELE_STR(x) #x
|
||||
#define SKELE_XSTR(x) SKELE_STR(x)
|
||||
#define SKELE_VERSION \
|
||||
SKELE_XSTR(SKELE_VERSION_MAJOR) \
|
||||
"." SKELE_XSTR(SKELE_VERSION_MINOR) "." SKELE_XSTR(SKELE_VERSION_PATCH)
|
||||
|
||||
#define SKELE_INIT_SUCCESS 1
|
||||
#define SKELE_INIT_FAILURE 0
|
||||
|
||||
#define SKELE_DEFAULT_TICK_RATE 35
|
||||
|
||||
extern uint64_t skele_tick_ns;
|
||||
|
||||
void skele_set_tick_rate(uint8_t rate);
|
||||
uint8_t skele_init(void);
|
||||
void skele_shutdown(void);
|
||||
void skele_tick(void);
|
||||
|
||||
uint8_t skele_stk_setup(void);
|
||||
void skele_stk_teardown(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* SKELE_H */
|
||||
@@ -0,0 +1,366 @@
|
||||
#include "client/input.h"
|
||||
#include "client/video.h"
|
||||
#include <SDL3/SDL.h>
|
||||
#include <string.h>
|
||||
|
||||
static uint8_t key_held[SKELE_KEY_COUNT];
|
||||
static uint8_t key_down[SKELE_KEY_COUNT];
|
||||
|
||||
static SDL_Gamepad *pads[SKELE_MAX_PADS];
|
||||
static uint8_t pad_btn_held[SKELE_MAX_PADS][SKELE_PAD_BUTTON_COUNT];
|
||||
static uint8_t pad_btn_down[SKELE_MAX_PADS][SKELE_PAD_BUTTON_COUNT];
|
||||
static float pad_axes[SKELE_MAX_PADS][SKELE_PAD_AXIS_COUNT];
|
||||
|
||||
static int32_t mouse_dx = 0;
|
||||
static int32_t mouse_dy = 0;
|
||||
|
||||
static skele_key_t scancode_to_key(SDL_Scancode sc)
|
||||
{
|
||||
switch (sc) {
|
||||
case SDL_SCANCODE_A:
|
||||
return SKELE_KEY_A;
|
||||
case SDL_SCANCODE_B:
|
||||
return SKELE_KEY_B;
|
||||
case SDL_SCANCODE_C:
|
||||
return SKELE_KEY_C;
|
||||
case SDL_SCANCODE_D:
|
||||
return SKELE_KEY_D;
|
||||
case SDL_SCANCODE_E:
|
||||
return SKELE_KEY_E;
|
||||
case SDL_SCANCODE_F:
|
||||
return SKELE_KEY_F;
|
||||
case SDL_SCANCODE_G:
|
||||
return SKELE_KEY_G;
|
||||
case SDL_SCANCODE_H:
|
||||
return SKELE_KEY_H;
|
||||
case SDL_SCANCODE_I:
|
||||
return SKELE_KEY_I;
|
||||
case SDL_SCANCODE_J:
|
||||
return SKELE_KEY_J;
|
||||
case SDL_SCANCODE_K:
|
||||
return SKELE_KEY_K;
|
||||
case SDL_SCANCODE_L:
|
||||
return SKELE_KEY_L;
|
||||
case SDL_SCANCODE_M:
|
||||
return SKELE_KEY_M;
|
||||
case SDL_SCANCODE_N:
|
||||
return SKELE_KEY_N;
|
||||
case SDL_SCANCODE_O:
|
||||
return SKELE_KEY_O;
|
||||
case SDL_SCANCODE_P:
|
||||
return SKELE_KEY_P;
|
||||
case SDL_SCANCODE_Q:
|
||||
return SKELE_KEY_Q;
|
||||
case SDL_SCANCODE_R:
|
||||
return SKELE_KEY_R;
|
||||
case SDL_SCANCODE_S:
|
||||
return SKELE_KEY_S;
|
||||
case SDL_SCANCODE_T:
|
||||
return SKELE_KEY_T;
|
||||
case SDL_SCANCODE_U:
|
||||
return SKELE_KEY_U;
|
||||
case SDL_SCANCODE_V:
|
||||
return SKELE_KEY_V;
|
||||
case SDL_SCANCODE_W:
|
||||
return SKELE_KEY_W;
|
||||
case SDL_SCANCODE_X:
|
||||
return SKELE_KEY_X;
|
||||
case SDL_SCANCODE_Y:
|
||||
return SKELE_KEY_Y;
|
||||
case SDL_SCANCODE_Z:
|
||||
return SKELE_KEY_Z;
|
||||
case SDL_SCANCODE_0:
|
||||
return SKELE_KEY_0;
|
||||
case SDL_SCANCODE_1:
|
||||
return SKELE_KEY_1;
|
||||
case SDL_SCANCODE_2:
|
||||
return SKELE_KEY_2;
|
||||
case SDL_SCANCODE_3:
|
||||
return SKELE_KEY_3;
|
||||
case SDL_SCANCODE_4:
|
||||
return SKELE_KEY_4;
|
||||
case SDL_SCANCODE_5:
|
||||
return SKELE_KEY_5;
|
||||
case SDL_SCANCODE_6:
|
||||
return SKELE_KEY_6;
|
||||
case SDL_SCANCODE_7:
|
||||
return SKELE_KEY_7;
|
||||
case SDL_SCANCODE_8:
|
||||
return SKELE_KEY_8;
|
||||
case SDL_SCANCODE_9:
|
||||
return SKELE_KEY_9;
|
||||
case SDL_SCANCODE_F1:
|
||||
return SKELE_KEY_F1;
|
||||
case SDL_SCANCODE_F2:
|
||||
return SKELE_KEY_F2;
|
||||
case SDL_SCANCODE_F3:
|
||||
return SKELE_KEY_F3;
|
||||
case SDL_SCANCODE_F4:
|
||||
return SKELE_KEY_F4;
|
||||
case SDL_SCANCODE_F5:
|
||||
return SKELE_KEY_F5;
|
||||
case SDL_SCANCODE_F6:
|
||||
return SKELE_KEY_F6;
|
||||
case SDL_SCANCODE_F7:
|
||||
return SKELE_KEY_F7;
|
||||
case SDL_SCANCODE_F8:
|
||||
return SKELE_KEY_F8;
|
||||
case SDL_SCANCODE_F9:
|
||||
return SKELE_KEY_F9;
|
||||
case SDL_SCANCODE_F10:
|
||||
return SKELE_KEY_F10;
|
||||
case SDL_SCANCODE_F11:
|
||||
return SKELE_KEY_F11;
|
||||
case SDL_SCANCODE_F12:
|
||||
return SKELE_KEY_F12;
|
||||
case SDL_SCANCODE_SPACE:
|
||||
return SKELE_KEY_SPACE;
|
||||
case SDL_SCANCODE_RETURN:
|
||||
return SKELE_KEY_ENTER;
|
||||
case SDL_SCANCODE_ESCAPE:
|
||||
return SKELE_KEY_ESCAPE;
|
||||
case SDL_SCANCODE_TAB:
|
||||
return SKELE_KEY_TAB;
|
||||
case SDL_SCANCODE_BACKSPACE:
|
||||
return SKELE_KEY_BACKSPACE;
|
||||
case SDL_SCANCODE_LSHIFT:
|
||||
return SKELE_KEY_LSHIFT;
|
||||
case SDL_SCANCODE_RSHIFT:
|
||||
return SKELE_KEY_RSHIFT;
|
||||
case SDL_SCANCODE_LCTRL:
|
||||
return SKELE_KEY_LCTRL;
|
||||
case SDL_SCANCODE_RCTRL:
|
||||
return SKELE_KEY_RCTRL;
|
||||
case SDL_SCANCODE_LALT:
|
||||
return SKELE_KEY_LALT;
|
||||
case SDL_SCANCODE_RALT:
|
||||
return SKELE_KEY_RALT;
|
||||
case SDL_SCANCODE_UP:
|
||||
return SKELE_KEY_UP;
|
||||
case SDL_SCANCODE_DOWN:
|
||||
return SKELE_KEY_DOWN;
|
||||
case SDL_SCANCODE_LEFT:
|
||||
return SKELE_KEY_LEFT;
|
||||
case SDL_SCANCODE_RIGHT:
|
||||
return SKELE_KEY_RIGHT;
|
||||
default:
|
||||
return SKELE_KEY_UNKNOWN;
|
||||
}
|
||||
}
|
||||
|
||||
static skele_pad_button_t sdl_btn_to_pad(SDL_GamepadButton btn)
|
||||
{
|
||||
switch (btn) {
|
||||
case SDL_GAMEPAD_BUTTON_SOUTH:
|
||||
return SKELE_PAD_A;
|
||||
case SDL_GAMEPAD_BUTTON_EAST:
|
||||
return SKELE_PAD_B;
|
||||
case SDL_GAMEPAD_BUTTON_WEST:
|
||||
return SKELE_PAD_X;
|
||||
case SDL_GAMEPAD_BUTTON_NORTH:
|
||||
return SKELE_PAD_Y;
|
||||
case SDL_GAMEPAD_BUTTON_LEFT_SHOULDER:
|
||||
return SKELE_PAD_LB;
|
||||
case SDL_GAMEPAD_BUTTON_RIGHT_SHOULDER:
|
||||
return SKELE_PAD_RB;
|
||||
case SDL_GAMEPAD_BUTTON_LEFT_STICK:
|
||||
return SKELE_PAD_LSTICK;
|
||||
case SDL_GAMEPAD_BUTTON_RIGHT_STICK:
|
||||
return SKELE_PAD_RSTICK;
|
||||
case SDL_GAMEPAD_BUTTON_START:
|
||||
return SKELE_PAD_START;
|
||||
case SDL_GAMEPAD_BUTTON_BACK:
|
||||
return SKELE_PAD_BACK;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_UP:
|
||||
return SKELE_PAD_DPAD_UP;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_DOWN:
|
||||
return SKELE_PAD_DPAD_DOWN;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_LEFT:
|
||||
return SKELE_PAD_DPAD_LEFT;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_RIGHT:
|
||||
return SKELE_PAD_DPAD_RIGHT;
|
||||
default:
|
||||
return SKELE_PAD_BUTTON_COUNT;
|
||||
}
|
||||
}
|
||||
|
||||
static int8_t pad_slot(SDL_JoystickID id)
|
||||
{
|
||||
uint8_t i;
|
||||
for (i = 0; i < SKELE_MAX_PADS; i++)
|
||||
if (pads[i] && SDL_GetGamepadID(pads[i]) == id)
|
||||
return (int8_t)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int8_t free_slot(void)
|
||||
{
|
||||
uint8_t i;
|
||||
for (i = 0; i < SKELE_MAX_PADS; i++)
|
||||
if (!pads[i])
|
||||
return (int8_t)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
static void update_axes(uint8_t slot)
|
||||
{
|
||||
pad_axes[slot][SKELE_PAD_AXIS_LX] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_LEFTX) / 32767.0f;
|
||||
pad_axes[slot][SKELE_PAD_AXIS_LY] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_LEFTY) / 32767.0f;
|
||||
pad_axes[slot][SKELE_PAD_AXIS_RX] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_RIGHTX) / 32767.0f;
|
||||
pad_axes[slot][SKELE_PAD_AXIS_RY] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_RIGHTY) / 32767.0f;
|
||||
pad_axes[slot][SKELE_PAD_AXIS_LT] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_LEFT_TRIGGER) /
|
||||
32767.0f;
|
||||
pad_axes[slot][SKELE_PAD_AXIS_RT] =
|
||||
SDL_GetGamepadAxis(pads[slot], SDL_GAMEPAD_AXIS_RIGHT_TRIGGER) /
|
||||
32767.0f;
|
||||
}
|
||||
|
||||
uint8_t skele_input_poll(void)
|
||||
{
|
||||
SDL_Event e;
|
||||
skele_key_t key;
|
||||
int8_t slot;
|
||||
uint8_t i;
|
||||
skele_pad_button_t btn;
|
||||
|
||||
memset(key_down, 0, sizeof(key_down));
|
||||
memset(pad_btn_down, 0, sizeof(pad_btn_down));
|
||||
mouse_dx = 0;
|
||||
mouse_dy = 0;
|
||||
|
||||
while (SDL_PollEvent(&e)) {
|
||||
switch (e.type) {
|
||||
case SDL_EVENT_QUIT:
|
||||
return 0;
|
||||
|
||||
case SDL_EVENT_MOUSE_MOTION:
|
||||
mouse_dx += (int32_t)e.motion.xrel;
|
||||
mouse_dy += (int32_t)e.motion.yrel;
|
||||
break;
|
||||
|
||||
case SDL_EVENT_KEY_DOWN:
|
||||
if (e.key.repeat)
|
||||
break;
|
||||
switch (e.key.scancode) {
|
||||
case SDL_SCANCODE_F11:
|
||||
skele_video_toggle_fullscreen();
|
||||
break;
|
||||
case SDL_SCANCODE_F4:
|
||||
skele_video_cycle_scale();
|
||||
break;
|
||||
default:
|
||||
key = scancode_to_key(e.key.scancode);
|
||||
if (key != SKELE_KEY_UNKNOWN) {
|
||||
key_down[key] = 1;
|
||||
key_held[key] = 1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case SDL_EVENT_KEY_UP:
|
||||
key = scancode_to_key(e.key.scancode);
|
||||
if (key != SKELE_KEY_UNKNOWN)
|
||||
key_held[key] = 0;
|
||||
break;
|
||||
|
||||
case SDL_EVENT_GAMEPAD_ADDED:
|
||||
slot = free_slot();
|
||||
if (slot >= 0) {
|
||||
pads[slot] = SDL_OpenGamepad(e.gdevice.which);
|
||||
if (pads[slot])
|
||||
memset(pad_btn_held[slot], 0,
|
||||
sizeof(pad_btn_held[slot]));
|
||||
}
|
||||
break;
|
||||
|
||||
case SDL_EVENT_GAMEPAD_REMOVED:
|
||||
slot = pad_slot(e.gdevice.which);
|
||||
if (slot >= 0) {
|
||||
SDL_CloseGamepad(pads[slot]);
|
||||
pads[slot] = NULL;
|
||||
memset(pad_btn_held[slot], 0,
|
||||
sizeof(pad_btn_held[slot]));
|
||||
memset(pad_axes[slot], 0,
|
||||
sizeof(pad_axes[slot]));
|
||||
}
|
||||
break;
|
||||
|
||||
case SDL_EVENT_GAMEPAD_BUTTON_DOWN:
|
||||
slot = pad_slot(e.gbutton.which);
|
||||
btn =
|
||||
sdl_btn_to_pad((SDL_GamepadButton)e.gbutton.button);
|
||||
if (slot >= 0 && btn != SKELE_PAD_BUTTON_COUNT) {
|
||||
pad_btn_down[slot][btn] = 1;
|
||||
pad_btn_held[slot][btn] = 1;
|
||||
}
|
||||
break;
|
||||
|
||||
case SDL_EVENT_GAMEPAD_BUTTON_UP:
|
||||
slot = pad_slot(e.gbutton.which);
|
||||
btn =
|
||||
sdl_btn_to_pad((SDL_GamepadButton)e.gbutton.button);
|
||||
if (slot >= 0 && btn != SKELE_PAD_BUTTON_COUNT)
|
||||
pad_btn_held[slot][btn] = 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < SKELE_MAX_PADS; i++)
|
||||
if (pads[i])
|
||||
update_axes(i);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
uint8_t skele_key_down(skele_key_t key)
|
||||
{
|
||||
return key < SKELE_KEY_COUNT ? key_down[key] : 0;
|
||||
}
|
||||
|
||||
uint8_t skele_key_held(skele_key_t key)
|
||||
{
|
||||
return key < SKELE_KEY_COUNT ? key_held[key] : 0;
|
||||
}
|
||||
|
||||
uint8_t skele_pad_connected(uint8_t pad)
|
||||
{
|
||||
return pad < SKELE_MAX_PADS ? pads[pad] != NULL : 0;
|
||||
}
|
||||
|
||||
uint8_t skele_pad_button_down(uint8_t pad, skele_pad_button_t btn)
|
||||
{
|
||||
return (pad < SKELE_MAX_PADS && btn < SKELE_PAD_BUTTON_COUNT)
|
||||
? pad_btn_down[pad][btn]
|
||||
: 0;
|
||||
}
|
||||
|
||||
uint8_t skele_pad_button_held(uint8_t pad, skele_pad_button_t btn)
|
||||
{
|
||||
return (pad < SKELE_MAX_PADS && btn < SKELE_PAD_BUTTON_COUNT)
|
||||
? pad_btn_held[pad][btn]
|
||||
: 0;
|
||||
}
|
||||
|
||||
float skele_pad_axis(uint8_t pad, skele_pad_axis_t axis)
|
||||
{
|
||||
return (pad < SKELE_MAX_PADS && axis < SKELE_PAD_AXIS_COUNT)
|
||||
? pad_axes[pad][axis]
|
||||
: 0.0f;
|
||||
}
|
||||
|
||||
void skele_mouse_delta(int32_t *dx, int32_t *dy)
|
||||
{
|
||||
if (dx)
|
||||
*dx = mouse_dx;
|
||||
if (dy)
|
||||
*dy = mouse_dy;
|
||||
}
|
||||
@@ -0,0 +1,179 @@
|
||||
#include "client/video.h"
|
||||
#include "skele.h"
|
||||
#include <SDL3/SDL.h>
|
||||
#include <stk/stk_log.h>
|
||||
|
||||
static SDL_Window *window = NULL;
|
||||
static SDL_GLContext gl_ctx = NULL;
|
||||
static uint16_t vid_w = 0;
|
||||
static uint16_t vid_h = 0;
|
||||
static uint8_t cur_scale = 1;
|
||||
static uint8_t fullscreen = 0;
|
||||
|
||||
static uint8_t max_scale(uint16_t rw, uint16_t rh)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
const SDL_DisplayMode *mode;
|
||||
uint16_t aw, ah;
|
||||
uint8_t scale;
|
||||
|
||||
display =
|
||||
window ? SDL_GetDisplayForWindow(window) : SDL_GetPrimaryDisplay();
|
||||
mode = SDL_GetCurrentDisplayMode(display);
|
||||
if (!mode)
|
||||
return 1;
|
||||
|
||||
aw = (uint16_t)((mode->w * 3) / 4);
|
||||
ah = (uint16_t)((mode->h * 3) / 4);
|
||||
scale = 1;
|
||||
while ((rw * (scale + 1)) <= aw && (rh * (scale + 1)) <= ah)
|
||||
scale++;
|
||||
|
||||
return scale;
|
||||
}
|
||||
|
||||
static void set_scale(uint8_t scale)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
cur_scale = scale;
|
||||
display = SDL_GetDisplayForWindow(window);
|
||||
SDL_SetWindowSize(window, (int)(vid_w * scale), (int)(vid_h * scale));
|
||||
SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED_DISPLAY(display),
|
||||
SDL_WINDOWPOS_CENTERED_DISPLAY(display));
|
||||
}
|
||||
|
||||
static void toggle_fullscreen(void)
|
||||
{
|
||||
fullscreen = !fullscreen;
|
||||
SDL_SetWindowFullscreen(window, fullscreen);
|
||||
}
|
||||
|
||||
static void cycle_scale(void)
|
||||
{
|
||||
uint8_t next;
|
||||
if (fullscreen)
|
||||
return;
|
||||
next = cur_scale + 1;
|
||||
if (next > max_scale(vid_w, vid_h))
|
||||
next = 1;
|
||||
set_scale(next);
|
||||
}
|
||||
|
||||
uint8_t skele_video_init(skele_video_config_t cfg)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
SDL_WindowFlags flags = 0;
|
||||
const SDL_DisplayMode *mode;
|
||||
uint16_t window_w, window_h, aw, ah;
|
||||
|
||||
if (!SDL_Init(SDL_INIT_VIDEO | SDL_INIT_GAMEPAD)) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_Init failed: %s",
|
||||
SDL_GetError());
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, GL_MAJOR);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, GL_MINOR);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK,
|
||||
SDL_GL_CONTEXT_PROFILE_CORE);
|
||||
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
|
||||
|
||||
flags |= SDL_WINDOW_OPENGL;
|
||||
if (cfg.flags & SKELE_VIDEO_FULLSCREEN)
|
||||
flags |= SDL_WINDOW_FULLSCREEN;
|
||||
if (cfg.flags & SKELE_VIDEO_BORDERLESS)
|
||||
flags |= SDL_WINDOW_BORDERLESS;
|
||||
if (cfg.flags & SKELE_VIDEO_RESIZABLE)
|
||||
flags |= SDL_WINDOW_RESIZABLE;
|
||||
if (cfg.flags & SKELE_VIDEO_HIGHDPI)
|
||||
flags |= SDL_WINDOW_HIGH_PIXEL_DENSITY;
|
||||
|
||||
display = SDL_GetPrimaryDisplay();
|
||||
vid_w =
|
||||
cfg.render_width ? cfg.render_width : SKELE_DEFAULT_RENDER_WIDTH;
|
||||
vid_h =
|
||||
cfg.render_height ? cfg.render_height : SKELE_DEFAULT_RENDER_HEIGHT;
|
||||
|
||||
if (cfg.window_width && cfg.window_height) {
|
||||
window_w = cfg.window_width;
|
||||
window_h = cfg.window_height;
|
||||
cur_scale = 1;
|
||||
} else {
|
||||
mode = SDL_GetCurrentDisplayMode(display);
|
||||
if (!mode) {
|
||||
stk_log(STK_LOG_ERROR,
|
||||
"video: SDL_GetCurrentDisplayMode failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
aw = (uint16_t)((mode->w * 3) / 4);
|
||||
ah = (uint16_t)((mode->h * 3) / 4);
|
||||
cur_scale = 1;
|
||||
while ((vid_w * (cur_scale + 1)) <= aw &&
|
||||
(vid_h * (cur_scale + 1)) <= ah)
|
||||
cur_scale++;
|
||||
|
||||
window_w = vid_w * cur_scale;
|
||||
window_h = vid_h * cur_scale;
|
||||
}
|
||||
|
||||
window = SDL_CreateWindow("skele", window_w, window_h,
|
||||
flags | SDL_WINDOW_HIDDEN);
|
||||
if (!window) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_CreateWindow failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED_DISPLAY(display),
|
||||
SDL_WINDOWPOS_CENTERED_DISPLAY(display));
|
||||
|
||||
if (cfg.flags & SKELE_VIDEO_FULLSCREEN)
|
||||
fullscreen = 1;
|
||||
|
||||
gl_ctx = SDL_GL_CreateContext(window);
|
||||
if (!gl_ctx) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_GL_CreateContext failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
SDL_GL_SetSwapInterval(1);
|
||||
SDL_ShowWindow(window);
|
||||
return SKELE_INIT_SUCCESS;
|
||||
}
|
||||
|
||||
void skele_video_shutdown(void)
|
||||
{
|
||||
if (gl_ctx)
|
||||
SDL_GL_DestroyContext(gl_ctx);
|
||||
if (window)
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
gl_ctx = NULL;
|
||||
window = NULL;
|
||||
vid_w = 0;
|
||||
vid_h = 0;
|
||||
cur_scale = 1;
|
||||
fullscreen = 0;
|
||||
}
|
||||
|
||||
void skele_video_present(void) { SDL_GL_SwapWindow(window); }
|
||||
void skele_video_toggle_fullscreen(void) { toggle_fullscreen(); }
|
||||
void skele_video_cycle_scale(void) { cycle_scale(); }
|
||||
|
||||
void skele_video_set_mouse_grab(uint8_t grab)
|
||||
{
|
||||
SDL_SetWindowMouseGrab(window, grab ? true : false);
|
||||
SDL_SetWindowRelativeMouseMode(window, grab ? true : false);
|
||||
}
|
||||
|
||||
void skele_video_set_title(const char *title)
|
||||
{
|
||||
SDL_SetWindowTitle(window, title);
|
||||
}
|
||||
@@ -0,0 +1,253 @@
|
||||
#include "client/blit.h"
|
||||
#include "client/palette.h"
|
||||
#include "client/video.h"
|
||||
#include "skele.h"
|
||||
#include <SDL3/SDL.h>
|
||||
#include <stdint.h>
|
||||
#include <stk/stk_log.h>
|
||||
#include <string.h>
|
||||
|
||||
static SDL_Window *window = NULL;
|
||||
static SDL_Renderer *renderer = NULL;
|
||||
static SDL_Texture *texture = NULL;
|
||||
static SDL_Palette *sdl_pal = NULL;
|
||||
static uint16_t vid_w = 0;
|
||||
static uint16_t vid_h = 0;
|
||||
static uint32_t vid_total = 0;
|
||||
static uint8_t cur_scale = 1;
|
||||
static uint8_t fullscreen = 0;
|
||||
|
||||
static uint8_t max_scale(uint16_t rw, uint16_t rh)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
const SDL_DisplayMode *mode;
|
||||
uint16_t aw, ah;
|
||||
uint8_t scale;
|
||||
|
||||
display =
|
||||
window ? SDL_GetDisplayForWindow(window) : SDL_GetPrimaryDisplay();
|
||||
mode = SDL_GetCurrentDisplayMode(display);
|
||||
if (!mode)
|
||||
return 1;
|
||||
|
||||
aw = (uint16_t)((mode->w * 3) / 4);
|
||||
ah = (uint16_t)((mode->h * 3) / 4);
|
||||
scale = 1;
|
||||
while ((rw * (scale + 1)) <= aw && (rh * (scale + 1)) <= ah)
|
||||
scale++;
|
||||
|
||||
return scale;
|
||||
}
|
||||
|
||||
static void set_scale(uint8_t scale)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
cur_scale = scale;
|
||||
display = SDL_GetDisplayForWindow(window);
|
||||
SDL_SetWindowSize(window, (int)(vid_w * scale), (int)(vid_h * scale));
|
||||
SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED_DISPLAY(display),
|
||||
SDL_WINDOWPOS_CENTERED_DISPLAY(display));
|
||||
}
|
||||
|
||||
static void toggle_fullscreen(void)
|
||||
{
|
||||
fullscreen = !fullscreen;
|
||||
SDL_SetWindowFullscreen(window, fullscreen);
|
||||
}
|
||||
|
||||
static void cycle_scale(void)
|
||||
{
|
||||
uint8_t next;
|
||||
if (fullscreen)
|
||||
return;
|
||||
next = cur_scale + 1;
|
||||
if (next > max_scale(vid_w, vid_h))
|
||||
next = 1;
|
||||
set_scale(next);
|
||||
}
|
||||
|
||||
uint8_t skele_video_init(skele_video_config_t cfg)
|
||||
{
|
||||
SDL_DisplayID display;
|
||||
SDL_WindowFlags flags = 0;
|
||||
const SDL_DisplayMode *mode;
|
||||
uint16_t window_w, window_h, aw, ah;
|
||||
|
||||
if (!SDL_Init(SDL_INIT_VIDEO | SDL_INIT_GAMEPAD)) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_Init failed: %s",
|
||||
SDL_GetError());
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
if (cfg.flags & SKELE_VIDEO_FULLSCREEN)
|
||||
flags |= SDL_WINDOW_FULLSCREEN;
|
||||
if (cfg.flags & SKELE_VIDEO_BORDERLESS)
|
||||
flags |= SDL_WINDOW_BORDERLESS;
|
||||
if (cfg.flags & SKELE_VIDEO_RESIZABLE)
|
||||
flags |= SDL_WINDOW_RESIZABLE;
|
||||
if (cfg.flags & SKELE_VIDEO_HIGHDPI)
|
||||
flags |= SDL_WINDOW_HIGH_PIXEL_DENSITY;
|
||||
|
||||
display = SDL_GetPrimaryDisplay();
|
||||
vid_w =
|
||||
cfg.render_width ? cfg.render_width : SKELE_DEFAULT_RENDER_WIDTH;
|
||||
vid_h =
|
||||
cfg.render_height ? cfg.render_height : SKELE_DEFAULT_RENDER_HEIGHT;
|
||||
vid_total = (uint32_t)(vid_w * vid_h);
|
||||
|
||||
if (cfg.window_width && cfg.window_height) {
|
||||
window_w = cfg.window_width;
|
||||
window_h = cfg.window_height;
|
||||
cur_scale = 1;
|
||||
} else {
|
||||
mode = SDL_GetCurrentDisplayMode(display);
|
||||
if (!mode) {
|
||||
stk_log(STK_LOG_ERROR,
|
||||
"video: SDL_GetCurrentDisplayMode failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
aw = (uint16_t)((mode->w * 3) / 4);
|
||||
ah = (uint16_t)((mode->h * 3) / 4);
|
||||
cur_scale = 1;
|
||||
while ((vid_w * (cur_scale + 1)) <= aw &&
|
||||
(vid_h * (cur_scale + 1)) <= ah)
|
||||
cur_scale++;
|
||||
|
||||
window_w = vid_w * cur_scale;
|
||||
window_h = vid_h * cur_scale;
|
||||
}
|
||||
|
||||
window = SDL_CreateWindow("skele", window_w, window_h,
|
||||
flags | SDL_WINDOW_HIDDEN);
|
||||
if (!window) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_CreateWindow failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
SDL_SetWindowPosition(window, SDL_WINDOWPOS_CENTERED_DISPLAY(display),
|
||||
SDL_WINDOWPOS_CENTERED_DISPLAY(display));
|
||||
|
||||
if (cfg.flags & SKELE_VIDEO_FULLSCREEN)
|
||||
fullscreen = 1;
|
||||
|
||||
renderer = SDL_CreateRenderer(window, NULL);
|
||||
if (!renderer) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_CreateRenderer failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
texture = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_INDEX8,
|
||||
SDL_TEXTUREACCESS_STREAMING, vid_w, vid_h);
|
||||
if (!texture) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_CreateTexture failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_DestroyRenderer(renderer);
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
sdl_pal = SDL_CreatePalette(SKELE_PALETTE_COLORS);
|
||||
if (!sdl_pal) {
|
||||
stk_log(STK_LOG_ERROR, "video: SDL_CreatePalette failed: %s",
|
||||
SDL_GetError());
|
||||
SDL_DestroyTexture(texture);
|
||||
SDL_DestroyRenderer(renderer);
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
SDL_SetTexturePalette(texture, sdl_pal);
|
||||
|
||||
{
|
||||
SDL_Color black[SKELE_PALETTE_COLORS];
|
||||
uint16_t i;
|
||||
memset(black, 0, sizeof(black));
|
||||
for (i = 0; i < SKELE_PALETTE_COLORS; i++)
|
||||
black[i].a = 255;
|
||||
SDL_SetPaletteColors(sdl_pal, black, 0, SKELE_PALETTE_COLORS);
|
||||
}
|
||||
|
||||
SDL_SetTextureScaleMode(texture, SDL_SCALEMODE_NEAREST);
|
||||
SDL_SetRenderVSync(renderer, 1);
|
||||
SDL_ShowWindow(window);
|
||||
return SKELE_INIT_SUCCESS;
|
||||
}
|
||||
|
||||
void skele_video_shutdown(void)
|
||||
{
|
||||
if (sdl_pal)
|
||||
SDL_DestroyPalette(sdl_pal);
|
||||
if (texture)
|
||||
SDL_DestroyTexture(texture);
|
||||
if (renderer)
|
||||
SDL_DestroyRenderer(renderer);
|
||||
if (window)
|
||||
SDL_DestroyWindow(window);
|
||||
SDL_Quit();
|
||||
sdl_pal = NULL;
|
||||
texture = NULL;
|
||||
renderer = NULL;
|
||||
window = NULL;
|
||||
vid_w = 0;
|
||||
vid_h = 0;
|
||||
vid_total = 0;
|
||||
cur_scale = 1;
|
||||
fullscreen = 0;
|
||||
}
|
||||
|
||||
void skele_video_present(void) { SDL_RenderPresent(renderer); }
|
||||
void skele_video_toggle_fullscreen(void) { toggle_fullscreen(); }
|
||||
void skele_video_cycle_scale(void) { cycle_scale(); }
|
||||
|
||||
void skele_video_set_mouse_grab(uint8_t grab)
|
||||
{
|
||||
SDL_SetWindowMouseGrab(window, grab ? true : false);
|
||||
SDL_SetWindowRelativeMouseMode(window, grab ? true : false);
|
||||
}
|
||||
|
||||
void skele_palette_set(skele_palette_t pal)
|
||||
{
|
||||
SDL_Color colors[SKELE_PALETTE_COLORS];
|
||||
uint16_t i;
|
||||
uint32_t c;
|
||||
|
||||
for (i = 0; i < SKELE_PALETTE_COLORS; i++) {
|
||||
c = pal[i];
|
||||
colors[i].r = (uint8_t)(c >> 16);
|
||||
colors[i].g = (uint8_t)(c >> 8);
|
||||
colors[i].b = (uint8_t)(c);
|
||||
colors[i].a = 255;
|
||||
}
|
||||
SDL_SetPaletteColors(sdl_pal, colors, 0, SKELE_PALETTE_COLORS);
|
||||
}
|
||||
|
||||
void skele_palette_set_index(uint8_t index, uint32_t color)
|
||||
{
|
||||
SDL_Color c;
|
||||
c.r = (uint8_t)(color >> 16);
|
||||
c.g = (uint8_t)(color >> 8);
|
||||
c.b = (uint8_t)(color);
|
||||
c.a = 255;
|
||||
SDL_SetPaletteColors(sdl_pal, &c, index, 1);
|
||||
}
|
||||
|
||||
void skele_video_blit(uint8_t *pixels)
|
||||
{
|
||||
SDL_UpdateTexture(texture, NULL, pixels, vid_w);
|
||||
SDL_RenderTexture(renderer, texture, NULL, NULL);
|
||||
}
|
||||
|
||||
void skele_video_set_title(const char *title)
|
||||
{
|
||||
SDL_SetWindowTitle(window, title);
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
#define _POSIX_C_SOURCE 199309L
|
||||
#include "clock.h"
|
||||
#include <signal.h>
|
||||
#include <time.h>
|
||||
|
||||
static void (*signal_cb)(void) = NULL;
|
||||
|
||||
static void handle_signal(int sig)
|
||||
{
|
||||
(void)sig;
|
||||
if (signal_cb)
|
||||
signal_cb();
|
||||
}
|
||||
|
||||
void skele_clock_init(void (*on_signal)(void))
|
||||
{
|
||||
signal_cb = on_signal;
|
||||
signal(SIGINT, handle_signal);
|
||||
signal(SIGTERM, handle_signal);
|
||||
}
|
||||
|
||||
uint64_t skele_time_ns(void)
|
||||
{
|
||||
struct timespec ts;
|
||||
clock_gettime(CLOCK_MONOTONIC, &ts);
|
||||
return (uint64_t)(ts.tv_sec * 1000000000ULL + ts.tv_nsec);
|
||||
}
|
||||
|
||||
void skele_sleep_ns(uint64_t ns)
|
||||
{
|
||||
struct timespec ts;
|
||||
ts.tv_sec = (time_t)(ns / 1000000000ULL);
|
||||
ts.tv_nsec = (long)(ns % 1000000000ULL);
|
||||
nanosleep(&ts, NULL);
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
#include "clock.h"
|
||||
#include <windows.h>
|
||||
|
||||
static void (*signal_cb)(void) = NULL;
|
||||
static LARGE_INTEGER perf_freq;
|
||||
|
||||
static BOOL WINAPI handle_ctrl(DWORD type)
|
||||
{
|
||||
(void)type;
|
||||
if (signal_cb)
|
||||
signal_cb();
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void skele_clock_init(void (*on_signal)(void))
|
||||
{
|
||||
signal_cb = on_signal;
|
||||
QueryPerformanceFrequency(&perf_freq);
|
||||
SetConsoleCtrlHandler(handle_ctrl, TRUE);
|
||||
}
|
||||
|
||||
uint64_t skele_time_ns(void)
|
||||
{
|
||||
LARGE_INTEGER cnt;
|
||||
QueryPerformanceCounter(&cnt);
|
||||
return (uint64_t)(cnt.QuadPart * 1000000000ULL / perf_freq.QuadPart);
|
||||
}
|
||||
|
||||
void skele_sleep_ns(uint64_t ns)
|
||||
{
|
||||
HANDLE timer = CreateWaitableTimer(NULL, TRUE, NULL);
|
||||
LARGE_INTEGER li;
|
||||
li.QuadPart = -(LONGLONG)(ns / 100);
|
||||
SetWaitableTimer(timer, &li, 0, NULL, NULL, FALSE);
|
||||
WaitForSingleObject(timer, INFINITE);
|
||||
CloseHandle(timer);
|
||||
}
|
||||
+51
@@ -0,0 +1,51 @@
|
||||
#include "skele.h"
|
||||
#include <stk/stk.h>
|
||||
#include <stk/stk_log.h>
|
||||
|
||||
uint64_t skele_tick_ns = 1000000000ULL / SKELE_DEFAULT_TICK_RATE;
|
||||
|
||||
static uint8_t stk_initialized = 0;
|
||||
|
||||
const char *skele_version(void) { return "0.0.0"; }
|
||||
|
||||
void skele_set_tick_rate(uint8_t rate)
|
||||
{
|
||||
skele_tick_ns = 1000000000ULL / (rate ? rate : SKELE_DEFAULT_TICK_RATE);
|
||||
}
|
||||
|
||||
uint8_t skele_init(void) { return SKELE_INIT_SUCCESS; }
|
||||
|
||||
void skele_shutdown(void) {}
|
||||
|
||||
void skele_tick(void) {}
|
||||
|
||||
uint8_t skele_stk_setup(void)
|
||||
{
|
||||
if (stk_initialized)
|
||||
return SKELE_INIT_SUCCESS;
|
||||
|
||||
stk_set_log_prefix("skele");
|
||||
stk_set_module_init_fn("skele_mod_init");
|
||||
stk_set_module_shutdown_fn("skele_mod_shutdown");
|
||||
stk_set_module_name_fn("skele_mod_name");
|
||||
stk_set_module_version_fn("skele_mod_ver");
|
||||
stk_set_module_description_fn("skele_mod_desc");
|
||||
stk_set_module_deps_sym("skele_mod_deps");
|
||||
|
||||
if (stk_init() != STK_INIT_SUCCESS) {
|
||||
stk_log(STK_LOG_ERROR, "failed to initialize stk");
|
||||
return SKELE_INIT_FAILURE;
|
||||
}
|
||||
|
||||
stk_initialized = 1;
|
||||
stk_log(STK_LOG_INFO, "skele v%s", SKELE_VERSION);
|
||||
return SKELE_INIT_SUCCESS;
|
||||
}
|
||||
|
||||
void skele_stk_teardown(void)
|
||||
{
|
||||
if (!stk_initialized)
|
||||
return;
|
||||
stk_shutdown();
|
||||
stk_initialized = 0;
|
||||
}
|
||||
Reference in New Issue
Block a user