From 6f95303feaf1801e9a814dfc143e2cb8f6bbff3e Mon Sep 17 00:00:00 2001 From: Jeremy Clarke Date: Sun, 14 Jun 2020 03:20:42 +0100 Subject: [PATCH 01/30] fill_dword(): Replace memset() with simple loop memset() sets bytes, we need to set dwords! The compiler will optimise this nicely, so no need for optimisations or assembly in the code. --- src/ppui/fastfill.h | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/ppui/fastfill.h b/src/ppui/fastfill.h index 1517c5a6..7aec92dd 100644 --- a/src/ppui/fastfill.h +++ b/src/ppui/fastfill.h @@ -28,11 +28,10 @@ * */ -#include - static inline void fill_dword(pp_uint32* buff, pp_uint32 dw, pp_uint32 len) { - memset(buff, dw, len); + while (len--) + *(buff++) = dw; } static inline void fill_dword_vertical(pp_uint32* buff, pp_uint32 dw, pp_uint32 len, pp_uint32 pitch) From e0652ecca58ff2d4fc89b9eaec5ec3cd015bea91 Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Fri, 9 Oct 2020 23:44:21 +0100 Subject: [PATCH 02/30] Fix #218: Inverted samples during signed-unsigned conversion --- src/milkyplay/SampleLoaderWAV.cpp | 2 +- src/milkyplay/XModule.cpp | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/milkyplay/SampleLoaderWAV.cpp b/src/milkyplay/SampleLoaderWAV.cpp index abcab22c..2a06c1f0 100644 --- a/src/milkyplay/SampleLoaderWAV.cpp +++ b/src/milkyplay/SampleLoaderWAV.cpp @@ -689,7 +689,7 @@ mp_sint32 SampleLoaderWAV::saveSample(const SYSCHAR* fileName, mp_sint32 index) mp_ubyte* dstPtr = new mp_ubyte[smp->samplen]; mp_ubyte* dst = dstPtr; for (mp_uint32 i = 0; i < smp->samplen; i++) - *dstPtr++ = ((mp_sbyte)smp->getSampleValue(i))^127; + *dstPtr++ = ((mp_sbyte)smp->getSampleValue(i))^128; f.write(dst, 1, smp->samplen); delete[] dst; } diff --git a/src/milkyplay/XModule.cpp b/src/milkyplay/XModule.cpp index 0315f0fb..e3fd719c 100644 --- a/src/milkyplay/XModule.cpp +++ b/src/milkyplay/XModule.cpp @@ -1519,7 +1519,7 @@ bool XModule::loadSample(XMFileBase& f,void* buffer,mp_uint32 size,mp_uint32 len if (flags & ST_UNSIGNED) { for (i = 0; i < length; i++) - dstPtr[i] = (dstPtr[i]^32767); + dstPtr[i] = (dstPtr[i]^32768); } } // 8 bit sample @@ -1539,7 +1539,7 @@ bool XModule::loadSample(XMFileBase& f,void* buffer,mp_uint32 size,mp_uint32 len if (flags & ST_UNSIGNED) { for (mp_uint32 i = 0; i < length; i++) - smpPtr[i] ^= 127; + smpPtr[i] ^= 128; } } From bb785e2d732219fce02a79f70e7b3460ff35df02 Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Sat, 10 Oct 2020 00:06:21 +0100 Subject: [PATCH 03/30] Fix #217: Difficult to resize sample selection Don't require ctrl/cmd modifier. Increase resizing zone to minimum 4 pixels. --- src/tracker/SampleEditorControl.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp index 16f7c1d7..42c123bd 100644 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -1097,16 +1097,16 @@ pp_int32 SampleEditorControl::dispatchEvent(PPEvent* event) pp_int32 x2 = (pp_int32)((sEnd)/xScale)-startPos + location.x + 2; pp_int32 minDist = (scrollDist>>4); - if (minDist < 1) minDist = 1; + if (minDist < 4) minDist = 4; pp_int32 sDist1 = abs(x1 - p->x); pp_int32 sDist2 = abs(p->x - x2); - if (sDist1 >= 0 && sDist1 <= minDist && (::getKeyModifier() == KeyModifierCTRL)) + if (sDist1 >= 0 && sDist1 <= minDist) { type = MouseCursorTypeResizeLeft; } - else if (sDist2 >= 0 && sDist2 <= minDist && (::getKeyModifier() == KeyModifierCTRL)) + else if (sDist2 >= 0 && sDist2 <= minDist) { type = MouseCursorTypeResizeRight; } From 216f802e493345f48ff4d3efd4fa6e1acbffc363 Mon Sep 17 00:00:00 2001 From: Cong Date: Wed, 28 Oct 2020 23:24:16 +1100 Subject: [PATCH 04/30] Fix windows build for non-MFC --- src/tracker/win32/Win32_resources.rc | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/tracker/win32/Win32_resources.rc b/src/tracker/win32/Win32_resources.rc index bfc5ef79..57d0ec37 100644 --- a/src/tracker/win32/Win32_resources.rc +++ b/src/tracker/win32/Win32_resources.rc @@ -7,7 +7,11 @@ // // Generated from the TEXTINCLUDE 2 resource. // -#include "afxres.h" +#include "windows.h" + +#ifndef IDC_STATIC +#define IDC_STATIC -1 +#endif ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS From 52e6a42d1f03c5fcb29b81f8cbdef8a9de9c4f55 Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Tue, 1 Dec 2020 21:50:48 +0000 Subject: [PATCH 05/30] Update zziplib submodule --- src/submodules/zziplib | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/submodules/zziplib b/src/submodules/zziplib index 9d82e19c..3921fc43 160000 --- a/src/submodules/zziplib +++ b/src/submodules/zziplib @@ -1 +1 @@ -Subproject commit 9d82e19c7f654722f9e37deaa9eb91c25ad544ec +Subproject commit 3921fc43bca7283f126bfb2e47ec7e7e24b5a5ea From ac29d03c21db299b83010a208a4f36d8d9b531a1 Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Wed, 9 Dec 2020 22:31:34 +0000 Subject: [PATCH 06/30] Update CI app keys --- .travis.yml | 2 +- appveyor.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 0092802e..acf05103 100644 --- a/.travis.yml +++ b/.travis.yml @@ -37,7 +37,7 @@ matrix: deploy: provider: releases api_key: - secure: C2RWNFq25CsR1OdJkguSBU2iYvi40UUTlSe2AZUWKB1qE4a0tERlvOj80ez2j72EuO0UdEzschQ+6jnAQG/Osz3TGYCjCOMGRP/09Am5TdVals3gcMC+hqrWuTMycmjh4qElh2Gu2cUXzrWM7K8kSvRhX7x5jE122K0geeiJeONRj9vfSnBeuwBFFJXQacXJ/vCBKzRn/S67FKBIn9WIvzh/ldlbAgdiIqQBV/8uQInNGwSYGlgq+fm6Pm18D0H2DILj0OT4atyxu+dGhSXLLqCHl/U0MfZXeNTfUKCvtKxen/vK9FlEJpiBG/+mZ7GwwQkoPPcr5ywsXuF8BtcncLFy8DS05BACVDQ8UYiqB3WUlsEEgJus8Uk64Gt0zvF9j6rH9NhWEBWicVvC5NhsNXzQYJjEkP3gjdGPebLqTAtKVMQtgm5Cz3gtKpVL+U/9E/xsijZ8M/X6ln/l1+oJyat9v6OGLyMLRRnf7a92j4SxBE7iqTrK07FF6stWyCAvSaWuRfwxOjhau3aA7KEWFpdizFsDzygXrGs0vvzcUOz6MMnS2lfWb3kI7DQiSwXQe8q2ZMnpQBA5C5oHXesaoAm6nP6JT2SS0GB7zimIQCDn61T6ZLFfHfDs245LmEr9Hp41AefF8bIYFBGub+xJDn8o4Q2TRJyOM2CXylUZ9SY= + secure: "tuoM4T5yYeqtmqjK5m9+zsVkLYqfwD/Lf5nyXPaONDRvgo7lh46OvNXPcHCu4QK6j80PmmzvhK/B0L836puEQpcaKsksdO8WTp3Lw4wPiidOC30rw+OR9jDnJzbPmv+PXxmqENIDUccLhDKpB9IGfosgcaxERvlvJZ44XlHnmgIPhXrKlESDnrV44snFJ/JkjlcNJr55nOdbCHTEUrW3J+kkYqjA3kyMW9/rS+iWx2PRLYKUBQDh+7U6frEjI8E4Ygpr5L6Cm7T2SuOWJhp+8tu9fEDZtfCngrU8ZTYclgAIqCyh1o6BU9ljcpU26CBcDYnNcqeFV8a7GcK/D32ix26rMvff9Ngei2uWs9ZYTGSSSC8CGnVpfPxi2ZSN15/pvqxhwr6I5Z/V/RX5+ZjdAyU6IIHo7GGt2y/e/zkoxfOBeiv1EV+gPZPbKafKkDX1Xghxp8t64qXynMctKiM3KCbcLRi+Z0Srym+lrIHYY2jo/cWk88VK6xGjCk5SDtQlkJgxN72Jbyy4kWMPIa7aOzrSA9WbUXG26osw38sNIGe5Rs1pErvSKMV3slLWBBDtzvh1Z/zUO34W6FyKilBwoE3zTvE/lnAZtBWyk0QCNxJvLReqNGZE53Zk8VuGmBQ9S9aIXqm21CSuEYVpvhogXAj82ePNH9Dy3B4A0KIqUBY=" skip_cleanup: true file_glob: true file: build/milkytracker-* diff --git a/appveyor.yml b/appveyor.yml index bc2d2359..69a5837e 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -32,7 +32,7 @@ deploy: description: Release $(appveyor_repo_tag_name) provider: GitHub auth_token: - secure: XtZUHo/SWVXr89Z4YQYylRE8lDQue+JwuaQdqEG/P57GePwPJipKzlPSxp8qOFiG + secure: k4eMw7MSycoyZwL8VfdAS8ejNXnwhFQ0KOVpif3IqyQDUrOGeGRyCHXm7FsD4kjb artifact: /milkytracker.*\.zip/ prerelease: false overwrite: true From 5ffac52ee67560924ecf046d03c7736a8fe21e3e Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Wed, 9 Dec 2020 19:59:15 +0000 Subject: [PATCH 07/30] Release v1.03 --- CMakeLists.txt | 2 +- ChangeLog.md | 23 +++ docs/ChangeLog.html | 349 ++++++++++++++++++++++++++++++----------- docs/MilkyTracker.html | 2 +- docs/TiTAN.nfo | 4 +- 5 files changed, 287 insertions(+), 93 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 9318dbce..4bdecf1b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -52,7 +52,7 @@ list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake) # Version number in format X.YY.ZZ set(VER_X 1) -set(VER_YY 02) +set(VER_YY 03) set(VER_ZZ 00) set(VER_FULL "${VER_X}.${VER_YY}.${VER_ZZ}") diff --git a/ChangeLog.md b/ChangeLog.md index 622e7b31..ab802bef 100644 --- a/ChangeLog.md +++ b/ChangeLog.md @@ -1,5 +1,28 @@ # MilkyTracker ChangeLog +## 12/12/2020 (v1.03): + +### What's new: +* Improved FT2 accuracy +* Alt-Backspace alternative for insert keybindings +* Improved mousewheel / touchpad scrolling for Windows/OSX/SDL2 +* Option to invert mousewheel for pattern editor +* New flanger effect +* Allow quarter periods in sample generator +* Click and drag to move selection in pattern editor +* More intuitive cutting/pasting of partial FX commands +* Allow selections by clicking outside the pattern bounds +* Easier and more intuitive sample selection resizing + +### Bugs fixed: +* Various compatibility fixes +* Jam channels stop working after applying settings +* Improper WAV chunk parsing for odd sizes +* Multiple heap & buffer overflow vulnerabilities +* MacOS compatibility +* Inverted samoples during signed to unsigned conversion +* ...and more, see git commit history for details + ## 24/02/2018 (v1.02): ### What's new: diff --git a/docs/ChangeLog.html b/docs/ChangeLog.html index db4385c5..118f6fa1 100644 --- a/docs/ChangeLog.html +++ b/docs/ChangeLog.html @@ -1,21 +1,186 @@ - - + + - - + - - + + ChangeLog + +

MilkyTracker ChangeLog

-

24/02/2018 (v1.02)

-

What's new:

+

12/12/2020 (v1.03):

+

What’s new:

+
    +
  • Improved FT2 accuracy
  • +
  • Alt-Backspace alternative for insert keybindings
  • +
  • Improved mousewheel / touchpad scrolling for Windows/OSX/SDL2
  • +
  • Option to invert mousewheel for pattern editor
  • +
  • New flanger effect
  • +
  • Allow quarter periods in sample generator
  • +
  • Click and drag to move selection in pattern editor
  • +
  • More intuitive cutting/pasting of partial FX commands
  • +
  • Allow selections by clicking outside the pattern bounds
  • +
  • Easier and more intuitive sample selection resizing
  • +
+

Bugs fixed:

+
    +
  • Various compatibility fixes
  • +
  • Jam channels stop working after applying settings
  • +
  • Improper WAV chunk parsing for odd sizes
  • +
  • Multiple heap & buffer overflow vulnerabilities
  • +
  • MacOS compatibility
  • +
  • Inverted samoples during signed to unsigned conversion
  • +
  • …and more, see git commit history for details
  • +
+

24/02/2018 (v1.02):

+

What’s new:

  • 99 channel MOD support
  • Alternative keybindings for inc/dec Row Insert
-

Bugs fixed:

+

Bugs fixed:

  • Fix Lxx command to also set panning envelope if volume sustain point is enabled.
  • Infinite loop when processing 8 digit hexadecimal numbers
  • @@ -25,39 +190,45 @@

    Bugs fixed:

  • Various loader memory corruption bugs

29/07/2017 (v1.01):

-

What's new:

+

What’s new:

  • Channel limit increased to 128 channels
  • -
  • New sample editor filters:
  • +
  • New sample editor filters: +
    • Phase modulation
    • AM & FM modulation
    • Selective equaliser
    • +
  • OSX: Insert key mapped to F13
  • GUI: Clickable checkbox labels
  • GNU: Use GNUInstallDirs
-

Bugs fixed:

+

Bugs fixed:

  • Errant characters inserts when selecting patterns using ALT + cursor keys
  • Windows: Window size now takes scale factor into consideration
  • Build: Default value used for PATH_MAX if not set (for GNU/Hurd)
  • -
  • Instrument editor:
  • +
  • Instrument editor: +
    • Prevent point inserts overlapping existing points
    • Reset cursor when changing presets or pasting envelopes
    • +
  • PT3 octave limit not reset when switching playback mode back to FT2
  • -
  • Sample editor:
  • +
  • Sample editor: +
    • Invert function now works correctly
    • Equaliser constants tweaked
    • No longer crashes when generating silence with no selection active
    • Noise generator on 64-bit systems
    • +
  • OSX: Core audio sample-rate switching
  • GUS frequencies lower than lowest note
  • Off-by-semitone issue in GUS patch loader
  • -
  • Corrupt display with window sizes that aren't multiples of 4
  • +
  • Corrupt display with window sizes that aren’t multiples of 4
  • Windows: Window position gradually moving off-screen on restarts

11/03/2017 (v1.00.00):

-

What's new:

+

What’s new:

  • 5 new customisable colours
  • X-Y mouse scrolling support
  • @@ -84,12 +255,12 @@

    What's new:

  • Mouse middle-click to solo channel
  • ..and more, see (commit log) for details
-

Bugs Fixed:

+

Bugs Fixed:

  • Segfault when loading <4 byte samples
  • Samples incorrectly offset when exporting .mod files
  • libalsa linker errors on some systems
  • -
  • .mod export: Don't zero first word of looping samples
  • +
  • .mod export: Don’t zero first word of looping samples
  • Decompress files despite possible mis-identification
  • Windows: Determine window dimensions based on client area
  • Update view if paste changes pattern length
  • @@ -106,26 +277,26 @@

    Bugs Fixed:

  • Sample/Ins editor listboxes scrolled right in certain circumstances

07/11/13 (v0.90.86):

-

Whats New:

+

Whats New:

    -
  • Unsafe notes now shown in red when "PT 3 octave limit" option enabled
  • +
  • Unsafe notes now shown in red when “PT 3 octave limit” option enabled
  • Haiku port (thanks jua)
  • Additional FT2 shortcuts (forum post)
  • Android port (thanks guillaum1)
  • Jack driver now connects to first available physical device
  • MilkyTracker source code now hosted on GitHub
-

Bugs Fixed:

+

Bugs Fixed:

    -
  • Loss of data when using 'backward' sample filter (forum post)
  • +
  • Loss of data when using ‘backward’ sample filter (forum post)
  • Warning displayed when exporting .mod files with samples over 64k (forum post)
  • Default panning settings applied when adding channels (forum post)
  • One-shot looping now works correctly (forum post)
  • First 2 bytes of samples cleared to zero when exporting to MOD (Amiga compatibility)
  • FT2 weirdness emulated when using the arpreggio command (thanks Saga_Musix)
  • -
  • In live mode, don't switch from pattern to song play when selecting a new pattern from the order list
  • +
  • In live mode, don’t switch from pattern to song play when selecting a new pattern from the order list
  • Check config file is open for writing before attempting to save to it.
  • -
  • Don't assume BACKUPxx.XM has been saved
  • +
  • Don’t assume BACKUPxx.XM has been saved
  • Crash when storing colour presets (forum post)
  • Segfault when loading XMs with zero-length loop (forum post)
  • Emulate FT2 behaviour for arpregios when speed>18
  • @@ -134,7 +305,7 @@

    Bugs Fixed:

  • Various build warnings and errors

