This commit is contained in:
Peter S. May
2014-11-24 13:31:23 -05:00
50 changed files with 1122 additions and 181 deletions
+11 -1
View File
@@ -2,7 +2,17 @@ local Color1 = color(Var "Color1");
local t = Def.ActorFrame {
LoadActor(Var "File1") .. {
OnCommand=cmd(x,SCREEN_CENTER_X;y,SCREEN_CENTER_Y;scale_or_crop_background;diffuse,Color1;loop,false;effectclock,"music");
OnCommand=function(self)
self:xy(SCREEN_CENTER_X,SCREEN_CENTER_Y)
self:scale_or_crop_background()
self:diffuse(Color1)
if self.loop ~= nil then
self:loop(false)
-- make videos start at beginning to prevent sticking on last frame
self:position(0)
end
self:effectclock("music")
end;
GainFocusCommand=cmd(play);
LoseFocusCommand=cmd(pause);
};
+9 -1
View File
@@ -2,7 +2,15 @@ local Color1 = color(Var "Color1");
local t = Def.ActorFrame {
LoadActor(Var "File1") .. {
OnCommand=cmd(x,SCREEN_CENTER_X;y,SCREEN_CENTER_Y;scale_or_crop_background;diffuse,Color1;position,0;effectclock,"music");
OnCommand=function(self)
self:xy(SCREEN_CENTER_X,SCREEN_CENTER_Y)
self:scale_or_crop_background()
self:diffuse(Color1)
if self.position ~= nil then
self:position(0)
end
self:effectclock("music")
end;
GainFocusCommand=cmd(play);
LoseFocusCommand=cmd(pause);
};
+30 -5
View File
@@ -4,22 +4,47 @@ The StepMania 5 Changelog covers all post-sm-ssc changes. For a list of changes
from StepMania 4 alpha 5 to sm-ssc v1.2.5, see Changelog_sm-ssc.txt.
________________________________________________________________________________
2014/11/15
----------
* [Preferences] Default Fail Type preference mechanism changed internally again.
Set your Default Fail Type preference again.
2014/11/05
----------
* [ScreenPrompt] Answer OnCommand metrics fixed to actually work.
2014/11/01
----------
* [RollingNumbers] Cropping and color during tweens fixed.
2014/10/23
----------
* [Global] approach, multiapproach, lerp, and lerp_color lua functions added.
2014/10/20
----------
* [StageStats] GetStepsSeconds function added.
* [Steps] If an unrecognized step type is saved, preserve that step instead of
deleting it. A warning will be placed in the log file during song load.
================================================================================
StepMania 5.0 beta 4a | 20141015
--------------------------------------------------------------------------------
2014/10/19
----------
* [BackgroundEffects] Fixed errors in StretchNoLoop and StretchRewind.
2014/10/13
----------
* [NoteDisplay] Var Player and Var Controller work for non-receptor arrows.
* [NoteDisplay] Var Player and Var Controller work for non-receptor arrows. [hanubeki]
* [Mac OS X] Allow StepMania to be built and run in Yosemite.
2014/10/11
----------
* [NoteDisplay] Add two noteskin metrics, {PartName}NoteColorType and
{PartName}NoteColorCount. View https://github.com/stepmania/stepmania/pull/328
for more information.
* [Steps] If an unrecognized step type is saved, preserve that step instead of
deleting it. A warning will be placed in the log file during song load.
{PartName}NoteColorCount. View https://github.com/stepmania/stepmania/pull/328
for more information. [hanubeki]
================================================================================
StepMania 5.0 beta 4 | 20140930
+5
View File
@@ -203,6 +203,7 @@
<Function name='WriteGamePrefToFile'/>
<Function name='WritePrefToFile'/>
<Function name='Year'/>
<Function name='approach'/>
<Function name='assert'/>
<Function name='clamp'/>
<Function name='class'/>
@@ -219,11 +220,14 @@
<Function name='ipairs'/>
<Function name='ivalues'/>
<Function name='join'/>
<Function name='lerp'/>
<Function name='lerp_color'/>
<Function name='load'/>
<Function name='loadfile'/>
<Function name='loadstring'/>
<Function name='mbstrlen'/>
<Function name='module'/>
<Function name='multiapproach'/>
<Function name='newproxy'/>
<Function name='next'/>
<Function name='pairs'/>
@@ -1584,6 +1588,7 @@
<Function name='GetPossibleSongs'/>
<Function name='GetStage'/>
<Function name='GetStageIndex'/>
<Function name='GetStepsSeconds'/>
<Function name='OnePassed'/>
<Function name='PlayerHasHighScore'/>
</Class>
+26 -8
View File
@@ -31,6 +31,10 @@ save yourself some time, copy this for undocumented things:
<Function name='Alpha' theme='_fallback' return='color' arguments='color c, float percent'>
[02 Colors.lua] Returns a <code>color</code> with the specified alpha.
</Function>
<Function name='approach' return='float' arguments='float current, float goal, float speed'>
Use this to make a current value approach a goal value at the given speed. Speed must not be negative. The value will not overshoot the goal.<br />
Note: When you see the error "approach: speed 1 is negative." it means that the speed value passed was negative. The 1 is there because approach and multiapproach use the same internal function and can be ignored when using approach.
</Function>
<Function name='ArbitrarySpeedMods' theme='_fallback' return='LuaOptionRow' arguments=''>
[03 CustomSpeedMods.lua]
</Function>
@@ -136,7 +140,7 @@ save yourself some time, copy this for undocumented things:
[03 Gameplay.lua]
</Function>
<Function name='fapproach' theme='_fallback' return='float' arguments='float val, float other_val, float to_move'>
[02 Utilities.lua]
[02 Utilities.lua] Old name for approach.
</Function>
<Function name='FindSelection' theme='_fallback' return='int' arguments='table list'>
[02 Utilities.lua] Return the index of a true value in <code>list</code>.
@@ -327,6 +331,12 @@ save yourself some time, copy this for undocumented things:
<Function name='JudgmentLineToStrokeColor' theme='_fallback' return='color' arguments='JudgmentLine jl'>
[02 Colors.lua]
</Function>
<Function name='lerp' return='float' arguments='float percent, float start, float end'>
Returns a number linearly interpolated between start and end by percent.
</Function>
<Function name='lerp_color' return='color' arguments='float percent, color start, color end'>
Same as lerp, but for colors. All channels will reach the end of the interpolation at the same time.
</Function>
<Function name='LoadActor' return='ActorDef' arguments='string sPath, ...'>
Returns an Actor definition for the actor at <code>sPath</code>. If <code>sPath</code> points to a Lua file, any additional arguments will be passed to that script.
</Function>
@@ -369,6 +379,11 @@ save yourself some time, copy this for undocumented things:
<Function name='MonthToString' return='string' arguments='Month m'>
Returns Month <code>m</code> as a string.
</Function>
<Function name='multiapproach' return='table' arguments='table currents, table goals, table speeds'>
Similar to approach, but operates on tables of values instead of single values. This will modify the contents of <code>currents</code> in place, as well as returning <code>currents</code>.<br />
<code>currents</code>, <code>goals</code>, and <code>speeds</code> must all be the same size and contain only numbers.<br />
Note: When you see the error "approach: speed 1 is negative." it means that a speed value passed was negative. The 1 tells you which entry in the table was invalid.
</Function>
<Function name='next' return='void' arguments='table t, int index'>
"Allows a program to traverse all fields of a table. Its first argument is a
table and its second argument is an index in this table.
@@ -969,7 +984,7 @@ save yourself some time, copy this for undocumented things:
Sets the Actor's alpha level to <code>fAlpha</code>, where <code>fAlpha</code> is in the range 0..1.
</Function>
<Function name='diffuseblink' return='void' arguments=''>
Makes the Actor switch between two colors immediately.
Makes the Actor switch between two colors immediately. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='diffusebottomedge' return='void' arguments=''>
Sets the Actor's bottom edge color to <code>c</code>.
@@ -987,13 +1002,13 @@ save yourself some time, copy this for undocumented things:
Sets the Actor's lower right corner color to <code>c</code>.
</Function>
<Function name='diffuseramp' return='void' arguments=''>
Makes the Actor switch between two colors, jumping back to the first after reaching the second.
Makes the Actor switch between two colors, jumping back to the first after reaching the second. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='diffuserightedge' return='void' arguments='color c'>
Sets the Actor's right edge color to <code>c</code>.
</Function>
<Function name='diffuseshift' return='void' arguments=''>
Makes the Actor shift between two colors smoothly.
Makes the Actor shift between two colors smoothly. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='diffusetopedge' return='void' arguments='color c'>
Sets the Actor's top edge color to <code>c</code>.
@@ -1129,13 +1144,13 @@ save yourself some time, copy this for undocumented things:
Sets the Actor's glow color.
</Function>
<Function name='glowblink' return='void' arguments=''>
Makes the Actor glow between two colors immediately.
Makes the Actor glow between two colors immediately. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='glowramp' return='void' arguments=''>
Makes the Actor glow between two colors smoothly, jumping back to the first at the end.
Makes the Actor glow between two colors smoothly, jumping back to the first at the end. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='glowshift' return='void' arguments=''>
Makes the Actor glow between two colors smoothly.
Makes the Actor glow between two colors smoothly. See Themerdocs/effect_colors.txt for an example.
</Function>
<Function name='halign' return='void' arguments='float fAlign'>
Set the fractional horizontal alignment of the Actor according to <code>fAlign</code> which should be a float in the range 0..1. An alignment of 0 is left aligned while an alignment of 1 is right aligned. See <Link function='horizalign' /> for the common case.
@@ -1192,7 +1207,7 @@ save yourself some time, copy this for undocumented things:
Basically creates a command named <code>!sMessageName</code> (Note the ! at the beginning. The source code says this: "Hack: use "!" as a marker to broadcast a command, instead of playing a command, so we don't have to add yet another element to every tween state for this rarely-used command.")
</Function>
<Function name='rainbow' return='void' arguments=''>
Makes the Actor change colors continually using colors of the rainbow.
Makes the Actor change colors continually using colors of the rainbow. Each channel follows a cosine wave, red starts at 0, green starts at 2pi/3, and blue starts at 4pi/3.
</Function>
<Function name='roll' return='void' arguments='float fRoll'>
Sets the roll of this Actor to <code>fRoll</code>.
@@ -2464,6 +2479,9 @@ save yourself some time, copy this for undocumented things:
<Function name='GetStageIndex' return='int' arguments=''>
Returns the current stage index.
</Function>
<Function name='GetStepsSeconds' return='float' arguments=''>
Returns the current StepsSeconds, which is the time value used to set the samples in a player's life record.
</Function>
<Function name='GetStageSeed' return='int' arguments=''>
Return the random seed for the current stage.
</Function>
+287
View File
@@ -0,0 +1,287 @@
Don't try to change the way keys are mapped in edit mode unless you have a good reason. It's complicated and easy to mess up.
If you do make a mistake, you can go back to the default edit mode keymapping just by removing the "User Data Folder/Save/EditMode_Keymaps.ini" file.
Edit Mode loads key mapping settings from "User Data Folder/Save/EditMode_Keymaps.ini". "User Data Folder" is a special name that means the folder where all your user data for stepmania is stored, the name depends on what OS you're on. See Docs/Userdocs/sm5_beginner.txt and search for "User Data Folder" to learn where it is on your OS.
Entries in EditMode_Keymaps.ini set which what keys trigger an action. Any function that doesn't have an entry in EditMode_Keymaps.ini will use the default mapping. Be careful when choosing a key for a function to make sure that same key isn't already mapped to something else either in the default mapping or in the mapping you are creating.
If you hold F3, you can use the Debug Menu to reload the screen while in Edit Mode, which will reload the key mapping, so you can adjust the mapping while stepmania is running.
EditMode_Keymaps.ini is broken up into four sections, one for each major mode that Edit Mode can be in. The "Edit" section is for when in normal editing mode. The "Play" section is for when Edit Mode is playing back a song. The "Record" section is for record mode, and the "RecordPaused" section is for when Record mode is paused.
Each line in a section is the name of the function being set, followed by "=", then the name of the key for that function. You can list two keys by seperating them with a ":". Examples:
SNAP_NEXT=Key_s
SNAP_PREV=Key_d:Key_v
Note that you cannot change which keys need to be held down for certain things, like holding shift for rolls.
Next will be a list of function names (headed by "Function Names"), then a list of key names (headed by "Key Names"), then the default key mapping (headed by "Default Mapping") as an example.
Function Names:
COLUMN_0
COLUMN_1
COLUMN_2
COLUMN_3
COLUMN_4
COLUMN_5
COLUMN_6
COLUMN_7
COLUMN_8
COLUMN_9
RIGHT_SIDE
LAY_ROLL
LAY_TAP_ATTACK
REMOVE_NOTE
CYCLE_TAP_LEFT
CYCLE_TAP_RIGHT
CYCLE_SEGMENT_LEFT
CYCLE_SEGMENT_RIGHT
SCROLL_UP_LINE
SCROLL_UP_PAGE
SCROLL_UP_TS
SCROLL_DOWN_LINE
SCROLL_DOWN_PAGE
SCROLL_DOWN_TS
SCROLL_NEXT_MEASURE
SCROLL_PREV_MEASURE
SCROLL_HOME
SCROLL_END
SCROLL_NEXT
SCROLL_PREV
SEGMENT_NEXT
SEGMENT_PREV
SCROLL_SELECT
LAY_SELECT
SCROLL_SPEED_UP
SCROLL_SPEED_DOWN
SNAP_NEXT
SNAP_PREV
OPEN_EDIT_MENU
OPEN_TIMING_MENU
OPEN_ALTER_MENU
OPEN_AREA_MENU
OPEN_BGCHANGE_LAYER1_MENU
OPEN_BGCHANGE_LAYER2_MENU
OPEN_COURSE_MENU
OPEN_COURSE_ATTACK_MENU
OPEN_STEP_ATTACK_MENU
ADD_STEP_MODS
OPEN_INPUT_HELP
BAKE_RANDOM_FROM_SONG_GROUP
BAKE_RANDOM_FROM_SONG_GROUP_AND_GENRE
PLAY_FROM_START
PLAY_FROM_CURSOR
PLAY_SELECTION
RECORD_FROM_CURSOR
RECORD_SELECTION
RETURN_TO_EDIT
INSERT
DELETE
INSERT_SHIFT_PAUSES
DELETE_SHIFT_PAUSES
OPEN_NEXT_STEPS
OPEN_PREV_STEPS
PLAY_SAMPLE_MUSIC
BPM_UP
BPM_DOWN
STOP_UP
STOP_DOWN
DELAY_UP
DELAY_DOWN
OFFSET_UP
OFFSET_DOWN
SAMPLE_START_UP
SAMPLE_START_DOWN
SAMPLE_LENGTH_UP
SAMPLE_LENGTH_DOWN
ADJUST_FINE
SAVE
UNDO
ADD_COURSE_MODS
SWITCH_PLAYERS
SWITCH_TIMINGS
Key Names:
(If you're really having trouble finding the name for a key, map it to something in the normal controller mapping screen and check Keymaps.ini to see what its name is.)
Most keys can be set with something like this: "Key_a", where "a" is the character typed by the key. This includes keys like ".", ",", and so on. For other keys, there are special names that can be used, which are listed below. "Key_." and "Key_period" both mean the same thing.
Some key names have spaces in them.
Key_period
Key_comma
Key_space
Key_delete
Key_backspace
Key_tab
Key_enter
Key_pause
Key_escape
Key_F1
Key_F2
(Don't map F3, it's used for the debug menu, so probably won't work.)
Key_F4
Key_F5
Key_F6
Key_F7
Key_F8
Key_F9
Key_F10
Key_F11
Key_F12
Key_F13
Key_F14
Key_F15
Key_F16
Key_left ctrl
Key_right ctrl
Key_left shift
Key_right shift
Key_left alt
Key_right alt
Key_left meta
Key_right meta
Key_left super
Key_right super
Key_menu
Key_function
Key_num lock
Key_scroll lock
Key_caps lock
Key_prtsc
Key_up
Key_down
Key_left
Key_right
Key_insert
Key_home
Key_end
Key_pgup
Key_pgdn
Key_KP 0
Key_KP 1
Key_KP 2
Key_KP 3
Key_KP 4
Key_KP 5
Key_KP 6
Key_KP 7
Key_KP 8
Key_KP 9
Key_KP /
Key_KP *
Key_KP -
Key_KP +
Key_KP .
Key_KP =
Key_KP enter
Default Mapping:
Comments are in this section to tell which things require a modifier key to be held.
Note that not all sections map all functions. This is because those functions aren't useful in all modes.
(if you spot a key name that is in all caps in this section, I missed it when editing at 4 AM and it's supposed to be lower case)
[Edit]
SCROLL_UP_LINE=Key_up
SCROLL_DOWN_LINE=Key_down
SCROLL_UP_PAGE=Key_pgup:Key_;
SCROLL_DOWN_PAGE=Key_pgdn:Key_'
# Scrolling by timing segments actually requires holding Ctrl.
SCROLL_UP_TS=Key_pgup:Key_;
SCROLL_DOWN_TS=Key_pgdn:Key_'
SCROLL_HOME=Key_home
SCROLL_END=Key_end
SCROLL_NEXT=Key_period
SCROLL_PREV=Key_comma
# Hold Ctrl for SEGMENT_NEXT and SEGMENT_PREV.
SEGMENT_NEXT=Key_period
SEGMENT_PREV=Key_comma
SCROLL_SELECT=Key_left shift:Key_right shift
LAY_SELECT=Key_space
# Hold Ctrl for PLAY_FROM_START.
PLAY_FROM_START=Key_p
# Hold Shift for PLAY_FROM_CURSOR.
PLAY_FROM_CURSOR=Key_p
PLAY_SELECTION=Key_p
OPEN_TIMING_MENU=Key_F4
# OPEN_PREV_STEPS/OPEN_NEXT_STEPS aren't allowed in home mode. It breaks the "delay creation until first save" logic.
OPEN_PREV_STEPS=Key_F5
OPEN_NEXT_STEPS=Key_F6
BPM_DOWN=Key_F7
BPM_UP=Key_F8
STOP_DOWN=Key_F9
STOP_UP=Key_F10
# Hold Shift for DELAY_DOWN and DELAY_UP.
DELAY_DOWN=Key_F9
DELAY_UP=Key_F10
OFFSET_DOWN=Key_F11
OFFSET_UP=Key_F12
SAMPLE_START_UP=Key_]
SAMPLE_START_DOWN=Key_[
# Hold Shift for SAMPLE_LENGTH_UP and SAMPLE_LENGTH_DOWN.
SAMPLE_LENGTH_UP=Key_]
SAMPLE_LENGTH_DOWN=Key_[
PLAY_SAMPLE_MUSIC=Key_l
OPEN_BGCHANGE_LAYER1_MENU=Key_b
# Hold Shift for OPEN_BGCHANGE_LAYER2_MENU.
OPEN_BGCHANGE_LAYER2_MENU=Key_b
# Hold Ctrl for INSERT_SHIFT_PAUSES and DELETE_SHIFT_PAUSES.
INSERT_SHIFT_PAUSES=Key_insert
DELETE_SHIFT_PAUSES=Key_DEL
COLUMN_0=Key_1
COLUMN_1=Key_2
COLUMN_2=Key_3
COLUMN_3=Key_4
COLUMN_4=Key_5
COLUMN_5=Key_6
COLUMN_6=Key_7
COLUMN_7=Key_8
COLUMN_8=Key_9
COLUMN_9=Key_0
# Yeah, you're screwed when editing techno-double8, bm-double5, or bm-double7, or any other style with more than 10 columns.
RIGHT_SIDE=Key_left alt:Key_right alt
LAY_ROLL=Key_left shift:Key_right shift
CYCLE_TAP_LEFT=Key_n
CYCLE_TAP_RIGHT=Key_m
# Hold Ctrl for CYCLE_SEGMENT_LEFT and CYCLE_SEGMENT_RIGHT.
CYCLE_SEGMENT_LEFT=Key_n
CYCLE_SEGMENT_RIGHT=Key_m
# Hold Ctrl for SCROLL_SPEED_UP and SCROLL_SPEED_DOWN
SCROLL_SPEED_UP=Key_up
SCROLL_SPEED_DOWN=Key_down
SCROLL_SELECT=Key_left shift:Key_right shift
SNAP_NEXT=Key_left
SNAP_PREV=Key_right
OPEN_EDIT_MENU=Key_escape
OPEN_AREA_MENU=Key_enter
OPEN_ALTER_MENU=Key_a
OPEN_INPUT_HELP=Key_F1
# Hold Alt for BAKE_RANDOM_FROM_SONG_GROUP.
BAKE_RANDOM_FROM_SONG_GROUP=Key_b
# Hold Ctrl for BAKE_RANDOM_FROM_SONG_GROUP_AND_GENRE.
BAKE_RANDOM_FROM_SONG_GROUP_AND_GENRE=Key_b
# Hold Ctrl for RECORD_SELECTION.
RECORD_SELECTION=Key_r
INSERT=Key_insert:Key_\
DELETE=Key_delete
ADJUST_FINE=Key_right alt:Key_left alt
# Hold Ctrl or Cmd (OS X) for SAVE.
SAVE=Key_s
UNDO=Key_u
SWITCH_PLAYERS=Key_/
SWITCH_TIMINGS=Key_t
[Play]
RETURN_TO_EDIT=Key_enter:Key_escape
[Record]
LAY_ROLL=Key_left shift:Key_right shift
REMOVE_NOTE=Key_left alt:Key_right alt
RETURN_TO_EDIT=Key_escape:Key_enter
[RecordPaused]
PLAY_SELECTION=Key_p
# Hold Ctrl for RECORD_SELECTION.
RECORD_SELECTION=Key_r
RECORD_FROM_CURSOR=Key_r
RETURN_TO_EDIT=Key_escape
UNDO=Key_u
+84
View File
@@ -0,0 +1,84 @@
This could use a bit nicer formatting, and something else should explain screen inheritance, but here's everything I was able to find on announcers from searching the source.
Each entry lists the event that triggers it, then the name of the folder that is searched for a sound to play.
Screen inheritance note:
The screen names listed below are actually the names of screen classes. Every screen has a class type, and some screen class types inherit from others. You can find the class type of a screen by looking at the metrics for the theme and reading the Class metric in a screen's metric group.
So sound names with "<screen name>" in them will actually occur on any screen that inherits from that class type, and the actual name of the screen will be inserted into the string when the announcer system goes to play the sound.
ScreenNameEntry
(entering screen) "name entry"
ScreenEnding
(entering screen) "music scroll"
ScreenEvaluation
(entering screen): (only one will occur, listed in order of precedence)
"evaluation new record"
"evaluation full combo W1"
"evaluation full combo W2"
grade string values: "AAAA" (tier 1), "AAA" (tier 2), "AA" (tier 3), "A" (tier 4), "B" (tier 5), "C" (tier 6), "D" (tier 7), "E" (tier failed), "N" (tier nodata)
"evaluation final <grade string>" (only in course mode on summary screen)
"evaluation win" (only in battle mode)
"evaluation lose" (only in battle mode)
"evaluation <grade string>" (only in non-course, non-battle)
(after CheerDelaySeconds) "evaluation cheer"
ScreenPlayerOptions
(entering screen) "player options intro"
ScreenSelectCharacter
(entering screen) "select group intro"
ScreenSelectMaster
(ScreenSelectMaster is the name of the class type of several different screens, so these will actually occur on any of the following: "ScreenTitleMenu", "ScreenSelectLanguage", "ScreenUnlockBrowse", "ScreenSelectStyle", "ScreenSelectPlayMode", "ScreenGameInformation", or any other screen that has "ScreenSelectMaster" as its Class metric)
(on moving to second page) "select difficulty challenge"
(side note: choices on ScreenSelectMaster are split into two pages, all choices after the amount set by the NumChoicesOnPage1 metric are on the second page. Default is 1024, so this will never play unless the theme sets the metric lower to have a second page)
(on picking a choice) "<screen name> comment <choice name>"
(<screen name> will be the full name of the screen, <choice name> will be the name field of the gamecommand that defines the choice, so this could be literally anything the themer feels like)
ScreenSelect
(every IdleCommentSeconds) "<screen name> IdleComment"
ScreenTitleMenu
(entering screen) "title menu game name"
ScreenWithMenuElements
(entering screen) "<screen name> intro"
ScreenSelectMusic
(entering screen) "select music intro"
(every IdleCommentSeconds) "<screen name> IdleComment"
(on picking a song played already this round) "select music comment repeat"
(on picking a song never played before) "select music comment new"
(on picking a song with a meter >= 10) "select music comment hard"
(on picking a song that is not one of the above) "select music comment general"
(on picking a course) "select course comment general"
ScreenGameplay
(entering screen) "gameplay intro"
(after fading in) "gameplay ready"
(on song start extra stage) "gameplay here we go extra"
(on song start final stage) "gameplay here we go final"
(on song start non-final non-extra stage) "gameplay here we go normal"
(on enemy death in battle mode?) "gameplay battle damage level3"
(on finishing gameplay, earned extra) "gameplay extra"
(on finishing gameplay, not earned extra) "gameplay cleared"
(when failing over halfway through course) "gameplay oni failed halfway"
(when failing less than halfway through course) "gameplay oni failed"
(when failing non-course) "gameplay failed"
(following separated by SecondsBetweenComments metric)
(when one life meter is hot) "gameplay comment hot"
(when one life meter is in danger) "gameplay comment danger"
(when neither of the above two) "gameplay comment good"
(in nonstop, oni, or endless mode) "gameplay comment oni"
(every hundred combos) "gameplay <amount> combo" (<amount> ranges from 100 to 1000)
(combo stopped) "gameplay combo stopped"
(combo continuing (every hundred over 1k)) "gameplay combo overflow"
(when a battle trick occurs) "gameplay battle trick level<n>" (<n> can be 1, 2, or 3)
(when battle damage occurs) "gameplay battle damage level<n>" (<n> can be 1, 2, or 3)
(when a menu timer runs low) "hurry up"
(whenever the theme calls SOUND:PlayAnnouncer("<anything>")) "<anything>"
+16
View File
@@ -0,0 +1,16 @@
General note on functions that use effect colors:
diffuseblink, diffuseramp, diffuseshift, glowblink, glowramp, and glowshift all use the two effect colors.
They set the effect colors to white when called, so you should call effectcolor1 and effectcolor2 afterwards to set the effect colors to the colors you want.
You should also call effectperiod to set the effect period if you don't want the default of 1.
Example:
Def.Quad{
Name= "glow quad test", InitCommand= function(self)
self:setsize(40, 40)
self:glowshift()
self:effectcolor1(color("#dc322f"))
self:effectcolor2(color("#2aa198"))
self:effectperiod(4)
self:xy(_screen.cx, _screen.cy)
end
}
+1 -23
View File
@@ -191,8 +191,6 @@ end
-- ColorToHex(c)
-- Takes in a normal color("") and returns the hex representation.
-- Adapted from code in LuaBit (http://luaforge.net/projects/bit/),
-- which is MIT licensed and copyright (C) 2006~2007 hanzhao.
function ColorToHex(c)
local r = c[1]
local g = c[2]
@@ -200,27 +198,7 @@ function ColorToHex(c)
local a = HasAlpha(c)
local function hex(value)
value = math.ceil(value)
local hexVals = { 'A', 'B', 'C', 'D', 'E', 'F' }
local out = ""
local last = 0
while(value ~= 0) do
last = math.mod(value, 16)
if(last < 10) then
out = tostring(last) .. out
else
out = hexVals[(last-10)+1] .. out
end
value = math.floor(value/16)
end
if(out == "") then
return "00"
end
return string.format( "%02X", tonumber(out,16) )
return ("%02X"):format(value)
end
local rX = hex( scale(r, 0, 1, 0, 255) )
@@ -66,6 +66,8 @@ function wrap(val,n)
end
function fapproach(val, other_val, to_move)
-- This does not use the (faster) C++ side version of approach because I
-- don't want to find out how many themes pass a negative speed. -Kyz
if val == other_val then
return val -- already done!
end
+2 -2
View File
@@ -706,7 +706,7 @@ PercentUseRemainder=false
ApplyScoreDisplayOptions=true
DancePointsDigits=5
#
Format="%2d"
Format=FormatPercentScore
#
RemainderFormat=
#
@@ -1399,7 +1399,7 @@ DancePointsDigits=1
PercentUseRemainder=true
ApplyScoreDisplayOptions=false
FormatPercentScore=FormatPercentScore
Format=
Format=FormatPercentScore
[SoundEffectControl]
LockToHold=false
@@ -70,13 +70,13 @@ local t = LoadFallbackB();
t[#t+1] = StandardDecorationFromFileOptional("StageDisplay","StageDisplay");
if ShowStandardDecoration("GraphDisplay") and not GAMESTATE:GetPlayMode() == "PlayMode_Rave" then
if ShowStandardDecoration("GraphDisplay") and GAMESTATE:GetPlayMode() ~= "PlayMode_Rave" then
for pn in ivalues(GAMESTATE:GetHumanPlayers()) do
t[#t+1] = StandardDecorationFromTable( "GraphDisplay" .. ToEnumShortString(pn), GraphDisplay(pn) );
end
end
if ShowStandardDecoration("ComboGraph") and not GAMESTATE:GetPlayMode() == "PlayMode_Rave" then
if ShowStandardDecoration("ComboGraph") and GAMESTATE:GetPlayMode() ~= "PlayMode_Rave" then
for pn in ivalues(GAMESTATE:GetHumanPlayers()) do
t[#t+1] = StandardDecorationFromTable( "ComboGraph" .. ToEnumShortString(pn), ComboGraph(pn) );
end
+1 -1
View File
@@ -246,7 +246,7 @@ Information=Information
Feet=Your feet will be used to play!
Tap=When the arrows rise to this point,\nstep on the matching panels.
Jump=Step on both panels if two different\narrows appear at the same time!
Miss=If you misstep repeatedly, your dance\nguage will decrease until the game is\nis over!
Miss=If you misstep repeatedly, your dance\ngauge will decrease until the game\nis over!
[Protiming]
-2
View File
@@ -140,8 +140,6 @@ NumLivesP2OnCommand=zoomx,-1
NumLivesP2LoseLifeCommand=zoomx,-1.5;zoomy,1.5;linear,0.15;zoomx,-1;zoomy,1
[LifeMeterBattery Percent]
# still asking for this even though it's in fallback... -aj
Format=
#
PercentP2OnCommand=zoom,0.7;zoomx,-0.7;shadowlength,0;diffuse,PlayerColor(PLAYER_2)
DancePointsP2OnCommand=zoom,0.7;zoomx,-0.7;shadowlength,0;diffuse,PlayerColor(PLAYER_2)
+21 -17
View File
@@ -370,21 +370,21 @@ void Actor::PreDraw() // calculate actor properties
/* XXX: Should diffuse_blink and diffuse_shift multiply the tempState color?
* (That would have the same effect with 1,1,1,1, and allow tweening the diffuse
* while blinking and shifting.) */
for(int i=0; i<4; i++)
for(int i=0; i<NUM_DIFFUSE_COLORS; i++)
{
tempState.diffuse[i] = bBlinkOn ? m_effectColor1 : m_effectColor2;
tempState.diffuse[i].a *= fOriginalAlpha; // multiply the alphas so we can fade even while an effect is playing
}
break;
case diffuse_shift:
for(int i=0; i<4; i++)
for(int i=0; i<NUM_DIFFUSE_COLORS; i++)
{
tempState.diffuse[i] = m_effectColor1*fPercentBetweenColors + m_effectColor2*(1.0f-fPercentBetweenColors);
tempState.diffuse[i].a *= fOriginalAlpha; // multiply the alphas so we can fade even while an effect is playing
}
break;
case diffuse_ramp:
for(int i=0; i<4; i++)
for(int i=0; i<NUM_DIFFUSE_COLORS; i++)
{
tempState.diffuse[i] = m_effectColor1*fPercentThroughEffect + m_effectColor2*(1.0f-fPercentThroughEffect);
tempState.diffuse[i].a *= fOriginalAlpha; // multiply the alphas so we can fade even while an effect is playing
@@ -408,7 +408,7 @@ void Actor::PreDraw() // calculate actor properties
RageFastCos( fPercentBetweenColors*2*PI + PI * 2.0f / 3.0f ) * 0.5f + 0.5f,
RageFastCos( fPercentBetweenColors*2*PI + PI * 4.0f / 3.0f) * 0.5f + 0.5f,
fOriginalAlpha );
for( int i=1; i<4; i++ )
for( int i=1; i<NUM_DIFFUSE_COLORS; i++ )
tempState.diffuse[i] = tempState.diffuse[0];
break;
case wag:
@@ -471,7 +471,7 @@ void Actor::PreDraw() // calculate actor properties
tempState = m_current;
}
for( int i=0; i<4; i++ )
for( int i=0; i<NUM_DIFFUSE_COLORS; i++ )
{
tempState.diffuse[i] *= m_internalDiffuse;
}
@@ -785,7 +785,7 @@ RString Actor::GetLineage() const
if( m_pParent )
sPath = m_pParent->GetLineage() + '/';
sPath += ssprintf( "<%s> %s", typeid(*this).name(), m_sName.c_str() );
sPath += ssprintf( "<type %s> %s", typeid(*this).name(), m_sName.c_str() );
return sPath;
}
@@ -889,7 +889,7 @@ void Actor::ScaleTo( const RectF &rect, StretchType st )
void Actor::SetEffectClockString( const RString &s )
{
if (s.EqualsNoCase("timer")) this->SetEffectClock( CLOCK_TIMER );
if (s.EqualsNoCase("timerglobal")) this->SetEffectClock( CLOCK_TIMER_GLOBAL );
else if(s.EqualsNoCase("timerglobal")) this->SetEffectClock( CLOCK_TIMER_GLOBAL );
else if(s.EqualsNoCase("beat")) this->SetEffectClock( CLOCK_BGM_BEAT );
else if(s.EqualsNoCase("music")) this->SetEffectClock( CLOCK_BGM_TIME );
else if(s.EqualsNoCase("bgm")) this->SetEffectClock( CLOCK_BGM_BEAT ); // compat, deprecated
@@ -899,9 +899,13 @@ void Actor::SetEffectClockString( const RString &s )
{
CabinetLight cl = StringToCabinetLight( s );
if( cl == CabinetLight_Invalid )
FAIL_M(ssprintf("Invalid cabinet light: %s", s.c_str()));
this->SetEffectClock( (EffectClock) (cl + CLOCK_LIGHT_1) );
{
LuaHelpers::ReportScriptErrorFmt("String '%s' is not an effect clock string or the name of a cabinet light.", s.c_str());
}
else
{
this->SetEffectClock(static_cast<EffectClock>(cl + CLOCK_LIGHT_1));
}
}
}
@@ -1130,7 +1134,7 @@ void Actor::RunCommands( const LuaReference& cmds, const LuaReference *pParamTab
{
if( !cmds.IsSet() || cmds.IsNil() )
{
LuaHelpers::ReportScriptError("RunCommands: command is unset or nil");
LuaHelpers::ReportScriptErrorFmt("RunCommands: commands for %s are unset or nil", GetLineage().c_str());
return;
}
@@ -1140,7 +1144,7 @@ void Actor::RunCommands( const LuaReference& cmds, const LuaReference *pParamTab
cmds.PushSelf( L );
if( lua_isnil(L, -1) )
{
LuaHelpers::ReportScriptError("Error compiling commands");
LuaHelpers::ReportScriptErrorFmt("RunCommands: Error compiling commands for %s", GetLineage().c_str());
LUA->Release(L);
return;
}
@@ -1155,7 +1159,7 @@ void Actor::RunCommands( const LuaReference& cmds, const LuaReference *pParamTab
pParamTable->PushSelf( L );
// call function with 2 arguments and 0 results
RString Error= "Error playing command: ";
RString Error= "Error playing command:";
LuaHelpers::RunScriptOnStack(L, Error, 2, 0, true);
LUA->Release(L);
@@ -1182,7 +1186,7 @@ float Actor::GetTweenTimeLeft() const
* being manipulated, which would add overhead ... */
void Actor::SetGlobalDiffuseColor( RageColor c )
{
for( int i=0; i<4; i++ ) // color, not alpha
for( int i=0; i<NUM_DIFFUSE_COLORS; i++ ) // color, not alpha
{
for( unsigned ts = 0; ts < m_Tweens.size(); ++ts )
{
@@ -1201,7 +1205,7 @@ void Actor::SetGlobalDiffuseColor( RageColor c )
void Actor::SetDiffuseColor( RageColor c )
{
for( int i=0; i<4; i++ )
for( int i=0; i<NUM_DIFFUSE_COLORS; i++ )
{
DestTweenState().diffuse[i].r = c.r;
DestTweenState().diffuse[i].g = c.g;
@@ -1220,7 +1224,7 @@ void Actor::TweenState::Init()
fSkewY = 0;
crop = RectF( 0,0,0,0 );
fade = RectF( 0,0,0,0 );
for( int i=0; i<4; i++ )
for( int i=0; i<NUM_DIFFUSE_COLORS; i++ )
diffuse[i] = RageColor( 1, 1, 1, 1 );
glow = RageColor( 1, 1, 1, 0 );
aux = 0;
@@ -1264,7 +1268,7 @@ void Actor::TweenState::MakeWeightedAverage( TweenState& average_out, const Twee
average_out.fade.right = lerp( fPercentBetween, ts1.fade.right, ts2.fade.right );
average_out.fade.bottom = lerp( fPercentBetween, ts1.fade.bottom, ts2.fade.bottom );
for( int i=0; i<4; ++i )
for( int i=0; i<NUM_DIFFUSE_COLORS; ++i )
average_out.diffuse[i] = lerp( fPercentBetween, ts1.diffuse[i], ts2.diffuse[i] );
average_out.glow = lerp( fPercentBetween, ts1.glow, ts2.glow );
+11 -4
View File
@@ -65,6 +65,13 @@ LuaDeclareType( VertAlign );
/** @brief The bottom vertical alignment constant. */
#define align_bottom 1.0f
// This is the number of colors in Actor::diffuse. Actor has multiple
// diffuse colors so that each edge can be a different color, and the actor
// is drawn with a gradient between them.
// I doubt I actually found all the places that touch diffuse and rely on the
// number of diffuse colors, so change this at your own risk. -Kyz
#define NUM_DIFFUSE_COLORS 4
// ssc futures:
/*
enum EffectAction
@@ -218,7 +225,7 @@ public:
* @brief Four values making up the diffuse in this TweenState.
*
* 0 = UpperLeft, 1 = UpperRight, 2 = LowerLeft, 3 = LowerRight */
RageColor diffuse[4];
RageColor diffuse[NUM_DIFFUSE_COLORS];
/** @brief The glow color for this TweenState. */
RageColor glow;
/** @brief A magical value that nobody really knows the use for. ;) */
@@ -272,7 +279,7 @@ public:
virtual void Update( float fDeltaTime ); // this can short circuit UpdateInternal
virtual void UpdateInternal( float fDeltaTime ); // override this
void UpdateTweening( float fDeltaTime );
// These next functions should all be overridden by a derived class that has its own tweening states to handl.
// These next functions should all be overridden by a derived class that has its own tweening states to handle.
virtual void SetCurrentTweenStart() {}
virtual void EraseHeadTween() {}
virtual void UpdatePercentThroughTween( float PercentThroughTween ) {}
@@ -433,8 +440,8 @@ public:
void SetGlobalDiffuseColor( RageColor c );
virtual void SetDiffuse( RageColor c ) { for(int i=0; i<4; i++) DestTweenState().diffuse[i] = c; };
virtual void SetDiffuseAlpha( float f ) { for(int i = 0; i < 4; ++i) { RageColor c = GetDiffuses( i ); c.a = f; SetDiffuses( i, c ); } }
virtual void SetDiffuse( RageColor c ) { for(int i=0; i<NUM_DIFFUSE_COLORS; i++) DestTweenState().diffuse[i] = c; };
virtual void SetDiffuseAlpha( float f ) { for(int i = 0; i < NUM_DIFFUSE_COLORS; ++i) { RageColor c = GetDiffuses( i ); c.a = f; SetDiffuses( i, c ); } }
float GetCurrentDiffuseAlpha() const { return m_current.diffuse[0].a; }
void SetDiffuseColor( RageColor c );
void SetDiffuses( int i, RageColor c ) { DestTweenState().diffuse[i] = c; };
+64 -9
View File
@@ -56,9 +56,6 @@ BitmapText::BitmapText()
m_iVertSpacing = 0;
m_MaxDimensionUsesZoom= false;
m_bHasGlowAttribute = false;
// We'd be better off not adding strokes to things we can't control
// themewise (ScreenDebugOverlay for example). -Midiman
m_StrokeColor = RageColor(0,0,0,0);
// Never, this way we dont have awkward settings between themes. -Midiman
SetShadowLength( 0 );
// SM4SVN r28328, "draw glow using stroke texture" forces the BitmapText to
@@ -95,7 +92,9 @@ BitmapText & BitmapText::operator=(const BitmapText &cpy)
CPY( m_vpFontPageTextures );
CPY( m_mAttributes );
CPY( m_bHasGlowAttribute );
CPY( m_StrokeColor );
CPY( BMT_Tweens );
CPY( BMT_current );
CPY( BMT_start );
#undef CPY
if( m_pFont )
@@ -117,6 +116,60 @@ BitmapText::BitmapText( const BitmapText &cpy ):
*this = cpy;
}
void BitmapText::SetCurrentTweenStart()
{
BMT_start= BMT_current;
}
void BitmapText::EraseHeadTween()
{
BMT_current= BMT_Tweens[0];
BMT_Tweens.erase(BMT_Tweens.begin());
}
void BitmapText::UpdatePercentThroughTween(float between)
{
BMT_TweenState::MakeWeightedAverage(BMT_current, BMT_start, BMT_Tweens[0],
between);
}
void BitmapText::BeginTweening(float time, ITween* interp)
{
Actor::BeginTweening(time, interp);
if(!BMT_Tweens.empty())
{
BMT_Tweens.push_back(BMT_Tweens.back());
}
else
{
BMT_Tweens.push_back(BMT_current);
}
}
void BitmapText::StopTweening()
{
BMT_Tweens.clear();
Actor::StopTweening();
}
void BitmapText::FinishTweening()
{
if(!BMT_Tweens.empty())
{
BMT_current= BMT_DestTweenState();
}
Actor::FinishTweening();
}
void BitmapText::BMT_TweenState::MakeWeightedAverage(BMT_TweenState& out,
BMT_TweenState const& from, BMT_TweenState const& to, float between)
{
out.m_stroke_color.b= lerp(between, from.m_stroke_color.b, to.m_stroke_color.b);
out.m_stroke_color.g= lerp(between, from.m_stroke_color.g, to.m_stroke_color.g);
out.m_stroke_color.r= lerp(between, from.m_stroke_color.r, to.m_stroke_color.r);
out.m_stroke_color.a= lerp(between, from.m_stroke_color.a, to.m_stroke_color.a);
}
void BitmapText::LoadFromNode( const XNode* node )
{
RString text;
@@ -613,12 +666,12 @@ void BitmapText::DrawPrimitives()
}
// render the stroke
if( m_StrokeColor.a > 0 )
RageColor stroke_color= GetCurrStrokeColor();
if( stroke_color.a > 0 )
{
RageColor c = m_StrokeColor;
c.a *= m_pTempState->diffuse[0].a;
stroke_color.a *= m_pTempState->diffuse[0].a;
for( unsigned i=0; i<m_aVertices.size(); i++ )
m_aVertices[i].c = c;
m_aVertices[i].c = stroke_color;
DrawChars( true );
}
@@ -832,7 +885,7 @@ void BitmapText::Attribute::FromStack( lua_State *L, int iPos )
lua_getfield( L, iTab, "Diffuses" );
if( !lua_isnil(L, -1) )
{
for( int i = 1; i <= 4; ++i )
for( int i = 1; i <= NUM_DIFFUSE_COLORS; ++i )
{
lua_rawgeti( L, -i, i );
diffuse[i-1].FromStack( L, -1 );
@@ -914,6 +967,7 @@ public:
}
static int ClearAttributes( T* p, lua_State * ) { p->ClearAttributes(); return 0; }
static int strokecolor( T* p, lua_State *L ) { RageColor c; c.FromStackCompat( L, 1 ); p->SetStrokeColor( c ); return 0; }
DEFINE_METHOD(getstrokecolor, GetStrokeColor());
static int uppercase( T* p, lua_State *L ) { p->SetUppercase( BArg(1) ); return 0; }
static int textglowmode( T* p, lua_State *L ) { p->SetTextGlowMode( Enum::Check<TextGlowMode>(L, 1) ); return 0; }
@@ -933,6 +987,7 @@ public:
ADD_METHOD( AddAttribute );
ADD_METHOD( ClearAttributes );
ADD_METHOD( strokecolor );
ADD_METHOD( getstrokecolor );
ADD_METHOD( uppercase );
ADD_METHOD( textglowmode );
//ADD_METHOD( LoadFromFont );
+43 -4
View File
@@ -19,6 +19,41 @@ public:
virtual void LoadFromNode( const XNode* pNode );
virtual BitmapText *Copy() const;
struct BMT_TweenState
{
// We'd be better off not adding strokes to things we can't control
// themewise (ScreenDebugOverlay for example). -Midiman
BMT_TweenState(): m_stroke_color(RageColor(0,0,0,0)) {}
static void MakeWeightedAverage(BMT_TweenState& out,
BMT_TweenState const& from, BMT_TweenState const& to, float between);
bool operator==(BMT_TweenState const& other) const;
bool operator!=(BMT_TweenState const& other) const { return !operator==(other); }
void SetStrokeColor(RageColor const& c) { m_stroke_color= c; }
RageColor const& GetStrokeColor() { return m_stroke_color; }
private:
RageColor m_stroke_color;
};
BMT_TweenState& BMT_DestTweenState()
{
if(BMT_Tweens.empty())
{ return BMT_current; }
else
{ return BMT_Tweens.back(); }
}
BMT_TweenState const& BMT_DestTweenState() const { return const_cast<BitmapText*>(this)->BMT_DestTweenState(); }
virtual void SetCurrentTweenStart();
virtual void EraseHeadTween();
virtual void UpdatePercentThroughTween(float between);
virtual void BeginTweening(float time, ITween* interp);
// This function exists because the compiler tried to connect a call of
// "BeginTweening(1.2f)" to the function above. -Kyz
virtual void BeginTweening(float time, TweenType tt = TWEEN_LINEAR)
{ Actor::BeginTweening(time, tt); }
virtual void StopTweening();
virtual void FinishTweening();
bool LoadFromFont( const RString& sFontName );
bool LoadFromTextureAndChars( const RString& sTexturePath, const RString& sChars );
virtual void SetText( const RString& sText, const RString& sAlternateText = "", int iWrapWidthPixels = -1 );
@@ -40,8 +75,10 @@ public:
void SetHorizAlign( float f );
void SetStrokeColor( RageColor c ) { m_StrokeColor = c; }
RageColor GetStrokeColor() { return m_StrokeColor; }
void SetStrokeColor(RageColor c) { BMT_DestTweenState().SetStrokeColor(c); }
RageColor const& GetStrokeColor() { return BMT_DestTweenState().GetStrokeColor(); }
void SetCurrStrokeColor(RageColor c) { BMT_current.SetStrokeColor(c); }
RageColor const& GetCurrStrokeColor() { return BMT_current.GetStrokeColor(); }
void SetTextGlowMode( TextGlowMode tgm ) { m_TextGlowMode = tgm; }
@@ -56,7 +93,7 @@ public:
{
Attribute() : length(-1), glow() { }
int length;
RageColor diffuse[4];
RageColor diffuse[NUM_DIFFUSE_COLORS];
RageColor glow;
void FromStack( lua_State *L, int iPos );
@@ -91,7 +128,6 @@ protected:
map<size_t, Attribute> m_mAttributes;
bool m_bHasGlowAttribute;
RageColor m_StrokeColor;
TextGlowMode m_TextGlowMode;
// recalculate the items in SetText()
@@ -101,6 +137,9 @@ protected:
private:
void SetTextInternal();
vector<BMT_TweenState> BMT_Tweens;
BMT_TweenState BMT_current;
BMT_TweenState BMT_start;
};
#endif
+3 -1
View File
@@ -54,7 +54,9 @@ void Foreground::LoadFromSong( const Song *pSong )
if( bga.m_bga == NULL )
continue;
bga.m_bga->SetName( sBGName );
bga.m_bga->PlayCommand( "Init" );
// ActorUtil::MakeActor calls LoadFromNode to load the actor, and
// LoadFromNode takes care of running the InitCommand, so do not run the
// InitCommand here. -Kyz
bga.m_fStartBeat = change.m_fStartBeat;
bga.m_bFinished = false;
+1 -1
View File
@@ -639,7 +639,7 @@ const InputScheme *InputMapper::GetInputScheme() const
return m_pInputScheme;
}
static const RString DEVICE_INPUT_SEPARATOR = ":"; // this isn't used in any key names
const RString DEVICE_INPUT_SEPARATOR = ":"; // this isn't used in any key names
void InputMapper::ReadMappingsFromDisk()
{
+1
View File
@@ -9,6 +9,7 @@ struct Game;
const int NUM_GAME_TO_DEVICE_SLOTS = 5; // five device inputs may map to one game input
const int NUM_SHOWN_GAME_TO_DEVICE_SLOTS = 3;
const int NUM_USER_GAME_TO_DEVICE_SLOTS = 2;
extern const RString DEVICE_INPUT_SEPARATOR;
struct AutoMappingEntry
{
+5
View File
@@ -266,6 +266,11 @@ void LuaFunc_Register_##func( lua_State *L ); \
void LuaFunc_Register_##func( lua_State *L ) { lua_register( L, #func, LuaFunc_##func ); } \
REGISTER_WITH_LUA_FUNCTION( LuaFunc_Register_##func );
#define LUAFUNC_REGISTER_COMMON(func_name) \
void LuaFunc_Register_##func_name(lua_State* L); \
void LuaFunc_Register_##func_name(lua_State* L) { lua_register(L, #func_name, LuaFunc_##func_name); } \
REGISTER_WITH_LUA_FUNCTION(LuaFunc_Register_##func_name);
#endif
/*
+2 -1
View File
@@ -73,7 +73,7 @@ void SMLoader::LoadFromTokens(
Trim( sDifficulty );
Trim( sNoteData );
// LOG->Trace( "Steps::LoadFromTokens()" );
// LOG->Trace( "Steps::LoadFromTokens(), %s", sStepsType.c_str() );
// backwards compatibility hacks:
// HACK: We eliminated "ez2-single-hard", but we should still handle it.
@@ -85,6 +85,7 @@ void SMLoader::LoadFromTokens(
sStepsType = "para-single";
out.m_StepsType = GAMEMAN->StringToStepsType( sStepsType );
out.m_StepsTypeStr = sStepsType;
out.SetDescription( sDescription );
out.SetCredit( sDescription ); // this is often used for both.
out.SetChartName(sDescription); // yeah, one more for good measure.
+2
View File
@@ -643,6 +643,7 @@ bool SSCLoader::LoadFromSimfile( const RString &sPath, Song &out, bool bFromCach
if( sValueName=="STEPSTYPE" )
{
pNewNotes->m_StepsType = GAMEMAN->StringToStepsType( sParams[1] );
pNewNotes->m_StepsTypeStr= sParams[1];
}
else if( sValueName=="CHARTSTYLE" )
@@ -965,6 +966,7 @@ bool SSCLoader::LoadEditFromMsd(const MsdFile &msd,
if( sValueName=="STEPSTYPE" )
{
pNewNotes->m_StepsType = GAMEMAN->StringToStepsType( sParams[1] );
pNewNotes->m_StepsTypeStr= sParams[1];
bSSCFormat = true;
}
+2 -2
View File
@@ -206,9 +206,9 @@ static RString GetSMNotesTag( const Song &song, const Steps &in )
lines.push_back( "" );
// Escape to prevent some clown from making a comment of "\r\n;"
lines.push_back( ssprintf("//---------------%s - %s----------------",
GAMEMAN->GetStepsTypeInfo(in.m_StepsType).szName, SmEscape(in.GetDescription()).c_str()) );
in.m_StepsTypeStr.c_str(), SmEscape(in.GetDescription()).c_str()) );
lines.push_back( song.m_vsKeysoundFile.empty() ? "#NOTES:" : "#NOTES2:" );
lines.push_back( ssprintf( " %s:", GAMEMAN->GetStepsTypeInfo(in.m_StepsType).szName ) );
lines.push_back( ssprintf( " %s:", in.m_StepsTypeStr.c_str() ) );
RString desc = (USE_CREDIT ? in.GetCredit() : in.GetChartName());
lines.push_back( ssprintf( " %s:", SmEscape(desc).c_str() ) );
lines.push_back( ssprintf( " %s:", DifficultyToString(in.GetDifficulty()).c_str() ) );
+2 -2
View File
@@ -349,10 +349,10 @@ static RString GetSSCNoteData( const Song &song, const Steps &in, bool bSavingCa
lines.push_back( "" );
// Escape to prevent some clown from making a comment of "\r\n;"
lines.push_back( ssprintf("//---------------%s - %s----------------",
GAMEMAN->GetStepsTypeInfo(in.m_StepsType).szName, SmEscape(in.GetDescription()).c_str()) );
in.m_StepsTypeStr.c_str(), SmEscape(in.GetDescription()).c_str()) );
lines.push_back( "#NOTEDATA:;" ); // our new separator.
lines.push_back( ssprintf( "#CHARTNAME:%s;", SmEscape(in.GetChartName()).c_str()));
lines.push_back( ssprintf( "#STEPSTYPE:%s;", GAMEMAN->GetStepsTypeInfo(in.m_StepsType).szName ) );
lines.push_back( ssprintf( "#STEPSTYPE:%s;", in.m_StepsTypeStr.c_str() ) );
lines.push_back( ssprintf( "#DESCRIPTION:%s;", SmEscape(in.GetDescription()).c_str() ) );
lines.push_back( ssprintf( "#CHARTSTYLE:%s;", SmEscape(in.GetChartStyle()).c_str() ) );
lines.push_back( ssprintf( "#DIFFICULTY:%s;", DifficultyToString(in.GetDifficulty()).c_str() ) );
+28 -11
View File
@@ -33,10 +33,22 @@ void PercentageDisplay::LoadFromNode( const XNode* pNode )
pNode->GetAttrValue( "AutoRefresh", m_bAutoRefresh );
{
Lua *L = LUA->Get();
if( pNode->PushAttrValue(L, "FormatPercentScore") )
if(pNode->PushAttrValue(L, "FormatPercentScore"))
{
m_FormatPercentScore.SetFromStack( L );
if(m_FormatPercentScore.GetLuaType() != LUA_TFUNCTION)
{
// Not reported as an error because _fallback and default provided bad
// examples in their [LifeMeterBattery Percent]:Format metric and nobody
// realized it was supposed to be set to a function. -Kyz
LOG->Trace("Format attribute for PercentageDisplay named '%s' is not a function. Defaulting to 'FormatPercentScore'.", GetName().c_str());
m_FormatPercentScore.SetFromExpression("FormatPercentScore");
}
}
else
{
lua_pop(L, 1);
}
LUA->Release(L);
}
@@ -86,9 +98,12 @@ void PercentageDisplay::Load( const PlayerState *pPlayerState, const PlayerStage
m_sPercentFormat = THEME->GetMetric( sMetricsGroup, "PercentFormat" );
m_sRemainderFormat = THEME->GetMetric( sMetricsGroup, "RemainderFormat" );
if( m_FormatPercentScore.IsNil() )
if(m_FormatPercentScore.GetLuaType() != LUA_TFUNCTION)
{
LOG->Trace( "Format is nil in [%s]. Defaulting to 'FormatPercentScore'.", sMetricsGroup.c_str() );
// Not reported as an error because _fallback and default provided bad
// examples in their [LifeMeterBattery Percent]:Format metric and nobody
// realized it was supposed to be set to a function. -Kyz
LOG->Trace("Format metric is not a function in [%s]. Defaulting to 'FormatPercentScore'.", sMetricsGroup.c_str());
m_FormatPercentScore.SetFromExpression( "FormatPercentScore" );
}
@@ -157,14 +172,16 @@ void PercentageDisplay::Refresh()
}
else
{
Lua *L = LUA->Get();
m_FormatPercentScore.PushSelf( L );
ASSERT( !lua_isnil(L, -1) );
LuaHelpers::Push( L, fPercentDancePoints );
RString Error= "Error running FormatPercentScore: ";
LuaHelpers::RunScriptOnStack(L, Error, 1, 1, true); // 1 arg, 1 result
LuaHelpers::Pop( L, sNumToDisplay );
LUA->Release(L);
if(m_FormatPercentScore.GetLuaType() == LUA_TFUNCTION)
{
Lua *L = LUA->Get();
m_FormatPercentScore.PushSelf( L );
LuaHelpers::Push( L, fPercentDancePoints );
RString Error= "Error running FormatPercentScore: ";
LuaHelpers::RunScriptOnStack(L, Error, 1, 1, true); // 1 arg, 1 result
LuaHelpers::Pop( L, sNumToDisplay );
LUA->Release(L);
}
// HACK: Use the last frame in the numbers texture as '-'
sNumToDisplay.Replace('-','x');
+64 -44
View File
@@ -11,6 +11,29 @@ struct TapScoreDistribution
{
float fPercent[NUM_TapNoteScore];
void ChangeWeightsToPercents()
{
float sum= 0;
for(int i= 0; i < NUM_TapNoteScore; ++i)
{
sum+= fPercent[i];
}
for(int i= 0; i < NUM_TapNoteScore; ++i)
{
fPercent[i]/= sum;
}
}
void SetDefaultWeights()
{
fPercent[TNS_None] = 0;
fPercent[TNS_Miss] = 1;
fPercent[TNS_W5] = 0;
fPercent[TNS_W4] = 0;
fPercent[TNS_W3] = 0;
fPercent[TNS_W2] = 0;
fPercent[TNS_W1] = 0;
}
TapNoteScore GetTapNoteScore()
{
float fRand = randomf(0,1);
@@ -31,57 +54,54 @@ static TapScoreDistribution g_Distributions[NUM_SKILL_LEVELS];
void PlayerAI::InitFromDisk()
{
bool bSuccess;
IniFile ini;
bSuccess = ini.ReadFile( AI_PATH );
ASSERT( bSuccess );
for( int i=0; i<NUM_SKILL_LEVELS; i++ )
bool bSuccess = ini.ReadFile( AI_PATH );
if(!bSuccess)
{
RString sKey = ssprintf("Skill%d", i);
XNode* pNode = ini.GetChild(sKey);
TapScoreDistribution& dist = g_Distributions[i];
if( pNode == NULL )
LuaHelpers::ReportScriptErrorFmt("Error trying to read \"%s\" to load AI player skill settings.", AI_PATH);
for(int i= 0; i < NUM_SKILL_LEVELS; ++i)
{
LuaHelpers::ReportScriptErrorFmt("AI.ini: \"%s\" doesn't exist.", sKey.c_str());
dist.fPercent[TNS_None] = 0;
dist.fPercent[TNS_Miss] = 1;
dist.fPercent[TNS_W5] = 0;
dist.fPercent[TNS_W4] = 0;
dist.fPercent[TNS_W3] = 0;
dist.fPercent[TNS_W2] = 0;
dist.fPercent[TNS_W1] = 0;
g_Distributions[i].SetDefaultWeights();
g_Distributions[i].ChangeWeightsToPercents();
}
else
}
else
{
for( int i=0; i<NUM_SKILL_LEVELS; i++ )
{
#define SET_MALF_IF(condition, tns) \
if(condition) \
{ \
LuaHelpers::ReportScriptError("AI weight for " #tns " not set."); \
dist.fPercent[tns]= 0; \
RString sKey = ssprintf("Skill%d", i);
XNode* pNode = ini.GetChild(sKey);
TapScoreDistribution& dist = g_Distributions[i];
if( pNode == NULL )
{
LuaHelpers::ReportScriptErrorFmt("AI.ini: \"%s\" section doesn't exist.", sKey.c_str());
dist.SetDefaultWeights();
}
dist.fPercent[TNS_None] = 0;
bSuccess = pNode->GetAttrValue( "WeightMiss", dist.fPercent[TNS_Miss] );
SET_MALF_IF(!bSuccess, TNS_Miss);
bSuccess = pNode->GetAttrValue( "WeightW5", dist.fPercent[TNS_W5] );
SET_MALF_IF(!bSuccess, TNS_W5);
bSuccess = pNode->GetAttrValue( "WeightW4", dist.fPercent[TNS_W4] );
SET_MALF_IF(!bSuccess, TNS_W4);
bSuccess = pNode->GetAttrValue( "WeightW3", dist.fPercent[TNS_W3] );
SET_MALF_IF(!bSuccess, TNS_W3);
bSuccess = pNode->GetAttrValue( "WeightW2", dist.fPercent[TNS_W2] );
SET_MALF_IF(!bSuccess, TNS_W2);
bSuccess = pNode->GetAttrValue( "WeightW1", dist.fPercent[TNS_W1] );
SET_MALF_IF(!bSuccess, TNS_W1);
#undef SET_MALF_IF
else
{
#define SET_MALF_IF(condition, tns) \
if(condition) \
{ \
LuaHelpers::ReportScriptErrorFmt("AI weight for " #tns " in \"%s\" section not set.", sKey.c_str()); \
dist.fPercent[tns]= 0; \
}
dist.fPercent[TNS_None] = 0;
bSuccess = pNode->GetAttrValue( "WeightMiss", dist.fPercent[TNS_Miss] );
SET_MALF_IF(!bSuccess, TNS_Miss);
bSuccess = pNode->GetAttrValue( "WeightW5", dist.fPercent[TNS_W5] );
SET_MALF_IF(!bSuccess, TNS_W5);
bSuccess = pNode->GetAttrValue( "WeightW4", dist.fPercent[TNS_W4] );
SET_MALF_IF(!bSuccess, TNS_W4);
bSuccess = pNode->GetAttrValue( "WeightW3", dist.fPercent[TNS_W3] );
SET_MALF_IF(!bSuccess, TNS_W3);
bSuccess = pNode->GetAttrValue( "WeightW2", dist.fPercent[TNS_W2] );
SET_MALF_IF(!bSuccess, TNS_W2);
bSuccess = pNode->GetAttrValue( "WeightW1", dist.fPercent[TNS_W1] );
SET_MALF_IF(!bSuccess, TNS_W1);
#undef SET_MALF_IF
}
dist.ChangeWeightsToPercents();
}
float fSum = 0;
for( int j=0; j<NUM_TapNoteScore; j++ )
fSum += dist.fPercent[j];
for( int j=0; j<NUM_TapNoteScore; j++ )
dist.fPercent[j] /= fSum;
}
}
-1
View File
@@ -74,7 +74,6 @@ void PlayerOptions::Init()
ZERO( m_bTurns );
ZERO( m_bTransforms );
m_bMuteOnError = false;
m_FailType = PREFSMAN->m_DefaultFailType;
m_sNoteSkin = "";
}
+1 -2
View File
@@ -221,7 +221,7 @@ PrefsManager::PrefsManager() :
m_iSongsPerPlay ( "SongsPerPlay", 3, ValidateSongsPerPlay ),
m_bDelayedCreditsReconcile ( "DelayedCreditsReconcile", false ),
m_bComboContinuesBetweenSongs ( "ComboContinuesBetweenSongs", false ),
m_ShowSongOptions ( "ShowSongOptions", Maybe_YES ),
m_ShowSongOptions ( "ShowSongOptions", Maybe_NO ),
m_bDancePointsForOni ( "DancePointsForOni", true ),
m_bPercentageScoring ( "PercentageScoring", false ),
m_fMinPercentageForMachineSongHighScore ( "MinPercentageForMachineSongHighScore", 0.0001f ), // This is for home, who cares how bad you do?
@@ -286,7 +286,6 @@ PrefsManager::PrefsManager() :
m_sCoursesToShowRanking ( "CoursesToShowRanking", "" ),
m_bQuirksMode ( "QuirksMode", false ),
m_DefaultFailType("DefaultFailtype", FailType_ImmediateContinue),
/* Debug: */
m_bLogToDisk ( "LogToDisk", true ),
-1
View File
@@ -294,7 +294,6 @@ public:
/** @brief Enable some quirky behavior used by some older versions of StepMania. */
Preference<bool> m_bQuirksMode;
Preference<FailType> m_DefaultFailType;
// Debug:
Preference<bool> m_bLogToDisk;
+7
View File
@@ -289,6 +289,13 @@ void RageBitmapTexture::Create()
if( !TEXTUREMAN->GetOddDimensionWarning() )
bRunCheck = false;
// Don't check if this is the screen texture, the theme can't do anything
// about it. -Kyz
if(actualID == TEXTUREMAN->GetScreenTextureID())
{
bRunCheck= false;
}
if( bRunCheck )
{
float fFrameWidth = this->GetSourceWidth() / (float)this->GetFramesWide();
+23 -2
View File
@@ -74,6 +74,14 @@ RString RageColor::NormalizeColorString( RString sColor )
return c.ToString();
}
void lerp_rage_color(RageColor& out, RageColor const& a, RageColor const& b, float t)
{
out.b= lerp(t, a.b, b.b);
out.g= lerp(t, a.g, b.g);
out.r= lerp(t, a.r, b.r);
out.a= lerp(t, a.a, b.a);
}
void WeightedAvergeOfRSVs(RageSpriteVertex& average_out, RageSpriteVertex const& rsv1, RageSpriteVertex const& rsv2, float percent_between)
{
average_out.p= lerp(percent_between, rsv1.p, rsv2.p);
@@ -207,8 +215,21 @@ int LuaFunc_color( lua_State *L )
c.PushTable( L );
return 1;
}
void LuaFunc_Register_color( lua_State *L ) { lua_register( L, "color", LuaFunc_color ); }
REGISTER_WITH_LUA_FUNCTION( LuaFunc_Register_color );
LUAFUNC_REGISTER_COMMON(color);
int LuaFunc_lerp_color(lua_State *L)
{
// Args: percent, color, color
// Returns: color
float percent= FArg(1);
RageColor a, b, c;
a.FromStack(L, 2);
b.FromStack(L, 3);
lerp_rage_color(c, a, b, percent);
c.PushTable(L);
return 1;
}
LUAFUNC_REGISTER_COMMON(lerp_color);
/*
* Copyright (c) 2006 Glenn Maynard
+1
View File
@@ -342,6 +342,7 @@ struct RageSpriteVertex // has color
RageVector2 t; // texture coordinates
};
void lerp_rage_color(RageColor& out, RageColor const& a, RageColor const& b, float t);
void WeightedAvergeOfRSVs(RageSpriteVertex& average_out, RageSpriteVertex const& rsv1, RageSpriteVertex const& rsv2, float percent_between);
struct RageModelVertex // doesn't have color. Relies on material color
+70
View File
@@ -2329,6 +2329,76 @@ LuaFunction( PrettyPercent, PrettyPercent( FArg(1), FArg(2) ) );
//LuaFunction( IsHexVal, IsHexVal( SArg(1) ) );
static bool UndocumentedFeature( RString s ){ sm_crash(s); return true; }
LuaFunction( UndocumentedFeature, UndocumentedFeature(SArg(1)) );
LuaFunction( lerp, lerp(FArg(1), FArg(2), FArg(3)) );
void luafunc_approach_internal(lua_State* L, int valind, int goalind, int speedind);
void luafunc_approach_internal(lua_State* L, int valind, int goalind, int speedind, int process_index)
{
#define TONUMBER_NICE(dest, num_name, index) \
if(!lua_isnumber(L, index)) \
{ \
luaL_error(L, "approach: " #num_name " for approach %d is not a number.", process_index); \
} \
dest= lua_tonumber(L, index);
float val= 0;
float goal= 0;
float speed= 0;
TONUMBER_NICE(val, current, valind);
TONUMBER_NICE(goal, goal, goalind);
TONUMBER_NICE(speed, speed, speedind);
#undef TONUMBER_NICE
if(speed < 0)
{
luaL_error(L, "approach: speed %d is negative.", process_index);
}
fapproach(val, goal, speed);
lua_pushnumber(L, val);
}
int LuaFunc_approach(lua_State* L);
int LuaFunc_approach(lua_State* L)
{
// Args: current, goal, speed
// Returns: new_current
luafunc_approach_internal(L, 1, 2, 3, 1);
return 1;
}
LUAFUNC_REGISTER_COMMON(approach);
int LuaFunc_multiapproach(lua_State* L);
int LuaFunc_multiapproach(lua_State* L)
{
// Args: {currents}, {goals}, {speeds}
// Returns: {currents}
// Modifies the values in {currents} in place.
if(lua_gettop(L) != 3)
{
luaL_error(L, "multiapproach: A table of current values, a table of goal values, and a table of speeds must be passed.");
}
size_t currents_len= lua_objlen(L, 1);
size_t goals_len= lua_objlen(L, 2);
size_t speeds_len= lua_objlen(L, 3);
if(currents_len != goals_len || currents_len != speeds_len)
{
luaL_error(L, "multiapproach: There must be the same number of current values, goal values, and speeds.");
}
if(!lua_istable(L, 1) || !lua_istable(L, 2) || !lua_istable(L, 3))
{
luaL_error(L, "multiapproach: current, goal, and speed must all be tables.");
}
for(size_t i= 1; i <= currents_len; ++i)
{
lua_rawgeti(L, 1, i);
lua_rawgeti(L, 2, i);
lua_rawgeti(L, 3, i);
luafunc_approach_internal(L, -3, -2, -1, i);
lua_rawseti(L, 1, i);
lua_pop(L, 3);
}
lua_pushvalue(L, 1);
return 1;
}
LUAFUNC_REGISTER_COMMON(multiapproach);
/*
* Copyright (c) 2001-2005 Chris Danford, Glenn Maynard
+30 -20
View File
@@ -25,15 +25,32 @@ void RollingNumbers::Load( const RString &sMetricsGroup )
UpdateText();
}
void RollingNumbers::DrawPart(RageColor const* diffuse, RageColor const& stroke,
float crop_left, float crop_right)
{
for(int i= 0; i < NUM_DIFFUSE_COLORS; ++i)
{
m_pTempState->diffuse[i]= diffuse[i];
}
SetCurrStrokeColor(stroke);
m_pTempState->crop.left= crop_left;
m_pTempState->crop.right= crop_right;
BitmapText::DrawPrimitives();
}
void RollingNumbers::DrawPrimitives()
{
RageColor c_orig = this->GetDiffuse();
RageColor c2_orig = this->GetStrokeColor();
RageColor c = this->GetDiffuse();
c *= LEADING_ZERO_MULTIPLY_COLOR;
RageColor c2 = this->GetStrokeColor();
c2 *= LEADING_ZERO_MULTIPLY_COLOR;
RageColor diffuse_orig[NUM_DIFFUSE_COLORS];
RageColor diffuse_temp[NUM_DIFFUSE_COLORS];
RageColor stroke_orig= GetCurrStrokeColor();
RageColor stroke_temp= stroke_orig * LEADING_ZERO_MULTIPLY_COLOR;
for(int i= 0; i < NUM_DIFFUSE_COLORS; ++i)
{
diffuse_orig[i]= m_pTempState->diffuse[i];
diffuse_temp[i]= m_pTempState->diffuse[i] * LEADING_ZERO_MULTIPLY_COLOR;
}
float original_crop_left= m_pTempState->crop.left;
float original_crop_right= m_pTempState->crop.right;
RString s = this->GetText();
int i;
@@ -53,21 +70,14 @@ void RollingNumbers::DrawPrimitives()
float f = i / (float)s.length();
// draw leading part
SetDiffuse( c );
SetStrokeColor( c2 );
SetCropLeft( 0 );
SetCropRight( 1-f );
BitmapText::DrawPrimitives();
DrawPart(diffuse_temp, stroke_temp,
max(0, original_crop_left), max(1-f, original_crop_right));
// draw regular color part
SetDiffuse( c_orig );
SetStrokeColor( c2_orig );
SetCropLeft( f );
SetCropRight( 0 );
BitmapText::DrawPrimitives();
DrawPart(diffuse_orig, stroke_orig,
max(f, original_crop_left), max(0, original_crop_right));
SetCropLeft( 0 );
SetCropRight( 0 );
m_pTempState->crop.left= original_crop_left;
m_pTempState->crop.right= original_crop_right;
}
void RollingNumbers::Update( float fDeltaTime )
+2
View File
@@ -13,6 +13,8 @@ public:
void Load( const RString &sMetricsGroup );
virtual RollingNumbers *Copy() const;
void DrawPart(RageColor const* diffuse, RageColor const& stroke,
float crop_left, float crop_right);
virtual void DrawPrimitives();
virtual void Update( float fDeltaTime );
+155
View File
@@ -30,6 +30,7 @@
#include "ScreenTextEntry.h"
#include "SongManager.h"
#include "SongUtil.h"
#include "SpecialFiles.h"
#include "StepsUtil.h"
#include "Style.h"
#include "ThemeManager.h"
@@ -115,8 +116,120 @@ static const char *EditStateNames[] = {
XToString( EditState );
LuaXType( EditState );
map<RString, EditButton> name_to_edit_button;
void ScreenEdit::InitEditMappings()
{
// Created courtesy of query replace regex.
name_to_edit_button["COLUMN_0"]= EDIT_BUTTON_COLUMN_0;
name_to_edit_button["COLUMN_1"]= EDIT_BUTTON_COLUMN_1;
name_to_edit_button["COLUMN_2"]= EDIT_BUTTON_COLUMN_2;
name_to_edit_button["COLUMN_3"]= EDIT_BUTTON_COLUMN_3;
name_to_edit_button["COLUMN_4"]= EDIT_BUTTON_COLUMN_4;
name_to_edit_button["COLUMN_5"]= EDIT_BUTTON_COLUMN_5;
name_to_edit_button["COLUMN_6"]= EDIT_BUTTON_COLUMN_6;
name_to_edit_button["COLUMN_7"]= EDIT_BUTTON_COLUMN_7;
name_to_edit_button["COLUMN_8"]= EDIT_BUTTON_COLUMN_8;
name_to_edit_button["COLUMN_9"]= EDIT_BUTTON_COLUMN_9;
name_to_edit_button["RIGHT_SIDE"]= EDIT_BUTTON_RIGHT_SIDE;
name_to_edit_button["LAY_ROLL"]= EDIT_BUTTON_LAY_ROLL;
name_to_edit_button["LAY_TAP_ATTACK"]= EDIT_BUTTON_LAY_TAP_ATTACK;
name_to_edit_button["REMOVE_NOTE"]= EDIT_BUTTON_REMOVE_NOTE;
name_to_edit_button["CYCLE_TAP_LEFT"]= EDIT_BUTTON_CYCLE_TAP_LEFT;
name_to_edit_button["CYCLE_TAP_RIGHT"]= EDIT_BUTTON_CYCLE_TAP_RIGHT;
name_to_edit_button["CYCLE_SEGMENT_LEFT"]= EDIT_BUTTON_CYCLE_SEGMENT_LEFT;
name_to_edit_button["CYCLE_SEGMENT_RIGHT"]= EDIT_BUTTON_CYCLE_SEGMENT_RIGHT;
name_to_edit_button["SCROLL_UP_LINE"]= EDIT_BUTTON_SCROLL_UP_LINE;
name_to_edit_button["SCROLL_UP_PAGE"]= EDIT_BUTTON_SCROLL_UP_PAGE;
name_to_edit_button["SCROLL_UP_TS"]= EDIT_BUTTON_SCROLL_UP_TS;
name_to_edit_button["SCROLL_DOWN_LINE"]= EDIT_BUTTON_SCROLL_DOWN_LINE;
name_to_edit_button["SCROLL_DOWN_PAGE"]= EDIT_BUTTON_SCROLL_DOWN_PAGE;
name_to_edit_button["SCROLL_DOWN_TS"]= EDIT_BUTTON_SCROLL_DOWN_TS;
name_to_edit_button["SCROLL_NEXT_MEASURE"]= EDIT_BUTTON_SCROLL_NEXT_MEASURE;
name_to_edit_button["SCROLL_PREV_MEASURE"]= EDIT_BUTTON_SCROLL_PREV_MEASURE;
name_to_edit_button["SCROLL_HOME"]= EDIT_BUTTON_SCROLL_HOME;
name_to_edit_button["SCROLL_END"]= EDIT_BUTTON_SCROLL_END;
name_to_edit_button["SCROLL_NEXT"]= EDIT_BUTTON_SCROLL_NEXT;
name_to_edit_button["SCROLL_PREV"]= EDIT_BUTTON_SCROLL_PREV;
name_to_edit_button["SEGMENT_NEXT"]= EDIT_BUTTON_SEGMENT_NEXT;
name_to_edit_button["SEGMENT_PREV"]= EDIT_BUTTON_SEGMENT_PREV;
name_to_edit_button["SCROLL_SELECT"]= EDIT_BUTTON_SCROLL_SELECT;
name_to_edit_button["LAY_SELECT"]= EDIT_BUTTON_LAY_SELECT;
name_to_edit_button["SCROLL_SPEED_UP"]= EDIT_BUTTON_SCROLL_SPEED_UP;
name_to_edit_button["SCROLL_SPEED_DOWN"]= EDIT_BUTTON_SCROLL_SPEED_DOWN;
name_to_edit_button["SNAP_NEXT"]= EDIT_BUTTON_SNAP_NEXT;
name_to_edit_button["SNAP_PREV"]= EDIT_BUTTON_SNAP_PREV;
name_to_edit_button["OPEN_EDIT_MENU"]= EDIT_BUTTON_OPEN_EDIT_MENU;
name_to_edit_button["OPEN_TIMING_MENU"]= EDIT_BUTTON_OPEN_TIMING_MENU;
name_to_edit_button["OPEN_ALTER_MENU"]= EDIT_BUTTON_OPEN_ALTER_MENU;
name_to_edit_button["OPEN_AREA_MENU"]= EDIT_BUTTON_OPEN_AREA_MENU;
name_to_edit_button["OPEN_BGCHANGE_LAYER1_MENU"]= EDIT_BUTTON_OPEN_BGCHANGE_LAYER1_MENU;
name_to_edit_button["OPEN_BGCHANGE_LAYER2_MENU"]= EDIT_BUTTON_OPEN_BGCHANGE_LAYER2_MENU;
name_to_edit_button["OPEN_COURSE_MENU"]= EDIT_BUTTON_OPEN_COURSE_MENU;
name_to_edit_button["OPEN_COURSE_ATTACK_MENU"]= EDIT_BUTTON_OPEN_COURSE_ATTACK_MENU;
name_to_edit_button["OPEN_STEP_ATTACK_MENU"]= EDIT_BUTTON_OPEN_STEP_ATTACK_MENU;
name_to_edit_button["ADD_STEP_MODS"]= EDIT_BUTTON_ADD_STEP_MODS;
name_to_edit_button["OPEN_INPUT_HELP"]= EDIT_BUTTON_OPEN_INPUT_HELP;
name_to_edit_button["BAKE_RANDOM_FROM_SONG_GROUP"]= EDIT_BUTTON_BAKE_RANDOM_FROM_SONG_GROUP;
name_to_edit_button["BAKE_RANDOM_FROM_SONG_GROUP_AND_GENRE"]= EDIT_BUTTON_BAKE_RANDOM_FROM_SONG_GROUP_AND_GENRE;
name_to_edit_button["PLAY_FROM_START"]= EDIT_BUTTON_PLAY_FROM_START;
name_to_edit_button["PLAY_FROM_CURSOR"]= EDIT_BUTTON_PLAY_FROM_CURSOR;
name_to_edit_button["PLAY_SELECTION"]= EDIT_BUTTON_PLAY_SELECTION;
name_to_edit_button["RECORD_FROM_CURSOR"]= EDIT_BUTTON_RECORD_FROM_CURSOR;
name_to_edit_button["RECORD_SELECTION"]= EDIT_BUTTON_RECORD_SELECTION;
name_to_edit_button["RETURN_TO_EDIT"]= EDIT_BUTTON_RETURN_TO_EDIT;
name_to_edit_button["INSERT"]= EDIT_BUTTON_INSERT;
name_to_edit_button["DELETE"]= EDIT_BUTTON_DELETE;
name_to_edit_button["INSERT_SHIFT_PAUSES"]= EDIT_BUTTON_INSERT_SHIFT_PAUSES;
name_to_edit_button["DELETE_SHIFT_PAUSES"]= EDIT_BUTTON_DELETE_SHIFT_PAUSES;
name_to_edit_button["OPEN_NEXT_STEPS"]= EDIT_BUTTON_OPEN_NEXT_STEPS;
name_to_edit_button["OPEN_PREV_STEPS"]= EDIT_BUTTON_OPEN_PREV_STEPS;
name_to_edit_button["PLAY_SAMPLE_MUSIC"]= EDIT_BUTTON_PLAY_SAMPLE_MUSIC;
name_to_edit_button["BPM_UP"]= EDIT_BUTTON_BPM_UP;
name_to_edit_button["BPM_DOWN"]= EDIT_BUTTON_BPM_DOWN;
name_to_edit_button["STOP_UP"]= EDIT_BUTTON_STOP_UP;
name_to_edit_button["STOP_DOWN"]= EDIT_BUTTON_STOP_DOWN;
name_to_edit_button["DELAY_UP"]= EDIT_BUTTON_DELAY_UP;
name_to_edit_button["DELAY_DOWN"]= EDIT_BUTTON_DELAY_DOWN;
name_to_edit_button["OFFSET_UP"]= EDIT_BUTTON_OFFSET_UP;
name_to_edit_button["OFFSET_DOWN"]= EDIT_BUTTON_OFFSET_DOWN;
name_to_edit_button["SAMPLE_START_UP"]= EDIT_BUTTON_SAMPLE_START_UP;
name_to_edit_button["SAMPLE_START_DOWN"]= EDIT_BUTTON_SAMPLE_START_DOWN;
name_to_edit_button["SAMPLE_LENGTH_UP"]= EDIT_BUTTON_SAMPLE_LENGTH_UP;
name_to_edit_button["SAMPLE_LENGTH_DOWN"]= EDIT_BUTTON_SAMPLE_LENGTH_DOWN;
name_to_edit_button["ADJUST_FINE"]= EDIT_BUTTON_ADJUST_FINE;
name_to_edit_button["SAVE"]= EDIT_BUTTON_SAVE;
name_to_edit_button["UNDO"]= EDIT_BUTTON_UNDO;
name_to_edit_button["ADD_COURSE_MODS"]= EDIT_BUTTON_ADD_COURSE_MODS;
name_to_edit_button["SWITCH_PLAYERS"]= EDIT_BUTTON_SWITCH_PLAYERS;
name_to_edit_button["SWITCH_TIMINGS"]= EDIT_BUTTON_SWITCH_TIMINGS;
m_EditMappingsDeviceInput.Clear();
// Common mappings:
@@ -381,8 +494,50 @@ void ScreenEdit::InitEditMappings()
m_RecordPausedMappingsDeviceInput.button[EDIT_BUTTON_RETURN_TO_EDIT][0] = DeviceInput(DEVICE_KEYBOARD, KEY_ESC);
m_RecordPausedMappingsMenuButton.button[EDIT_BUTTON_RETURN_TO_EDIT][1] = GAME_BUTTON_BACK;
m_RecordPausedMappingsDeviceInput.button[EDIT_BUTTON_UNDO][0] = DeviceInput(DEVICE_KEYBOARD, KEY_Cu);
IniFile mapping_ini;
// Only use the mappings file if it exists. It's meant to be optional, and
// only used in rare cases like someone having critical keys broken. -Kyz
if(mapping_ini.ReadFile(SpecialFiles::EDIT_MODE_KEYMAPS_PATH))
{
LoadKeymapSectionIntoMappingsMember(mapping_ini.GetChild("Edit"),
m_EditMappingsDeviceInput);
LoadKeymapSectionIntoMappingsMember(mapping_ini.GetChild("Play"),
m_PlayMappingsDeviceInput);
LoadKeymapSectionIntoMappingsMember(mapping_ini.GetChild("Record"),
m_RecordMappingsDeviceInput);
LoadKeymapSectionIntoMappingsMember(mapping_ini.GetChild("RecordPaused"),
m_RecordPausedMappingsDeviceInput);
}
}
void ScreenEdit::LoadKeymapSectionIntoMappingsMember(XNode const* section, MapEditToDI& mappings)
{
if(section == NULL) {return;} // Not an error, sections are optional. -Kyz
FOREACH_CONST_Attr(section, attr)
{
map<RString, EditButton>::iterator name_entry=
name_to_edit_button.find(attr->first);
if(name_entry != name_to_edit_button.end())
{
RString joined_names;
attr->second->GetValue(joined_names);
vector<RString> key_names;
split(joined_names, DEVICE_INPUT_SEPARATOR, key_names, false);
for(size_t k= 0; k < key_names.size() && k < NUM_EDIT_TO_DEVICE_SLOTS; ++k)
{
DeviceInput devi;
devi.FromString(key_names[k]);
if(devi.IsValid())
{
mappings.button[name_entry->second][k]= devi;
}
}
}
}
}
/* Given a DeviceInput that was just depressed, return an active edit function. */
EditButton ScreenEdit::DeviceToEdit( const DeviceInput &DeviceI ) const
{
+3
View File
@@ -39,6 +39,7 @@ LuaDeclareType( EditState );
enum EditButton
{
// Add to the name_to_edit_button list when adding to this enum. -Kyz
EDIT_BUTTON_COLUMN_0,
EDIT_BUTTON_COLUMN_1,
EDIT_BUTTON_COLUMN_2,
@@ -151,6 +152,7 @@ enum EditButton
EDIT_BUTTON_SWITCH_TIMINGS, /**< Allow switching between Song and Step TimingData. */
// Add to the name_to_edit_button list when adding to this enum. -Kyz
NUM_EditButton, // leave this at the end
EditButton_Invalid
};
@@ -665,6 +667,7 @@ public:
bool EditIsBeingPressed( EditButton button ) const;
const MapEditToDI *GetCurrentDeviceInputMap() const;
const MapEditButtonToMenuButton *GetCurrentMenuButtonMap() const;
void LoadKeymapSectionIntoMappingsMember(XNode const* section, MapEditToDI& mappings);
MapEditToDI m_EditMappingsDeviceInput;
MapEditToDI m_PlayMappingsDeviceInput;
MapEditToDI m_RecordMappingsDeviceInput;
+1 -1
View File
@@ -2369,7 +2369,7 @@ bool ScreenGameplay::Input( const InputEventPlus &input )
{
AbortGiveUp( true );
if( GamePreferences::m_AutoPlay == PC_HUMAN && GAMESTATE->m_pPlayerState[PLAYER_1]->m_PlayerOptions.GetCurrent().m_fPlayerAutoPlay == 0 )
if( GamePreferences::m_AutoPlay == PC_HUMAN && GAMESTATE->m_pPlayerState[input.pn]->m_PlayerOptions.GetCurrent().m_fPlayerAutoPlay == 0 )
{
PlayerInfo& pi = GetPlayerInfoForInput( input );
+2 -2
View File
@@ -673,7 +673,7 @@ void ScreenOptions::PositionRows( bool bTween )
i < first_start ||
(i >= first_end && i < second_start) ||
i >= second_end;
for( int j=0; j<4; j++ )
for( int j=0; j<NUM_DIFFUSE_COLORS; j++ )
tsDestination.diffuse[j].a = bHidden? 0.0f:1.0f;
if( !bHidden )
pos++;
@@ -686,7 +686,7 @@ void ScreenOptions::PositionRows( bool bTween )
tsDestination.Init();
tsDestination.pos.y = SEPARATE_EXIT_ROW_Y;
for( int j=0; j<4; j++ )
for( int j=0; j<NUM_DIFFUSE_COLORS; j++ )
tsDestination.diffuse[j].a = 1.0f;
pSeparateExitRow->SetDestination( tsDestination, bTween );
}
+33 -5
View File
@@ -30,10 +30,12 @@ static void GetPrefsDefaultModifiers( PlayerOptions &po, SongOptions &so )
static void SetPrefsDefaultModifiers( const PlayerOptions &po, const SongOptions &so )
{
vector<RString> as;
if( po.GetString() != "" )
as.push_back( po.GetString() );
if( so.GetString() != "" )
as.push_back( so.GetString() );
#define remove_empty_back() if(as.back() == "") { as.pop_back(); }
as.push_back(po.GetString());
remove_empty_back();
as.push_back(so.GetString());
remove_empty_back();
#undef remove_empty_back
PREFSMAN->m_sDefaultModifiers.Set( join(", ",as) );
}
@@ -336,6 +338,32 @@ static void DefaultNoteSkin( int &sel, bool ToSel, const ConfOption *pConfOption
}
}
static void DefaultFailChoices(vector<RString>& out)
{
out.push_back("Immediate");
out.push_back("ImmediateContinue");
out.push_back("EndOfSong");
out.push_back("Off");
}
static void DefaultFailType(int& sel, bool to_sel, const ConfOption* conf_option)
{
if(to_sel)
{
PlayerOptions po;
po.FromString(PREFSMAN->m_sDefaultModifiers);
sel= po.m_FailType;
}
else
{
PlayerOptions po;
SongOptions so;
GetPrefsDefaultModifiers(po, so);
po.m_FailType= static_cast<FailType>(sel);
SetPrefsDefaultModifiers(po, so);
}
}
// Background options
static void BGBrightness( int &sel, bool ToSel, const ConfOption *pConfOption )
{
@@ -708,7 +736,7 @@ static void InitializeConfOptions()
ADD( ConfOption( "ProgressiveLifebar", MovePref<int>, "Off","|1","|2","|3","|4","|5","|6","|7","|8") );
ADD( ConfOption( "ProgressiveStageLifebar", MovePref<int>, "Off","|1","|2","|3","|4","|5","|6","|7","|8","Insanity") );
ADD( ConfOption( "ProgressiveNonstopLifebar", MovePref<int>, "Off","|1","|2","|3","|4","|5","|6","|7","|8","Insanity") );
ADD( ConfOption( "DefaultFailType", MovePref<FailType>, "Immediate","ImmediateContinue","EndOfSong","Off" ) );
ADD( ConfOption( "DefaultFailType", DefaultFailType, DefaultFailChoices ) );
ADD( ConfOption( "CoinsPerCredit", CoinsPerCredit, "|1","|2","|3","|4","|5","|6","|7","|8","|9","|10","|11","|12","|13","|14","|15","|16" ) );
ADD( ConfOption( "Premium", MovePref<Premium>, "Off","Double for 1 Credit","2 Players for 1 Credit" ) );
ADD( ConfOption( "JointPremium", JointPremium, "Off","2 Players for 1 Credit" ) );
+9 -1
View File
@@ -66,7 +66,12 @@ void ScreenPrompt::Init()
for( int i=0; i<NUM_PromptAnswer; i++ )
{
m_textAnswer[i].LoadFromFont( THEME->GetPathF(m_sName,"answer") );
LOAD_ALL_COMMANDS( m_textAnswer[i] );
// The name of the actor isn't set because it is not known at this point
// how many answers there will be, and the name depends on the number of
// answers as a clumsy way of letting the themer set different positions
// for different answer groups. The name is set in BeginScreen, and
// then the commands are loaded. -Kyz (At least, that seems like the
// explanation to me, reading the code years after the author left)
this->AddChild( &m_textAnswer[i] );
}
@@ -90,6 +95,9 @@ void ScreenPrompt::BeginScreen()
{
RString sElem = ssprintf("Answer%dOf%d", i+1, g_PromptType+1);
m_textAnswer[i].SetName( sElem );
LOAD_ALL_COMMANDS(m_textAnswer[i]);
// Side note: Because LOAD_ALL_COMMANDS occurs here, InitCommand will
// not be run for the actors. People can just use OnCommand instead.
RString sAnswer = PromptAnswerToString( (PromptAnswer)i );
// FRAGILE
if( g_PromptType == PROMPT_OK )
+33 -4
View File
@@ -42,7 +42,7 @@
* @brief The internal version of the cache for StepMania.
*
* Increment this value to invalidate the current cache. */
const int FILE_CACHE_VERSION = 220;
const int FILE_CACHE_VERSION = 222;
/** @brief How long does a song sample last by default? */
const float DEFAULT_MUSIC_SAMPLE_LENGTH = 12.f;
@@ -89,6 +89,11 @@ Song::~Song()
FOREACH( Steps*, m_vpSteps, s )
SAFE_DELETE( *s );
m_vpSteps.clear();
FOREACH(Steps*, m_UnknownStyleSteps, s)
{
SAFE_DELETE(*s);
}
m_UnknownStyleSteps.clear();
// It's the responsibility of the owner of this Song to make sure
// that all pointers to this Song and its Steps are invalidated.
@@ -99,6 +104,7 @@ void Song::DetachSteps()
m_vpSteps.clear();
FOREACH_ENUM( StepsType, st )
m_vpStepsByType[st].clear();
m_UnknownStyleSteps.clear();
}
float Song::GetFirstSecond() const
@@ -154,6 +160,11 @@ void Song::Reset()
m_vpSteps.clear();
FOREACH_ENUM( StepsType, st )
m_vpStepsByType[st].clear();
FOREACH(Steps*, m_UnknownStyleSteps, s)
{
SAFE_DELETE(*s);
}
m_UnknownStyleSteps.clear();
Song empty;
*this = empty;
@@ -1023,6 +1034,10 @@ bool Song::SaveToSMFile()
vpStepsToSave.push_back( pSteps );
}
FOREACH_CONST(Steps*, m_UnknownStyleSteps, s)
{
vpStepsToSave.push_back(*s);
}
return NotesWriterSM::Write( sPath, *this, vpStepsToSave );
@@ -1055,6 +1070,10 @@ bool Song::SaveToSSCFile( RString sPath, bool bSavingCache )
pSteps->SetFilename(path);
vpStepsToSave.push_back( pSteps );
}
FOREACH_CONST(Steps*, m_UnknownStyleSteps, s)
{
vpStepsToSave.push_back(*s);
}
if (bSavingCache)
{
@@ -1504,9 +1523,19 @@ RString Song::GetTranslitFullTitle() const
void Song::AddSteps( Steps* pSteps )
{
m_vpSteps.push_back( pSteps );
ASSERT_M( pSteps->m_StepsType < NUM_StepsType, ssprintf("%i", pSteps->m_StepsType) );
m_vpStepsByType[pSteps->m_StepsType].push_back( pSteps );
// Songs of unknown stepstype are saved as a forwards compatibility feature
// so that editing a simfile made by a future version that has a new style
// won't delete those steps. -Kyz
if(pSteps->m_StepsType != StepsType_Invalid)
{
m_vpSteps.push_back( pSteps );
ASSERT_M( pSteps->m_StepsType < NUM_StepsType, ssprintf("%i", pSteps->m_StepsType) );
m_vpStepsByType[pSteps->m_StepsType].push_back( pSteps );
}
else
{
m_UnknownStyleSteps.push_back(pSteps);
}
}
void Song::DeleteSteps( const Steps* pSteps, bool bReAutoGen )
+2
View File
@@ -447,6 +447,8 @@ private:
vector<Steps*> m_vpSteps;
/** @brief the Steps of a particular StepsType that belong to this Song. */
vector<Steps*> m_vpStepsByType[NUM_StepsType];
/** @brief the Steps that are of unrecognized Styles. */
vector<Steps*> m_UnknownStyleSteps;
};
#endif
+1
View File
@@ -4,6 +4,7 @@
const RString SpecialFiles::USER_PACKAGES_DIR = "UserPackages/";
const RString SpecialFiles::PACKAGES_DIR = "Packages/";
const RString SpecialFiles::KEYMAPS_PATH = "Save/Keymaps.ini";
const RString SpecialFiles::EDIT_MODE_KEYMAPS_PATH = "Save/EditMode_Keymaps.ini";
const RString SpecialFiles::PREFERENCES_INI_PATH = "Save/Preferences.ini";
const RString SpecialFiles::THEMES_DIR = "Themes/";
const RString SpecialFiles::LANGUAGES_SUBDIR = "Languages/";
+4
View File
@@ -16,6 +16,10 @@ namespace SpecialFiles
* This is not the user packages directory. */
extern const RString PACKAGES_DIR;
extern const RString KEYMAPS_PATH;
/** @brief Edit Mode keymaps are separate from standard keymaps because
* it should not change with the gametype, and to avoid possible
* interference with the normal keymaps system. -Kyz */
extern const RString EDIT_MODE_KEYMAPS_PATH;
extern const RString PREFERENCES_INI_PATH;
/** @brief The directory that contains the themes. */
extern const RString THEMES_DIR;
+2
View File
@@ -377,6 +377,7 @@ public:
static int AllFailed( T* p, lua_State *L ) { lua_pushboolean(L, p->AllFailed()); return 1; }
static int GetStage( T* p, lua_State *L ) { LuaHelpers::Push( L, p->m_Stage ); return 1; }
DEFINE_METHOD( GetStageIndex, m_iStageIndex )
DEFINE_METHOD(GetStepsSeconds, m_fStepsSeconds)
static int PlayerHasHighScore( T* p, lua_State *L )
{
lua_pushboolean(L, p->PlayerHasHighScore(Enum::Check<PlayerNumber>(L, 1)));
@@ -395,6 +396,7 @@ public:
ADD_METHOD( AllFailed );
ADD_METHOD( GetStage );
ADD_METHOD( GetStageIndex );
ADD_METHOD( GetStepsSeconds );
ADD_METHOD( PlayerHasHighScore );
ADD_METHOD( GetEarnedExtraStage );
}
+16 -1
View File
@@ -258,8 +258,20 @@ float Steps::PredictMeter() const
void Steps::TidyUpData()
{
// Don't set the StepsType to dance single if it's invalid. That just
// causes unrecognized charts to end up where they don't belong.
// Leave it as StepsType_Invalid so the Song can handle it specially. This
// is a forwards compatibility feature, so that if a future version adds a
// new style, editing a simfile with unrecognized Steps won't silently
// delete them. -Kyz
if( m_StepsType == StepsType_Invalid )
m_StepsType = StepsType_dance_single;
{
LOG->Warn("Detected steps with unknown style '%s' in '%s'", m_StepsTypeStr.c_str(), m_pSong->m_sSongFileName.c_str());
}
else if(m_StepsTypeStr == "")
{
m_StepsTypeStr= GAMEMAN->GetStepsTypeInfo(m_StepsType).szName;
}
if( GetDifficulty() == Difficulty_Invalid )
SetDifficulty( StringToDifficulty(GetDescription()) );
@@ -465,12 +477,14 @@ void Steps::AutogenFrom( const Steps *parent_, StepsType ntTo )
{
parent = parent_;
m_StepsType = ntTo;
m_StepsTypeStr= GAMEMAN->GetStepsTypeInfo(ntTo).szName;
m_Timing = parent->m_Timing;
}
void Steps::CopyFrom( Steps* pSource, StepsType ntTo, float fMusicLengthSeconds ) // pSource does not have to be of the same StepsType
{
m_StepsType = ntTo;
m_StepsTypeStr= GAMEMAN->GetStepsTypeInfo(ntTo).szName;
NoteData noteData;
pSource->GetNoteData( noteData );
noteData.SetNumTracks( GAMEMAN->GetStepsTypeInfo(ntTo).iNumTracks );
@@ -489,6 +503,7 @@ void Steps::CopyFrom( Steps* pSource, StepsType ntTo, float fMusicLengthSeconds
void Steps::CreateBlank( StepsType ntTo )
{
m_StepsType = ntTo;
m_StepsTypeStr= GAMEMAN->GetStepsTypeInfo(ntTo).szName;
NoteData noteData;
noteData.SetNumTracks( GAMEMAN->GetStepsTypeInfo(ntTo).iNumTracks );
this->SetNoteData( noteData );
+2
View File
@@ -177,6 +177,8 @@ public:
void PushSelf( lua_State *L );
StepsType m_StepsType;
/** @brief The string form of the StepsType, for dealing with unrecognized styles. */
RString m_StepsTypeStr;
/** @brief The Song these Steps are associated with */
Song *m_pSong;