jak-project/goal_src/jak1/engine/gfx/merc/merc-blend-shape.gc
2022-06-29 22:20:09 -04:00

267 lines
8.6 KiB
Common Lisp

;;-*-Lisp-*-
(in-package goal)
;; name: merc-blend-shape.gc
;; name in dgo: merc-blend-shape
;; dgos: GAME, ENGINE
;; The merc-blend-shape renderer does face animations.
;; This is missing most functions right now, but just has the types that we need for
;; looking into merc.
;; DECOMP BEGINS
(define *stats-blerc* #f)
(deftype blerc-block-header (structure)
((tag generic-merc-tag :inline :offset-assert 0)
(vtx-count uint32 :offset-assert 16)
(overlap uint32 :offset-assert 20)
(lump-dest uint32 :offset-assert 24)
(lump-qwc uint32 :offset-assert 28)
)
:method-count-assert 9
:size-assert #x20
:flag-assert #x900000020
)
(deftype blerc-block (structure)
((output uint8 848 :offset-assert 0)
(header blerc-block-header :inline :offset-assert 848)
)
:method-count-assert 9
:size-assert #x370
:flag-assert #x900000370
)
(deftype blerc-dcache (structure)
((repl-mult vector 40 :inline :offset-assert 0)
)
:method-count-assert 9
:size-assert #x280
:flag-assert #x900000280
)
(deftype blerc-globals (structure)
((first uint32 :offset-assert 0)
(next uint32 :offset-assert 4)
(min-val int16 :offset-assert 8)
(max-val int16 :offset-assert 10)
(fragment-count int32 :offset-assert 12)
(vtx-count int32 :offset-assert 16)
(target-vtx-count int32 :offset-assert 20)
)
:method-count-assert 9
:size-assert #x18
:flag-assert #x900000018
)
(define *blerc-globals* (new 'global 'blerc-globals))
(deftype blerc-context (structure)
((block-a blerc-block :inline :offset-assert 0)
(dummy uint8 7312 :offset-assert 880)
(block-b blerc-block :inline :offset-assert 8192)
)
:method-count-assert 9
:size-assert #x2370
:flag-assert #x900002370
)
(defun-debug blerc-stats-init ()
(when *stats-blerc*
(when (nonzero? (-> *blerc-globals* fragment-count))
(format *stdcon* "~%BLERC (merc blend target) STATS~%")
(format
*stdcon*
" ~D fragments, ~D vertices~%"
(-> *blerc-globals* fragment-count)
(-> *blerc-globals* vtx-count)
)
(format
*stdcon*
" ~D blend target computations (~F average)~%"
(-> *blerc-globals* target-vtx-count)
(/ (the float (-> *blerc-globals* target-vtx-count)) (the float (-> *blerc-globals* vtx-count)))
)
(if (< (-> *blerc-globals* min-val) 0)
(format *stdcon* "MINIMUM OUT OF RANGE: ~D~%" (-> *blerc-globals* min-val))
)
(if (< 255 (-> *blerc-globals* max-val))
(format *stdcon* "MAXIMUM OUT OF RANGE: ~D~%" (-> *blerc-globals* max-val))
)
)
(let ((a0-7 *blerc-globals*))
(set! (-> a0-7 min-val) 255)
(set! (-> a0-7 max-val) 0)
(set! (-> a0-7 fragment-count) 0)
(set! (-> a0-7 vtx-count) 0)
(set! (-> a0-7 target-vtx-count) 0)
)
)
0
(none)
)
(defun blerc-init ()
(blerc-stats-init)
(let ((v1-0 *blerc-globals*))
(set! (-> v1-0 first) (the-as uint 0))
(set! (-> v1-0 next) (the-as uint 0))
)
0
(none)
)
;; todo blerc-a-fragment (unused)
;; todo dma-from-spr (unused)
;; todo merc-dma-chain-to-spr (unused)
;; todo blerc-execute
(def-mips2c blerc-execute (function none))
(define-extern setup-blerc-chains (function merc-ctrl (pointer int16) dma-buffer none))
;; todo merc-blend-shape
(defun merc-blend-shape ((arg0 process-drawable))
(let* ((v1-2 (-> arg0 skel root-channel 0))
(a3-0 (-> v1-2 frame-group))
)
(when (and a3-0
(> (-> arg0 skel active-channels) 0)
(zero? (-> arg0 draw cur-lod))
(logtest? (-> arg0 skel status) (janim-status blerc))
)
(let ((a1-4 (-> a3-0 blerc-data)))
(when a1-4
(let* ((a0-10 (-> arg0 draw mgeo))
(a2-0 (-> a0-10 header blend-target-count))
(t0-0 (-> v1-2 frame-num))
(t1-0 (the int t0-0))
(v1-4 (&+ a1-4 (* (the-as uint t1-0) a2-0)))
(a1-5 (new 'stack-no-clear 'array 'int16 128))
)
(let ((a2-1 (-> a0-10 header blend-target-count)))
(cond
((< t1-0 (+ (-> a3-0 data 0 length) -1))
(let* ((a3-5 (&+ v1-4 a2-1))
(t0-1 (* 64.0 (- t0-0 (the float t1-0))))
(t1-1 (- 64.0 t0-1))
)
(dotimes (t2-0 (the-as int a2-1))
(set! (-> a1-5 t2-0)
(the int (+ (* (the float (+ (-> v1-4 t2-0) -64)) t1-1) (* (the float (+ (-> a3-5 t2-0) -64)) t0-1)))
)
)
)
)
(else
(dotimes (a3-6 (the-as int a2-1))
(set! (-> a1-5 a3-6) (the-as int (* (+ (-> v1-4 a3-6) -64) 64)))
)
)
)
)
(setup-blerc-chains a0-10 a1-5 (-> *display* frames (-> *display* on-screen) frame global-buf))
)
(logior! (-> arg0 skel status) (janim-status blerc-done))
(return (the-as object #f))
)
)
)
)
(when (logtest? (-> arg0 skel status) (janim-status blerc-done))
(logclear! (-> arg0 skel status) (janim-status blerc-done))
(setup-blerc-chains
(-> arg0 draw lod-set lod 0 geo)
(new 'static 'array int16 32 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0)
(-> *display* frames (-> *display* on-screen) frame global-buf)
)
)
0
)
;; TODO setup-blerc-chains-for-one-fragment
(def-mips2c setup-blerc-chains-for-one-fragment (function object object object object object object object))
(defun setup-blerc-chains ((arg0 merc-ctrl) (arg1 (pointer int16)) (arg2 dma-buffer))
(local-vars
(sv-16 uint)
(sv-20 pointer)
(sv-24 merc-effect)
(sv-28 uint)
(sv-32 object)
(sv-48 int)
(sv-64 int)
)
(set! sv-16 (-> arg0 header effect-count))
(let ((s3-0 (-> arg0 header blend-target-count))
(v1-1 (-> arg2 base))
)
(set! sv-20 (&+ v1-1 0))
(let ((a2-1 (the-as object (&+ v1-1 16))))
(if (zero? (-> *blerc-globals* first))
(set! (-> *blerc-globals* first) (the-as uint a2-1))
)
(dotimes (s2-0 (the-as int sv-16))
(set! sv-24 (-> arg0 effect s2-0))
(set! sv-28 (-> sv-24 blend-frag-count))
(when (nonzero? sv-28)
(let ((v1-15 (the-as object (-> sv-24 frag-geo)))
(s1-0 (the-as structure (-> sv-24 frag-ctrl)))
(s0-0 (the-as object (-> sv-24 blend-data)))
)
(set! sv-32 (-> sv-24 blend-ctrl))
(set! sv-48 0)
(while (< sv-48 (the-as int sv-28))
(set! sv-64 (+ (the-as int v1-15)
(logand (* (+ (-> (the-as merc-fragment-control s1-0) unsigned-four-count) 3) 4) #xfff0)
)
)
(if (nonzero? (-> (the-as (pointer uint8) sv-32) 0))
(set! a2-1 (setup-blerc-chains-for-one-fragment s3-0 arg1 a2-1 s0-0 sv-32 sv-64))
)
(let ((a0-14 (logand (+ (* (the-as uint 6) (-> (the-as merc-blend-ctrl sv-32) blend-vtx-count)) 15) #xfff0)))
(set! v1-15
(+ sv-64
(logand (* (+ (-> (the-as merc-fragment-control s1-0) lump-four-count) 3) 4) #xfff0)
(* (-> (the-as merc-fragment-control s1-0) fp-qwc) 16)
)
)
(set! s1-0 (&+ s1-0 (* (-> (the-as merc-fragment-control s1-0) mat-xfer-count) 2) 4))
(set! s0-0
(+ (the-as int s0-0) (* (the-as uint a0-14) (+ (-> (the-as merc-blend-ctrl sv-32) nonzero-index-count) 1)))
)
)
(set! sv-32 (+ (the-as int sv-32) s3-0 2))
(the-as int sv-32)
(set! sv-48 (+ sv-48 1))
)
)
)
)
(set! (-> (the-as (pointer int64) sv-20)) (logior #x20000000 (shr (shl (the-as int a2-1) 33) 1)))
(let ((v1-33 (the-as (pointer uint32) sv-20)))
(set! (-> (&+ v1-33 8)) 0)
)
(let ((v1-34 (the-as (pointer uint32) sv-20)))
(set! (-> (&+ v1-34 12)) 0)
)
(set! (-> arg2 base) (the-as pointer a2-1))
)
)
0
(none)
)