01/01/10 (v0.90.85):

-

Whats New:

+

Whats New:

  • Ability to move dialogs.
  • Keyboard shortcut Shift-U (unmute all).
  • @@ -147,7 +318,7 @@

    Whats New:

  • New font: IDC-Harmonica (12x12)
  • New font: IDC-MicroKnight (12x12)
  • Ability to detect desktop display resolution.
  • -
  • Added '1' as note-off key in MilkyTracker mode.
  • +
  • Added ‘1’ as note-off key in MilkyTracker mode.
  • Ability to adjust screen magnification factor.
  • Milkyplay license changed from GPL to BSD (MilkyTracker remains GPL).
  • Working close button in OSX.
  • @@ -155,10 +326,10 @@

    Whats New:

  • Improved constants for 10 band EQ.
  • New font: Topaz 1.3 & Topaz 2.0 (8x8)
-

Bugs Fixed:

+

Bugs Fixed:

  • (Unix) JACK client thread gets zombified causing playback to block.
  • -
  • Crash when using the '-orientation ROTATE90CW' switch on SDL versions.
  • +
  • Crash when using the ‘-orientation ROTATE90CW’ switch on SDL versions.
  • Screen input lock after showing a system message.
  • Bug in xm loader for old xm variant causing 8 bit samples to not load correctly.
  • Added FT2 note range clipping to live playback.
  • @@ -173,22 +344,22 @@

    Bugs Fixed:

  • Mouse repeat bug on SDL version.
  • Small bug in SDL Midi code.
  • Little bug in the advanced edit panel (limit of subsequent channels).
  • -
  • Undefined .XM sample type 0x3 causes sample loop to appear "one shot".
  • +
  • Undefined .XM sample type 0x3 causes sample loop to appear “one shot”.
  • Instrument vibrato depth value gets doubled when copying instruments.
  • PSM loader can now store sub-song information correctly.
  • XM loading problems with 16-bit odd sample sizes.
  • -
  • Support for callbacks on systems that don't use C style function calls (ie, OS/2)
  • -
  • Instrument fadeout value initially doesn't match the slider position when adding new instruments to a loaded module.
  • -
  • Selecting an instrument with the numpad doesn't update the instrument or sample editors with the selected instrument, but with the previous one.
  • +
  • Support for callbacks on systems that don’t use C style function calls (ie, OS/2)
  • +
  • Instrument fadeout value initially doesn’t match the slider position when adding new instruments to a loaded module.
  • +
  • Selecting an instrument with the numpad doesn’t update the instrument or sample editors with the selected instrument, but with the previous one.
  • Bug in auto-detection of playmode for XM modules (panning was not set).
  • Set envelope position after sustain points.
  • Ignored lower 3 bits of finetune for more accurate FT2 playback
  • Crash while loading sample during playback
  • Screen refresh issues
  • Problem with French keyboard layout.
  • -
  • The current pattern length under the song title isn't updated when the mod is zapped.
  • -
  • Shrinking a 2-row pattern isn't possible.
  • -
  • Undoing an action doesn't register as a change.
  • +
  • The current pattern length under the song title isn’t updated when the mod is zapped.
  • +
  • Shrinking a 2-row pattern isn’t possible.
  • +
  • Undoing an action doesn’t register as a change.
  • A slight graphical bug occurs when using the seq and cln buttons on the FEth pattern of a mod.
  • Crash when converting sample resolution.
  • Freeze on exit when using DirectSound on Windows 7.
  • @@ -196,8 +367,8 @@

    Bugs Fixed:

04/13/08 (v0.90.80):

Important note:

-

This version of MilkyTracker will update your current configuration file in a way that it's no longer usable with older versions. It is recommended that you keep a backup of your configuration file. On Windows the configuration is stored in the application folder. When using MilkyTracker on OS X or Unix systems the configuration is stored in your home directory in a file called .milkytracker_config.

-

What's New:

+

This version of MilkyTracker will update your current configuration file in a way that it’s no longer usable with older versions. It is recommended that you keep a backup of your configuration file. On Windows the configuration is stored in the application folder. When using MilkyTracker on OS X or Unix systems the configuration is stored in your home directory in a file called .milkytracker_config.

+

What’s New:

  • Killer feature: Open up to 32 modules using tabs(*):
      @@ -225,14 +396,14 @@

      What's New:

    • WAV loader recognizes loop points and also exports them

    (*) Only available in the Desktop version of MilkyTracker

    -

    Bugs Fixed:

    +

    Bugs Fixed:

    Replay

    • Fixed bug in bidirectional looping which caused clicks on short samples
    • Introduced smart loop area double buffering to eliminate sample looping clicks
    • Fixed issue when switching between 4xx and Vx
    • Fixed issue when having a Dxx on the last order and restart is not zero
    • -
    • Milky's note range was going slightly higher than that of Ft2's.
    • +
    • Milky’s note range was going slightly higher than that of Ft2’s.

    Other

      @@ -242,12 +413,12 @@

      Other

    • Cutting arpeggio commands by selecting only the operand digits leaves invisible 000 commands on the pattern that repeat the previous arpeggio from effect memory.
    • GUS patch loader note mapping more accurate now
    • Some custom screen resolutions lead to distorted rendering.
    • -
    • The Apple AIFF loader doesn't load big endian samples correctly.
    • +
    • The Apple AIFF loader doesn’t load big endian samples correctly.
    • Rewritten major parts of the GUI & editor code to be more reliable.
    • Countless bugs you might not even have found yet

    05/20/07 (v0.90.60):

    -

    What's New:

    +

    What’s New:

    • New imported (obscure) module formats (mainly for personal satisfaction):
        @@ -261,16 +432,16 @@

        What's New:

      • Scrollbars in the list boxes dynamically show/hide depending on content (saves some space)
      • Row preview with Shift+Space
      • Song Preview Alt+Space
      • -
      • Integrated disk browser (click "flip" in the disk operations panel)
      • +
      • Integrated disk browser (click “flip” in the disk operations panel)
      • Sample editor got EQ filters now (3 and 10 bands)
      • Sample editor got waveform generators for sine, square, triangle and sawtooth
      • Solid scopes (ProTracker style, toggle in the config under the misc. tab)
      • -
      • Pattern replay is a bit more like Ft2 now (switching to different pattern doesn't reset cursor to row 0)
      • +
      • Pattern replay is a bit more like Ft2 now (switching to different pattern doesn’t reset cursor to row 0)
      • Clone button to clone the current order
      • -
      • "Mix paste" in the sample editor: paste in a sample from the clipboard and get it mixed with the current selection/entire sample.
      • +
      • “Mix paste” in the sample editor: paste in a sample from the clipboard and get it mixed with the current selection/entire sample.
      • As usually: more Ft2-compatible replay
      -

      Bugs Fixed:

      +

      Bugs Fixed:

      Replay

      • A severe volume ramping bug has been fixed
      • @@ -290,19 +461,19 @@

        Other

      • Crash: when loading modules without instruments.
      • FREEZE: when zooming way in/loading LOOONG instrument envelopes.
      • FREEZE (on Windows Vista): when initializing audio on startup.
      • -
      • Assigning samples to notes in the instrument editor by clicking and holding (painting) doesn't have effect on C-0.
      • +
      • Assigning samples to notes in the instrument editor by clicking and holding (painting) doesn’t have effect on C-0.
      • Certain hot words in song titles cause incorrect module format detection (improved at least ;)).
      • -
      • Clear button above sample box didn't work properly.
      • +
      • Clear button above sample box didn’t work properly.
      • Dxx on the last row of a pattern caused a display error when xx is greater than the number of rows on the current pattern.
      • Insert silence screwed up 16 bit samples.
      • Instrument panning settings defaulted to center on key-release when key-jamming.
      • -
      • Optimizer functions "Minimize all samples" and "Samples to 8-bit" triggered one another when only one of them were selected.
      • +
      • Optimizer functions “Minimize all samples” and “Samples to 8-bit” triggered one another when only one of them were selected.
      • Selection block is truncated to current pattern length (you know, after being taller on a taller pattern).
      • Several things like applying sample editor filters and using the optimizer reset global volume.
      • -
      • Other things I can't remember :P
      • +
      • Other things I can’t remember :P

      09/26/06 (v0.90.50), Tons of fixes and added features:

      -

      What's New:

      +

      What’s New:

      • New platforms supported:
          @@ -318,8 +489,8 @@

          What's New:

        • GMC (Game Music Creator)
        • IT (Impulse Tracker)
            -
          • NOTE: MilkyTracker will remain an Ft2 clone, importing converts everything to this environment and accurate playback is not pursued. It's just like with the rest of the imported formats apart from MOD and XM.
          • -
          • MORE IMPORTANTLY: MilkyTracker refuses to import modules with more than 32 channels. It's not that the XM format couldn't handle it but the Fasttracker II framework doesn't, so there.
          • +
          • NOTE: MilkyTracker will remain an Ft2 clone, importing converts everything to this environment and accurate playback is not pursued. It’s just like with the rest of the imported formats apart from MOD and XM.
          • +
          • MORE IMPORTANTLY: MilkyTracker refuses to import modules with more than 32 channels. It’s not that the XM format couldn’t handle it but the Fasttracker II framework doesn’t, so there.
      • Low-latency audio driver support: @@ -327,7 +498,7 @@

        What's New:

      • ALSA on Linux
      • ASIO and DirectX on Win32, thanks to RtAudio
          -
        • 48kHz mixing resolution now available also on Win32. NOTE: MMSYSTEM/WaveOut can't handle 48kHz, so don't mix these two.
        • +
        • 48kHz mixing resolution now available also on Win32. NOTE: MMSYSTEM/WaveOut can’t handle 48kHz, so don’t mix these two.
    • Adjustable MOD channel panning
    • @@ -342,65 +513,65 @@

      What's New:

    • Skippable splash screen
    • Volume boost/fade dialogs accept negative values (useful for chip sample generation, sample phase inversion etc)
    -

    Bugs Fixed:

    +

    Bugs Fixed:

    Replay

    • A rogue EDx note delay without a note should retrigger the previous note when x is lesser than or equal to song speed.
    • -
    • EDx+EEy, that is delayed notes on a pattern delayed row played when x was larger than or equal to the song speed. Sadly, this shouldn't happen according to Ft2, thus it doesn't anymore.
    • +
    • EDx+EEy, that is delayed notes on a pattern delayed row played when x was larger than or equal to the song speed. Sadly, this shouldn’t happen according to Ft2, thus it doesn’t anymore.
    • E5x finetune setting implemented.
    • -
    • E9x note retrig was a little off, now it's ever closer to Ft2.
    • -
    • F00 speed setting wasn't implemented, now it stops playback +
    • E9x note retrig was a little off, now it’s ever closer to Ft2.
    • +
    • F00 speed setting wasn’t implemented, now it stops playback
        -
      • Fasttracker II slows down to advancing one row every 10 or so minutes. If you can justify this behavior, i.e. convince us how you can rationally utilize it (a 10 minute pause) in a song, it will be implemented.
      • +
      • Fasttracker II slows down to advancing one row every 10 or so minutes. If you can justify this behavior, i.e. convince us how you can rationally utilize it (a 10 minute pause) in a song, it will be implemented.
    • K00 did not send a noteOff but set the volume to zero.
    • -
    • Mx volume column tone portamento acted as M0 when starting a song from scratch and you couldn't actually enter an M0 because a 1 was was automatically filled in as the parameter. All fixed and dandy now.
    • +
    • Mx volume column tone portamento acted as M0 when starting a song from scratch and you couldn’t actually enter an M0 because a 1 was was automatically filled in as the parameter. All fixed and dandy now.
    • Rxx multiretrig, see E9x.
    • -
    • Something clicked in the mixer, literally. Now smoother than a baby's butt.
    • +
    • Something clicked in the mixer, literally. Now smoother than a baby’s butt.

    User interface

      -
    • A channel could get stuck playing only one instrument when volume ramping was off. Ain't life peculiar?
    • -
    • A crash happened when selecting a range in sample editor and the mouse was released outside the MilkyTracker window followed by a cut or copy operation. You see the selection was still in progress and the poor tracker got confused because it didn't know where the range started/ended.
    • +
    • A channel could get stuck playing only one instrument when volume ramping was off. Ain’t life peculiar?
    • +
    • A crash happened when selecting a range in sample editor and the mouse was released outside the MilkyTracker window followed by a cut or copy operation. You see the selection was still in progress and the poor tracker got confused because it didn’t know where the range started/ended.
    • A pattern that was deleted from the orderlist remained on the screen.
    • An instrument stayed selected after it had been removed with the minus button.
    • Block operation areas did not always match block selections.
    • -
    • Global volume wasn't reset on stop/play.
    • +
    • Global volume wasn’t reset on stop/play.
    • Key release now effects the correct note (not necessarily the note that is playing).
    • Multisample instruments got rearranged/optimized automatically.
    • Scrollbar positions were reset upon screen switches. Added botox.
    • Standard-breaking XI instruments (w/ stereo and more than 16 samples) were crashing MilkyTracker. Now stereo is converted to mono and surplus samples are dismissed.
    • The MilkyTracker window insisted on staying topmost after switching from fullscreen to windowed.
    • -
    • The F10 key brought up the system menu on Win32. Now it just jumps to row 10h like it's supposed to.
    • -
    • The selection disappeared after pasting a block. Doesn't anymore.
    • -
    • When tabbing to a channel outside the current display, the screen shifted one whole "page". Very confusing for young, fragile artists. Now it moves one channel at a time, à la Ft2.
    • +
    • The F10 key brought up the system menu on Win32. Now it just jumps to row 10h like it’s supposed to.
    • +
    • The selection disappeared after pasting a block. Doesn’t anymore.
    • +
    • When tabbing to a channel outside the current display, the screen shifted one whole “page”. Very confusing for young, fragile artists. Now it moves one channel at a time, à la Ft2.

    02/14/06 (v0.90.30), Mainly bugfixes and minor additions:

    -

    Bugs fixed:

    +

    Bugs fixed:

      -
    • ProTracker modules using 'one shot'-looped samples seem to crash the replayer sometimes. Fixed.
    • +
    • ProTracker modules using ‘one shot’-looped samples seem to crash the replayer sometimes. Fixed.
    • There was a bug in the mod exporter when trying to export samples with a loopstart set to 0. Fixed.
    • The windows version would crash when inserting MANY points between two points in an envelope. Fixed.
    • -
    • The right-left combined mouse click on the scopes didn't work properly. Fixed.
    • +
    • The right-left combined mouse click on the scopes didn’t work properly. Fixed.
    • switching between the loop types caused crashes. Fixed.
    • Redo filter seems to crash/erase sample in the win32 version. Fixed.
    • Retrig command was still a little bit buggy (when used in combination with delay note). Fixed.
    • -
    • Arpeggio was still a little bit buggy (won't be noticed when tickspeed%3 == 0). Fixed.
    • +
    • Arpeggio was still a little bit buggy (won’t be noticed when tickspeed%3 == 0). Fixed.
    • Putting a position jump inbetween a pattern loop will cause the song length estimator to hang in an infinite loop. Fixed.
    • -
    • Trying to enable the volume envelope when it says 'none selected' in the envelope editor Milky would crash. Fixed.
    • +
    • Trying to enable the volume envelope when it says ‘none selected’ in the envelope editor Milky would crash. Fixed.
    • Block transpose up/down was buggy. Fixed.
    • -
    • Pattern Len display isn't updated to reflect new length after block was pasted and pattern grew. Fixed.
    • -
    • Scopes didn't update after loading samples/instruments
    • +
    • Pattern Len display isn’t updated to reflect new length after block was pasted and pattern grew. Fixed.
    • +
    • Scopes didn’t update after loading samples/instruments
    • Dozens of other fixes…

    Features added:

    • Multichannel record/keyjazz/editing (like in FT2)
    • Disable pattern grow when pasting
    • -
    • Enable "by channel tabbing" (like in FT2)
    • +
    • Enable “by channel tabbing” (like in FT2)
    • Instrument quick select using numerical keypad
    • Select sample within instrument in FT2 edit mode (Shift+Alt+Up/Down)
    • -
    • Emulate insert key with Ctrl+Up in the OSX version (select from the OSX main menu under option "special")
    • +
    • Emulate insert key with Ctrl+Up in the OSX version (select from the OSX main menu under option “special”)
    • Dragging files from the win-explorer/osx finder into the MilkyTracker window loads the file (works for modules, instruments, patterns, tracks, samples etc.)
    • Load/Save IFF samples
    • More WAV sample types recognized and loaded
    • @@ -412,7 +583,7 @@

      Features added:

    • PocketPC: Added scopes as well
    • PocketPC: Jam page with extended keyboard or pattern
    -

    11/29/05 (v0.90.00), Lots of improvements, really can't remember them all:

    +

    11/29/05 (v0.90.00), Lots of improvements, really can’t remember them all:

    • Improved mixer, improved FT2 effect compatibility (especially tremolo, tremor, vibrato)
    • Scopes (finally) (only for Desktop versions)
    • @@ -426,11 +597,11 @@

      11/29/05 (v
    • Dozens of sample filters
    • Reworked GUI (especially menus)
    • Sample offset can be shown in sample editor
    • -
    • Drawing samples (but remember to turn on looping, otherwise doesn't sound good ;))
    • +
    • Drawing samples (but remember to turn on looping, otherwise doesn’t sound good ;))
    • Toggle Hex count for rows in pattern editor
    • Show zero effect as 00 instead of dots (see config->layout)
    • Improved Protracker 2.x, 3.x replay modes (see options)
    • -
    • Skip through song while it's playing (with cursor keys or scrollwheel)
    • +
    • Skip through song while it’s playing (with cursor keys or scrollwheel)
    • Time length calculation/play time meter
    • Peak meters
    • Sequencer button (see order list)
    • @@ -446,14 +617,14 @@

      10/07/05:

    • New: Zoom sample in/out by using the scroll wheel of your mouse
    • New: Swap channels (select source with cursor and swap with destination channel by menu)
    • New: Split track (spread notes from one channel across subsequent channels)
    • -
    • New: Use virtual channels when playing instruments (enable in config first) (instruments played on virtual channels won't cut instruments used in song)
    • -
    • Other stuff (don't remember all of it)
    • +
    • New: Use virtual channels when playing instruments (enable in config first) (instruments played on virtual channels won’t cut instruments used in song)
    • +
    • Other stuff (don’t remember all of it)

    09/01/05:

    • Fixed lots of crashes =)
    • cut/copy/paste works in sample editor (hopefully, not much tested yet)
    • -
    • you're able to change default screen resolution but you need to restart MilkyTracker to apply
    • +
    • you’re able to change default screen resolution but you need to restart MilkyTracker to apply
    • Save patterns/tracks in FT2 formats .XP/.XT
    • Save Protracker compatible mods
    • Fixed some small issues
    • @@ -463,11 +634,11 @@

      07/01/05:

    • Fixed lots of crashes
    • Undo/Redo in sample editor (cut/copy/paste is following soon)
    • Minor cosmetical changes
    • -
    • Vibrato volume command now works in pattern editor (press "v")
    • -
    • Vibrato speed volume command now works in pattern editor (press "s")
    • +
    • Vibrato volume command now works in pattern editor (press “v”)
    • +
    • Vibrato speed volume command now works in pattern editor (press “s”)
    • X command works in pattern editor
    • MOD loader now recognises 15 channel mods
    • -
    • Added "large" font for tracking <= 4 channel songs ;)
    • +
    • Added “large” font for tracking <= 4 channel songs ;)
    • Del. key can be used for deleting note+ins./volume/effect

    06/22/05:

    @@ -488,7 +659,7 @@

    06/13/05:

  • Added more FT2 keyboard shortcuts (Ctrl+I, Ctrl +S, Ctrl +X etc.)
  • Minor fixes + Additions
  • Added support for mouse scrollwheel
  • -
  • PocketPC: "Full" onscreen keyboard (probably still buggy)
  • +
  • PocketPC: “Full” onscreen keyboard (probably still buggy)

05/27/05:

    @@ -504,9 +675,9 @@

    05/22/05:

05/14/05:

    -
  • Fixed some "focus" issues
  • -
  • Divided "save" option into "save" and "save as…"
  • -
  • Added value interpolation (available in the "Advanced Editor")
  • +
  • Fixed some “focus” issues
  • +
  • Divided “save” option into “save” and “save as…”
  • +
  • Added value interpolation (available in the “Advanced Editor”)
  • Fixed an instrument load/save issue
  • PocketPC: Fixed bug, which prevented the progress bar from disappearing when saving instruments/samples.
@@ -529,7 +700,7 @@

04/29/05:

04/25/05:

    -
  • First "official" PocketPC pre-release.
  • +
  • First “official” PocketPC pre-release.
diff --git a/docs/MilkyTracker.html b/docs/MilkyTracker.html index a4511838..0ae3941a 100644 --- a/docs/MilkyTracker.html +++ b/docs/MilkyTracker.html @@ -1,7 +1,7 @@ - MilkyTracker Manual v1.02 + MilkyTracker Manual v1.03 -

MilkyTracker Manual v1.0.1

+

MilkyTracker Manual v1.03

Hello and welcome to MilkyTracker, an open source multi-platform Fasttracker II compatible music tracker program. This document holds a lot of valuable information about the tracker but it's not a tracking manual. If you want to learn more about tracking and how it's done, the Internet is your friend. We host some resources on MilkyTracker.titandemo.org as well.

@@ -980,7 +980,7 @@

Pattern editor:

Caps-LockEnter key-off (Windows only) - 1Enter key-off (OS X only) + 1Enter key-off DelDelete note or volume column at cursor diff --git a/src/tracker/PatternEditorControlKeyboard.cpp b/src/tracker/PatternEditorControlKeyboard.cpp index 81f55846..db7b55c4 100644 --- a/src/tracker/PatternEditorControlKeyboard.cpp +++ b/src/tracker/PatternEditorControlKeyboard.cpp @@ -540,9 +540,7 @@ pp_int32 PatternEditorControl::ScanCodeToNote(pp_int16 scanCode) // CAPS-lock case SC_CAPSLOCK: -#ifndef WIN32 case SC_1: -#endif return PatternTools::getNoteOffNote(); case SC_SMALLERGREATER: From be016986168a4d03b8d160303fa61296070a6e2c Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Thu, 31 Dec 2020 18:34:11 +0000 Subject: [PATCH 11/30] Fix #96: Alternative keybinding for Insert in FT2 mode Alt-Backspace -> insert row on current track only Shift-Alt-Backspace -> Insert row on all tracks --- docs/MilkyTracker.html | 10 ++++++++-- src/tracker/PatternEditorControlKeyboard.cpp | 2 ++ 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/docs/MilkyTracker.html b/docs/MilkyTracker.html index be013076..38a0ca9f 100644 --- a/docs/MilkyTracker.html +++ b/docs/MilkyTracker.html @@ -703,10 +703,10 @@

Pattern Editor:

Shift-InsertInsert row at cursor position - Alt-BackspaceInsert space on current track at cursor position + Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key) - Shift-Alt-BackspaceInsert row at cursor position + Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key) BackspaceDelete previous note @@ -1000,6 +1000,12 @@

