598 |
init += "CombinerParameterNV NUM_GENERAL_COMBINERS_NV %s\n" % stage["num"] |
init += "CombinerParameterNV NUM_GENERAL_COMBINERS_NV %s\n" % stage["num"] |
599 |
|
|
600 |
return init + code |
return init + code |
601 |
|
|
602 |
|
|
603 |
|
|
604 |
|
|
605 |
|
# Fragment program implementation of register combiners |
606 |
|
# Not finished yet |
607 |
|
class fpCombiner: |
608 |
|
def __init__(self): |
609 |
|
self.initializedRegs = {} |
610 |
|
|
611 |
|
self.generalinput = [{} for i in range(0,16)] |
612 |
|
|
613 |
|
self.code = """ |
614 |
|
temp A, B, C, D; |
615 |
|
temp AB, CD, SUM; |
616 |
|
""" |
617 |
|
|
618 |
|
self.colorSumClamp = 0 |
619 |
|
|
620 |
|
self.finalinput = {} |
621 |
|
|
622 |
|
def initreg(self, reg, output = 0): |
623 |
|
initmap = { |
624 |
|
"TEXTURE0": "TXP TEXTURE0, fragment.texcoord[0], texture[0], 2D;", |
625 |
|
"TEXTURE1": "TXP TEXTURE1, fragment.texcoord[1], texture[1], 2D;", |
626 |
|
"TEXTURE2": "TXP TEXTURE2, fragment.texcoord[2], texture[2], 2D;", |
627 |
|
"TEXTURE3": "TXP TEXTURE3, fragment.texcoord[3], texture[3], 2D;", |
628 |
|
"PRIMARY_COLOR_NV": "mov PRIMARY_COLOR_NV, fragment.color.primary;", |
629 |
|
"SECONDARY_COLOR_NV": "mov SECONDARY_COLOR_NV, fragment.color.secondary;", |
630 |
|
"FOG": "mov FOG, state.fog.color;", |
631 |
|
"SPARE0_NV": "mov SPARE0_NV.w, TEXTURE0;", |
632 |
|
"SPARE1_NV": "", |
633 |
|
"CONSTANT_COLOR0_NV": "", |
634 |
|
"CONSTANT_COLOR1_NV": "", |
635 |
|
"ZERO": "mov ZERO, 0;", |
636 |
|
"E_TIMES_F_NV": "MUL E_TIMES_F_NV, E, F;", |
637 |
|
"SPARE0_PLUS_SECONDARY_COLOR_NV": "ADD SPARE0_PLUS_SECONDARY_COLOR_NV, SPARE0, SECONDARY_COLOR_NV;" |
638 |
|
} |
639 |
|
|
640 |
|
if self.colorSumClamp: |
641 |
|
initmap["SPARE0_PLUS_SECONDARY_COLOR_NV"] = "ADD_SAT SPARE0_PLUS_SECONDARY_COLOR_NV, SPARE0, SECONDARY_COLOR_NV;" |
642 |
|
|
643 |
|
if not self.initializedRegs.has_key(reg): |
644 |
|
self.code += "TEMP %s;\n"; |
645 |
|
if not output: |
646 |
|
if reg == "SPARE0_NV": |
647 |
|
self.initreg("TEXTURE0") |
648 |
|
|
649 |
|
self.code += initmap[reg] + "\n"; |
650 |
|
|
651 |
|
self.initializedRegs[reg] = 1 |
652 |
|
|
653 |
|
|
654 |
|
def genInputMapping(var, reg, mapping, comp): |
655 |
|
inmap = { |
656 |
|
# Might need to consider clamping the SIGNED_ mappings, too. |
657 |
|
"UNSIGNED_IDENTITY_NV": "MOV_SAT TMP, %s;\n", |
658 |
|
"UNSIGNED_INVERT_NV": "SUB_SAT TMP, 1, %s;\n", |
659 |
|
"SIGNED_IDENTITY_NV": "MOV TMP, %s;\n", |
660 |
|
"SIGNED_NEGATE_NV": "MOV TMP, -%s;\n", |
661 |
|
"EXPAND_NORMAL_NV": "MOV_SAT TMP, %s; MAD TMP, 2, TMP, -1;\n", |
662 |
|
"EXPAND_NEGATE_NV": "MOV_SAT TMP, %s; MAD TMP, 2, -TMP, 1;\n", |
663 |
|
"HALF_BIAS_NORMAL_NV": "MOV_SAT TMP, %s; SUB TMP, TMP, .5;\n", |
664 |
|
"HALF_BIAS_NEGATE_NV": "MOV_SAT TMP, %s; SUB TMP, .5, TMP;\n", |
665 |
|
} |
666 |
|
|
667 |
|
self.initreg(reg) |
668 |
|
|
669 |
|
if comp == "BLUE": reg += ".z" |
670 |
|
if comp == "ALPHA": reg += ".w" |
671 |
|
|
672 |
|
self.code += inmap[mapping].replace("TMP", var) % reg; |
673 |
|
|
674 |
|
def genOutputMapping(reg, tmp, scale, bias): |
675 |
|
self.initreg(reg, output = 1) |
676 |
|
|
677 |
|
outmap = { |
678 |
|
("SCALE_BY_ONE_HALF_NV","NONE"): "MUL %s, .5, %s;\n", |
679 |
|
("NONE","NONE"): "MOV %s, %s;\n", |
680 |
|
("NONE","BIAS_BY_NEGATIVE_ONE_HALF_NV"): "SUB %s, %s, .5;\n", |
681 |
|
("SCALE_BY_TWO_NV","NONE"): "MUL %s, %s, 2;\n", |
682 |
|
("SCALE_BY_TWO_NV","BIAS_BY_NEGATIVE_ONE_HALF_NV"): "MAD %s, %s, 2, -1", |
683 |
|
("SCALE_BY_FOUR_NV","NONE"): "MUL %s, %s, 4;\n", |
684 |
|
} |
685 |
|
return outmap[(scale,bias)] % (reg, tmp); |
686 |
|
|
687 |
|
|
688 |
|
def genGeneralCombiner(self, abOut, cdOut, sumOut, scale, bias, abDot, cdDot, muxSum, comp = "RGB"): |
689 |
|
suff = "" |
690 |
|
if comp == "ALPHA": suff = ".w" |
691 |
|
|
692 |
|
if abOut != "DISCARD_NV" or sumOut != "DISCARD_NV": |
693 |
|
if abDot: |
694 |
|
self.code += "DP3 AB, A, B;\n" |
695 |
|
else: |
696 |
|
self.code += "MUL AB, A, B;\n" |
697 |
|
|
698 |
|
if abOut != "DISCARD_NV": |
699 |
|
self.genOutputMapping(abOut + suff, "AB", scale, bias); |
700 |
|
|
701 |
|
if cdOut != "DISCARD_NV" or sumOut != "DISCARD_NV": |
702 |
|
if cdDot: |
703 |
|
self.code += "DP3 CD, C, D;\n" |
704 |
|
else: |
705 |
|
self.code += "MUL CD, C, D;\n" |
706 |
|
|
707 |
|
if cdOut != "DISCARD_NV": |
708 |
|
self.genOutputMapping(cdOut + suff, "CD", scale, bias); |
709 |
|
|
710 |
|
if sumOut != "DISCARD_NV": |
711 |
|
if muxSum: |
712 |
|
# FIXME: |
713 |
|
print "ERROR: mux not supported yet!\n" |
714 |
|
else: |
715 |
|
self.code += "ADD SUM, AB, CD;\n" |
716 |
|
self.genOutputMapping(sumOut + suff, "SUM", scale, bias); |
717 |
|
|
718 |
|
|
719 |
|
def genFinalCombiner(self): |
720 |
|
self.code += """ |
721 |
|
# Final combiner |
722 |
|
TEMP E, F, G; |
723 |
|
""" |
724 |
|
|
725 |
|
vars = self.finalinput |
726 |
|
|
727 |
|
# E and F need to be first for the proper initialization order |
728 |
|
for var in "E", "F", "A", "B", "C", "D", "G": |
729 |
|
if vars.has_key(var): |
730 |
|
self.genInputMapping(var, vars[var][0], vars[var][1], vars[var][2]) |
731 |
|
|
732 |
|
self.code += """ |
733 |
|
MAD D, A, B, D; |
734 |
|
TEMP invA; |
735 |
|
SUB invA, 1, A; |
736 |
|
MAD_SAT result.color.xyz, invA, C, D; |
737 |
|
|
738 |
|
MOV result.color.w, G; |
739 |
|
""" |