Pattern editor:

Shift-InsInsert row at cursor position (shift-F13 on mac) + + Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key) + + + Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key) + BackspaceDelete previous note diff --git a/src/tracker/PatternEditorControlKeyboard.cpp b/src/tracker/PatternEditorControlKeyboard.cpp index db7b55c4..3e8d60fe 100644 --- a/src/tracker/PatternEditorControlKeyboard.cpp +++ b/src/tracker/PatternEditorControlKeyboard.cpp @@ -108,6 +108,8 @@ void PatternEditorControl::initKeyBindings() eventKeyDownBindingsFastTracker->addBinding(VK_INSERT, 0, &PatternEditorControl::eventKeyDownBinding_InsertNote); eventKeyDownBindingsFastTracker->addBinding(VK_INSERT, KeyModifierSHIFT, &PatternEditorControl::eventKeyDownBinding_InsertLine); + eventKeyDownBindingsFastTracker->addBinding(VK_BACK, KeyModifierALT, &PatternEditorControl::eventKeyDownBinding_InsertNote); + eventKeyDownBindingsFastTracker->addBinding(VK_BACK, KeyModifierALT | KeyModifierSHIFT, &PatternEditorControl::eventKeyDownBinding_InsertLine); eventKeyDownBindingsFastTracker->addBinding(VK_BACK, 0, &PatternEditorControl::eventKeyDownBinding_DeleteNoteSlot); eventKeyDownBindingsFastTracker->addBinding(VK_BACK, KeyModifierSHIFT, &PatternEditorControl::eventKeyDownBinding_DeleteLine); From 9f19025cb7922f177419bbec64d446d03ac4fda8 Mon Sep 17 00:00:00 2001 From: Johannes Schultz Date: Sat, 29 May 2021 23:30:56 +0200 Subject: [PATCH 12/30] Fix various inaccuracies in (commented-out) AMF DSMI loader --- src/milkyplay/LoaderAMF.cpp | 52 +++++++++++++++++++++++++------------ 1 file changed, 36 insertions(+), 16 deletions(-) diff --git a/src/milkyplay/LoaderAMF.cpp b/src/milkyplay/LoaderAMF.cpp index eabe830a..763ae5f5 100644 --- a/src/milkyplay/LoaderAMF.cpp +++ b/src/milkyplay/LoaderAMF.cpp @@ -225,8 +225,10 @@ const char* LoaderAMF_2::identifyModule(const mp_ubyte* buffer) if (!memcmp(buffer,"AMF", 3)) { // check for version - if (buffer[3] < 0xA || - buffer[3] > 0xE) + if (buffer[3] < 0x8 && + buffer[3] != 0x1) + return NULL; + if (buffer[3] > 0xE) return NULL; return "AMF_2"; @@ -278,7 +280,14 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) mp_uword numTracks = f.readWord(); - header->channum = f.readByte(); + if (ver >= 9) + { + header->channum = f.readByte(); + } + else + { + header->channum = 4; + } mp_sint32 channelRemap[16]; @@ -287,7 +296,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) mp_ubyte panpos[32]; f.read(panpos, 1, (ver >= 13) ? 32 : 16); } - else + else if (ver >= 9) { for (mp_sint32 i = 0; i < 16; i++) channelRemap[i] = f.readByte(); @@ -353,7 +362,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) else { loopstart = f.readWord(); - loopend = length; + loopend = f.readWord(); } if (type) @@ -407,7 +416,12 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) mp_sbyte arg; tracksize = f.readWord(); - tracksize+=((mp_sint32)f.readByte()) << 16; + f.readByte(); // track type + + if (tracksize && ver == 1) + { + tracksize++; + } if (tracksize) while(tracksize--) @@ -535,9 +549,9 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) nEff = 0x1C; nOp = op; break; - + // Volume slide - case 2: + case 2: nEff = 0x0A; if (op) { @@ -547,7 +561,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) nOp = (-op)&0xf; } break; - + // set volume case 0x03: nEff = 0x0C; @@ -593,7 +607,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) break; // Porta + Volume slide - case 0xA: + case 0xA: nEff = 0x05; if (op) { @@ -605,7 +619,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) break; // Vibrato + Volume slide - case 0xB: + case 0xB: nEff = 0x06; if (op) { @@ -641,8 +655,8 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) break; // Fine Volume slide - case 0x11: - if (op) + case 0x11: + if (op) { if (op>=0) { @@ -658,7 +672,7 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) break; // Fine Porta - case 0x12: + case 0x12: if (op) { if (op>=0) @@ -1264,10 +1278,16 @@ mp_sint32 LoaderAMF_2::load(XMFileBase& f, XModule* module) // Set panning case 0x17: - if (op > 64) + if (op == 100) { + // surround nEff = 0x08; - nOp = XModule::vol64to255(op); + nOp = 0x80; + } + else + { + nEff = 0x08; + nOp = XModule::vol128to255(op + 64); } break; } From 450a9986ccb953f4255af65e5cf63b0ecde90e1a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Olav=20S=C3=B8rensen?= Date: Tue, 1 Jun 2021 12:34:14 +0200 Subject: [PATCH 13/30] Fix for 16-bit samples in S3M importer --- src/milkyplay/LoaderS3M.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/milkyplay/LoaderS3M.cpp b/src/milkyplay/LoaderS3M.cpp index edf0fd54..afbf208d 100644 --- a/src/milkyplay/LoaderS3M.cpp +++ b/src/milkyplay/LoaderS3M.cpp @@ -488,9 +488,13 @@ mp_sint32 LoaderS3M::load(XMFileBase& f, XModule* module) if (flags & 4) { smp[s].type |= 16; + + // 8bitbubsy: fix for 16-bit S3M samples (Units are in samples, not bytes. Don't divide by two!) + /* smp[s].samplen >>= 1; smp[s].loopstart >>= 1; smp[s].looplen >>= 1; + */ } mp_uint32 c4spd = f.readDword(); From d3b2c78b66b9aae22f73d7034af58b9ae7466e4d Mon Sep 17 00:00:00 2001 From: Casey Joy <67843601+caseyjoy@users.noreply.github.com> Date: Mon, 15 Mar 2021 05:29:21 -0600 Subject: [PATCH 14/30] Add #107 Feature Request "set loop to selection" --- src/ppui/Menu.h | 1 + src/tracker/SampleEditor.cpp | 20 ++++++++++++++++++++ src/tracker/SampleEditor.h | 3 ++- src/tracker/SampleEditorControl.cpp | 15 +++++++++++++++ src/tracker/SampleEditorControl.h | 1 + 5 files changed, 39 insertions(+), 1 deletion(-) diff --git a/src/ppui/Menu.h b/src/ppui/Menu.h index 4aab71c5..e6bf390b 100644 --- a/src/ppui/Menu.h +++ b/src/ppui/Menu.h @@ -46,6 +46,7 @@ enum MenuCommandIDs MenuCommandIDPaste = 3, MenuCommandIDSelectAll = 4, MenuCommandIDSelectNothing = 5, + MenuCommandIDLoopRange = 6, MenuCommandIDUndo = 7, MenuCommandIDRedo = 8, MenuCommandIDHide = 0x10000 diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp index 09fb46b2..55605733 100644 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -444,6 +444,26 @@ void SampleEditor::selectAll() selectionEnd = sample->samplen; } +void SampleEditor::loopRange() +{ + if (!hasValidSelection()) + return; + + // If a loop type is not enabled, set loop to Forward. + // - Changes loop type to Forward when loop type is set to One shot + // and the start of the selection is not at the start of the sample, + // but so does dragging the start of the loop. + if (!getLoopType()) + setLoopType(1); + + // Once loop is enabled, set the loop start/end points to selection start/end points. + setRepeatStart(getSelectionStart()); + setRepeatEnd(getSelectionEnd()); + + // Doesn't currently have undo or have the sample do the new loop + // until it retriggers, but neither does dragging the loop points. +} + bool SampleEditor::validate() { if (isEmptySample()) diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h index 872fdcfb..8d30b1b1 100644 --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -184,7 +184,8 @@ class SampleEditor : public EditorBase bool hasValidSelection() const { return ((selectionStart >= 0 && selectionEnd >= 0) && (selectionStart != selectionEnd)); } void selectAll(); - + void loopRange(); + bool validate(); // --- Multilevel UNDO / REDO -------------------------------------------- diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp index 42c123bd..78e92cb8 100644 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -168,6 +168,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, editMenuControl->addEntry("Paste", MenuCommandIDPaste); editMenuControl->addEntry("Crop", MenuCommandIDCrop); editMenuControl->addEntry("Range all", MenuCommandIDSelectAll); + editMenuControl->addEntry("Loop range", MenuCommandIDLoopRange); editMenuControl->addEntry(seperatorStringMed, -1); editMenuControl->addEntry("Advanced \x10", 0xFFFF, subMenuAdvanced); editMenuControl->addEntry("Ext. Paste \x10", 0xFFFF, subMenuXPaste); @@ -1437,6 +1438,14 @@ void SampleEditorControl::rangeAll(bool updateNotify/* = false*/) notifyUpdate(); } +void SampleEditorControl::loopRange(bool updateNotify/* = false*/) +{ + sampleEditor->loopRange(); + + if (updateNotify) + notifyUpdate(); +} + void SampleEditorControl::rangeClear(bool updateNotify/* = false*/) { sampleEditor->resetSelection(); @@ -1664,6 +1673,7 @@ void SampleEditorControl::invokeContextMenu(const PPPoint& p, bool translatePoin editMenuControl->setState(MenuCommandIDCut, !hasValidSelection()); editMenuControl->setState(MenuCommandIDCrop, !hasValidSelection()); editMenuControl->setState(MenuCommandIDSelectAll, isEmptySample); + editMenuControl->setState(MenuCommandIDLoopRange, !hasValidSelection()); // update submenu states subMenuAdvanced->setState(MenuCommandIDNormalize, isEmptySample); @@ -1770,6 +1780,11 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) rangeAll(true); break; + // set loop to current selection + case MenuCommandIDLoopRange: + loopRange(true); + break; + // Invoke tools case MenuCommandIDNew: invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeNew); diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h index c0df4e16..c40d866b 100644 --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -161,6 +161,7 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub void showRange(); void rangeAll(bool updateNotify = false); void rangeClear(bool updateNotify = false); + void loopRange(bool updateNotify = false); // set loop points to current range void increaseRangeStart(); void decreaseRangeStart(); From 075d32ec2662cbbf52caf45e1ec97a2df3254248 Mon Sep 17 00:00:00 2001 From: Leon Date: Tue, 6 Jul 2021 15:59:46 +0200 Subject: [PATCH 15/30] easily 'sample' current pattern into current sample --- src/tracker/ModuleEditor.h | 2 ++ src/tracker/SampleEditorControl.cpp | 11 +++++++++++ src/tracker/SampleEditorControl.h | 8 +++++++- src/tracker/SectionSamples.cpp | 2 +- src/tracker/Tracker.h | 3 +++ src/tracker/TrackerKeyboard.cpp | 15 +++++++++++++++ 6 files changed, 39 insertions(+), 2 deletions(-) mode change 100644 => 100755 src/tracker/ModuleEditor.h mode change 100644 => 100755 src/tracker/SampleEditorControl.cpp mode change 100644 => 100755 src/tracker/SampleEditorControl.h mode change 100644 => 100755 src/tracker/SectionSamples.cpp mode change 100644 => 100755 src/tracker/Tracker.h mode change 100644 => 100755 src/tracker/TrackerKeyboard.cpp diff --git a/src/tracker/ModuleEditor.h b/src/tracker/ModuleEditor.h old mode 100644 new mode 100755 index 823f63f1..3519362c --- a/src/tracker/ModuleEditor.h +++ b/src/tracker/ModuleEditor.h @@ -34,6 +34,7 @@ class SampleEditor; class EnvelopeEditor; class ModuleServices; class PlayerCriticalSection; +class Tracker; class ModuleEditor { @@ -385,6 +386,7 @@ class ModuleEditor static PPSystemString getTempFilename(); friend class ChangesListener; + friend class Tracker; }; #endif diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp old mode 100644 new mode 100755 index 78e92cb8..4af98615 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -28,6 +28,8 @@ #include "ContextMenu.h" #include "Piano.h" #include "Tools.h" +#include "Tracker.h" +#include "SampleEditor.h" #include "TrackerConfig.h" #include "PlayerController.h" #include "DialogBase.h" @@ -64,6 +66,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, EventListenerInterface* eventListener, const PPPoint& location, const PPSize& size, + Tracker& tracker, bool border/*= true*/) : PPControl(id, parentScreen, eventListener, location, size), border(border), @@ -144,6 +147,8 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, subMenuXPaste->addEntry("Phase Modulate", MenuCommandIDPHPaste); subMenuXPaste->addEntry("Flanger", MenuCommandIDFLPaste); subMenuXPaste->addEntry("Selective EQ" PPSTR_PERIODS, MenuCommandIDSelectiveEQ10Band); + subMenuXPaste->addEntry("Capture pattern" PPSTR_PERIODS, MenuCommandIDCapturePattern); + subMenuPT = new PPContextMenu(6, parentScreen, this, PPPoint(0,0), TrackerConfig::colorThemeMain); subMenuPT->addEntry("Boost", MenuCommandIDPTBoost); @@ -178,6 +183,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, // Create tool handler responder toolHandlerResponder = new ToolHandlerResponder(*this); dialog = NULL; + this->tracker = (Tracker *)&tracker; resetLastValues(); } @@ -1718,6 +1724,7 @@ void SampleEditorControl::hideContextMenu() void SampleEditorControl::executeMenuCommand(pp_int32 commandId) { + switch (commandId) { // cut @@ -1790,6 +1797,10 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeNew); break; + case MenuCommandIDCapturePattern: + tracker->eventKeyDownBinding_InvokePatternCapture(); + break; + case MenuCommandIDVolumeBoost: invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeVolume); break; diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h old mode 100644 new mode 100755 index c40d866b..7f6f06f6 --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -26,7 +26,9 @@ #include "BasicTypes.h" #include "Control.h" #include "Event.h" +#include "Tracker.h" #include "SampleEditor.h" +#include "EditorBase.h" #include "SampleEditorControlLastValues.h" // Forwards @@ -63,6 +65,7 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub PPControl* caughtControl; bool controlCaughtByLMouseButton, controlCaughtByRMouseButton; + Tracker* tracker; PPContextMenu* editMenuControl; PPContextMenu* subMenuAdvanced; PPContextMenu* subMenuXPaste; @@ -126,6 +129,7 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub EventListenerInterface* eventListener, const PPPoint& location, const PPSize& size, + Tracker& tracker, bool border = true); virtual ~SampleEditorControl(); @@ -296,6 +300,7 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub MenuCommandIDEQ3Band, MenuCommandIDEQ10Band, MenuCommandIDSelectiveEQ10Band, + MenuCommandIDCapturePattern, MenuCommandIDGenerateSilence, MenuCommandIDGenerateNoise, MenuCommandIDGenerateSine, @@ -363,7 +368,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub }; friend class ToolHandlerResponder; - + friend class Tracker; + PPDialogBase* dialog; ToolHandlerResponder* toolHandlerResponder; diff --git a/src/tracker/SectionSamples.cpp b/src/tracker/SectionSamples.cpp old mode 100644 new mode 100755 index 6fcc5f61..8a78f1bb --- a/src/tracker/SectionSamples.cpp +++ b/src/tracker/SectionSamples.cpp @@ -500,7 +500,7 @@ void SectionSamples::init(pp_int32 x, pp_int32 y) PPContainer* sampleEditorContainer = new PPContainer(CONTAINER_SAMPLEEDITOR, screen, this, PPPoint(x, y), PPSize(screen->getWidth(), cHeight), false); sampleEditorContainer->setColor(TrackerConfig::colorThemeMain); - sampleEditorControl = new SampleEditorControl(SAMPLE_EDITOR, screen, this, PPPoint(x+2, y+2), PPSize(sampleEditorContainer->getSize().width-4, sampleEditorContainer->getSize().height-4)); + sampleEditorControl = new SampleEditorControl(SAMPLE_EDITOR, screen, this, PPPoint(x+2, y+2), PPSize(sampleEditorContainer->getSize().width-4, sampleEditorContainer->getSize().height-4), tracker ); sampleEditorControl->attachSampleEditor(tracker.moduleEditor->getSampleEditor()); sampleEditorControl->setBorderColor(TrackerConfig::colorThemeMain); diff --git a/src/tracker/Tracker.h b/src/tracker/Tracker.h old mode 100644 new mode 100755 index 067add69..a396887e --- a/src/tracker/Tracker.h +++ b/src/tracker/Tracker.h @@ -580,6 +580,8 @@ class Tracker : public EventListenerInterface void eventKeyDownBinding_DecCurOrderPattern(); void eventKeyDownBinding_IncCurOrderPattern(); + void eventKeyDownBinding_InvokePatternCapture(); + private: // - friend classes -------------------------------------------------------- @@ -609,6 +611,7 @@ class Tracker : public EventListenerInterface friend class RecorderLogic; friend class Zapper; friend class SectionSwitcher; + friend class SampleEditorControl; }; #endif diff --git a/src/tracker/TrackerKeyboard.cpp b/src/tracker/TrackerKeyboard.cpp old mode 100644 new mode 100755 index 2ab0d31c..f68efb46 --- a/src/tracker/TrackerKeyboard.cpp +++ b/src/tracker/TrackerKeyboard.cpp @@ -171,6 +171,9 @@ void Tracker::initKeyBindings() eventKeyDownBindingsMilkyTracker->addBinding(VK_DECIMAL, 0, &Tracker::eventKeyDownBinding_InvokeQuickChooseInstrument); eventKeyDownBindingsMilkyTracker->addBinding(VK_DIVIDE, 0, &Tracker::eventKeyDownBinding_InvokeQuickChooseInstrument); + eventKeyDownBindingsMilkyTracker->addBinding('V', KeyModifierCTRL | KeyModifierSHIFT, &Tracker::eventKeyDownBinding_InvokePatternCapture); + + // Key-down bindings for Fasttracker // tab stuff eventKeyDownBindingsFastTracker->addBinding('T', KeyModifierCTRL|KeyModifierSHIFT, &Tracker::eventKeyDownBinding_OpenTab); @@ -261,6 +264,8 @@ void Tracker::initKeyBindings() eventKeyDownBindingsFastTracker->addBinding(VK_F11, KeyModifierCTRL, &Tracker::eventKeyDownBinding_DecCurOrderPattern); eventKeyDownBindingsFastTracker->addBinding(VK_F12, KeyModifierCTRL, &Tracker::eventKeyDownBinding_IncCurOrderPattern); + eventKeyDownBindingsFastTracker->addBinding('V', KeyModifierCTRL|KeyModifierSHIFT, &Tracker::eventKeyDownBinding_InvokePatternCapture); + eventKeyDownBindings = eventKeyDownBindingsMilkyTracker; } @@ -1006,3 +1011,13 @@ void Tracker::eventKeyDownBinding_IncCurOrderPattern() moduleEditor->increaseOrderPosition(getOrderListBoxIndex()); updateOrderlist(); } + +void Tracker::eventKeyDownBinding_InvokePatternCapture() +{ + sectionHDRecorder->selectSampleOutput(); + sectionHDRecorder->smpIndex = moduleEditor->currentSampleIndex; + sectionHDRecorder->insIndex = moduleEditor->currentInstrumentIndex; + sectionHDRecorder->fromOrder = getOrderListBoxIndex(); + sectionHDRecorder->toOrder = getOrderListBoxIndex(); + sectionHDRecorder->exportWAVAsSample(); +} From ac29eaddea14c764dfb2581e9a886c5c9cd1bee9 Mon Sep 17 00:00:00 2001 From: Leon Date: Tue, 13 Jul 2021 21:08:13 +0200 Subject: [PATCH 16/30] capture should respect mutes --- src/tracker/TrackerKeyboard.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/tracker/TrackerKeyboard.cpp b/src/tracker/TrackerKeyboard.cpp index f68efb46..8239f80e 100755 --- a/src/tracker/TrackerKeyboard.cpp +++ b/src/tracker/TrackerKeyboard.cpp @@ -1019,5 +1019,6 @@ void Tracker::eventKeyDownBinding_InvokePatternCapture() sectionHDRecorder->insIndex = moduleEditor->currentInstrumentIndex; sectionHDRecorder->fromOrder = getOrderListBoxIndex(); sectionHDRecorder->toOrder = getOrderListBoxIndex(); + sectionHDRecorder->setSettingsAllowMuting(true); sectionHDRecorder->exportWAVAsSample(); } From c8e5ad4c880901069398b3d6a43cfbba7dd0f188 Mon Sep 17 00:00:00 2001 From: Cong Date: Wed, 9 Jun 2021 20:15:16 +1000 Subject: [PATCH 17/30] Add half sine generator #239 --- src/tracker/SampleEditor.cpp | 51 +++++++++++++++++++ src/tracker/SampleEditor.h | 1 + src/tracker/SampleEditorControl.cpp | 6 +++ src/tracker/SampleEditorControl.h | 6 ++- .../SampleEditorControlToolHandler.cpp | 13 +++++ 5 files changed, 75 insertions(+), 2 deletions(-) diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp index 55605733..e0934b78 100644 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -2914,6 +2914,57 @@ void SampleEditor::tool_generateSawtooth(const FilterParameters* par) postFilter(); } +void SampleEditor::tool_generateHalfSine(const FilterParameters* par) +{ + if (isEmptySample()) + return; + + pp_int32 sStart = selectionStart; + pp_int32 sEnd = selectionEnd; + + if (hasValidSelection()) + { + if (sStart >= 0 && sEnd >= 0) + { + if (sEnd < sStart) + { + pp_int32 s = sEnd; sEnd = sStart; sStart = s; + } + } + } + else + { + sStart = 0; + sEnd = sample->samplen; + } + + preFilter(&SampleEditor::tool_generateHalfSine, par); + + mp_sint32 sLen = sEnd - sStart; + + prepareUndo(); + + pp_int32 i; + + const float numPeriods = (float)(6.283185307179586476925286766559 * par->getParameter(1).floatPart); + const float amplify = par->getParameter(0).floatPart; + + // generate half sine wave here + for (i = sStart; i < sEnd / 2; i++) + { + float per = (i - sStart) / (float)sLen * numPeriods; + setFloatSampleInWaveform(i, (float)sin(per) * amplify); + } + for (i = sEnd / 2; i < sEnd; i++) + { + setFloatSampleInWaveform(i, 0); + } + + finishUndo(); + + postFilter(); +} + bool SampleEditor::tool_canApplyLastFilter() const { return lastFilterFunc != NULL && isValidSample(); diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h index 8d30b1b1..b96f6f2e 100644 --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -350,6 +350,7 @@ class SampleEditor : public EditorBase void tool_generateSquare(const FilterParameters* par); void tool_generateTriangle(const FilterParameters* par); void tool_generateSawtooth(const FilterParameters* par); + void tool_generateHalfSine(const FilterParameters* par); void tool_applyLastFilter(); bool tool_canApplyLastFilter() const; diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp index 78e92cb8..4598a81b 100644 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -154,6 +154,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, subMenuGenerators->addEntry("Square" PPSTR_PERIODS, MenuCommandIDGenerateSquare); subMenuGenerators->addEntry("Triangle" PPSTR_PERIODS, MenuCommandIDGenerateTriangle); subMenuGenerators->addEntry("Sawtooth" PPSTR_PERIODS, MenuCommandIDGenerateSawtooth); + subMenuGenerators->addEntry("Half Sine" PPSTR_PERIODS, MenuCommandIDGenerateHalfSine); subMenuGenerators->addEntry("Silence" PPSTR_PERIODS, MenuCommandIDGenerateSilence); // build context menu @@ -1705,6 +1706,7 @@ void SampleEditorControl::invokeContextMenu(const PPPoint& p, bool translatePoin subMenuGenerators->setState(MenuCommandIDGenerateSquare, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateTriangle, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateSawtooth, isEmptySample); + subMenuGenerators->setState(MenuCommandIDGenerateHalfSine, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateSilence, isEmptySample); parentScreen->setContextMenuControl(editMenuControl); @@ -1878,6 +1880,10 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateSawtooth); break; + case MenuCommandIDGenerateHalfSine: + invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateHalfSine); + break; + } } diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h index c40d866b..19ce50fc 100644 --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -301,7 +301,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub MenuCommandIDGenerateSine, MenuCommandIDGenerateSquare, MenuCommandIDGenerateTriangle, - MenuCommandIDGenerateSawtooth + MenuCommandIDGenerateSawtooth, + MenuCommandIDGenerateHalfSine }; void executeMenuCommand(pp_int32 commandId); @@ -345,7 +346,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub SampleToolTypeGenerateSine, SampleToolTypeGenerateSquare, SampleToolTypeGenerateTriangle, - SampleToolTypeGenerateSawtooth + SampleToolTypeGenerateSawtooth, + SampleToolTypeGenerateHalfSine }; private: diff --git a/src/tracker/SampleEditorControlToolHandler.cpp b/src/tracker/SampleEditorControlToolHandler.cpp index 3348e574..703052f3 100644 --- a/src/tracker/SampleEditorControlToolHandler.cpp +++ b/src/tracker/SampleEditorControlToolHandler.cpp @@ -153,6 +153,7 @@ bool SampleEditorControl::invokeToolParameterDialog(SampleEditorControl::ToolHan case ToolHandlerResponder::SampleToolTypeGenerateSquare: case ToolHandlerResponder::SampleToolTypeGenerateTriangle: case ToolHandlerResponder::SampleToolTypeGenerateSawtooth: + case ToolHandlerResponder::SampleToolTypeGenerateHalfSine: { dialog = new DialogWithValues(parentScreen, toolHandlerResponder, PP_DEFAULT_ID, "Generate waveform" PPSTR_PERIODS, DialogWithValues::ValueStyleEnterTwoValues); static_cast(dialog)->setValueOneCaption("Volume in percent:"); @@ -331,6 +332,18 @@ bool SampleEditorControl::invokeTool(ToolHandlerResponder::SampleToolTypes type) sampleEditor->tool_generateSawtooth(&par); break; } + + case ToolHandlerResponder::SampleToolTypeGenerateHalfSine: + { + lastValues.waveFormVolume = static_cast(dialog)->getValueOne(); + lastValues.waveFormNumPeriods = static_cast(dialog)->getValueTwo(); + FilterParameters par(2); + par.setParameter(0, FilterParameters::Parameter(lastValues.waveFormVolume / 100.0f)); + par.setParameter(1, FilterParameters::Parameter(lastValues.waveFormNumPeriods)); + sampleEditor->tool_generateHalfSine(&par); + break; + } + default: break; } From 7f005f9cb6d7d1cf9fc372c02191a2907c49aa58 Mon Sep 17 00:00:00 2001 From: Leon Date: Tue, 6 Jul 2021 18:38:52 +0200 Subject: [PATCH 18/30] added quick and dirty dynamic compression --- src/tracker/SampleEditor.cpp | 71 +++++++++++++++++++++++++++++ src/tracker/SampleEditor.h | 1 + src/tracker/SampleEditorControl.cpp | 6 +++ src/tracker/SampleEditorControl.h | 1 + 4 files changed, 79 insertions(+) mode change 100644 => 100755 src/tracker/SampleEditor.cpp mode change 100644 => 100755 src/tracker/SampleEditor.h mode change 100644 => 100755 src/tracker/SampleEditorControl.cpp mode change 100644 => 100755 src/tracker/SampleEditorControl.h diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp old mode 100644 new mode 100755 index e0934b78..216238b0 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -1840,6 +1840,77 @@ void SampleEditor::tool_normalizeSample(const FilterParameters* par) postFilter(); } +void SampleEditor::tool_compressSample(const FilterParameters* par) +{ + if (isEmptySample()) + return; + + pp_int32 sStart = selectionStart; + pp_int32 sEnd = selectionEnd; + + if (hasValidSelection()) + { + if (sStart >= 0 && sEnd >= 0) + { + if (sEnd < sStart) + { + pp_int32 s = sEnd; sEnd = sStart; sStart = s; + } + } + } + else + { + sStart = 0; + sEnd = sample->samplen; + } + + preFilter(&SampleEditor::tool_compressSample, par); + + prepareUndo(); + + float maxLevel = ((par == NULL) ? 1.0f : par->getParameter(0).floatPart); + float peak_pre = 0.0f; + float peak_post = 0.0f; + float compress = 0.8; + + pp_int32 i; + + // find peak value (pre) + for (i = sStart; i < sEnd; i++) + { + float f = getFloatSampleFromWaveform(i); + if (ppfabs(f) > peak_pre) peak_pre = ppfabs(f); + } + + // compress + for (i = sStart; i < sEnd; i++) + { + float f = getFloatSampleFromWaveform(i); + f = compress * tanh(f / compress); // upward compression + setFloatSampleInWaveform(i, f); + } + + // find peak value (post) + for (i = sStart; i < sEnd; i++) + { + float f = getFloatSampleFromWaveform(i); + if (ppfabs(f) > peak_post) peak_post = ppfabs(f); + } + + float scale = 1.0f + (peak_pre - peak_post); + + for (i = sStart; i < sEnd; i++) + { + float f = getFloatSampleFromWaveform(i); + setFloatSampleInWaveform(i, f * scale); + } + + finishUndo(); + + postFilter(); +} + + void SampleEditor::tool_reverseSample(const FilterParameters* par) { if (isEmptySample()) diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h old mode 100644 new mode 100755 index b96f6f2e..949f98aa --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -329,6 +329,7 @@ class SampleEditor : public EditorBase // filters void tool_scaleSample(const FilterParameters* par); void tool_normalizeSample(const FilterParameters* par); + void tool_compressSample(const FilterParameters* par); void tool_reverseSample(const FilterParameters* par); void tool_PTboostSample(const FilterParameters* par); bool isValidxFadeSelection(); diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp old mode 100644 new mode 100755 index 4598a81b..0ccf5608 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -119,6 +119,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, subMenuAdvanced->addEntry("Volume boost" PPSTR_PERIODS, MenuCommandIDVolumeBoost); subMenuAdvanced->addEntry("Volume fade" PPSTR_PERIODS, MenuCommandIDVolumeFade); subMenuAdvanced->addEntry("Normalize", MenuCommandIDNormalize); + subMenuAdvanced->addEntry("Compress", MenuCommandIDCompress); subMenuAdvanced->addEntry(seperatorStringLarge, -1); subMenuAdvanced->addEntry("Backwards", MenuCommandIDReverse); subMenuAdvanced->addEntry("Cross-fade", MenuCommandIDXFade); @@ -1678,6 +1679,7 @@ void SampleEditorControl::invokeContextMenu(const PPPoint& p, bool translatePoin // update submenu states subMenuAdvanced->setState(MenuCommandIDNormalize, isEmptySample); + subMenuAdvanced->setState(MenuCommandIDCompress, isEmptySample); subMenuAdvanced->setState(MenuCommandIDVolumeFade, isEmptySample); subMenuAdvanced->setState(MenuCommandIDVolumeBoost, isEmptySample); subMenuAdvanced->setState(MenuCommandIDReverse, isEmptySample); @@ -1812,6 +1814,10 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) sampleEditor->tool_normalizeSample(NULL); break; + case MenuCommandIDCompress: + sampleEditor->tool_compressSample(NULL); + break; + case MenuCommandIDReverse: sampleEditor->tool_reverseSample(NULL); break; diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h old mode 100644 new mode 100755 index 19ce50fc..4cf6090c --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -281,6 +281,7 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub MenuCommandIDPHPaste, MenuCommandIDFLPaste, MenuCommandIDNormalize, + MenuCommandIDCompress, MenuCommandIDVolumeBoost, MenuCommandIDVolumeFade, MenuCommandIDReverse, From d2cd52c9bc53d239fa65c0a8212b6638d267b917 Mon Sep 17 00:00:00 2001 From: Coder of Salvation / Leon van Kammen Date: Thu, 29 Jul 2021 23:03:32 +0200 Subject: [PATCH 19/30] docs updated with ctrl-shift-v shortcut --- docs/MilkyTracker.html | 3 +++ 1 file changed, 3 insertions(+) diff --git a/docs/MilkyTracker.html b/docs/MilkyTracker.html index 38a0ca9f..7cd8bb65 100644 --- a/docs/MilkyTracker.html +++ b/docs/MilkyTracker.html @@ -681,6 +681,9 @@

Pattern Editor:

Ctrl-VPaste + + Ctrl-Shift-VConvert current pattern to sample + Ctrl-IInterpolate values From 3d306a02d847a42ce582ea574008ef4aa8c16020 Mon Sep 17 00:00:00 2001 From: Coder of Salvation / Leon van Kammen Date: Thu, 29 Jul 2021 23:18:52 +0200 Subject: [PATCH 20/30] prevented future 'oddevenoddevenoddeven'-chore by introducing css feature --- docs/MilkyTracker.html | 873 ++++++++++++++++++++++------------------- 1 file changed, 469 insertions(+), 404 deletions(-) diff --git a/docs/MilkyTracker.html b/docs/MilkyTracker.html index 7cd8bb65..46672bcb 100644 --- a/docs/MilkyTracker.html +++ b/docs/MilkyTracker.html @@ -68,7 +68,7 @@ vertical-align: top; } - tr.odd { + tr:nth-child(odd) { background-color: #eee; } @@ -299,97 +299,97 @@

I. Modules

Import:

- + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - +
.669669 Composer/Unis669 (PC)
.AMFAsylum Music Format ("Crusader" in-game music) (PC)
Digital Sound and Music Interface (DSMI) library (PC)
.AMSExtreme Tracker (PC)
Velvet Studio (PC)
.CBAChuck Biscuits+Black Artist module format (PC)
.DBMDigiBooster Pro (Amiga)
.DIGIDigibooster 1.0-1.7 (Amiga)
.DSMDigisound Interface Kit (DSIK) library (PC)
Dynamic Studio (PC)
.DTMDigital Tracker (Atari)
DigiTrekker 3.0 (PC)
.FARFarandole Composer (PC)
.GDMGeneral Digimusic (PC)
.GMCGame Music Creator (Amiga)
.IMFImago Orpheus (PC)
.ITImpulse Tracker (PC)
.MDLDigiTrakker 1.0-3.0 (PC)
.MODSound-/ProTracker and variants (Amiga & PC)
.MTMMultiTracker (PC)
.MXMCubic Tiny XM (PC)
.OKTOktalyzer (Amiga)
.PLMDisorderTracker II (PC)
.PSMEpic MegaGames MASI (PC)
.PTMPolyTracker (PC)
.S3MScream Tracker 3.0 (PC)
.SFXSoundFX (Amiga)
.STMScream Tracker 2.0 (PC)
.ULTUltraTracker (PC)
.UNIMikMod (PC)
.XMFasttracker II (PC)
@@ -398,13 +398,13 @@

Import:

Export:

- + - + - +
.MODProTracker boundaries (including 64kb max sample length), although can save 2–32 channels
.WAVMicrosoft/IBM PCM Waveform audio rendering
.XMFasttracker II compatible, not as common as one might think
@@ -417,25 +417,25 @@

II. Samples

Import:

- + - + - + - +
.8SVX / .IFFCompressed/uncompressed Interchange File Format
.AIF / .AIFFApple Audio Interchange File Format
.WAVMicrosoft/IBM uncompressed PCM Waveform audio
.*RAW PCM audio

Export:

- + - +
.IFFUncompressed Interchange File Format
.WAVMicrosoft/IBM uncompressed PCM Waveform audio
@@ -467,43 +467,43 @@

5. Keyboard shortcuts

Please note that under Mac OS X the Command key is used instead of the Ctrl key.

- + - + - + - + - + - + - + - + - + - + - + - + - +
Alt-EnterSwitch between full screen and windowed display (Windows & SDL)
Shift-Command-FSwitch between full screen and windowed display (OS X)
Shift-MMute current channel
Ctrl-Shift-MInvert muting
Shift-UUn-mute all
Ctrl-Shift-TOpen a new tab
Ctrl-Shift-WClose current tab
Ctrl-Shift-LeftSelect previous tab
Ctrl-Shift-RightSelect next tab
Ctrl-=Increment instrument number of all notes in the current selection
Ctrl--Decrement instrument number of all notes in the current selection
Ctrl-Shift-=Increment instrument number of all notes in the current track under the cursor
Ctrl-Shift--Decrement instrument number of all notes in the current track under the cursor
@@ -513,274 +513,309 @@

I. MilkyTracker edit mode

Section switching:

- + - + - + - + - + - + - + - + - + - +
Ctrl-Alt-
AAdvanced edit
CConfiguration
DDisk operations
IInstrument editor
RDisk recorder
SSample editor
TTranspose
XMain screen
ZToggle scopes

Global:

- + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - +
2, 3, 5, 6…Play / insert notes (depending on whether edit mode is on)
Q, W, E, R…
S, D, F, G…
Z, X, C, V…
F1…F8Select octave
Ctrl-Shift-1…8
SpaceToggle pattern editor focus (edit mode on/off)
EnterPlay song from current order
Ctrl-EnterPlay current pattern from beginning
Shift-EnterPlay current pattern from cursor position
Shift-F9Play current pattern from beginning (same as Ctrl-Enter)
Shift-F10Play current pattern from position after the first quarter of the pattern length
Shift-F11Play current pattern from position after the second quarter of the pattern length
Shift-F12Play current pattern from position after the third quarter of the pattern length
Alt-SpacePlay song from current row (stop and return when keys are released)
Shift-SpacePlay row by row
EscStop
Ctrl-FToggle song follow
Ctrl-PToggle prospective pattern view
Ctrl-WToggle pattern wrapping
Ctrl-LToggle pattern change behavior (live mode)
Ctrl-OLoad song
Ctrl-SSave song
Ctrl-Shift-SSave song as…
Ctrl-QExit program
Alt-F4

Pattern Editor:

- - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + + + + + - - + + + - - + + + - - + + + - - + + + - - - - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + +
Cursor keysMove around
Cursor keysMove around
TabJump to next channel
TabJump to next channel
PageUpJump 16 rows up
PageUpJump 16 rows up
PageDownJump 16 rows down
PageDownJump 16 rows down
HomeJump to first row
HomeJump to first row
EndJump to last row
EndJump to last row
F9Jump to beginning of the pattern
F9Jump to beginning of the pattern
F10Jump to position ¼ through the pattern
F10Jump to position ¼ through the pattern
F11Jump to position halfway through the pattern
F11Jump to position halfway through the pattern
F12Jump to position ¾ through the pattern
F12Jump to position ¾ through the pattern
Ctrl-ZUndo
Ctrl-ZUndo
Ctrl-YRedo
Ctrl-YRedo
Shift-Cursor keysSelect block
Shift-Cursor keysSelect block
Shift-Alt-Cursor keysExtend block
Shift-Alt-Cursor keysExtend block
Ctrl-ASelect entire pattern
Ctrl-ASelect entire pattern
Ctrl-XCut
Ctrl-XCut
Ctrl-CCopy
Ctrl-CCopy
Ctrl-VPaste
Ctrl-VPaste
Ctrl-Shift-VConvert current pattern to sample
Ctrl-Shift-VConvert current pattern to sample
Ctrl-IInterpolate values
Ctrl-IInterpolate values
DeleteDelete note/instrument/volume/effect/parameter
DeleteDelete note/instrument/volume/effect/parameter
Shift-DelDelete note, volume and effect at cursor
Shift-DelDelete note, volume and effect at cursor
Ctrl-DelDelete volume and effect at cursor
Ctrl-DelDelete volume and effect at cursor
Alt-DeleteDelete effect at cursor
Alt-DeleteDelete effect at cursor
InsertInsert space on current track at cursor position
InsertInsert space on current track at cursor position
Shift-InsertInsert row at cursor position
Shift-InsertInsert row at cursor position
Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key)
Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key)
Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key)
Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key)
BackspaceDelete previous note
BackspaceDelete previous note
Shift-BackspaceDelete previous row
Shift-BackspaceDelete previous row
The key right of LShiftEnter key-off
The key right of LShiftEnter key-off
The key below EscEnter key-off (Windows only)
The key below EscEnter key-off (Windows only)
1Enter key-off (OS X only)
1Enter key-off (OS X only)
Alt-MinusIncrease Add value
Alt-MinusIncrease Add value
or Alt-PlusDecrease Add value
or Alt-PlusDecrease Add value

Transpose:

- + - + - + - + - + - + - + - + - + - + - + - +
Alt-F7Transpose current instrument in block down
Alt-F8Transpose current instrument in block up
Shift-F7Transpose current instrument in track down
Shift-F8Transpose current instrument in track up
Ctrl-F7Transpose current instrument in pattern down
Ctrl-F8Transpose current instrument in pattern up
Alt-F1Transpose all instruments in block down
Alt-F2Transpose all instruments in block up
Shift-F1Transpose all instruments in track down
Shift-F2Transpose all instruments in track up
Ctrl-F1Transpose all instruments in pattern down
Ctrl-F2Transpose all instruments in pattern up

Sample Editor:

- + - + - +
Shift & dragQuick draw
Ctrl & dragResize selection
Alt & dragMove selection or loop range
@@ -793,142 +828,142 @@

II. Fasttracker II edit mode

Section switching:

- + - + - + - + - + - + - + - + - + - +
Ctrl-
AAdvanced edit
CConfiguration
DDisk operations
IInstrument editor
RDisk recorder
SSample editor
TTranspose
XMain screen
ZToggle scopes

Global:

- + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - +
2, 3, 5, 6…Play / insert notes (depending on whether edit mode is on)
Q, W, E, R…
S, D, F, G…
Z, X, C, V…
F1…F8Select octave
Right CtrlPlay song from current order
EnterPlay song from current order
Right AltPlay current pattern from beginning (Windows &SDL)
Ctrl-EnterPlay current pattern from beginning
Shift-EnterPlay current pattern from current row
Shift-F9Play current pattern from beginning (same as Ctrl-Enter/Right Alt)
Shift-F10Play current pattern from position after the first quarter of the pattern length
Shift-F11Play current pattern from position after the second quarter of the pattern length
Shift-F12Play current pattern from position after the third quarter of the pattern length
Alt-SpacePlay song from current row (stop and return when keys are released)
Shift-SpacePlay row by row
SpaceStop / Edit
Shift-LeftIncrease song position
Shift-RightDecrease song position
Ctrl-LeftIncrease current pattern number
Ctrl-RightDecrease current pattern number
Ctrl-F9Delete current order position
Ctrl-F10Insert new order position
Ctrl-F11Decrease current order pattern number
Ctrl-F12Increase current order pattern number
Key below ESC (ANSI: Alt-Minus)*Increase Add value
Shift-key below ESC (ANSI: Alt-Plus)*Decrease Add value
Ctrl-FToggle song follow
Ctrl-PToggle prospective pattern view
Ctrl-WToggle pattern wrapping
Ctrl-LToggle pattern change behavior (live mode)
Shift-Ctrl-LLoad song
Shift-RToggle record mode
Shift-Ctrl-SSave song
EscExit program
@@ -937,217 +972,247 @@

Global:

Pattern editor:

- - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + + + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + + - - + + +
Cursor keysMove around
Cursor keysMove around
PageUpJump 16 rows up
PageUpJump 16 rows up
PageDownJump 16 rows down
PageDownJump 16 rows down
HomeJump to first row
HomeJump to first row
EndJump to last row
EndJump to last row
TabJump to next track
TabJump to next track
Shift-TabJump to previous track
Shift-TabJump to previous track
Alt-Q…IJump to track (0…7) MOD N-Channels
Alt-Q…IJump to track (0…7) MOD N-Channels
Alt-A…KJump to track (8…15) MOD N-Channels
Alt-A…KJump to track (8…15) MOD N-Channels
F9Jump to beginning of the pattern
F9Jump to beginning of the pattern
F10Jump to position ¼ through the pattern
F10Jump to position ¼ through the pattern
F11Jump to position halfway through the pattern
F11Jump to position halfway through the pattern
F12Jump to position ¾ through the pattern
F12Jump to position ¾ through the pattern
The key right of LShiftEnter key-off
The key right of LShiftEnter key-off
Caps-LockEnter key-off (Windows only)
Caps-LockEnter key-off (Windows only)
1Enter key-off
1Enter key-off
DelDelete note or volume column at cursor
DelDelete note or volume column at cursor
Shift-DelDelete note, volume and effect at cursor
Shift-DelDelete note, volume and effect at cursor
Ctrl-DelDelete volume and effect at cursor
Ctrl-DelDelete volume and effect at cursor
Alt-DeleteDelete effect at cursor
Alt-DeleteDelete effect at cursor
InsInsert space on current track at cursor position (F13 on mac)
InsInsert space on current track at cursor position (F13 on mac)
Shift-InsInsert row at cursor position (shift-F13 on mac)
Shift-InsInsert row at cursor position (shift-F13 on mac)
Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key)
Alt-BackspaceInsert space on current track at cursor position (alternative for keyboards with no Insert key)
Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key)
Shift-Alt-BackspaceInsert row at cursor position (alternative for keyboards with no Insert key)
BackspaceDelete previous note
BackspaceDelete previous note
Shift-BackspaceDelete previous row
Shift-BackspaceDelete previous row
Ctrl-Shift-VConvert current pattern to sample

Clipboard operations:

- + - + - + - + - + - + - + - + - + - + - + - + - + - +
Alt-Cursor keysSelect block
Shift-Alt-Cursor keysExtend block
Alt-F3Cut block
Alt-F4Copy block (yes, even under Windows =)
Alt-F5Paste block
Alt-F6Porous paste block
Shift-F3Cut track
Shift-F4Copy track
Shift-F5Paste track
Shift-F6Porous paste track
Ctrl-F3Cut pattern
Ctrl-F4Copy pattern
Ctrl-F5Paste pattern
Ctrl-F6Porous paste pattern

Additional shortcuts (not found in FT2):

- + - + - + - +
Ctrl-Alt-ZUndo
Ctrl-Alt-YRedo
Ctrl-Alt-ASelect entire pattern
Shift-IInterpolate values

Volume scaling:

- + - + - +
Alt-VVolume scale block
Shift-VVolume scale track
Ctrl-VVolume scale pattern

Command/Volume macro:

- + - +
Shift-Alt-1…0Read command/volume at cursor
Alt-1…0Write command/volume at cursor

Transpose:

- + - + - + - + - + - + - + - + - + - + - + - +
Alt-F7Transpose current instrument in block down
Alt-F8Transpose current instrument in block up
Shift-F7Transpose current instrument in track down
Shift-F8Transpose current instrument in track up
Ctrl-F7Transpose current instrument in pattern down
Ctrl-F8Transpose current instrument in pattern up
Alt-F1Transpose all instruments in block down
Alt-F2Transpose all instruments in block up
Shift-F1Transpose all instruments in track down
Shift-F2Transpose all instruments in track up
Ctrl-F1Transpose all instruments in pattern down
Ctrl-F2Transpose all instruments in pattern up

Instrument selection:

- + - + - + - +
Shift-UpSelect previous instrument
Shift-DownSelect next instrument
Ctrl-Shift-UpSelect previous sample
Ctrl-Shift-DownSelect next sample
@@ -1156,40 +1221,40 @@

Instrument selection:

keypad, the layout is like this:

- + - + - + - + - + - + - + - +
PCMac
Num 0…9Num 0…9Digit 0…9
Num /Num =Digit A
Num *Num /Digit B
Num -Num *Digit C
Num +Num -Digit D
Num EnterNum +Digit E
Num ,Num EnterDigit F

Sample editor:

- + - + - +
Shift & dragQuick draw
Ctrl & dragResize selection
Alt & dragMove selection or loop range
@@ -1199,25 +1264,25 @@

Sample editor:

6. Effect command reference

I. Glossary

- + - + - + - + - + - + - +
BPMTraditionally Beats Per Minute, but in tracker terminology it defines the speed of ticks.
Effect memoryWhen an effect command is called with 0 parameters, previous parameters are used.
Row/lineRefers to one line of "text" on a pattern. In playback its duration depends on how many ticks there are per row (Speed) and fast they are (BPM).
Sample fine-tune/volume/panningPer sample default settings available through the instrument editor (thus also called instrument volume etc). Overrideable with effect commands. .MODs support these as well but with lower precision. (Save module and load back to enforce .MOD precision.)
TickThe base time unit in traditional trackers like MilkyTracker, originating from Amiga. Notes are triggered on the first tick of a row (unless delayed) and effects are applied on the following ticks.
SemitoneThe smallest musical interval in Western music and in MilkyTracker. A C# note is one semitone away from the note C.
Speed (Spd.)Number of ticks per row.
@@ -1308,7 +1373,7 @@

0xy Arpeggio

y = semitone offset - + Example: @@ -1335,7 +1400,7 @@

Fasttracker II

- + Notes:

In MilkyTracker you don't have to and indeed you CAN'T enter the effect digit 0. Just start with the parameter digits and the effect digit will be filled in.

@@ -1362,7 +1427,7 @@

1xx Portamento up

xx = portamento speed - + Example: @@ -1385,7 +1450,7 @@

Amiga frequencies

- + Notes:

ProTracker 2/3

@@ -1404,7 +1469,7 @@

2xx Portamento down

xx = portamento speed - + Example: @@ -1421,7 +1486,7 @@

2xx Portamento down

Works similarly to 1xx portamento up, only bending note pitch down instead of up. - + Notes:

ProTracker 2/3

@@ -1440,7 +1505,7 @@

3xx Portamento to note

xx = portamento speed - + Example: @@ -1472,7 +1537,7 @@

4xy Vibrato

y = depth - + Example: @@ -1504,7 +1569,7 @@

5xy Portamento to note with volume slide

y = volume slide down speed - + Example: @@ -1523,7 +1588,7 @@

5xy Portamento to note with volume slide

- + Notes:

ProTracker 2/3

@@ -1545,7 +1610,7 @@

6xy Vibrato with volume slide

y = volume slide down speed - + Example: @@ -1564,7 +1629,7 @@

6xy Vibrato with volume slide

- + Notes:

ProTracker 2/3

@@ -1586,7 +1651,7 @@

7xy Tremolo

y = depth - + Example: @@ -1615,7 +1680,7 @@

8xx Set note panning position

xx = panning position - + Example: @@ -1634,7 +1699,7 @@

8xx Set note panning position

- + Notes:

ProTracker 2/3

@@ -1657,7 +1722,7 @@

9xx Sample offset

xx = sample offset - + Example: @@ -1676,7 +1741,7 @@

9xx Sample offset

- + Tips: Resampling a loop to exactly (0x10000=) 65536 bytes gives you the highest possible level of control over the sample. @@ -1695,7 +1760,7 @@

Axy Volume slide

y = volume slide down speed - + Example: @@ -1714,7 +1779,7 @@

Axy Volume slide

- + Notes: - + Notes:

@@ -1991,7 +2056,7 @@

E5x Set note fine-tune

x = fine-tune - + Example: @@ -2073,7 +2138,7 @@

E6x Pattern loop

x = set loop point / number of iterations - + Example: @@ -2092,7 +2157,7 @@

E6x Pattern loop

- + Notes:

@@ -2117,7 +2182,7 @@

E7x Tremolo control

x = tremolo waveform selection - + Example: @@ -2144,7 +2209,7 @@

E7x Tremolo control

- + Notes:

@@ -2162,7 +2227,7 @@

E8x Set note panning position

x = panning position - + Explanation:

@@ -2188,7 +2253,7 @@

E9x Re-trigger note

x = triggering interval - + Example: @@ -2217,7 +2282,7 @@

EAx Fine volume slide up

x = speed - + Example: @@ -2246,7 +2311,7 @@

EBx Fine volume slide down

x = speed - + Example: @@ -2275,7 +2340,7 @@

ECx Note cut

x = tick number - + Example: @@ -2304,7 +2369,7 @@

EDx Note delay

x = tick number - + Example: @@ -2333,7 +2398,7 @@

EEx Pattern delay

x = amount of rows - + Example: @@ -2362,7 +2427,7 @@

Fxx Set song speed/BPM

xx = speed/BPM value - + Example: @@ -2391,7 +2456,7 @@

Gxx Set global volume

xx = volume - + Example: @@ -2423,7 +2488,7 @@

Hxy Global volume slide

y = volume slide down speed - + Example: @@ -2442,7 +2507,7 @@

Hxy Global volume slide

- + Notes:

@@ -2460,7 +2525,7 @@

Kxx Key-off

xx = tick number - + Example: @@ -2489,7 +2554,7 @@

Lxx Set envelope position

xx = envelope position - + Example: @@ -2522,7 +2587,7 @@

Pxy Panning slide

y = panning slide left speed - + Example: @@ -2541,7 +2606,7 @@

Pxy Panning slide

- + Notes:

@@ -2562,7 +2627,7 @@

Rxy Re-trigger note with volume slide

y = triggering interval - + Example: @@ -2599,7 +2664,7 @@

Rxy Re-trigger note with volume slide

- + Notes:

This command is very buggy from the start, straight from the source, Fasttracker II. While FT2's own documentation is inaccurate in many places, this is different. Extensive testing has revealed almost bizarre qualities of this effect and it's up to MilkyTracker to emulate it all. Without doubt the quirk the team has spent the most time and iterations working on getting it right. And still we advise to be careful with it. When using Rxy, check your song with FT2 (render to .WAV if you don't have the hardware (to emulate)), or at least BASS/XMPlay. And if you do find something odd, please report the bug as accurately and detailed as possible. @@ -2630,7 +2695,7 @@

Txy Tremor

y + 1 = ticks off - + Example: @@ -2649,7 +2714,7 @@

Txy Tremor

- + Notes:

@@ -2667,7 +2732,7 @@

X1x Extra fine portamento up

x = speed - + Example: @@ -2696,7 +2761,7 @@

X2x Extra fine portamento down

x = speed - + Example: @@ -2723,7 +2788,7 @@

xx Set note volume

Syntax:xx = volume - + Example: @@ -2752,7 +2817,7 @@

+x Volume slide up

x = speed - + Example: @@ -2781,7 +2846,7 @@

-x Volume slide down

x = speed - + Example: @@ -2810,7 +2875,7 @@

Dx Fine volume slide down (displayed as ▼x)< x = speed - + Example: @@ -2839,7 +2904,7 @@

Lx Panning slide left (displayed as ◀x)

x = speed - + Example: @@ -2868,7 +2933,7 @@

Mx Portamento to note

x = speed - + Example: @@ -2887,7 +2952,7 @@

Mx Portamento to note

- + Tips:

@@ -2905,7 +2970,7 @@

Px Set note panning position

x = speed - + Example: @@ -2924,7 +2989,7 @@

Px Set note panning position

- + Tips:

@@ -2942,7 +3007,7 @@

Rx Panning slide right (displayed as ▶x)

x = speed - + Example: @@ -2971,7 +3036,7 @@

Sx Set vibrato speed

x = speed - + Example: @@ -3000,7 +3065,7 @@

Ux Fine volume slide up (displayed as ▲x) x = speed - + Example: @@ -3029,7 +3094,7 @@

Vx Vibrato

x = depth - + Example: @@ -3048,7 +3113,7 @@

Vx Vibrato

- + Notes:

@@ -3065,15 +3130,15 @@

7. MIDI support

MilkyTracker supports basic MIDI input, which means you can use your MIDI device to feed notes into MilkyTracker. Enabling MIDI input varies a little from platform to platform - here's how to do it on…

- + - + - + From 50267642dffe12b6c4c2aa2144c0f110baea0d02 Mon Sep 17 00:00:00 2001 From: Christopher O'Neill Date: Sun, 1 Aug 2021 11:04:04 +0100 Subject: [PATCH 21/30] Remove executable bit on source files --- src/tracker/ModuleEditor.h | 0 src/tracker/SampleEditor.cpp | 0 src/tracker/SampleEditor.h | 0 src/tracker/SampleEditorControl.cpp | 0 src/tracker/SampleEditorControl.h | 0 src/tracker/SectionSamples.cpp | 0 src/tracker/Tracker.h | 0 src/tracker/TrackerKeyboard.cpp | 0 8 files changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 src/tracker/ModuleEditor.h mode change 100755 => 100644 src/tracker/SampleEditor.cpp mode change 100755 => 100644 src/tracker/SampleEditor.h mode change 100755 => 100644 src/tracker/SampleEditorControl.cpp mode change 100755 => 100644 src/tracker/SampleEditorControl.h mode change 100755 => 100644 src/tracker/SectionSamples.cpp mode change 100755 => 100644 src/tracker/Tracker.h mode change 100755 => 100644 src/tracker/TrackerKeyboard.cpp diff --git a/src/tracker/ModuleEditor.h b/src/tracker/ModuleEditor.h old mode 100755 new mode 100644 diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp old mode 100755 new mode 100644 diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h old mode 100755 new mode 100644 diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp old mode 100755 new mode 100644 diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h old mode 100755 new mode 100644 diff --git a/src/tracker/SectionSamples.cpp b/src/tracker/SectionSamples.cpp old mode 100755 new mode 100644 diff --git a/src/tracker/Tracker.h b/src/tracker/Tracker.h old mode 100755 new mode 100644 diff --git a/src/tracker/TrackerKeyboard.cpp b/src/tracker/TrackerKeyboard.cpp old mode 100755 new mode 100644 From 6cac112683e92b57686536fe76e4af5909687df5 Mon Sep 17 00:00:00 2001 From: Cong Date: Sun, 1 Aug 2021 22:57:53 +1000 Subject: [PATCH 22/30] Add absolute sine generator #239 --- src/tracker/SampleEditor.cpp | 52 +++++++++++++++++++ src/tracker/SampleEditor.h | 1 + src/tracker/SampleEditorControl.cpp | 6 +++ src/tracker/SampleEditorControl.h | 6 ++- .../SampleEditorControlToolHandler.cpp | 12 +++++ 5 files changed, 75 insertions(+), 2 deletions(-) diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp index 216238b0..35550136 100644 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -3036,6 +3036,58 @@ void SampleEditor::tool_generateHalfSine(const FilterParameters* par) postFilter(); } +void SampleEditor::tool_generateAbsoluteSine(const FilterParameters* par) +{ + if (isEmptySample()) + return; + + pp_int32 sStart = selectionStart; + pp_int32 sEnd = selectionEnd; + + if (hasValidSelection()) + { + if (sStart >= 0 && sEnd >= 0) + { + if (sEnd < sStart) + { + pp_int32 s = sEnd; sEnd = sStart; sStart = s; + } + } + } + else + { + sStart = 0; + sEnd = sample->samplen; + } + + preFilter(&SampleEditor::tool_generateAbsoluteSine, par); + + mp_sint32 sLen = sEnd - sStart; + + prepareUndo(); + + pp_int32 i; + + const float numPeriods = (float)(6.283185307179586476925286766559 * par->getParameter(1).floatPart); + const float amplify = par->getParameter(0).floatPart; + + // generate half sine wave in first and second halves + for (i = sStart; i < sEnd / 2; i++) + { + float per = (i - sStart) / (float)sLen * numPeriods; + setFloatSampleInWaveform(i, (float)sin(per) * amplify); + } + for (i = sEnd / 2; i < sEnd; i++) + { + float per = (i - sEnd / 2) / (float)sLen * numPeriods; + setFloatSampleInWaveform(i, (float)sin(per) * amplify); + } + + finishUndo(); + + postFilter(); +} + bool SampleEditor::tool_canApplyLastFilter() const { return lastFilterFunc != NULL && isValidSample(); diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h index 949f98aa..62c87b6e 100644 --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -352,6 +352,7 @@ class SampleEditor : public EditorBase void tool_generateTriangle(const FilterParameters* par); void tool_generateSawtooth(const FilterParameters* par); void tool_generateHalfSine(const FilterParameters* par); + void tool_generateAbsoluteSine(const FilterParameters* par); void tool_applyLastFilter(); bool tool_canApplyLastFilter() const; diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp index 30afb393..de6d8bae 100644 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -161,6 +161,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, subMenuGenerators->addEntry("Triangle" PPSTR_PERIODS, MenuCommandIDGenerateTriangle); subMenuGenerators->addEntry("Sawtooth" PPSTR_PERIODS, MenuCommandIDGenerateSawtooth); subMenuGenerators->addEntry("Half Sine" PPSTR_PERIODS, MenuCommandIDGenerateHalfSine); + subMenuGenerators->addEntry("Absolute Sine" PPSTR_PERIODS, MenuCommandIDGenerateAbsoluteSine); subMenuGenerators->addEntry("Silence" PPSTR_PERIODS, MenuCommandIDGenerateSilence); // build context menu @@ -1715,6 +1716,7 @@ void SampleEditorControl::invokeContextMenu(const PPPoint& p, bool translatePoin subMenuGenerators->setState(MenuCommandIDGenerateTriangle, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateSawtooth, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateHalfSine, isEmptySample); + subMenuGenerators->setState(MenuCommandIDGenerateAbsoluteSine, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateSilence, isEmptySample); parentScreen->setContextMenuControl(editMenuControl); @@ -1901,6 +1903,10 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateHalfSine); break; + case MenuCommandIDGenerateAbsoluteSine: + invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateAbsoluteSine); + break; + } } diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h index 26b12404..570aabcc 100644 --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -308,7 +308,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub MenuCommandIDGenerateSquare, MenuCommandIDGenerateTriangle, MenuCommandIDGenerateSawtooth, - MenuCommandIDGenerateHalfSine + MenuCommandIDGenerateHalfSine, + MenuCommandIDGenerateAbsoluteSine }; void executeMenuCommand(pp_int32 commandId); @@ -353,7 +354,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub SampleToolTypeGenerateSquare, SampleToolTypeGenerateTriangle, SampleToolTypeGenerateSawtooth, - SampleToolTypeGenerateHalfSine + SampleToolTypeGenerateHalfSine, + SampleToolTypeGenerateAbsoluteSine }; private: diff --git a/src/tracker/SampleEditorControlToolHandler.cpp b/src/tracker/SampleEditorControlToolHandler.cpp index 703052f3..366c6c04 100644 --- a/src/tracker/SampleEditorControlToolHandler.cpp +++ b/src/tracker/SampleEditorControlToolHandler.cpp @@ -154,6 +154,7 @@ bool SampleEditorControl::invokeToolParameterDialog(SampleEditorControl::ToolHan case ToolHandlerResponder::SampleToolTypeGenerateTriangle: case ToolHandlerResponder::SampleToolTypeGenerateSawtooth: case ToolHandlerResponder::SampleToolTypeGenerateHalfSine: + case ToolHandlerResponder::SampleToolTypeGenerateAbsoluteSine: { dialog = new DialogWithValues(parentScreen, toolHandlerResponder, PP_DEFAULT_ID, "Generate waveform" PPSTR_PERIODS, DialogWithValues::ValueStyleEnterTwoValues); static_cast(dialog)->setValueOneCaption("Volume in percent:"); @@ -344,6 +345,17 @@ bool SampleEditorControl::invokeTool(ToolHandlerResponder::SampleToolTypes type) break; } + case ToolHandlerResponder::SampleToolTypeGenerateAbsoluteSine: + { + lastValues.waveFormVolume = static_cast(dialog)->getValueOne(); + lastValues.waveFormNumPeriods = static_cast(dialog)->getValueTwo(); + FilterParameters par(2); + par.setParameter(0, FilterParameters::Parameter(lastValues.waveFormVolume / 100.0f)); + par.setParameter(1, FilterParameters::Parameter(lastValues.waveFormNumPeriods)); + sampleEditor->tool_generateAbsoluteSine(&par); + break; + } + default: break; } From d9fe42ca254fbe66eb11d3dd8ee4e4e8bd17047c Mon Sep 17 00:00:00 2001 From: Peter Barth <69579956+peterbart-lmi@users.noreply.github.com> Date: Sun, 29 Aug 2021 21:55:56 +0200 Subject: [PATCH 23/30] Feature: Add 9xx adjustment option to sample resampler (#247) * feat: Add an option to the sample resampler so it's possible to automatically adjust sample offset (9xx) commands --- src/tracker/DialogResample.cpp | 38 +++++++--- src/tracker/DialogResample.h | 9 ++- src/tracker/ModuleEditor.cpp | 75 +++++++++++++++++++ src/tracker/ModuleEditor.h | 2 + src/tracker/SampleEditor.cpp | 12 +++ src/tracker/SampleEditor.h | 4 + src/tracker/SampleEditorControlLastValues.h | 10 ++- .../SampleEditorControlToolHandler.cpp | 4 +- 8 files changed, 141 insertions(+), 13 deletions(-) diff --git a/src/tracker/DialogResample.cpp b/src/tracker/DialogResample.cpp index d2d4ac3b..06e4e07b 100644 --- a/src/tracker/DialogResample.cpp +++ b/src/tracker/DialogResample.cpp @@ -94,12 +94,13 @@ DialogResample::DialogResample(PPScreen* screen, count(0), resamplerHelper(new ResamplerHelper()), interpolationType(1), - adjustFtAndRelnote(true) + adjustFtAndRelnote(true), + adjustSampleOffsetCommand(false) { #ifdef __LOWRES__ - initDialog(screen, responder, id, "Resample" PPSTR_PERIODS, 290, 142+15+20+16, 26+15, "Ok", "Cancel"); + initDialog(screen, responder, id, "Resample" PPSTR_PERIODS, 290, 158+15+20+16, 26+15, "Ok", "Cancel"); #else - initDialog(screen, responder, id, "Resample" PPSTR_PERIODS, 290, 142+20+16, 26, "Ok", "Cancel"); + initDialog(screen, responder, id, "Resample" PPSTR_PERIODS, 290, 158+20+16, 26, "Ok", "Cancel"); #endif pp_int32 x = getMessageBoxContainer()->getLocation().x; @@ -200,13 +201,23 @@ DialogResample::DialogResample(PPScreen* screen, y2+=16; x2 = x + width / 2 - (10 * 8 + 35 + 14 * 8) / 2 + 21 * 8; - checkBox = new PPCheckBox(MESSAGEBOX_CONTROL_USER2, screen, this, PPPoint(x2, y2 + 1)); - checkBox->checkIt(adjustFtAndRelnote); - messageBoxContainerGeneric->addControl(checkBox); + checkBoxAdjustFtAndRelnote = new PPCheckBox(MESSAGEBOX_CONTROL_USER2, screen, this, PPPoint(x2, y2 + 1)); + checkBoxAdjustFtAndRelnote->checkIt(adjustFtAndRelnote); + messageBoxContainerGeneric->addControl(checkBoxAdjustFtAndRelnote); x2 -= 21 * 8; - messageBoxContainerGeneric->addControl(new PPCheckBoxLabel(0, screen, this, PPPoint(x2, y2 + 2), "Adjust Ft/Rel.Note:", checkBox, true)); - + messageBoxContainerGeneric->addControl(new PPCheckBoxLabel(0, screen, this, PPPoint(x2, y2 + 2), "Adjust Ft/Rel.Note:", checkBoxAdjustFtAndRelnote, true)); + + y2+=16; + + x2 = x + width / 2 - (10 * 8 + 35 + 14 * 8) / 2 + 21 * 8; + checkBoxAdjustSampleOffsetCommand = new PPCheckBox(MESSAGEBOX_CONTROL_USER3, screen, this, PPPoint(x2, y2 + 1)); + checkBoxAdjustSampleOffsetCommand->checkIt(adjustSampleOffsetCommand); + messageBoxContainerGeneric->addControl(checkBoxAdjustSampleOffsetCommand); + + x2 -= 21 * 8; + messageBoxContainerGeneric->addControl(new PPCheckBoxLabel(0, screen, this, PPPoint(x2, y2 + 2), "Adjust 9xx commands:", checkBoxAdjustSampleOffsetCommand, true)); + y2+=16; #ifdef __LOWRES__ @@ -372,6 +383,14 @@ pp_int32 DialogResample::handleEvent(PPObject* sender, PPEvent* event) break; } + case MESSAGEBOX_CONTROL_USER3: + { + if (event->getID() != eCommand) + break; + + this->adjustSampleOffsetCommand = reinterpret_cast(sender)->isChecked(); + break; + } } } else if (event->getID() == eValueChanged) @@ -422,7 +441,8 @@ void DialogResample::updateListBoxes() PPStaticText* staticText = static_cast(messageBoxContainerGeneric->getControlByID(MESSAGEBOX_STATICTEXT_USER1)); staticText->setHexValue(finalSize, 8); - checkBox->checkIt(adjustFtAndRelnote); + checkBoxAdjustFtAndRelnote->checkIt(adjustFtAndRelnote); + checkBoxAdjustSampleOffsetCommand->checkIt(adjustSampleOffsetCommand); } void DialogResample::updateListBox(pp_int32 id, float val, pp_int32 numDecimals) diff --git a/src/tracker/DialogResample.h b/src/tracker/DialogResample.h index 785b26fa..d63d6dac 100644 --- a/src/tracker/DialogResample.h +++ b/src/tracker/DialogResample.h @@ -37,7 +37,8 @@ class DialogResample : public PPDialogBase { private: class PPListBox* listBoxes[3]; - class PPCheckBox* checkBox; + class PPCheckBox* checkBoxAdjustFtAndRelnote; + class PPCheckBox* checkBoxAdjustSampleOffsetCommand; pp_int32 currentSelectedListBox; pp_int32 relnote, finetune; pp_uint32 size, finalSize; @@ -48,6 +49,7 @@ class DialogResample : public PPDialogBase class ResamplerHelper* resamplerHelper; pp_int32 interpolationType; bool adjustFtAndRelnote; + bool adjustSampleOffsetCommand; public: DialogResample(PPScreen* screen, @@ -74,7 +76,10 @@ class DialogResample : public PPDialogBase void setAdjustFtAndRelnote(bool adjustFtAndRelnote) { this->adjustFtAndRelnote = adjustFtAndRelnote; } bool getAdjustFtAndRelnote() const { return adjustFtAndRelnote; } - + + void setAdjustSampleOffsetCommand(bool adjustSampleOffsetCommand) { this->adjustSampleOffsetCommand = adjustSampleOffsetCommand; } + bool getAdjustSampleOffsetCommand() const { return adjustSampleOffsetCommand; } + private: void listBoxEnterEditState(pp_int32 id); diff --git a/src/tracker/ModuleEditor.cpp b/src/tracker/ModuleEditor.cpp index fa930997..eb5df129 100644 --- a/src/tracker/ModuleEditor.cpp +++ b/src/tracker/ModuleEditor.cpp @@ -21,9 +21,11 @@ */ #include +#include #include "ModuleEditor.h" #include "PatternEditor.h" #include "SampleEditor.h" +#include "FilterParameters.h" #include "EnvelopeEditor.h" #include "ModuleServices.h" #include "PlayerCriticalSection.h" @@ -75,7 +77,17 @@ class ChangesListener : public EditorBase::EditorNotificationListener case EditorBase::NotificationChanges: { if (sender == moduleEditor.sampleEditor) + { moduleEditor.finishSamples(); + if (moduleEditor.sampleEditor->isLastOperationResampling()) + { + const bool adjustSampleOffsetCommand = moduleEditor.sampleEditor->getLastParameters()->getParameter(3).intPart; + if (adjustSampleOffsetCommand) + { + moduleEditor.adjustSampleOffsetCommandAfterSampleSizeChange(moduleEditor.sampleEditor->getSample(), moduleEditor.sampleEditor->getUndoSample()->getSampLen()); + } + } + } moduleEditor.setChanged(); break; } @@ -2463,6 +2475,69 @@ void ModuleEditor::optimizeSamples(bool convertTo8Bit, bool minimize, changed = true; } +void ModuleEditor::adjustSampleOffsetCommandAfterSampleSizeChange(TXMSample *sample, pp_int32 oldSize) +{ + mp_sint32 i,j; + + mp_ubyte* lastIns = new mp_ubyte[module->header.channum]; + memset(lastIns, 0, module->header.channum); + + for (mp_sint32 l = 0; l < module->header.ordnum; l++) + { + TXMPattern* pattern = &module->phead[module->header.ord[l]]; + + if (pattern->patternData == NULL) + continue; + + mp_sint32 slotSize = pattern->effnum * 2 + 2; + mp_sint32 rowSizeSrc = slotSize*pattern->channum; + + for (i = 0; i < pattern->rows; i++) + { + for (j = 0; j < pattern->channum; j++) + { + mp_ubyte* src = pattern->patternData + i*rowSizeSrc+j*slotSize; + + if (src[1]) + { + lastIns[j] = src[1]; + } + + + if (src[0] && src[0] < 120) + { + for (mp_sint32 k = 0; k < pattern->effnum; k++) { + if (src[k * 2 + 2] == 0x9) { + + mp_sint32 op = src[k * 2 + 3]; + if (lastIns[j]) + { + mp_sint32 insIndex = lastIns[j] - 1; + + mp_sint32 smpIndex = module->instr[insIndex].snum[src[0]-1]; + + if (smpIndex >= 0 && smpIndex < MP_MAXSAMPLES) + { + if (&module->smp[smpIndex] == sample) + { + const float factor = (float)sample->samplen / (float)oldSize; + op = (mp_sint32)roundf(op * factor); + if (op > 255) { + op = 255; + } + src[k * 2 + 3] = (mp_ubyte)op; + } + } + } + + } + } + } + } + } + } +} + void ModuleEditor::insertText(char* dst, const char* src, mp_sint32 max) { char name[MP_MAXTEXT+1]; diff --git a/src/tracker/ModuleEditor.h b/src/tracker/ModuleEditor.h index 3519362c..773ba164 100644 --- a/src/tracker/ModuleEditor.h +++ b/src/tracker/ModuleEditor.h @@ -379,6 +379,8 @@ class ModuleEditor void optimizeSamples(bool convertTo8Bit, bool minimize, mp_sint32& numConvertedSamples, mp_sint32& numMinimizedSamples, bool evaluate); + + void adjustSampleOffsetCommandAfterSampleSizeChange(TXMSample *sample, pp_int32 oldSize); public: static void insertText(char* dst, const char* src, mp_sint32 max); diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp index 35550136..4624184b 100644 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -804,6 +804,18 @@ pp_int32 SampleEditor::getPanning() const return sample ? sample->pan : 0; } +bool SampleEditor::isLastOperationResampling() const { + return lastFilterFunc == &SampleEditor::tool_resampleSample; +} + +const FilterParameters* SampleEditor::getLastParameters() const { + return lastParameters; +} + +const SampleUndoStackEntry* SampleEditor::getUndoSample() const { + return before; +} + void SampleEditor::startDrawing() { if (sample) diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h index 62c87b6e..a516c967 100644 --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -239,6 +239,10 @@ class SampleEditor : public EditorBase bool isEmpty() const { if (sample && !sample->sample) return true; else return false; } + bool isLastOperationResampling() const; + const FilterParameters* getLastParameters() const; + const SampleUndoStackEntry* getUndoSample() const; + void startDrawing(); bool isDrawing() const { return drawing; } void drawSample(pp_int32 sampleIndex, float s); diff --git a/src/tracker/SampleEditorControlLastValues.h b/src/tracker/SampleEditorControlLastValues.h index 7b58516d..118e7e49 100644 --- a/src/tracker/SampleEditorControlLastValues.h +++ b/src/tracker/SampleEditorControlLastValues.h @@ -47,6 +47,7 @@ struct SampleEditorControlLastValues pp_int32 resampleInterpolationType; bool adjustFtAndRelnote; + bool adjustSampleOffsetCommand; static float invalidFloatValue() { @@ -72,6 +73,7 @@ struct SampleEditorControlLastValues hasEQ3BandValues = hasEQ10BandValues = false; resampleInterpolationType = invalidIntValue(); adjustFtAndRelnote = true; + adjustSampleOffsetCommand = false; } PPDictionary convertToDictionary() @@ -97,6 +99,8 @@ struct SampleEditorControlLastValues result.store("resampleInterpolationType", resampleInterpolationType); result.store("adjustFtAndRelnote", adjustFtAndRelnote); + + result.store("adjustSampleOffsetCommands", adjustSampleOffsetCommand); return result; } @@ -149,7 +153,11 @@ struct SampleEditorControlLastValues { adjustFtAndRelnote = key->getBoolValue(); } - + else if (key->getKey().compareToNoCase("adjustSampleOffsetCommands") == 0) + { + adjustSampleOffsetCommand = key->getBoolValue(); + } + key = dictionary.getNextKey(); } } diff --git a/src/tracker/SampleEditorControlToolHandler.cpp b/src/tracker/SampleEditorControlToolHandler.cpp index 366c6c04..675d0b55 100644 --- a/src/tracker/SampleEditorControlToolHandler.cpp +++ b/src/tracker/SampleEditorControlToolHandler.cpp @@ -234,11 +234,13 @@ bool SampleEditorControl::invokeTool(ToolHandlerResponder::SampleToolTypes type) { lastValues.resampleInterpolationType = static_cast(dialog)->getInterpolationType(); lastValues.adjustFtAndRelnote = static_cast(dialog)->getAdjustFtAndRelnote(); + lastValues.adjustSampleOffsetCommand = static_cast(dialog)->getAdjustSampleOffsetCommand(); - FilterParameters par(3); + FilterParameters par(4); par.setParameter(0, FilterParameters::Parameter(static_cast(dialog)->getC4Speed())); par.setParameter(1, FilterParameters::Parameter(static_cast(lastValues.resampleInterpolationType))); par.setParameter(2, FilterParameters::Parameter(lastValues.adjustFtAndRelnote ? 1 : 0)); + par.setParameter(3, FilterParameters::Parameter(lastValues.adjustSampleOffsetCommand ? 1 : 0)); sampleEditor->tool_resampleSample(&par); break; } From 3533e5d836e3ac642b277b0a96ba044a9af5d8d4 Mon Sep 17 00:00:00 2001 From: Peter Barth Date: Sun, 29 Aug 2021 22:26:56 +0200 Subject: [PATCH 24/30] feat: Add tracker string parameter to saveExtendedModule function --- src/milkyplay/ExporterXM.cpp | 21 ++++++++++++++------- src/milkyplay/XModule.h | 2 +- src/tracker/ModuleEditor.cpp | 6 +++--- 3 files changed, 18 insertions(+), 11 deletions(-) diff --git a/src/milkyplay/ExporterXM.cpp b/src/milkyplay/ExporterXM.cpp index 865f0cee..a59b0141 100644 --- a/src/milkyplay/ExporterXM.cpp +++ b/src/milkyplay/ExporterXM.cpp @@ -1341,7 +1341,7 @@ static void sort(mp_sword* array,mp_sint32 l, mp_sint32 r) if (i 20 ? 20 : len); + f.write(trackerStringBuffer, 1, 20); + } + else + { + f.write(header.tracker, 1, 20); + } + header.ver = 0x104; f.writeWord(header.ver); header.hdrsize = 276; diff --git a/src/milkyplay/XModule.h b/src/milkyplay/XModule.h index 4f04a2d2..67457faa 100644 --- a/src/milkyplay/XModule.h +++ b/src/milkyplay/XModule.h @@ -640,7 +640,7 @@ class XModule /////////////////////////////////////////////////// // Module exporters // /////////////////////////////////////////////////// - mp_sint32 saveExtendedModule(const SYSCHAR* fileName); // FT2 (.XM) + mp_sint32 saveExtendedModule(const SYSCHAR* fileName, const char* trackerString = NULL); // FT2 (.XM) mp_sint32 saveProtrackerModule(const SYSCHAR* fileName); // Protracker compatible (.MOD) /////////////////////////////////////////////////// diff --git a/src/tracker/ModuleEditor.cpp b/src/tracker/ModuleEditor.cpp index eb5df129..f5dda8e9 100644 --- a/src/tracker/ModuleEditor.cpp +++ b/src/tracker/ModuleEditor.cpp @@ -31,6 +31,7 @@ #include "PlayerCriticalSection.h" #include "TrackerConfig.h" #include "PPSystem.h" +#include "version.h" static const char validCharacters[] = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_!."; @@ -787,7 +788,7 @@ bool ModuleEditor::saveSong(const SYSCHAR* fileName, ModSaveTypes saveType/* = e { case ModSaveTypeDefault: case ModSaveTypeXM: - res = module->saveExtendedModule(fileName) == 0; + res = module->saveExtendedModule(fileName, MILKYTRACKER_VERSION_STRING) == 0; break; case ModSaveTypeMOD: @@ -809,10 +810,9 @@ bool ModuleEditor::saveSong(const SYSCHAR* fileName, ModSaveTypes saveType/* = e mp_sint32 ModuleEditor::saveBackup(const SYSCHAR* fileName) { - return module->saveExtendedModule(fileName); + return module->saveExtendedModule(fileName, MILKYTRACKER_VERSION_STRING); } - void ModuleEditor::increaseSongLength() { if (module->header.ordnum < 255) From 4f97b7011b20519890e30368e2c2cf17c81020b6 Mon Sep 17 00:00:00 2001 From: Johannes Schultz Date: Sat, 15 Jan 2022 00:38:13 +0100 Subject: [PATCH 25/30] Fix various heap corruptions and crashes in PSM loader --- src/milkyplay/LoaderPSM.cpp | 41 +++++++++++++++++++++---------------- 1 file changed, 23 insertions(+), 18 deletions(-) diff --git a/src/milkyplay/LoaderPSM.cpp b/src/milkyplay/LoaderPSM.cpp index 81aa1923..ea27593c 100644 --- a/src/milkyplay/LoaderPSM.cpp +++ b/src/milkyplay/LoaderPSM.cpp @@ -70,6 +70,7 @@ static bool PATTTest(mp_ubyte* p, mp_sint32& size) patterns[i] = NULL; \ } \ delete[] patterns; \ + delete[] patternSizes; \ } const char* LoaderPSMv2::identifyModule(const mp_ubyte* buffer) @@ -487,29 +488,32 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) mp_sint32 offset = 6+patIDSize; mp_ubyte* packed = patterns[i]+offset; - mp_uint32 index = 0; mp_uint32 row = 0; - + mp_uint32 numRows = LittleEndian::GET_WORD(patterns[i] + offset - 2); + if (numRows > 256) + { + RELEASE_PATTERNS; + return MP_OUT_OF_MEMORY; + } + mp_uint32 maxChannels = 0; - while (index<(patternSizes[i]-offset)) + while (index<(patternSizes[i]-offset) && row < numRows) { - mp_uint32 size = ((mp_uword)LittleEndian::GET_WORD(packed+index))-2; - index+=2; // advance pointer - + mp_uint32 size = ((mp_uword)LittleEndian::GET_WORD(packed+index)); mp_uint32 dstIndex = index+size; - - if (size) + index += 2; // advance pointer + + if (size > 2) { - do { mp_ubyte pi = packed[index++]; - mp_uint32 chn = packed[index++]; + mp_uint32 chn = packed[index++] & 0x1F; if (chn>maxChannels) maxChannels = chn; @@ -553,7 +557,11 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) } else if (slot[3] == 0x2D) { - slot[4] = packed[index+=3]; + slot[4] = packed[index+=3]; // ??? + } + else if (slot[3] == 0x33) + { + index++; } } @@ -564,12 +572,12 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) if (index!=dstIndex) printf("nagnag "); #endif - + index = dstIndex; + } - row++; + row++; } - delete[] patternSizes; maxChannels++; @@ -577,7 +585,7 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) maxChannels = header->channum; // convert pattern here: - phead[i].rows = (mp_uword)LittleEndian::GET_WORD(patterns[i]+offset-2); + phead[i].rows = (mp_uword)numRows; phead[i].effnum = 3; phead[i].channum = maxChannels; @@ -585,7 +593,6 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) if (phead[i].patternData == NULL) { - delete[] pattern; RELEASE_PATTERNS; return MP_OUT_OF_MEMORY; } @@ -839,8 +846,6 @@ mp_sint32 LoaderPSMv2::load(XMFileBase& f, XModule* module) } - delete[] pattern; - RELEASE_PATTERNS; header->smpnum = smpIndex; From 9647e01292e254dfeb868a28659dbc7dd0e7b7cb Mon Sep 17 00:00:00 2001 From: j v Date: Mon, 11 Apr 2022 11:36:43 -0700 Subject: [PATCH 26/30] Fix missing argument to SampleEditorControl --- src/tracker/SectionSamples.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tracker/SectionSamples.cpp b/src/tracker/SectionSamples.cpp index 8a78f1bb..c3753bb5 100644 --- a/src/tracker/SectionSamples.cpp +++ b/src/tracker/SectionSamples.cpp @@ -759,7 +759,7 @@ void SectionSamples::init(pp_int32 x, pp_int32 y) PPContainer* sampleEditorContainer = new PPContainer(CONTAINER_SAMPLEEDITOR, screen, this, PPPoint(x, y), PPSize(320, 92), false); sampleEditorContainer->setColor(TrackerConfig::colorThemeMain); - sampleEditorControl = new SampleEditorControl(SAMPLE_EDITOR, screen, this, PPPoint(x+2, y+2), PPSize(316, 92-4)); + sampleEditorControl = new SampleEditorControl(SAMPLE_EDITOR, screen, this, PPPoint(x+2, y+2), PPSize(316, 92-4), tracker); sampleEditorControl->attachSampleEditor(tracker.moduleEditor->getSampleEditor()); sampleEditorControl->setBorderColor(TrackerConfig::colorThemeMain); From 3a5474f9102cbdc10fbd9e7b1b2c8d3f3f45d91b Mon Sep 17 00:00:00 2001 From: Johannes Schultz Date: Sun, 26 Jun 2022 17:53:59 +0200 Subject: [PATCH 27/30] Fix possible stack corruption with XM instrument headers claiming a size of less than 4 Closes #275 --- src/milkyplay/LoaderXM.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/milkyplay/LoaderXM.cpp b/src/milkyplay/LoaderXM.cpp index f87f5c11..303e3493 100644 --- a/src/milkyplay/LoaderXM.cpp +++ b/src/milkyplay/LoaderXM.cpp @@ -478,7 +478,7 @@ mp_sint32 LoaderXM::load(XMFileBase& f, XModule* module) f.readDwords(&instr[y].size,1); - if (instr[y].size < 29) + if (instr[y].size >= 4 && instr[y].size < 29) { mp_ubyte buffer[29]; memset(buffer, 0, sizeof(buffer)); From 3c60de3b4376df1d105a9efaf581b9adf8d3ab36 Mon Sep 17 00:00:00 2001 From: nyanpasu64 Date: Wed, 13 Jul 2022 05:11:41 -0700 Subject: [PATCH 28/30] Fix About screen crash caused by missing null terminator (#255) --- src/tracker/AnimatedFXControl.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/tracker/AnimatedFXControl.cpp b/src/tracker/AnimatedFXControl.cpp index 010ba7b1..8693085c 100644 --- a/src/tracker/AnimatedFXControl.cpp +++ b/src/tracker/AnimatedFXControl.cpp @@ -141,6 +141,7 @@ AnimatedFXControl::AnimatedFXControl(pp_int32 id, textBufferMaxChars = visibleWidth*2 / font->getCharWidth(); textBuffer = new char[textBufferMaxChars + 1]; + textBuffer[textBufferMaxChars] = '\0'; currentCharIndex = 0; pp_int32 j = currentCharIndex % strlen(text); From 59f01750f1492fe4f558f73813b056303a9fafe0 Mon Sep 17 00:00:00 2001 From: Cong Date: Wed, 13 Jul 2022 22:14:30 +1000 Subject: [PATCH 29/30] Add quarter sine generator #239 (#250) Also fix half sine and absolute sine generator ranges --- src/tracker/SampleEditor.cpp | 67 +++++++++++++++++-- src/tracker/SampleEditor.h | 1 + src/tracker/SampleEditorControl.cpp | 6 ++ src/tracker/SampleEditorControl.h | 6 +- .../SampleEditorControlToolHandler.cpp | 12 ++++ 5 files changed, 84 insertions(+), 8 deletions(-) diff --git a/src/tracker/SampleEditor.cpp b/src/tracker/SampleEditor.cpp index 4624184b..792f36c9 100644 --- a/src/tracker/SampleEditor.cpp +++ b/src/tracker/SampleEditor.cpp @@ -3033,12 +3033,12 @@ void SampleEditor::tool_generateHalfSine(const FilterParameters* par) const float amplify = par->getParameter(0).floatPart; // generate half sine wave here - for (i = sStart; i < sEnd / 2; i++) + for (i = sStart; i < sStart + sLen / 2; i++) { float per = (i - sStart) / (float)sLen * numPeriods; setFloatSampleInWaveform(i, (float)sin(per) * amplify); } - for (i = sEnd / 2; i < sEnd; i++) + for (; i < sEnd; i++) { setFloatSampleInWaveform(i, 0); } @@ -3083,17 +3083,72 @@ void SampleEditor::tool_generateAbsoluteSine(const FilterParameters* par) const float numPeriods = (float)(6.283185307179586476925286766559 * par->getParameter(1).floatPart); const float amplify = par->getParameter(0).floatPart; - // generate half sine wave in first and second halves - for (i = sStart; i < sEnd / 2; i++) + // generate absolute sine wave here + for (i = sStart; i < sEnd; i++) + { + float per = (i - sStart) / (float)sLen * numPeriods; + setFloatSampleInWaveform(i, fabs((float)sin(per) * amplify)); + } + + finishUndo(); + + postFilter(); +} + +void SampleEditor::tool_generateQuarterSine(const FilterParameters* par) +{ + if (isEmptySample()) + return; + + pp_int32 sStart = selectionStart; + pp_int32 sEnd = selectionEnd; + + if (hasValidSelection()) + { + if (sStart >= 0 && sEnd >= 0) + { + if (sEnd < sStart) + { + pp_int32 s = sEnd; sEnd = sStart; sStart = s; + } + } + } + else + { + sStart = 0; + sEnd = sample->samplen; + } + + preFilter(&SampleEditor::tool_generateQuarterSine, par); + + mp_sint32 sLen = sEnd - sStart; + + prepareUndo(); + + pp_int32 i; + + const float numPeriods = (float)(6.283185307179586476925286766559 * par->getParameter(1).floatPart); + const float amplify = par->getParameter(0).floatPart; + + // generate quarter sine wave in first and third quarters + for (i = sStart; i < sStart + sLen / 4; i++) { float per = (i - sStart) / (float)sLen * numPeriods; setFloatSampleInWaveform(i, (float)sin(per) * amplify); } - for (i = sEnd / 2; i < sEnd; i++) + for (; i < sStart + sLen / 2; i++) { - float per = (i - sEnd / 2) / (float)sLen * numPeriods; + setFloatSampleInWaveform(i, 0); + } + for (; i < sStart + sLen * 3 / 4; i++) + { + float per = (i - (sStart + sLen / 2)) / (float)sLen * numPeriods; setFloatSampleInWaveform(i, (float)sin(per) * amplify); } + for (; i < sEnd; i++) + { + setFloatSampleInWaveform(i, 0); + } finishUndo(); diff --git a/src/tracker/SampleEditor.h b/src/tracker/SampleEditor.h index a516c967..8757eeff 100644 --- a/src/tracker/SampleEditor.h +++ b/src/tracker/SampleEditor.h @@ -357,6 +357,7 @@ class SampleEditor : public EditorBase void tool_generateSawtooth(const FilterParameters* par); void tool_generateHalfSine(const FilterParameters* par); void tool_generateAbsoluteSine(const FilterParameters* par); + void tool_generateQuarterSine(const FilterParameters* par); void tool_applyLastFilter(); bool tool_canApplyLastFilter() const; diff --git a/src/tracker/SampleEditorControl.cpp b/src/tracker/SampleEditorControl.cpp index de6d8bae..a6b6e407 100644 --- a/src/tracker/SampleEditorControl.cpp +++ b/src/tracker/SampleEditorControl.cpp @@ -162,6 +162,7 @@ SampleEditorControl::SampleEditorControl(pp_int32 id, subMenuGenerators->addEntry("Sawtooth" PPSTR_PERIODS, MenuCommandIDGenerateSawtooth); subMenuGenerators->addEntry("Half Sine" PPSTR_PERIODS, MenuCommandIDGenerateHalfSine); subMenuGenerators->addEntry("Absolute Sine" PPSTR_PERIODS, MenuCommandIDGenerateAbsoluteSine); + subMenuGenerators->addEntry("Quarter Sine" PPSTR_PERIODS, MenuCommandIDGenerateQuarterSine); subMenuGenerators->addEntry("Silence" PPSTR_PERIODS, MenuCommandIDGenerateSilence); // build context menu @@ -1717,6 +1718,7 @@ void SampleEditorControl::invokeContextMenu(const PPPoint& p, bool translatePoin subMenuGenerators->setState(MenuCommandIDGenerateSawtooth, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateHalfSine, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateAbsoluteSine, isEmptySample); + subMenuGenerators->setState(MenuCommandIDGenerateQuarterSine, isEmptySample); subMenuGenerators->setState(MenuCommandIDGenerateSilence, isEmptySample); parentScreen->setContextMenuControl(editMenuControl); @@ -1907,6 +1909,10 @@ void SampleEditorControl::executeMenuCommand(pp_int32 commandId) invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateAbsoluteSine); break; + case MenuCommandIDGenerateQuarterSine: + invokeToolParameterDialog(ToolHandlerResponder::SampleToolTypeGenerateQuarterSine); + break; + } } diff --git a/src/tracker/SampleEditorControl.h b/src/tracker/SampleEditorControl.h index 570aabcc..9f9bd0bf 100644 --- a/src/tracker/SampleEditorControl.h +++ b/src/tracker/SampleEditorControl.h @@ -309,7 +309,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub MenuCommandIDGenerateTriangle, MenuCommandIDGenerateSawtooth, MenuCommandIDGenerateHalfSine, - MenuCommandIDGenerateAbsoluteSine + MenuCommandIDGenerateAbsoluteSine, + MenuCommandIDGenerateQuarterSine }; void executeMenuCommand(pp_int32 commandId); @@ -355,7 +356,8 @@ class SampleEditorControl : public PPControl, public EventListenerInterface, pub SampleToolTypeGenerateTriangle, SampleToolTypeGenerateSawtooth, SampleToolTypeGenerateHalfSine, - SampleToolTypeGenerateAbsoluteSine + SampleToolTypeGenerateAbsoluteSine, + SampleToolTypeGenerateQuarterSine }; private: diff --git a/src/tracker/SampleEditorControlToolHandler.cpp b/src/tracker/SampleEditorControlToolHandler.cpp index 675d0b55..62292600 100644 --- a/src/tracker/SampleEditorControlToolHandler.cpp +++ b/src/tracker/SampleEditorControlToolHandler.cpp @@ -155,6 +155,7 @@ bool SampleEditorControl::invokeToolParameterDialog(SampleEditorControl::ToolHan case ToolHandlerResponder::SampleToolTypeGenerateSawtooth: case ToolHandlerResponder::SampleToolTypeGenerateHalfSine: case ToolHandlerResponder::SampleToolTypeGenerateAbsoluteSine: + case ToolHandlerResponder::SampleToolTypeGenerateQuarterSine: { dialog = new DialogWithValues(parentScreen, toolHandlerResponder, PP_DEFAULT_ID, "Generate waveform" PPSTR_PERIODS, DialogWithValues::ValueStyleEnterTwoValues); static_cast(dialog)->setValueOneCaption("Volume in percent:"); @@ -358,6 +359,17 @@ bool SampleEditorControl::invokeTool(ToolHandlerResponder::SampleToolTypes type) break; } + case ToolHandlerResponder::SampleToolTypeGenerateQuarterSine: + { + lastValues.waveFormVolume = static_cast(dialog)->getValueOne(); + lastValues.waveFormNumPeriods = static_cast(dialog)->getValueTwo(); + FilterParameters par(2); + par.setParameter(0, FilterParameters::Parameter(lastValues.waveFormVolume / 100.0f)); + par.setParameter(1, FilterParameters::Parameter(lastValues.waveFormNumPeriods)); + sampleEditor->tool_generateQuarterSine(&par); + break; + } + default: break; } From 6d5dafa489bcb576e0a2a3c5f2b30c32b033d64d Mon Sep 17 00:00:00 2001 From: mothcompute <94941435+mothcompute@users.noreply.github.com> Date: Thu, 14 Jul 2022 00:00:43 -0700 Subject: [PATCH 30/30] fix segfault when passing invalid filename on command line (#276) * fix segfault when passing invalid filename on command line * fix formatting --- src/tracker/sdl/SDL_Main.cpp | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/src/tracker/sdl/SDL_Main.cpp b/src/tracker/sdl/SDL_Main.cpp index 75ffa1df..35a95b6b 100644 --- a/src/tracker/sdl/SDL_Main.cpp +++ b/src/tracker/sdl/SDL_Main.cpp @@ -65,6 +65,7 @@ #include #include #include +#include #include #include "SDL_KeyTranslation.h" @@ -971,13 +972,21 @@ int main(int argc, char *argv[]) if (loadFile) { - PPSystemString newCwd = path.getCurrent(); - path.change(oldCwd); - SendFile(realpath(loadFile, loadFileAbsPath)); - path.change(newCwd); - pp_uint16 chr[3] = {VK_RETURN, 0, 0}; - PPEvent event(eKeyDown, &chr, sizeof(chr)); - RaiseEventSerialized(&event); + struct stat statBuf; + if (stat(loadFile, &statBuf) != 0) + { + fprintf(stderr, "could not open %s: %s\n", loadFile, strerror(errno)); + } + else + { + PPSystemString newCwd = path.getCurrent(); + path.change(oldCwd); + SendFile(realpath(loadFile, loadFileAbsPath)); + path.change(newCwd); + pp_uint16 chr[3] = {VK_RETURN, 0, 0}; + PPEvent event(eKeyDown, &chr, sizeof(chr)); + RaiseEventSerialized(&event); + } } // Main event loop
Windows: Select Preferences from the system menu (top left corner of the window)
OSX: Select Preferences from the MilkyTracker menu or press Command-,
Linux: Enabled by default if available on the system. See the Linux readme for details.