shithub: pt2-clone

Download patch

ref: 8b9bbe660ea1dad5f1f8e695e752ed24293533ec
parent: 0ba37bb2ad4c53eaf89f84c7e46b5a54a69472a0
author: Olav Sørensen <olav.sorensen@live.no>
date: Wed Apr 29 13:45:18 EDT 2020

Pushed v1.12 code

- Fixed a bug where the right loop-pin could sometimes disappear when zoomed in
  and scrolled all the way to the right.
- A much needed code refactoring of data structs. The code now also compiles
  with GCC 10 (fixed GitHub issue #7).

--- a/.gitignore
+++ b/.gitignore
@@ -18,3 +18,4 @@
 vs2019_project/pt2-clone/x64/Debug/pt2-clone.vcxproj.FileListAbsolute.txt
 *.opendb
 *.cod
+vs2019_project/pt2-clone/Debug/pt2-clone.vcxproj.FileListAbsolute.txt
--- a/src/pt2_audio.c
+++ b/src/pt2_audio.c
@@ -31,6 +31,7 @@
 #include "pt2_visuals.h"
 #include "pt2_scopes.h"
 #include "pt2_mod2wav.h"
+#include "pt2_structs.h"
 
 #define INITIAL_DITHER_SEED 0x12345000
 
@@ -48,6 +49,8 @@
 	double dVolume, dDelta, dDeltaMul, dPhase, dLastDelta, dLastDeltaMul, dLastPhase, dPanL, dPanR;
 } paulaVoice_t;
 
+audio_t audio; // globalized
+
 static volatile int8_t filterFlags;
 static int8_t defStereoSep;
 static bool amigaPanFlag;
@@ -67,12 +70,12 @@
 
 bool intMusic(void); // defined in pt_modplayer.c
 
-static uint16_t bpm2SmpsPerTick(uint32_t bpm, uint32_t audioFreq)
+static uint16_t bpm2SmpsPerTick(int32_t bpm, uint32_t audioFreq)
 {
 	if (bpm == 0)
 		return 0;
 
-	const uint32_t ciaVal = (uint32_t)(1773447 / bpm); // yes, PT truncates here
+	const int32_t ciaVal = (int32_t)(1773447 / bpm); // yes, PT truncates here
 	const double dCiaHz = (double)CIA_PAL_CLK / ciaVal;
 
 	int32_t smpsPerTick = (int32_t)((audioFreq / dCiaHz) + 0.5); // rounded
@@ -81,7 +84,7 @@
 
 static void generateBpmTables(void)
 {
-	for (uint32_t i = 32; i <= 255; i++)
+	for (int32_t i = 32; i <= 255; i++)
 	{
 		audio.bpmTab[i-32] = bpm2SmpsPerTick(i, audio.outputRate);
 		audio.bpmTab28kHz[i-32] = bpm2SmpsPerTick(i, 28836); // PAT2SMP hi quality
@@ -100,6 +103,10 @@
 
 void setLEDFilter(bool state)
 {
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
+		lockAudio();
+
 	editor.useLEDFilter = state;
 	if (editor.useLEDFilter)
 	{
@@ -110,10 +117,17 @@
 	{
 		filterFlags &= ~FILTER_LED_ENABLED;
 	}
+
+	if (audioWasntLocked)
+		unlockAudio();
 }
 
 void toggleLEDFilter(void)
 {
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
+		lockAudio();
+
 	editor.useLEDFilter ^= 1;
 	if (editor.useLEDFilter)
 	{
@@ -124,6 +138,9 @@
 	{
 		filterFlags &= ~FILTER_LED_ENABLED;
 	}
+
+	if (audioWasntLocked)
+		unlockAudio();
 }
 
 /* Imperfect "LED" filter implementation. This may be further improved in the future.
@@ -326,10 +343,10 @@
 	paula[ch].dPanR = sinApx(dPan);
 }
 
-void mixerKillVoice(uint8_t ch)
+void mixerKillVoice(int32_t ch)
 {
-	const bool wasLocked = audio.locked;
-	if (!wasLocked)
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
 		lockAudio();
 
 	// copy old pans
@@ -346,17 +363,17 @@
 	memset(&blep[ch], 0, sizeof (blep_t));
 	memset(&blepVol[ch], 0, sizeof (blep_t));
 
-	if (!wasLocked)
+	if (audioWasntLocked)
 		unlockAudio();
 }
 
 void turnOffVoices(void)
 {
-	const bool wasLocked = audio.locked;
-	if (!wasLocked)
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
 		lockAudio();
 
-	for (uint8_t i = 0; i < AMIGA_VOICES; i++)
+	for (int32_t i = 0; i < AMIGA_VOICES; i++)
 		mixerKillVoice(i);
 
 	clearRCFilterState(&filterLo);
@@ -367,18 +384,18 @@
 
 	editor.tuningFlag = false;
 
-	if (!wasLocked)
+	if (audioWasntLocked)
 		unlockAudio();
 }
 
 void resetCachedMixerPeriod(void)
 {
-	oldPeriod = 0xFFFFFFFF;
+	oldPeriod = -1;
 }
 
 // the following routines are only called from the mixer thread.
 
-void paulaSetPeriod(uint8_t ch, uint16_t period)
+void paulaSetPeriod(int32_t ch, uint16_t period)
 {
 	int32_t realPeriod;
 	double dPeriodToDeltaDiv;
@@ -426,7 +443,7 @@
 	if (v->dLastDeltaMul == 0.0) v->dLastDeltaMul = v->dDeltaMul;
 }
 
-void paulaSetVolume(uint8_t ch, uint16_t vol)
+void paulaSetVolume(int32_t ch, uint16_t vol)
 {
 	vol &= 127; // confirmed behavior on real Amiga
 
@@ -436,7 +453,7 @@
 	paula[ch].dVolume = vol * (1.0 / 64.0);
 }
 
-void paulaSetLength(uint8_t ch, uint16_t len)
+void paulaSetLength(int32_t ch, uint16_t len)
 {
 	if (len == 0)
 	{
@@ -450,7 +467,7 @@
 	scopeExt[ch].newLength = paula[ch].newLength = len << 1;
 }
 
-void paulaSetData(uint8_t ch, const int8_t *src)
+void paulaSetData(int32_t ch, const int8_t *src)
 {
 	uint8_t smp;
 	moduleSample_t *s;
@@ -477,12 +494,12 @@
 	*se = tmp; // update it
 }
 
-void paulaStopDMA(uint8_t ch)
+void paulaStopDMA(int32_t ch)
 {
 	scopeExt[ch].active = paula[ch].active = false;
 }
 
-void paulaStartDMA(uint8_t ch)
+void paulaStartDMA(int32_t ch)
 {
 	const int8_t *dat;
 	int32_t length;
@@ -536,11 +553,13 @@
 
 void toggleA500Filters(void)
 {
-	lockAudio();
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
+		lockAudio();
+
 	clearRCFilterState(&filterLo);
 	clearRCFilterState(&filterHi);
 	clearLEDFilterState();
-	unlockAudio();
 
 	if (filterFlags & FILTER_A500)
 	{
@@ -552,6 +571,9 @@
 		filterFlags |= FILTER_A500;
 		displayMsg("LP FILTER: A500");
 	}
+
+	if (audioWasntLocked)
+		unlockAudio();
 }
 
 void mixChannels(int32_t numSamples)
@@ -886,7 +908,7 @@
 		if (editor.pat2SmpPos+samplesTodo > MAX_SAMPLE_LEN)
 			samplesTodo = MAX_SAMPLE_LEN-editor.pat2SmpPos;
 
-		mixChannelsMultiStep(numSamples);
+		mixChannelsMultiStep(samplesTodo);
 
 		outStream = &editor.pat2SmpBuf[editor.pat2SmpPos];
 		for (i = 0; i < samplesTodo; i++)
@@ -1078,7 +1100,7 @@
 	SDL_AudioSpec want, have;
 
 	want.freq = config.soundFrequency;
-	want.samples = config.soundBufferSize;
+	want.samples = (uint16_t)config.soundBufferSize;
 	want.format = AUDIO_S16;
 	want.channels = 2;
 	want.callback = audioCallback;
@@ -1179,6 +1201,10 @@
 
 void toggleAmigaPanMode(void)
 {
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
+		lockAudio();
+
 	amigaPanFlag ^= 1;
 	if (!amigaPanFlag)
 	{
@@ -1190,6 +1216,9 @@
 		mixerCalcVoicePans(100);
 		displayMsg("AMIGA PANNING ON");
 	}
+
+	if (audioWasntLocked)
+		unlockAudio();
 }
 
 void normalize32bitSigned(int32_t *sampleData, uint32_t sampleLength)
--- a/src/pt2_audio.h
+++ b/src/pt2_audio.h
@@ -1,6 +1,3 @@
-/* The "LED" filter and BLEP routines were coded by aciddose.
-** Low-pass filter is based on https://bel.fi/alankila/modguide/interpolate.txt */
-
 #pragma once
 
 #include <stdint.h>
@@ -15,6 +12,17 @@
 	double c, c2, g, cg;
 } rcFilter_t;
 
+typedef struct audio_t
+{
+	volatile bool locked;
+	bool forceMixerOff;
+	uint16_t bpmTab[256-32], bpmTab28kHz[256-32], bpmTab22kHz[256-32], bpmTabMod2Wav[256-32];
+	uint32_t outputRate, audioBufferSize;
+	double dPeriodToDeltaDiv;
+} audio_t;
+
+extern audio_t audio; // pt2_audio.c
+
 void resetCachedMixerPeriod(void);
 void resetAudioDithering(void);
 void calcRCFilterCoeffs(const double sr, const double hz, rcFilter_t *f);
@@ -31,16 +39,16 @@
 void toggleLEDFilter(void);
 void toggleAmigaPanMode(void);
 void toggleA500Filters(void);
-void paulaStopDMA(uint8_t ch);
-void paulaStartDMA(uint8_t ch);
-void paulaSetPeriod(uint8_t ch, uint16_t period);
-void paulaSetVolume(uint8_t ch, uint16_t vol);
-void paulaSetLength(uint8_t ch, uint16_t len);
-void paulaSetData(uint8_t ch, const int8_t *src);
+void paulaStopDMA(int32_t ch);
+void paulaStartDMA(int32_t ch);
+void paulaSetPeriod(int32_t ch, uint16_t period);
+void paulaSetVolume(int32_t ch, uint16_t vol);
+void paulaSetLength(int32_t ch, uint16_t len);
+void paulaSetData(int32_t ch, const int8_t *src);
 void lockAudio(void);
 void unlockAudio(void);
 void mixerUpdateLoops(void);
-void mixerKillVoice(uint8_t ch);
+void mixerKillVoice(int32_t ch);
 void turnOffVoices(void);
 void mixerCalcVoicePans(uint8_t stereoSeparation);
 void mixerSetSamplesPerTick(uint32_t val);
--- a/src/pt2_blep.c
+++ b/src/pt2_blep.c
@@ -1,8 +1,9 @@
 // these BLEP routines were coded by aciddose
 
 #include <stdint.h>
+#include <stdbool.h>
+#include <assert.h>
 #include "pt2_blep.h"
-#include "pt2_helpers.h"
 
 /* Why this table is not represented as readable floating-point numbers:
 ** Accurate double representation in string format requires at least 14 digits and normalized
@@ -83,6 +84,8 @@
 
 const double *get_minblep_table(void) { return (const double *)minblepdata; }
 
+#define LERP(x, y, z) ((x) + ((y) - (x)) * (z))
+
 void blepAdd(blep_t *b, double dOffset, double dAmplitude)
 {
 	assert(dOffset >= 0.0 && dOffset < 1.0);
@@ -116,8 +119,9 @@
 	for (int32_t n = 0; n < BLEP_NS; n++)
 	{
 		b->dBuffer[i] += dAmplitude * (*dBlepSrc);
-		i = (i + 1) & BLEP_RNS;
 		dBlepSrc += BLEP_SP;
+
+		i = (i + 1) & BLEP_RNS;
 	}
 
 	b->samplesLeft = BLEP_NS;
--- a/src/pt2_blep.h
+++ b/src/pt2_blep.h
@@ -1,10 +1,10 @@
-// This BLEP implementation was coded by aciddose/adejr
+// these BLEP routines were coded by aciddose
 
 #pragma once
 
 #include <stdint.h>
 
-/* aciddose/adejr:
+/* aciddose:
 ** information on blep variables
 **
 ** ZC = zero crossings, the number of ripples in the impulse
--- a/src/pt2_config.c
+++ b/src/pt2_config.c
@@ -27,6 +27,8 @@
 static char oldCwd[PATH_MAX];
 #endif
 
+config_t config; // globalized
+
 static bool loadProTrackerDotIni(FILE *f);
 static FILE *openPTDotConfig(void);
 static bool loadPTDotConfig(FILE *f);
--- a/src/pt2_config.h
+++ b/src/pt2_config.h
@@ -3,7 +3,7 @@
 #include <stdint.h>
 #include <stdbool.h>
 
-struct config_t
+typedef struct config_t
 {
 	char *defModulesDir, *defSamplesDir;
 	bool dottedCenterFlag, pattDots, a500LowPassFilter, compoMode, autoCloseDiskOp, hideDiskOpDates, hwMouse;
@@ -12,6 +12,8 @@
 	int8_t stereoSeparation, videoScaleFactor, accidental;
 	uint16_t quantizeValue;
 	uint32_t soundFrequency, soundBufferSize;
-} config;
+} config_t;
+
+extern config_t config; // pt2_config.c
 
 void loadConfig(void);
--- a/src/pt2_diskop.c
+++ b/src/pt2_diskop.c
@@ -105,7 +105,7 @@
 	if (!UNICHAR_STRNICMP(f->nameU, ".", 1))
 		return false; // skip ".name" entries
 
-	if (f->isDir || editor.diskop.mode == DISKOP_MODE_SMP)
+	if (f->isDir || diskop.mode == DISKOP_MODE_SMP)
 		return true; // list all entries
 
 	if (entryName >= 4)
@@ -298,31 +298,31 @@
 
 void diskOpShowSelectText(void)
 {
-	if (!editor.ui.diskOpScreenShown || editor.ui.pointerMode == POINTER_MODE_MSG1 || editor.errorMsgActive)
+	if (!ui.diskOpScreenShown || ui.pointerMode == POINTER_MODE_MSG1 || editor.errorMsgActive)
 		return;
 
-	if (editor.diskop.mode == DISKOP_MODE_MOD)
+	if (diskop.mode == DISKOP_MODE_MOD)
 		setStatusMessage("SELECT MODULE", NO_CARRY);
 	else
 		setStatusMessage("SELECT SAMPLE", NO_CARRY);
 }
 
-void handleEntryJumping(char jumpToChar) // SHIFT+character
+void handleEntryJumping(SDL_Keycode jumpToChar) // SHIFT+character
 {
 	int32_t i;
 
 	if (diskOpEntry != NULL)
 	{
-		for (i = 0; i < editor.diskop.numEntries; i++)
+		for (i = 0; i < diskop.numEntries; i++)
 		{
 			if (jumpToChar == diskOpEntry[i].firstAnsiChar)
 			{
 				// fix visual overrun
-				if (editor.diskop.numEntries > DISKOP_LINES && i > editor.diskop.numEntries-DISKOP_LINES)
-					i = editor.diskop.numEntries - DISKOP_LINES;
+				if (diskop.numEntries > DISKOP_LINES && i > diskop.numEntries-DISKOP_LINES)
+					i = diskop.numEntries - DISKOP_LINES;
 
-				editor.diskop.scrollOffset = i;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset = i;
+				ui.updateDiskOpFileList = true;
 				return;
 			}
 		}
@@ -338,7 +338,7 @@
 
 bool diskOpEntryIsEmpty(int32_t fileIndex)
 {
-	if (editor.diskop.scrollOffset+fileIndex >= editor.diskop.numEntries)
+	if (diskop.scrollOffset+fileIndex >= diskop.numEntries)
 		return true;
 
 	return false;
@@ -349,7 +349,7 @@
 	if (diskOpEntry != NULL)
 	{
 		if (!diskOpEntryIsEmpty(fileIndex))
-			return diskOpEntry[editor.diskop.scrollOffset+fileIndex].isDir;
+			return diskOpEntry[diskop.scrollOffset+fileIndex].isDir;
 	}
 
 	return false; // couldn't look up entry
@@ -361,7 +361,7 @@
 
 	if (diskOpEntry != NULL && !diskOpEntryIsEmpty(fileIndex))
 	{
-		filenameU = diskOpEntry[editor.diskop.scrollOffset+fileIndex].nameU;
+		filenameU = diskOpEntry[diskop.scrollOffset+fileIndex].nameU;
 		if (filenameU != NULL)
 		{
 			unicharToAnsi(fileNameBuffer, filenameU, PATH_MAX);
@@ -375,7 +375,7 @@
 UNICHAR *diskOpGetUnicodeEntry(int32_t fileIndex)
 {
 	if (diskOpEntry != NULL && !diskOpEntryIsEmpty(fileIndex))
-		return diskOpEntry[editor.diskop.scrollOffset+fileIndex].nameU;
+		return diskOpEntry[diskop.scrollOffset+fileIndex].nameU;
 
 	return NULL;
 }
@@ -386,13 +386,13 @@
 	memset(editor.currPathU, 0, (PATH_MAX + 2) * sizeof (UNICHAR));
 	UNICHAR_GETCWD(editor.currPathU, PATH_MAX);
 
-	if (editor.diskop.mode == DISKOP_MODE_MOD)
+	if (diskop.mode == DISKOP_MODE_MOD)
 		UNICHAR_STRCPY(editor.modulesPathU, editor.currPathU);
 	else
 		UNICHAR_STRCPY(editor.samplesPathU, editor.currPathU);
 
 	unicharToAnsi(editor.currPath, editor.currPathU, PATH_MAX);
-	editor.ui.updateDiskOpPathText = true;
+	ui.updateDiskOpPathText = true;
 }
 
 bool changePathToHome(void)
@@ -420,7 +420,7 @@
 
 void setPathFromDiskOpMode(void)
 {
-	UNICHAR_CHDIR((editor.diskop.mode == DISKOP_MODE_MOD) ? editor.modulesPathU : editor.samplesPathU);
+	UNICHAR_CHDIR((diskop.mode == DISKOP_MODE_MOD) ? editor.modulesPathU : editor.samplesPathU);
 	setVisualPathToCwd();
 }
 
@@ -431,12 +431,12 @@
 		setVisualPathToCwd();
 
 		if (cache)
-			editor.diskop.cached = false;
+			diskop.cached = false;
 
-		if (editor.ui.diskOpScreenShown)
-			editor.ui.updateDiskOpFileList = true;
+		if (ui.diskOpScreenShown)
+			ui.updateDiskOpFileList = true;
 
-		editor.diskop.scrollOffset = 0;
+		diskop.scrollOffset = 0;
 		return true;
 	}
 	else
@@ -518,7 +518,7 @@
 {
 	if (diskOpEntry != NULL)
 	{
-		for (int32_t i = 0; i < editor.diskop.numEntries; i++)
+		for (int32_t i = 0; i < diskop.numEntries; i++)
 		{
 			if (diskOpEntry[i].nameU != NULL)
 				free(diskOpEntry[i].nameU);
@@ -528,7 +528,7 @@
 		diskOpEntry = NULL;
 	}
 
-	editor.diskop.numEntries = 0;
+	diskop.numEntries = 0;
 }
 
 static bool swapEntries(int32_t a, int32_t b)
@@ -535,7 +535,7 @@
 {
 	fileEntry_t tmpBuffer;
 
-	if (a >= editor.diskop.numEntries || b >= editor.diskop.numEntries)
+	if (a >= diskop.numEntries || b >= diskop.numEntries)
 		return false;
 
 	tmpBuffer = diskOpEntry[a];
@@ -586,13 +586,13 @@
 	char *p1, *p2;
 	uint32_t offset, limit, i;
 
-	if (editor.diskop.numEntries < 2)
+	if (diskop.numEntries < 2)
 		return; // no need to sort
 
-	offset = editor.diskop.numEntries / 2;
+	offset = diskop.numEntries / 2;
 	while (offset > 0)
 	{
-		limit = editor.diskop.numEntries - offset;
+		limit = diskop.numEntries - offset;
 		do
 		{
 			didSwap = false;
@@ -636,7 +636,7 @@
 	uint8_t lastFindFileFlag;
 	fileEntry_t tmpBuffer, *newPtr;
 
-	editor.diskop.scrollOffset = 0;
+	diskop.scrollOffset = 0;
 
 	// do we have a path set?
 	if (editor.currPathU[0] == '\0')
@@ -650,7 +650,7 @@
 	lastFindFileFlag = findFirst(&tmpBuffer);
 	if (lastFindFileFlag != LFF_DONE && lastFindFileFlag != LFF_SKIP)
 	{
-		diskOpEntry = (fileEntry_t *)malloc(sizeof (fileEntry_t) * (editor.diskop.numEntries + 1));
+		diskOpEntry = (fileEntry_t *)malloc(sizeof (fileEntry_t) * (diskop.numEntries + 1));
 		if (diskOpEntry == NULL)
 		{
 			findClose();
@@ -659,8 +659,8 @@
 			return false;
 		}
 
-		memcpy(&diskOpEntry[editor.diskop.numEntries], &tmpBuffer, sizeof (fileEntry_t));
-		editor.diskop.numEntries++;
+		memcpy(&diskOpEntry[diskop.numEntries], &tmpBuffer, sizeof (fileEntry_t));
+		diskop.numEntries++;
 	}
 
 	// read remaining files
@@ -669,7 +669,7 @@
 		lastFindFileFlag = findNext(&tmpBuffer);
 		if (lastFindFileFlag != LFF_DONE && lastFindFileFlag != LFF_SKIP)
 		{
-			newPtr = (fileEntry_t *)realloc(diskOpEntry, sizeof (fileEntry_t) * (editor.diskop.numEntries + 1));
+			newPtr = (fileEntry_t *)realloc(diskOpEntry, sizeof (fileEntry_t) * (diskop.numEntries + 1));
 			if (newPtr == NULL)
 			{
 				findClose();
@@ -679,14 +679,14 @@
 			}
 			diskOpEntry = newPtr;
 
-			memcpy(&diskOpEntry[editor.diskop.numEntries], &tmpBuffer, sizeof (fileEntry_t));
-			editor.diskop.numEntries++;
+			memcpy(&diskOpEntry[diskop.numEntries], &tmpBuffer, sizeof (fileEntry_t));
+			diskop.numEntries++;
 		}
 	}
 
 	findClose();
 
-	if (editor.diskop.numEntries > 0)
+	if (diskop.numEntries > 0)
 	{
 		sortEntries();
 	}
@@ -695,7 +695,7 @@
 		// access denied or out of memory - create parent directory link
 		diskOpEntry = bufferCreateEmptyDir();
 		if (diskOpEntry != NULL)
-			editor.diskop.numEntries = 1;
+			diskop.numEntries = 1;
 		else
 			statusOutOfMemory();
 	}
@@ -707,11 +707,11 @@
 {
 	(void)ptr;
 
-	editor.diskop.isFilling = true;
+	diskop.isFilling = true;
 	diskOpFillBuffer();
-	editor.diskop.isFilling = false;
+	diskop.isFilling = false;
 
-	editor.ui.updateDiskOpFileList = true;
+	ui.updateDiskOpFileList = true;
 	return true;
 }
 
@@ -798,17 +798,17 @@
 
 	diskOpShowSelectText();
 
-	if (editor.diskop.forceStopReading)
+	if (diskop.forceStopReading)
 		return;
 
 	// if needed, update the file list and add entries
-	if (!editor.diskop.cached)
+	if (!diskop.cached)
 	{
-		editor.diskop.fillThread = SDL_CreateThread(diskOpFillThreadFunc, NULL, NULL);
-		if (editor.diskop.fillThread != NULL)
-			SDL_DetachThread(editor.diskop.fillThread);
+		diskop.fillThread = SDL_CreateThread(diskOpFillThreadFunc, NULL, NULL);
+		if (diskop.fillThread != NULL)
+			SDL_DetachThread(diskop.fillThread);
 
-		editor.diskop.cached = true;
+		diskop.cached = true;
 		return;
 	}
 
@@ -822,16 +822,16 @@
 		dstPtr += SCREEN_W;
 	}
 
-	if (editor.diskop.isFilling || diskOpEntry == NULL)
+	if (diskop.isFilling || diskOpEntry == NULL)
 		return;
 
 	// list entries
 	for (i = 0; i < DISKOP_LINES; i++)
 	{
-		if (editor.diskop.scrollOffset+i >= editor.diskop.numEntries)
+		if (diskop.scrollOffset+i >= diskop.numEntries)
 			break;
 
-		entry = &diskOpEntry[editor.diskop.scrollOffset+i];
+		entry = &diskOpEntry[diskop.scrollOffset+i];
 		entryName = diskOpGetAnsiEntry(i);
 		entryLength = (int32_t)strlen(entryName);
 
@@ -876,7 +876,7 @@
 		filePath = diskOpGetUnicodeEntry(fileEntryRow);
 		if (filePath != NULL)
 		{
-			if (editor.diskop.mode == DISKOP_MODE_MOD)
+			if (diskop.mode == DISKOP_MODE_MOD)
 			{
 				if (songModifiedCheck && modEntry->modified)
 				{
@@ -901,7 +901,7 @@
 					statusAllRight();
 
 					if (config.autoCloseDiskOp)
-						editor.ui.diskOpScreenShown = false;
+						ui.diskOpScreenShown = false;
 
 					if (config.rememberPlayMode)
 					{
@@ -943,7 +943,7 @@
 					setErrPointer();
 				}
 			}
-			else if (editor.diskop.mode == DISKOP_MODE_SMP)
+			else if (diskop.mode == DISKOP_MODE_SMP)
 			{
 				loadSample(filePath, diskOpGetAnsiEntry(fileEntryRow));
 			}
--- a/src/pt2_diskop.h
+++ b/src/pt2_diskop.h
@@ -2,8 +2,7 @@
 
 #include <stdint.h>
 #include <stdbool.h>
-#include "pt2_unicode.h"
-
+#include "pt2_header.h"
 enum
 {
 	DISKOP_NO_CACHE = 0,
@@ -15,7 +14,7 @@
 void diskOpShowSelectText(void);
 void diskOpLoadFile(uint32_t fileEntryRow, bool songModifiedCheck);
 void diskOpLoadFile2(void);
-void handleEntryJumping(char jumpToChar);
+void handleEntryJumping(SDL_Keycode jumpToChar);
 bool diskOpEntryIsEmpty(int32_t fileIndex);
 bool diskOpEntryIsDir(int32_t fileIndex);
 char *diskOpGetAnsiEntry(int32_t fileIndex);
--- a/src/pt2_edit.c
+++ b/src/pt2_edit.c
@@ -27,6 +27,7 @@
 #include "pt2_visuals.h"
 #include "pt2_keyboard.h"
 #include "pt2_scopes.h"
+#include "pt2_structs.h"
 
 const int8_t scancode2NoteLo[52] = // "USB usage page standard" order
 {
@@ -63,32 +64,32 @@
 	switch (editObject)
 	{
 		default: break;
-		case PTB_SONGNAME:  editor.ui.updateSongName = true; break;
-		case PTB_SAMPLENAME: editor.ui.updateCurrSampleName = true; break;
-		case PTB_PE_PATT: editor.ui.updatePosEd = true; break;
-		case PTB_EO_QUANTIZE: editor.ui.updateQuantizeText = true; break;
-		case PTB_EO_METRO_1: editor.ui.updateMetro1Text = true; break;
-		case PTB_EO_METRO_2: editor.ui.updateMetro2Text = true; break;
-		case PTB_EO_FROM_NUM: editor.ui.updateFromText = true; break;
-		case PTB_EO_TO_NUM: editor.ui.updateToText = true; break;
-		case PTB_EO_MIX: editor.ui.updateMixText = true; break;
-		case PTB_EO_POS_NUM: editor.ui.updatePosText = true; break;
-		case PTB_EO_MOD_NUM: editor.ui.updateModText = true; break;
-		case PTB_EO_VOL_NUM: editor.ui.updateVolText = true; break;
-		case PTB_DO_DATAPATH: editor.ui.updateDiskOpPathText = true; break;
-		case PTB_POSS: editor.ui.updateSongPos = true; break;
-		case PTB_PATTERNS: editor.ui.updateSongPattern = true; break;
-		case PTB_LENGTHS: editor.ui.updateSongLength = true; break;
-		case PTB_SAMPLES: editor.ui.updateCurrSampleNum = true; break;
-		case PTB_SVOLUMES: editor.ui.updateCurrSampleVolume = true; break;
-		case PTB_SLENGTHS: editor.ui.updateCurrSampleLength = true; break;
-		case PTB_SREPEATS: editor.ui.updateCurrSampleRepeat = true; break;
-		case PTB_SREPLENS: editor.ui.updateCurrSampleReplen = true; break;
-		case PTB_PATTDATA: editor.ui.updateCurrPattText = true; break;
-		case PTB_SA_VOL_FROM_NUM: editor.ui.updateVolFromText = true; break;
-		case PTB_SA_VOL_TO_NUM: editor.ui.updateVolToText = true; break;
-		case PTB_SA_FIL_LP_CUTOFF: editor.ui.updateLPText = true; break;
-		case PTB_SA_FIL_HP_CUTOFF: editor.ui.updateHPText = true; break;
+		case PTB_SONGNAME: ui.updateSongName = true; break;
+		case PTB_SAMPLENAME: ui.updateCurrSampleName = true; break;
+		case PTB_PE_PATT: ui.updatePosEd = true; break;
+		case PTB_EO_QUANTIZE: ui.updateQuantizeText = true; break;
+		case PTB_EO_METRO_1: ui.updateMetro1Text = true; break;
+		case PTB_EO_METRO_2: ui.updateMetro2Text = true; break;
+		case PTB_EO_FROM_NUM: ui.updateFromText = true; break;
+		case PTB_EO_TO_NUM: ui.updateToText = true; break;
+		case PTB_EO_MIX: ui.updateMixText = true; break;
+		case PTB_EO_POS_NUM: ui.updatePosText = true; break;
+		case PTB_EO_MOD_NUM: ui.updateModText = true; break;
+		case PTB_EO_VOL_NUM: ui.updateVolText = true; break;
+		case PTB_DO_DATAPATH: ui.updateDiskOpPathText = true; break;
+		case PTB_POSS: ui.updateSongPos = true; break;
+		case PTB_PATTERNS: ui.updateSongPattern = true; break;
+		case PTB_LENGTHS: ui.updateSongLength = true; break;
+		case PTB_SAMPLES: ui.updateCurrSampleNum = true; break;
+		case PTB_SVOLUMES: ui.updateCurrSampleVolume = true; break;
+		case PTB_SLENGTHS: ui.updateCurrSampleLength = true; break;
+		case PTB_SREPEATS: ui.updateCurrSampleRepeat = true; break;
+		case PTB_SREPLENS: ui.updateCurrSampleReplen = true; break;
+		case PTB_PATTDATA: ui.updateCurrPattText = true; break;
+		case PTB_SA_VOL_FROM_NUM: ui.updateVolFromText = true; break;
+		case PTB_SA_VOL_TO_NUM: ui.updateVolToText = true; break;
+		case PTB_SA_FIL_LP_CUTOFF: ui.updateLPText = true; break;
+		case PTB_SA_FIL_HP_CUTOFF: ui.updateHPText = true; break;
 	}
 }
 
@@ -104,7 +105,7 @@
 	SDL_StopTextInput();
 
 	// if user updated the disk op path text
-	if (editor.ui.diskOpScreenShown && editor.ui.editObject == PTB_DO_DATAPATH)
+	if (ui.diskOpScreenShown && ui.editObject == PTB_DO_DATAPATH)
 	{
 		pathU = (UNICHAR *)calloc(PATH_MAX + 2, sizeof (UNICHAR));
 		if (pathU != NULL)
@@ -119,12 +120,12 @@
 		}
 	}
 
-	if (editor.ui.editTextType != TEXT_EDIT_STRING)
+	if (ui.editTextType != TEXT_EDIT_STRING)
 	{
-		if (editor.ui.dstPos != editor.ui.numLen)
+		if (ui.dstPos != ui.numLen)
 			removeTextEditMarker();
 
-		updateTextObject(editor.ui.editObject);
+		updateTextObject(ui.editObject);
 	}
 	else
 	{
@@ -131,23 +132,23 @@
 		removeTextEditMarker();
 
 		// yet another kludge...
-		if (editor.ui.editObject == PTB_PE_PATT)
-			editor.ui.updatePosEd = true;
+		if (ui.editObject == PTB_PE_PATT)
+			ui.updatePosEd = true;
 	}
 
-	editor.ui.editTextFlag = false;
+	ui.editTextFlag = false;
 
-	editor.ui.lineCurX = 0;
-	editor.ui.lineCurY = 0;
-	editor.ui.editPos = NULL;
-	editor.ui.dstPos = 0;
+	ui.lineCurX = 0;
+	ui.lineCurY = 0;
+	ui.editPos = NULL;
+	ui.dstPos = 0;
 
-	if (editor.ui.editTextType == TEXT_EDIT_STRING)
+	if (ui.editTextType == TEXT_EDIT_STRING)
 	{
-		if (editor.ui.dstOffset != NULL)
-			*editor.ui.dstOffset = '\0';
+		if (ui.dstOffset != NULL)
+			*ui.dstOffset = '\0';
 
-		if (editor.ui.editObject == PTB_SONGNAME)
+		if (ui.editObject == PTB_SONGNAME)
 		{
 			for (i = 0; i < 20; i++)
 				modEntry->head.moduleTitle[i] = (char)tolower(modEntry->head.moduleTitle[i]);
@@ -163,7 +164,7 @@
 		// set back GUI text pointers and update values (if requested)
 
 		s = &modEntry->samples[editor.currSample];
-		switch (editor.ui.editObject)
+		switch (ui.editObject)
 		{
 			case PTB_SA_FIL_LP_CUTOFF:
 			{
@@ -171,11 +172,11 @@
 
 				if (updateValue)
 				{
-					editor.lpCutOff = editor.ui.tmpDisp16;
+					editor.lpCutOff = ui.tmpDisp16;
 					if (editor.lpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 						editor.lpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-					editor.ui.updateLPText = true;
+					ui.updateLPText = true;
 				}
 			}
 			break;
@@ -186,11 +187,11 @@
 
 				if (updateValue)
 				{
-					editor.hpCutOff = editor.ui.tmpDisp16;
+					editor.hpCutOff = ui.tmpDisp16;
 					if (editor.hpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 						editor.hpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-					editor.ui.updateHPText = true;
+					ui.updateHPText = true;
 				}
 			}
 			break;
@@ -201,11 +202,11 @@
 
 				if (updateValue)
 				{
-					editor.vol1 = editor.ui.tmpDisp16;
+					editor.vol1 = ui.tmpDisp16;
 					if (editor.vol1 > 200)
 						editor.vol1 = 200;
 
-					editor.ui.updateVolFromText = true;
+					ui.updateVolFromText = true;
 					showVolFromSlider();
 				}
 			}
@@ -217,11 +218,11 @@
 
 				if (updateValue)
 				{
-					editor.vol2 = editor.ui.tmpDisp16;
+					editor.vol2 = ui.tmpDisp16;
 					if (editor.vol2 > 200)
 						editor.vol2 = 200;
 
-					editor.ui.updateVolToText = true;
+					ui.updateVolToText = true;
 					showVolToSlider();
 				}
 			}
@@ -233,8 +234,8 @@
 
 				if (updateValue)
 				{
-					editor.sampleVol = editor.ui.tmpDisp16;
-					editor.ui.updateVolText = true;
+					editor.sampleVol = ui.tmpDisp16;
+					ui.updateVolText = true;
 				}
 			}
 			break;
@@ -245,11 +246,11 @@
 
 				if (updateValue)
 				{
-					editor.samplePos = editor.ui.tmpDisp16;
+					editor.samplePos = ui.tmpDisp16;
 					if (editor.samplePos > modEntry->samples[editor.currSample].length)
 						editor.samplePos = modEntry->samples[editor.currSample].length;
 
-					editor.ui.updatePosText = true;
+					ui.updatePosText = true;
 				}
 			}
 			break;
@@ -260,11 +261,11 @@
 
 				if (updateValue)
 				{
-					if (editor.ui.tmpDisp16 > 63)
-						editor.ui.tmpDisp16 = 63;
+					if (ui.tmpDisp16 > 63)
+						ui.tmpDisp16 = 63;
 
-					config.quantizeValue = editor.ui.tmpDisp16;
-					editor.ui.updateQuantizeText = true;
+					config.quantizeValue = ui.tmpDisp16;
+					ui.updateQuantizeText = true;
 				}
 			}
 			break;
@@ -275,11 +276,11 @@
 
 				if (updateValue)
 				{
-					if (editor.ui.tmpDisp16 > 64)
-						editor.ui.tmpDisp16 = 64;
+					if (ui.tmpDisp16 > 64)
+						ui.tmpDisp16 = 64;
 
-					editor.metroSpeed = editor.ui.tmpDisp16;
-					editor.ui.updateMetro1Text = true;
+					editor.metroSpeed = ui.tmpDisp16;
+					ui.updateMetro1Text = true;
 				}
 			}
 			break;
@@ -290,11 +291,11 @@
 
 				if (updateValue)
 				{
-					if (editor.ui.tmpDisp16 > 4)
-						editor.ui.tmpDisp16 = 4;
+					if (ui.tmpDisp16 > 4)
+						ui.tmpDisp16 = 4;
 
-					editor.metroChannel = editor.ui.tmpDisp16;
-					editor.ui.updateMetro2Text = true;
+					editor.metroChannel = ui.tmpDisp16;
+					ui.updateMetro2Text = true;
 				}
 			}
 			break;
@@ -305,13 +306,13 @@
 
 				if (updateValue)
 				{
-					editor.sampleFrom = editor.ui.tmpDisp8;
+					editor.sampleFrom = ui.tmpDisp8;
 
 					// signed check + normal check
 					if (editor.sampleFrom < 0x00 || editor.sampleFrom > 0x1F)
 						editor.sampleFrom = 0x1F;
 
-					editor.ui.updateFromText = true;
+					ui.updateFromText = true;
 				}
 			}
 			break;
@@ -322,13 +323,13 @@
 
 				if (updateValue)
 				{
-					editor.sampleTo = editor.ui.tmpDisp8;
+					editor.sampleTo = ui.tmpDisp8;
 
 					// signed check + normal check
 					if (editor.sampleTo < 0x00 || editor.sampleTo > 0x1F)
 						editor.sampleTo = 0x1F;
 
-					editor.ui.updateToText = true;
+					ui.updateToText = true;
 				}
 			}
 			break;
@@ -343,18 +344,18 @@
 
 				if (updateValue)
 				{
-					if (editor.ui.tmpDisp16 > MAX_PATTERNS-1)
-						editor.ui.tmpDisp16 = MAX_PATTERNS-1;
+					if (ui.tmpDisp16 > MAX_PATTERNS-1)
+						ui.tmpDisp16 = MAX_PATTERNS-1;
 
-					modEntry->head.order[posEdPos] = editor.ui.tmpDisp16;
+					modEntry->head.order[posEdPos] = ui.tmpDisp16;
 
 					updateWindowTitle(MOD_IS_MODIFIED);
 
-					if (editor.ui.posEdScreenShown)
-						editor.ui.updatePosEd = true;
+					if (ui.posEdScreenShown)
+						ui.updatePosEd = true;
 
-					editor.ui.updateSongPattern = true;
-					editor.ui.updateSongSize = true;
+					ui.updateSongPattern = true;
+					ui.updateSongSize = true;
 				}
 			}
 			break;
@@ -365,7 +366,7 @@
 
 				if (updateValue)
 				{
-					tmp16 = editor.ui.tmpDisp16;
+					tmp16 = ui.tmpDisp16;
 					if (tmp16 > 126)
 						tmp16 = 126;
 
@@ -374,11 +375,11 @@
 						modEntry->currOrder = tmp16;
 						editor.currPatternDisp = &modEntry->head.order[modEntry->currOrder];
 
-						if (editor.ui.posEdScreenShown)
-							editor.ui.updatePosEd = true;
+						if (ui.posEdScreenShown)
+							ui.updatePosEd = true;
 
-						editor.ui.updateSongPos = true;
-						editor.ui.updatePatternData = true;
+						ui.updateSongPos = true;
+						ui.updatePatternData = true;
 					}
 				}
 			}
@@ -390,7 +391,7 @@
 
 				if (updateValue)
 				{
-					tmp16 = editor.ui.tmpDisp16;
+					tmp16 = ui.tmpDisp16;
 					if (tmp16 > MAX_PATTERNS-1)
 						tmp16 = MAX_PATTERNS-1;
 
@@ -400,11 +401,11 @@
 
 						updateWindowTitle(MOD_IS_MODIFIED);
 
-						if (editor.ui.posEdScreenShown)
-							editor.ui.updatePosEd = true;
+						if (ui.posEdScreenShown)
+							ui.updatePosEd = true;
 
-						editor.ui.updateSongPattern = true;
-						editor.ui.updateSongSize = true;
+						ui.updateSongPattern = true;
+						ui.updateSongSize = true;
 					}
 				}
 			}
@@ -416,7 +417,7 @@
 
 				if (updateValue)
 				{
-					tmp16 = CLAMP(editor.ui.tmpDisp16, 1, 127);
+					tmp16 = CLAMP(ui.tmpDisp16, 1, 127);
 
 					if (modEntry->head.orderCount != tmp16)
 					{
@@ -428,11 +429,11 @@
 
 						editor.currPosEdPattDisp = &modEntry->head.order[posEdPos];
 
-						if (editor.ui.posEdScreenShown)
-							editor.ui.updatePosEd = true;
+						if (ui.posEdScreenShown)
+							ui.updatePosEd = true;
 
-						editor.ui.updateSongLength = true;
-						editor.ui.updateSongSize = true;
+						ui.updateSongLength = true;
+						ui.updateSongSize = true;
 						updateWindowTitle(MOD_IS_MODIFIED);
 					}
 				}
@@ -445,11 +446,11 @@
 
 				if (updateValue)
 				{
-					if (modEntry->currPattern != editor.ui.tmpDisp16)
+					if (modEntry->currPattern != ui.tmpDisp16)
 					{
-						setPattern(editor.ui.tmpDisp16);
-						editor.ui.updatePatternData = true;
-						editor.ui.updateCurrPattText = true;
+						setPattern(ui.tmpDisp16);
+						ui.updatePatternData = true;
+						ui.updateCurrPattText = true;
 					}
 				}
 			}
@@ -461,7 +462,7 @@
 
 				if (updateValue)
 				{
-					tmp8 = editor.ui.tmpDisp8;
+					tmp8 = ui.tmpDisp8;
 					if (tmp8 < 0x00) // (signed) if >0x7F was entered, clamp to 0x1F
 						tmp8 = 0x1F;
 
@@ -482,7 +483,7 @@
 
 				if (updateValue)
 				{
-					tmp8 = editor.ui.tmpDisp8;
+					tmp8 = ui.tmpDisp8;
 
 					// signed check + normal check
 					if (tmp8 < 0x00 || tmp8 > 0x40)
@@ -491,7 +492,7 @@
 					if (s->volume != tmp8)
 					{
 						s->volume = tmp8;
-						editor.ui.updateCurrSampleVolume = true;
+						ui.updateCurrSampleVolume = true;
 						updateWindowTitle(MOD_IS_MODIFIED);
 					}
 				}
@@ -504,7 +505,7 @@
 
 				if (updateValue)
 				{
-					tmp32 = editor.ui.tmpDisp16 & 0xFFFE; // even'ify
+					tmp32 = ui.tmpDisp16 & 0xFFFE; // even'ify
 
 					if (s->loopStart+s->loopLength > 2)
 					{
@@ -517,13 +518,13 @@
 					if (s->length != tmp32)
 					{
 						turnOffVoices();
-						s->length = tmp32;
+						s->length = (uint16_t)tmp32;
 
-						editor.ui.updateCurrSampleLength = true;
-						editor.ui.updateSongSize = true;
+						ui.updateCurrSampleLength = true;
+						ui.updateSongSize = true;
 						updateSamplePos();
 
-						if (editor.ui.samplerScreenShown)
+						if (ui.samplerScreenShown)
 							redrawSample();
 
 						recalcChordLength();
@@ -539,7 +540,7 @@
 
 				if (updateValue)
 				{
-					tmp32 = editor.ui.tmpDisp16 & 0xFFFE; // even'ify
+					tmp32 = ui.tmpDisp16 & 0xFFFE; // even'ify
 
 					if (s->length >= s->loopLength)
 					{
@@ -556,15 +557,15 @@
 					if (s->loopStart != tmp32)
 					{
 						turnOffVoices();
-						s->loopStart = tmp32;
+						s->loopStart = (uint16_t)tmp32;
 						mixerUpdateLoops();
 
-						editor.ui.updateCurrSampleRepeat = true;
+						ui.updateCurrSampleRepeat = true;
 
-						if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3)
-							editor.ui.updateLengthText = true;
+						if (ui.editOpScreenShown && ui.editOpScreen == 3)
+							ui.updateLengthText = true;
 
-						if (editor.ui.samplerScreenShown)
+						if (ui.samplerScreenShown)
 							setLoopSprites();
 
 						updateWindowTitle(MOD_IS_MODIFIED);
@@ -579,7 +580,7 @@
 
 				if (updateValue)
 				{
-					tmp32 = editor.ui.tmpDisp16 & 0xFFFE; // even'ify
+					tmp32 = ui.tmpDisp16 & 0xFFFE; // even'ify
 
 					if (s->length >= s->loopStart)
 					{
@@ -599,14 +600,14 @@
 					if (s->loopLength != tmp32)
 					{
 						turnOffVoices();
-						s->loopLength = tmp32;
+						s->loopLength = (uint16_t)tmp32;
 						mixerUpdateLoops();
 
-						editor.ui.updateCurrSampleReplen = true;
-						if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3)
-							editor.ui.updateLengthText = true;
+						ui.updateCurrSampleReplen = true;
+						if (ui.editOpScreenShown && ui.editOpScreen == 3)
+							ui.updateLengthText = true;
 
-						if (editor.ui.samplerScreenShown)
+						if (ui.samplerScreenShown)
 							setLoopSprites();
 
 						updateWindowTitle(MOD_IS_MODIFIED);
@@ -621,7 +622,7 @@
 		pointerSetPreviousMode();
 	}
 
-	editor.ui.editTextType = 0;
+	ui.editTextType = 0;
 }
 
 void getTextLine(int16_t editObject)
@@ -628,17 +629,17 @@
 {
 	pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 
-	editor.ui.lineCurY = (editor.ui.editTextPos / 40) + 5;
-	editor.ui.lineCurX = ((editor.ui.editTextPos % 40) * FONT_CHAR_W) + 4;
-	editor.ui.dstPtr = editor.ui.showTextPtr;
-	editor.ui.editPos = editor.ui.showTextPtr;
-	editor.ui.dstPos = 0;
-	editor.ui.editTextFlag = true;
-	editor.ui.editTextType = TEXT_EDIT_STRING;
-	editor.ui.editObject = editObject;
+	ui.lineCurY = (ui.editTextPos / 40) + 5;
+	ui.lineCurX = ((ui.editTextPos % 40) * FONT_CHAR_W) + 4;
+	ui.dstPtr = ui.showTextPtr;
+	ui.editPos = ui.showTextPtr;
+	ui.dstPos = 0;
+	ui.editTextFlag = true;
+	ui.editTextType = TEXT_EDIT_STRING;
+	ui.editObject = editObject;
 
-	if (editor.ui.dstOffset != NULL)
-	   *editor.ui.dstOffset  = '\0';
+	if (ui.dstOffset != NULL)
+	   *ui.dstOffset  = '\0';
 
 	// kludge
 	if (editor.mixFlag)
@@ -657,12 +658,12 @@
 {
 	pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 
-	editor.ui.lineCurY = (editor.ui.editTextPos / 40) + 5;
-	editor.ui.lineCurX = ((editor.ui.editTextPos % 40) * FONT_CHAR_W) + 4;
-	editor.ui.dstPos = 0;
-	editor.ui.editTextFlag = true;
-	editor.ui.editTextType = type;
-	editor.ui.editObject = editObject;
+	ui.lineCurY = (ui.editTextPos / 40) + 5;
+	ui.lineCurX = ((ui.editTextPos % 40) * FONT_CHAR_W) + 4;
+	ui.dstPos = 0;
+	ui.editTextFlag = true;
+	ui.editTextType = type;
+	ui.editObject = editObject;
 
 	renderTextEditMarker();
 	SDL_StartTextInput();
@@ -673,10 +674,10 @@
 	int8_t key, hexKey, numberKey;
 	note_t *note;
 
-	if (editor.ui.editTextFlag)
+	if (ui.editTextFlag)
 		return;
 
-	if (editor.ui.samplerScreenShown || (editor.currMode == MODE_IDLE || editor.currMode == MODE_PLAY))
+	if (ui.samplerScreenShown || (editor.currMode == MODE_IDLE || editor.currMode == MODE_PLAY))
 	{
 		// at this point it will only jam, not place it
 		if (!keyb.leftAltPressed && !keyb.leftAmigaPressed && !keyb.leftCtrlPressed && !keyb.shiftPressed)
@@ -698,7 +699,7 @@
 	}
 
 	// are we editing a note, or other stuff?
-	if (editor.cursor.mode != CURSOR_NOTE)
+	if (cursor.mode != CURSOR_NOTE)
 	{
 		// if we held down any key modifier at this point, then do nothing
 		if (keyb.leftAltPressed || keyb.leftAmigaPressed || keyb.leftCtrlPressed || keyb.shiftPressed)
@@ -735,9 +736,9 @@
 				key += hexKey;
 			}
 
-			note = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+			note = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 
-			switch (editor.cursor.mode)
+			switch (cursor.mode)
 			{
 				case CURSOR_SAMPLE1:
 				{
@@ -819,7 +820,7 @@
 		{
 			if (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD)
 			{
-				note = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				note = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 
 				if (!keyb.leftAltPressed)
 				{
@@ -858,8 +859,8 @@
 		return false;
 
 	patt = modEntry->patterns[modEntry->currPattern];
-	note = &patt[(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
-	prevNote = &patt[(((modEntry->currRow - 1) & 0x3F) * AMIGA_VOICES) + editor.cursor.channel];
+	note = &patt[(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
+	prevNote = &patt[(((modEntry->currRow - 1) & 0x3F) * AMIGA_VOICES) + cursor.channel];
 
 	if (scancode >= SDL_SCANCODE_1 && scancode <= SDL_SCANCODE_0)
 	{
@@ -914,7 +915,7 @@
 	moduleSample_t *s;
 	note_t *note;
 
-	ch = editor.cursor.channel;
+	ch = cursor.channel;
 	assert(ch < AMIGA_VOICES);
 
 	chn = &modEntry->channels[ch];
@@ -939,9 +940,9 @@
 			chn->n_volume = s->volume;
 			chn->n_period = tempPeriod;
 			chn->n_start = &modEntry->sampleData[s->offset];
-			chn->n_length = (s->loopStart > 0) ? (uint32_t)(s->loopStart + s->loopLength) / 2 : s->length / 2;
+			chn->n_length = (s->loopStart > 0) ? (s->loopStart + s->loopLength) >> 1 : s->length >> 1;
 			chn->n_loopstart = &modEntry->sampleData[s->offset + s->loopStart];
-			chn->n_replen = s->loopLength / 2;
+			chn->n_replen = s->loopLength >> 1;
 
 			if (chn->n_length == 0)
 				chn->n_length = 1;
@@ -967,7 +968,7 @@
 			if (normalMode || editor.pNoteFlag == 2)
 			{
 				// insert note and sample number
-				if (!editor.ui.samplerScreenShown && (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD))
+				if (!ui.samplerScreenShown && (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD))
 				{
 					note->sample = editor.sampleZero ? 0 : (editor.currSample + 1);
 					note->period = cleanPeriod;
@@ -997,7 +998,7 @@
 
 		if (normalMode || editor.pNoteFlag == 2)
 		{
-			if (!editor.ui.samplerScreenShown && (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD))
+			if (!ui.samplerScreenShown && (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD))
 			{
 				note->period = 0;
 				note->sample = 0;
@@ -1062,7 +1063,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void copySampleTrack(void)
@@ -1103,7 +1104,7 @@
 		memcpy(&modEntry->sampleData[smpTo->offset], &modEntry->sampleData[smpFrom->offset], MAX_SAMPLE_LEN);
 
 		updateCurrSample();
-		editor.ui.updateSongSize = true;
+		ui.updateSongSize = true;
 	}
 	else
 	{
@@ -1112,7 +1113,7 @@
 		{
 			for (i = 0; i < MOD_ROWS; i++)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 				if (noteSrc->sample == editor.sampleFrom)
 					noteSrc->sample = editor.sampleTo;
 			}
@@ -1130,7 +1131,7 @@
 			}
 		}
 
-		editor.ui.updatePatternData = true;
+		ui.updatePatternData = true;
 	}
 
 	editor.samplePos = 0;
@@ -1201,7 +1202,7 @@
 		{
 			for (i = 0; i < MOD_ROWS; i++)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 				     if (noteSrc->sample == editor.sampleFrom) noteSrc->sample = editor.sampleTo;
 				else if (noteSrc->sample == editor.sampleTo) noteSrc->sample = editor.sampleFrom;
@@ -1221,7 +1222,7 @@
 			}
 		}
 
-		editor.ui.updatePatternData = true;
+		ui.updatePatternData = true;
 	}
 
 	editor.samplePos = 0;
@@ -1240,7 +1241,7 @@
 	{
 		for (i = 0; i < MOD_ROWS; i++)
 		{
-			noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+			noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 			if (noteSrc->sample == editor.currSample+1)
 			{
 				noteSrc->period = 0;
@@ -1269,7 +1270,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void trackNoteUp(bool sampleAllFlag, uint8_t from, uint8_t to)
@@ -1288,7 +1289,7 @@
 	saveUndo();
 	for (uint8_t i = from; i <= to; i++)
 	{
-		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 		if (!sampleAllFlag && noteSrc->sample != editor.currSample+1)
 			continue;
@@ -1322,7 +1323,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void trackNoteDown(bool sampleAllFlag, uint8_t from, uint8_t to)
@@ -1341,7 +1342,7 @@
 	saveUndo();
 	for (uint8_t i = from; i <= to; i++)
 	{
-		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 		if (!sampleAllFlag && noteSrc->sample != editor.currSample+1)
 			continue;
@@ -1375,7 +1376,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void trackOctaUp(bool sampleAllFlag, uint8_t from, uint8_t to)
@@ -1396,7 +1397,7 @@
 	saveUndo();
 	for (uint8_t i = from; i <= to; i++)
 	{
-		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 		if (!sampleAllFlag && noteSrc->sample != editor.currSample+1)
 			continue;
@@ -1435,7 +1436,7 @@
 	if (noteChanged)
 	{
 		updateWindowTitle(MOD_IS_MODIFIED);
-		editor.ui.updatePatternData = true;
+		ui.updatePatternData = true;
 	}
 }
 
@@ -1455,7 +1456,7 @@
 	saveUndo();
 	for (uint8_t i = from; i <= to; i++)
 	{
-		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+		noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 		if (!sampleAllFlag && noteSrc->sample != editor.currSample+1)
 			continue;
@@ -1487,7 +1488,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void pattNoteUp(bool sampleAllFlag)
@@ -1536,7 +1537,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void pattNoteDown(bool sampleAllFlag)
@@ -1585,7 +1586,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void pattOctaUp(bool sampleAllFlag)
@@ -1632,7 +1633,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 void pattOctaDown(bool sampleAllFlag)
@@ -1679,7 +1680,7 @@
 	}
 
 	updateWindowTitle(MOD_IS_MODIFIED);
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 }
 
 int8_t keyToNote(SDL_Scancode scancode)
--- a/src/pt2_header.h
+++ b/src/pt2_header.h
@@ -14,7 +14,7 @@
 #include "pt2_unicode.h"
 #include "pt2_palette.h"
 
-#define PROG_VER_STR "1.11"
+#define PROG_VER_STR "1.12"
 
 #ifdef _WIN32
 #define DIR_DELIMITER '\\'
@@ -25,13 +25,6 @@
 
 #include "pt2_config.h" // this must be included after PATH_MAX definition
 
-#ifdef _MSC_VER
-#pragma warning(disable:4244) // disable 'conversion from' warings
-#pragma warning(disable:4820) // disable struct padding warnings
-#pragma warning(disable:4996) // disable deprecated POSIX warnings
-#pragma warning(disable:4127) // disable while (true) warnings
-#endif
-
 #ifndef _WIN32
 #define _stricmp strcasecmp
 #define _strnicmp strncasecmp
@@ -217,253 +210,6 @@
 	TEXT_EDIT_HEX = 2
 };
 
-typedef struct wavHeader_t
-{
-	uint32_t chunkID, chunkSize, format, subchunk1ID, subchunk1Size;
-	uint16_t audioFormat, numChannels;
-	uint32_t sampleRate, byteRate;
-	uint16_t blockAlign, bitsPerSample;
-	uint32_t subchunk2ID, subchunk2Size;
-} wavHeader_t;
-
-typedef struct sampleLoop_t
-{
-	uint32_t dwIdentifier, dwType, dwStart;
-	uint32_t dwEnd, dwFraction, dwPlayCount;
-} sampleLoop_t;
-
-typedef struct samplerChunk_t
-{
-	uint32_t chunkID, chunkSize, dwManufacturer, dwProduct;
-	uint32_t dwSamplePeriod, dwMIDIUnityNote, wMIDIPitchFraction;
-	uint32_t dwSMPTEFormat, dwSMPTEOffset, cSampleLoops, cbSamplerData;
-	sampleLoop_t loop;
-} samplerChunk_t;
-
-typedef struct note_t
-{
-	uint8_t param, sample, command;
-	uint16_t period;
-} note_t;
-
-typedef struct moduleHeader_t
-{
-	char moduleTitle[20 + 1];
-	uint16_t order[MOD_ORDERS], orderCount;
-	uint16_t initialTempo; // used for STK/UST modules after module is loaded
-} moduleHeader_t;
-
-typedef struct moduleSample_t
-{
-	volatile int8_t *volumeDisp;
-	volatile uint16_t *lengthDisp, *loopStartDisp, *loopLengthDisp;
-	char text[22 + 1];
-	int8_t volume;
-	uint8_t fineTune;
-	uint16_t length, loopStart, loopLength;
-	int32_t offset;
-} moduleSample_t;
-
-typedef struct moduleChannel_t
-{
-	int8_t *n_start, *n_wavestart, *n_loopstart, n_chanindex, n_volume;
-	int8_t n_toneportdirec, n_vibratopos, n_tremolopos, n_pattpos, n_loopcount;
-	uint8_t n_wavecontrol, n_glissfunk, n_sampleoffset, n_toneportspeed;
-	uint8_t n_vibratocmd, n_tremolocmd, n_finetune, n_funkoffset, n_samplenum;
-	int16_t n_period, n_note, n_wantedperiod;
-	uint16_t n_cmd;
-	uint32_t n_scopedelta, n_length, n_replen;
-} moduleChannel_t;
-
-typedef struct module_t
-{
-	int8_t *sampleData, currRow, modified, row;
-	uint8_t currSpeed, moduleLoaded;
-	uint16_t currOrder, currPattern, currBPM;
-	uint32_t rowsCounter, rowsInTotal;
-	moduleHeader_t head;
-	moduleSample_t samples[MOD_SAMPLES];
-	moduleChannel_t channels[AMIGA_VOICES];
-	note_t *patterns[MAX_PATTERNS];
-} module_t;
-
-struct audio_t
-{
-	volatile bool locked;
-	bool forceMixerOff;
-	uint16_t bpmTab[256-32], bpmTab28kHz[256-32], bpmTab22kHz[256-32], bpmTabMod2Wav[256-32];
-	uint32_t outputRate, audioBufferSize;
-	double dPeriodToDeltaDiv;
-} audio;
-
-struct keyb_t
-{
-	bool repeatKey, delayKey;
-	bool shiftPressed, leftCtrlPressed, leftAltPressed;
-	bool leftCommandPressed, leftAmigaPressed, keypadEnterPressed;
-	uint8_t repeatCounter, delayCounter;
-	uint64_t repeatFrac;
-	SDL_Scancode lastRepKey, lastKey;
-} keyb;
-
-struct mouse_t
-{
-	volatile bool setPosFlag;
-	bool buttonWaiting, leftButtonPressed, rightButtonPressed;
-	uint8_t repeatCounter, buttonWaitCounter;
-	int32_t x, y, lastMouseX, setPosX, setPosY, lastGUIButton, lastSmpFilterButton, prevX, prevY;
-	uint32_t buttonState;
-} mouse;
-
-struct video_t
-{
-	bool fullscreen, vsync60HzPresent, windowHidden;
-	int32_t renderX, renderY, renderW, renderH, displayW, displayH;
-	int32_t xScale, yScale;
-	double dMouseXMul, dMouseYMul;
-	SDL_PixelFormat *pixelFormat;
-	uint32_t *frameBuffer, *frameBufferUnaligned;
-
-	SDL_Window *window;
-	SDL_Renderer *renderer;
-	SDL_Texture  *texture;
-
-	uint32_t palette[PALETTE_NUM];
-
-#ifdef _WIN32
-	HWND hWnd;
-#endif
-} video;
-
-// this is massive...
-struct editor_t
-{
-	volatile int8_t vuMeterVolumes[AMIGA_VOICES], spectrumVolumes[SPECTRUM_BAR_NUM];
-	volatile int8_t *sampleFromDisp, *sampleToDisp, *currSampleDisp, realVuMeterVolumes[AMIGA_VOICES];
-	volatile bool songPlaying, programRunning, isWAVRendering, isSMPRendering, smpRenderingDone;
-	volatile uint8_t modTick, modSpeed;
-	volatile uint16_t *quantizeValueDisp, *metroSpeedDisp, *metroChannelDisp, *sampleVolDisp;
-	volatile uint16_t *vol1Disp, *vol2Disp, *currEditPatternDisp, *currPosDisp, *currPatternDisp;
-	volatile uint16_t *currPosEdPattDisp, *currLengthDisp, *lpCutOffDisp, *hpCutOffDisp;
-	volatile uint16_t *samplePosDisp, *chordLengthDisp;
-
-	char mixText[16];
-	char *entryNameTmp, *currPath, *dropTempFileName;
-	UNICHAR *fileNameTmpU, *currPathU, *modulesPathU, *samplesPathU;
-
-	bool errorMsgActive, errorMsgBlock, multiFlag, metroFlag, keypadToggle8CFlag, normalizeFiltersFlag;
-	bool sampleAllFlag, halfClipFlag, newOldFlag, pat2SmpHQ, mixFlag, useLEDFilter;
-	bool modLoaded, autoInsFlag, repeatKeyFlag, sampleZero, tuningFlag;
-	bool stepPlayEnabled, stepPlayBackwards, blockBufferFlag, blockMarkFlag, didQuantize;
-	bool swapChannelFlag, configFound, abortMod2Wav, chordLengthMin, rowVisitTable[MOD_ORDERS * MOD_ROWS];
-	bool muted[AMIGA_VOICES];
-
-	int8_t smpRedoFinetunes[MOD_SAMPLES], smpRedoVolumes[MOD_SAMPLES], multiModeNext[4], trackPattFlag;
-	int8_t *smpRedoBuffer[MOD_SAMPLES], *tempSample, currSample, recordMode, sampleFrom, sampleTo, autoInsSlot;
-	int8_t keypadSampleOffset, note1, note2, note3, note4, oldNote1, oldNote2, oldNote3, oldNote4;
-	uint8_t playMode, currMode, tuningChan, tuningVol, errorMsgCounter, buffFromPos, buffToPos;
-	uint8_t blockFromPos, blockToPos, timingMode, f6Pos, f7Pos, f8Pos, f9Pos, f10Pos, keyOctave, pNoteFlag;
-	uint8_t tuningNote, resampleNote, initialTempo, initialSpeed, editMoveAdd;
-
-	int16_t *pat2SmpBuf, modulateSpeed;
-	uint16_t metroSpeed, metroChannel, sampleVol, samplePos, chordLength;
-	uint16_t effectMacros[10], oldTempo, currPlayNote, vol1, vol2, lpCutOff, hpCutOff;
-	int32_t smpRedoLoopStarts[MOD_SAMPLES], smpRedoLoopLengths[MOD_SAMPLES], smpRedoLengths[MOD_SAMPLES];
-	int32_t modulatePos, modulateOffset, markStartOfs, markEndOfs;
-	uint32_t musicTime, vblankTimeLen, vblankTimeLenFrac, pat2SmpPos;
-	double dPerfFreq, dPerfFreqMulMicro;
-	note_t trackBuffer[MOD_ROWS], cmdsBuffer[MOD_ROWS], blockBuffer[MOD_ROWS];
-	note_t patternBuffer[MOD_ROWS * AMIGA_VOICES], undoBuffer[MOD_ROWS * AMIGA_VOICES];
-	SDL_Thread *mod2WavThread, *pat2SmpThread;
-
-	struct diskop_t
-	{
-		volatile bool cached, isFilling, forceStopReading;
-		bool modPackFlg;
-		int8_t mode, smpSaveType;
-		int32_t numEntries, scrollOffset;
-		SDL_Thread *fillThread;
-	} diskop;
-
-	struct cursor_t
-	{
-		uint8_t lastPos, pos, mode, channel;
-		uint32_t bgBuffer[11 * 14];
-	} cursor;
-
-	struct text_offsets_t
-	{
-		uint16_t diskOpPath;
-	} textofs;
-
-	struct ui_t
-	{
-		char statusMessage[18], prevStatusMessage[18];
-		char *dstPtr, *editPos, *textEndPtr, *showTextPtr;
-
-		bool answerNo, answerYes, throwExit, editTextFlag, askScreenShown, samplerScreenShown;
-		bool leftLoopPinMoving, rightLoopPinMoving, changingSmpResample, changingDrumPadNote;
-		bool forceSampleDrag, forceSampleEdit, introScreenShown;
-		bool aboutScreenShown, clearScreenShown, posEdScreenShown, diskOpScreenShown;
-		bool samplerVolBoxShown, samplerFiltersBoxShown, editOpScreenShown;
-
-		int8_t *numPtr8, tmpDisp8, pointerMode, editOpScreen, editTextType, askScreenType;
-		int8_t visualizerMode, previousPointerMode, forceVolDrag, changingChordNote;
-		uint8_t numLen, numBits;
-
-		// render/update flags
-		bool updateStatusText, updatePatternData;
-		bool updateSongName, updateMod2WavDialog, mod2WavFinished;
-
-		// edit op. #2
-		bool updateRecordText, updateQuantizeText, updateMetro1Text, updateMetro2Text;
-		bool updateFromText, updateKeysText, updateToText;
-
-		// edit op. #3
-		bool updateMixText, updatePosText, updateModText, updateVolText;
-
-		// edit op. #4 (sample chord editor)
-		bool updateLengthText, updateNote1Text, updateNote2Text;
-		bool updateNote3Text, updateNote4Text;
-
-		//sampler
-		bool updateResampleNote, updateVolFromText, updateVolToText, updateLPText;
-		bool updateHPText, updateNormFlag, update9xxPos;
-
-		// general
-		bool updateSongPos, updateSongPattern, updateSongLength, updateCurrSampleFineTune;
-		bool updateCurrSampleNum, updateCurrSampleVolume, updateCurrSampleLength;
-		bool updateCurrSampleRepeat, updateCurrSampleReplen, updateCurrSampleName;
-		bool updateSongSize, updateSongTiming, updateSongBPM;
-		bool updateCurrPattText, updateTrackerFlags, pat2SmpDialogShown;
-
-		// disk op.
-		bool updateLoadMode, updatePackText, updateSaveFormatText, updateDiskOpPathText;
-
-		// pos ed.
-		bool updatePosEd, updateDiskOpFileList;
-
-		// these are used when things are drawn on top, for example clear/ask dialogs
-		bool disablePosEd, disableVisualizer;
-
-		int16_t lineCurX, lineCurY, editObject, sampleMarkingPos;
-		uint16_t *numPtr16, tmpDisp16, *dstOffset, dstPos, textLength, editTextPos;
-		uint16_t dstOffsetEnd, lastSampleOffset;
-		int32_t askTempData;
-	} ui;
-
-	struct sampler_t
-	{
-		const int8_t *samStart;
-		int8_t *blankSample, *copyBuf;
-		int16_t loopStartPos, loopEndPos;
-		uint16_t dragStart, dragEnd;
-		int32_t samPointWidth, samOffset, samDisplay, samLength, saveMouseX, lastSamPos;
-		int32_t lastMouseX, lastMouseY, tmpLoopStart, tmpLoopLength;
-		uint32_t copyBufSize, samDrawStart, samDrawEnd;
-	} sampler;
-} editor;
-
 void restartSong(void);
 void resetSong(void);
 void incPatt(void);
@@ -482,5 +228,3 @@
 void clearSamples(void);
 void clearAll(void);
 void modSetPattern(uint8_t pattern);
-
-extern module_t *modEntry; // pt_main.c
--- a/src/pt2_helpers.c
+++ b/src/pt2_helpers.c
@@ -19,6 +19,7 @@
 #include "pt2_header.h"
 #include "pt2_tables.h"
 #include "pt2_palette.h"
+#include "pt2_structs.h"
 
 // used for Windows usleep() implementation
 #ifdef _WIN32
@@ -198,6 +199,6 @@
 		}
 	}
 
-	if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3)
-		editor.ui.updateLengthText = true;
+	if (ui.editOpScreenShown && ui.editOpScreen == 3)
+		ui.updateLengthText = true;
 }
--- a/src/pt2_helpers.h
+++ b/src/pt2_helpers.h
@@ -33,7 +33,6 @@
 #define MIN(a, b) (((a) < (b)) ? (a) : (b))
 #define MAX(a, b) (((a) > (b)) ? (a) : (b))
 #define CLAMP(x, low, high) (((x) > (high)) ? (high) : (((x) < (low)) ? (low) : (x)))
-#define LERP(x, y, z) ((x) + ((y) - (x)) * (z))
 
 #define R12(x) (((x) >> 8) & 0xF)
 #define G12(x) (((x) >> 4) & 0xF)
--- a/src/pt2_keyboard.c
+++ b/src/pt2_keyboard.c
@@ -27,7 +27,7 @@
 #include "pt2_mouse.h"
 #include "pt2_unicode.h"
 
-#ifdef _WIN32
+#if defined _WIN32 && !defined _DEBUG
 extern bool windowsKeyIsDown;
 extern HHOOK g_hKeyboardHook;
 #endif
@@ -45,8 +45,8 @@
 
 void gotoNextMulti(void)
 {
-	editor.cursor.channel = (editor.multiModeNext[editor.cursor.channel] - 1) & 3;
-	editor.cursor.pos = editor.cursor.channel * 6;
+	cursor.channel = (editor.multiModeNext[cursor.channel] - 1) & 3;
+	cursor.pos = cursor.channel * 6;
 	updateCursorPos();
 }
 
@@ -59,16 +59,21 @@
 	keyb.leftCtrlPressed = (modState & KMOD_LCTRL)  ? true : false;
 	keyb.leftAltPressed = (modState & KMOD_LALT) ? true : false;
 	keyb.shiftPressed = (modState & (KMOD_LSHIFT + KMOD_RSHIFT)) ? true : false;
+
 #ifdef __APPLE__
 	keyb.leftCommandPressed = (modState & KMOD_LGUI) ? true : false;
 #endif
-#ifndef _WIN32 // MS Windows: handled in lowLevelKeyboardProc
+
+#if defined _WIN32 && !defined _DEBUG // Windows: handled in lowLevelKeyboardProc
 	keyb.leftAmigaPressed = (modState & KMOD_LGUI) ? true : false;
 #endif
 }
 
-#ifdef _WIN32
-// for taking control over windows key and numlock on keyboard if app has focus
+#if defined _WIN32 && !defined _DEBUG
+/* For taking control over windows key and numlock on keyboard if app has focus.
+** Warning: Don't do this in debug mode, it will completely ruin the keyboard input
+** latency when the debugger is breaking.
+*/
 LRESULT CALLBACK lowLevelKeyboardProc(int32_t nCode, WPARAM wParam, LPARAM lParam)
 {
 	bool bEatKeystroke;
@@ -159,20 +164,20 @@
 // these four functions are for the text edit cursor
 void textMarkerMoveLeft(void)
 {
-	if (editor.ui.dstPos > 0)
+	if (ui.dstPos > 0)
 	{
 		removeTextEditMarker();
-		editor.ui.dstPos--;
-		editor.ui.lineCurX -= FONT_CHAR_W;
+		ui.dstPos--;
+		ui.lineCurX -= FONT_CHAR_W;
 		renderTextEditMarker();
 	}
 	else
 	{
-		if (editor.ui.dstOffset != NULL)
+		if (ui.dstOffset != NULL)
 		{
-			(*editor.ui.dstOffset)--;
-			if (editor.ui.editObject == PTB_DO_DATAPATH)
-				editor.ui.updateDiskOpPathText = true;
+			(*ui.dstOffset)--;
+			if (ui.editObject == PTB_DO_DATAPATH)
+				ui.updateDiskOpPathText = true;
 		}
 	}
 }
@@ -179,22 +184,22 @@
 
 void textMarkerMoveRight(void)
 {
-	if (editor.ui.editTextType == TEXT_EDIT_STRING)
+	if (ui.editTextType == TEXT_EDIT_STRING)
 	{
-		if (editor.ui.dstPos < editor.ui.textLength-1)
+		if (ui.dstPos < ui.textLength-1)
 		{
 			removeTextEditMarker();
-			editor.ui.dstPos++;
-			editor.ui.lineCurX += FONT_CHAR_W;
+			ui.dstPos++;
+			ui.lineCurX += FONT_CHAR_W;
 			renderTextEditMarker();
 		}
 		else
 		{
-			if (editor.ui.dstOffset != NULL)
+			if (ui.dstOffset != NULL)
 			{
-				(*editor.ui.dstOffset)++;
-				if (editor.ui.editObject == PTB_DO_DATAPATH)
-					editor.ui.updateDiskOpPathText = true;
+				(*ui.dstOffset)++;
+				if (ui.editObject == PTB_DO_DATAPATH)
+					ui.updateDiskOpPathText = true;
 			}
 		}
 	}
@@ -202,13 +207,13 @@
 	{
 		// we end up here when entering a number/hex digit
 
-		if (editor.ui.dstPos < editor.ui.numLen)
+		if (ui.dstPos < ui.numLen)
 			removeTextEditMarker();
 
-		editor.ui.dstPos++;
-		editor.ui.lineCurX += FONT_CHAR_W;
+		ui.dstPos++;
+		ui.lineCurX += FONT_CHAR_W;
 
-		if (editor.ui.dstPos < editor.ui.numLen)
+		if (ui.dstPos < ui.numLen)
 			renderTextEditMarker();
 
 		// don't clamp, dstPos is tested elsewhere to check if done editing a number
@@ -217,13 +222,13 @@
 
 void textCharPrevious(void)
 {
-	if (editor.ui.editTextType != TEXT_EDIT_STRING)
+	if (ui.editTextType != TEXT_EDIT_STRING)
 	{
-		if (editor.ui.dstPos > 0)
+		if (ui.dstPos > 0)
 		{
 			removeTextEditMarker();
-			editor.ui.dstPos--;
-			editor.ui.lineCurX -= FONT_CHAR_W;
+			ui.dstPos--;
+			ui.lineCurX -= FONT_CHAR_W;
 			renderTextEditMarker();
 		}
 
@@ -230,29 +235,28 @@
 		return;
 	}
 
-	if (editor.mixFlag && editor.ui.dstPos <= 4)
+	if (editor.mixFlag && ui.dstPos <= 4)
 		return;
 
-	if (editor.ui.editPos > editor.ui.showTextPtr)
+	if (ui.editPos > ui.showTextPtr)
 	{
 		removeTextEditMarker();
 
-		editor.ui.editPos--;
+		ui.editPos--;
 		textMarkerMoveLeft();
 
-		if (editor.mixFlag) // special mode for mix window
+		if (editor.mixFlag) // special case for "Mix" input field in Edit. Op.
 		{
-			if (editor.ui.dstPos == 12)
+			if (ui.dstPos == 12)
 			{
-				for (uint8_t i = 0; i < 4; i++)
-				{
-					editor.ui.editPos--;
-					textMarkerMoveLeft();
-				}
+				ui.editPos--; textMarkerMoveLeft();
+				ui.editPos--; textMarkerMoveLeft();
+				ui.editPos--; textMarkerMoveLeft();
+				ui.editPos--; textMarkerMoveLeft();
 			}
-			else if (editor.ui.dstPos == 6)
+			else if (ui.dstPos == 6)
 			{
-				editor.ui.editPos--;
+				ui.editPos--;
 				textMarkerMoveLeft();
 			}
 		}
@@ -260,18 +264,18 @@
 		renderTextEditMarker();
 	}
 
-	editor.ui.dstOffsetEnd = false;
+	ui.dstOffsetEnd = false;
 }
 
 void textCharNext(void)
 {
-	if (editor.ui.editTextType != TEXT_EDIT_STRING)
+	if (ui.editTextType != TEXT_EDIT_STRING)
 	{
-		if (editor.ui.dstPos < editor.ui.numLen-1)
+		if (ui.dstPos < ui.numLen-1)
 		{
 			removeTextEditMarker();
-			editor.ui.dstPos++;
-			editor.ui.lineCurX += FONT_CHAR_W;
+			ui.dstPos++;
+			ui.lineCurX += FONT_CHAR_W;
 			renderTextEditMarker();
 		}
 
@@ -278,31 +282,30 @@
 		return;
 	}
 
-	if (editor.mixFlag && editor.ui.dstPos >= 14)
+	if (editor.mixFlag && ui.dstPos >= 14)
 		return;
 
-	if (editor.ui.editPos < editor.ui.textEndPtr)
+	if (ui.editPos < ui.textEndPtr)
 	{
-		if (*editor.ui.editPos != '\0')
+		if (*ui.editPos != '\0')
 		{
 			removeTextEditMarker();
 
-			editor.ui.editPos++;
+			ui.editPos++;
 			textMarkerMoveRight();
 
-			if (editor.mixFlag) // special mode for mix window
+			if (editor.mixFlag) // special case for "Mix" input field in Edit. Op.
 			{
-				if (editor.ui.dstPos == 9)
+				if (ui.dstPos == 9)
 				{
-					for (uint8_t i = 0; i < 4; i++)
-					{
-						editor.ui.editPos++;
-						textMarkerMoveRight();
-					}
+					ui.editPos++; textMarkerMoveRight();
+					ui.editPos++; textMarkerMoveRight();
+					ui.editPos++; textMarkerMoveRight();
+					ui.editPos++; textMarkerMoveRight();
 				}
-				else if (editor.ui.dstPos == 6)
+				else if (ui.dstPos == 6)
 				{
-					editor.ui.editPos++;
+					ui.editPos++;
 					textMarkerMoveRight();
 				}
 			}
@@ -311,12 +314,12 @@
 		}
 		else
 		{
-			editor.ui.dstOffsetEnd = true;
+			ui.dstOffsetEnd = true;
 		}
 	}
 	else
 	{
-		editor.ui.dstOffsetEnd = true;
+		ui.dstOffsetEnd = true;
 	}
 }
 // --------------------------------
@@ -323,12 +326,8 @@
 
 void keyUpHandler(SDL_Scancode scancode, SDL_Keycode keycode)
 {
-	(void)keycode;
-
 	if (scancode == SDL_SCANCODE_KP_PLUS)
-	{
 		keyb.keypadEnterPressed = false;
-	}
 
 	if (scancode == keyb.lastRepKey)
 		keyb.lastRepKey = SDL_SCANCODE_UNKNOWN;
@@ -358,6 +357,8 @@
 		}
 		break;
 	}
+
+	(void)keycode;
 }
 
 static void incMulti(uint8_t slot)
@@ -391,7 +392,7 @@
 
 	// kludge to allow certain repeat-keys to use custom repeat/delay values
 	if (editor.repeatKeyFlag && keyb.repeatKey && scancode == keyb.lastRepKey &&
-	    (keyb.leftAltPressed || keyb.leftAmigaPressed || keyb.leftCtrlPressed))
+		(keyb.leftAltPressed || keyb.leftAmigaPressed || keyb.leftCtrlPressed))
 	{
 		return;
 	}
@@ -442,7 +443,7 @@
 	}
 
 	// ENTRY JUMPING IN DISK OP. FILELIST
-	if (editor.ui.diskOpScreenShown && keyb.shiftPressed && !editor.ui.editTextFlag)
+	if (ui.diskOpScreenShown && keyb.shiftPressed && !ui.editTextFlag)
 	{
 		if (keycode >= 32 && keycode <= 126)
 		{
@@ -453,9 +454,9 @@
 
 	if (!handleGeneralModes(keycode, scancode)) return;
 	if (!handleTextEditMode(scancode)) return;
-	if (editor.ui.samplerVolBoxShown) return;
+	if (ui.samplerVolBoxShown) return;
 
-	if (editor.ui.samplerFiltersBoxShown)
+	if (ui.samplerFiltersBoxShown)
 	{
 		handleEditKeys(scancode, EDIT_NORMAL);
 		return;
@@ -478,7 +479,7 @@
 				if (editor.autoInsSlot < 0)
 					editor.autoInsSlot = 0;
 
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 		}
 		break;
@@ -507,7 +508,7 @@
 					editor.pNoteFlag = (editor.pNoteFlag + 1) % 3;
 				}
 
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 		}
 		break;
@@ -519,7 +520,7 @@
 #endif
 		{
 			// right Amiga key on Amiga keyb
-			if (!editor.ui.askScreenShown)
+			if (!ui.askScreenShown)
 			{
 				editor.playMode = PLAY_MODE_NORMAL;
 				modPlay(DONT_SET_PATTERN, modEntry->currOrder, DONT_SET_ROW);
@@ -537,7 +538,7 @@
 #endif
 		{
 			// right alt on Amiga keyb
-			if (!editor.ui.askScreenShown)
+			if (!ui.askScreenShown)
 			{
 				editor.playMode = PLAY_MODE_PATTERN;
 				modPlay(modEntry->currPattern, DONT_SET_ORDER, DONT_SET_ROW);
@@ -551,7 +552,7 @@
 		case SDL_SCANCODE_RSHIFT:
 		{
 			// right shift on Amiga keyb
-			if (!editor.ui.samplerScreenShown && !editor.ui.askScreenShown)
+			if (!ui.samplerScreenShown && !ui.askScreenShown)
 			{
 				editor.playMode = PLAY_MODE_PATTERN;
 				modPlay(modEntry->currPattern, DONT_SET_ORDER, DONT_SET_ROW);
@@ -564,29 +565,29 @@
 
 		case SDL_SCANCODE_ESCAPE:
 		{
-			if (editor.ui.posEdScreenShown)
+			if (ui.posEdScreenShown)
 			{
-				editor.ui.posEdScreenShown = false;
+				ui.posEdScreenShown = false;
 				displayMainScreen();
 			}
-			else if (editor.ui.diskOpScreenShown)
+			else if (ui.diskOpScreenShown)
 			{
-				editor.ui.diskOpScreenShown = false;
+				ui.diskOpScreenShown = false;
 				displayMainScreen();
 			}
-			else if (editor.ui.samplerScreenShown)
+			else if (ui.samplerScreenShown)
 			{
 				exitFromSam();
 			}
-			else if (editor.ui.editOpScreenShown)
+			else if (ui.editOpScreenShown)
 			{
-				editor.ui.editOpScreenShown = false;
+				ui.editOpScreenShown = false;
 				displayMainScreen();
 			}
 			else
 			{
-				editor.ui.askScreenShown = true;
-				editor.ui.askScreenType = ASK_QUIT;
+				ui.askScreenShown = true;
+				ui.askScreenType = ASK_QUIT;
 
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				setStatusMessage("REALLY QUIT ?", NO_CARRY);
@@ -601,7 +602,7 @@
 
 		case SDL_SCANCODE_INSERT:
 		{
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 			{
 				samplerSamPaste();
 				return;
@@ -611,7 +612,7 @@
 
 		case SDL_SCANCODE_PAGEUP:
 		{
-			if (editor.ui.posEdScreenShown)
+			if (ui.posEdScreenShown)
 			{
 				if (modEntry->currOrder > 0)
 				{
@@ -621,13 +622,13 @@
 						modSetPos(0, DONT_SET_ROW);
 				}
 			}
-			else if (editor.ui.diskOpScreenShown)
+			else if (ui.diskOpScreenShown)
 			{
-				editor.diskop.scrollOffset -= DISKOP_LINES - 1;
-				if (editor.diskop.scrollOffset < 0)
-					editor.diskop.scrollOffset = 0;
+				diskop.scrollOffset -= DISKOP_LINES - 1;
+				if (diskop.scrollOffset < 0)
+					diskop.scrollOffset = 0;
 
-				editor.ui.updateDiskOpFileList = true;
+				ui.updateDiskOpFileList = true;
 			}
 			else
 			{
@@ -652,7 +653,7 @@
 
 		case SDL_SCANCODE_PAGEDOWN:
 		{
-			if (editor.ui.posEdScreenShown)
+			if (ui.posEdScreenShown)
 			{
 				if (modEntry->currOrder != modEntry->head.orderCount-1)
 				{
@@ -662,15 +663,15 @@
 						modSetPos(modEntry->head.orderCount - 1, DONT_SET_ROW);
 				}
 			}
-			else if (editor.ui.diskOpScreenShown)
+			else if (ui.diskOpScreenShown)
 			{
-				if (editor.diskop.numEntries > DISKOP_LINES)
+				if (diskop.numEntries > DISKOP_LINES)
 				{
-					editor.diskop.scrollOffset += DISKOP_LINES-1;
-					if (editor.diskop.scrollOffset > editor.diskop.numEntries-DISKOP_LINES)
-						editor.diskop.scrollOffset = editor.diskop.numEntries-DISKOP_LINES;
+					diskop.scrollOffset += DISKOP_LINES-1;
+					if (diskop.scrollOffset > diskop.numEntries-DISKOP_LINES)
+						diskop.scrollOffset = diskop.numEntries-DISKOP_LINES;
 
-					editor.ui.updateDiskOpFileList = true;
+					ui.updateDiskOpFileList = true;
 				}
 			}
 			else
@@ -689,17 +690,17 @@
 
 		case SDL_SCANCODE_HOME:
 		{
-			if (editor.ui.posEdScreenShown)
+			if (ui.posEdScreenShown)
 			{
 				if (modEntry->currOrder > 0)
 					modSetPos(0, DONT_SET_ROW);
 			}
-			else if (editor.ui.diskOpScreenShown)
+			else if (ui.diskOpScreenShown)
 			{
-				if (editor.diskop.scrollOffset != 0)
+				if (diskop.scrollOffset != 0)
 				{
-					editor.diskop.scrollOffset = 0;
-					editor.ui.updateDiskOpFileList = true;
+					diskop.scrollOffset = 0;
+					ui.updateDiskOpFileList = true;
 				}
 			}
 			else
@@ -712,16 +713,16 @@
 
 		case SDL_SCANCODE_END:
 		{
-			if (editor.ui.posEdScreenShown)
+			if (ui.posEdScreenShown)
 			{
 				modSetPos(modEntry->head.orderCount - 1, DONT_SET_ROW);
 			}
-			else if (editor.ui.diskOpScreenShown)
+			else if (ui.diskOpScreenShown)
 			{
-				if (editor.diskop.numEntries > DISKOP_LINES)
+				if (diskop.numEntries > DISKOP_LINES)
 				{
-					editor.diskop.scrollOffset = editor.diskop.numEntries - DISKOP_LINES;
-					editor.ui.updateDiskOpFileList = true;
+					diskop.scrollOffset = diskop.numEntries - DISKOP_LINES;
+					ui.updateDiskOpFileList = true;
 				}
 			}
 			else
@@ -734,7 +735,7 @@
 
 		case SDL_SCANCODE_DELETE:
 		{
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				samplerSamDelete(NO_SAMPLE_CUT);
 			else
 				handleEditKeys(scancode, EDIT_NORMAL);
@@ -756,7 +757,7 @@
 					modSetTempo(editor.oldTempo);
 				}
 
-				editor.ui.updateSongTiming = true;
+				ui.updateSongTiming = true;
 			}
 			else if (keyb.shiftPressed)
 			{
@@ -771,11 +772,11 @@
 
 		case SDL_SCANCODE_RETURN:
 		{
-			if (editor.ui.askScreenShown)
+			if (ui.askScreenShown)
 			{
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
-				editor.ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
+				ui.askScreenShown = false;
 
 				handleAskYes();
 			}
@@ -807,7 +808,7 @@
 							modEntry->currRow++;
 
 							updateWindowTitle(MOD_IS_MODIFIED);
-							editor.ui.updatePatternData = true;
+							ui.updatePatternData = true;
 						}
 					}
 					else
@@ -816,8 +817,8 @@
 						{
 							for (i = 62; i >= modEntry->currRow; i--)
 							{
-								noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 0) * AMIGA_VOICES) + editor.cursor.channel];
-								noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel];
+								noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 0) * AMIGA_VOICES) + cursor.channel];
+								noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel];
 
 								if (keyb.leftCtrlPressed)
 								{
@@ -830,7 +831,7 @@
 								}
 							}
 
-							noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel];
+							noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel];
 
 							if (!keyb.leftCtrlPressed)
 							{
@@ -844,7 +845,7 @@
 							modEntry->currRow++;
 
 							updateWindowTitle(MOD_IS_MODIFIED);
-							editor.ui.updatePatternData = true;
+							ui.updatePatternData = true;
 						}
 					}
 				}
@@ -872,7 +873,7 @@
 			}
 			else if (editor.currMode == MODE_EDIT || editor.currMode == MODE_RECORD)
 			{
-				if (!editor.ui.samplerScreenShown)
+				if (!ui.samplerScreenShown)
 				{
 					modStop();
 					editor.currMode = MODE_IDLE;
@@ -880,7 +881,7 @@
 					statusAllRight();
 				}
 			}
-			else if (!editor.ui.samplerScreenShown)
+			else if (!ui.samplerScreenShown)
 			{
 				modStop();
 				editor.currMode = MODE_EDIT;
@@ -895,7 +896,7 @@
 
 		case SDL_SCANCODE_F3:
 		{
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 			{
 				samplerSamDelete(SAMPLE_CUT);
 			}
@@ -909,7 +910,7 @@
 					noteDst = editor.trackBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
 					{
-						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						*noteDst++ = *noteSrc;
 
 						noteSrc->period = 0;
@@ -919,7 +920,7 @@
 					}
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 				else if (keyb.leftAltPressed)
 				{
@@ -933,7 +934,7 @@
 						sizeof (note_t) * (AMIGA_VOICES * MOD_ROWS));
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 				else if (keyb.leftCtrlPressed)
 				{
@@ -943,7 +944,7 @@
 					noteDst = editor.cmdsBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
 					{
-						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						*noteDst++ = *noteSrc;
 
 						noteSrc->command = 0;
@@ -951,7 +952,7 @@
 					}
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 			}
 		}
@@ -959,7 +960,7 @@
 
 		case SDL_SCANCODE_F4:
 		{
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 			{
 				samplerSamCopy();
 			}
@@ -971,7 +972,7 @@
 
 					noteDst = editor.trackBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
-						*noteDst++ = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						*noteDst++ = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 				}
 				else if (keyb.leftAltPressed)
 				{
@@ -987,7 +988,7 @@
 					noteDst = editor.cmdsBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
 					{
-						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						noteDst->command = noteSrc->command;
 						noteDst->param = noteSrc->param;
 
@@ -1000,7 +1001,7 @@
 
 		case SDL_SCANCODE_F5:
 		{
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 			{
 				samplerSamPaste();
 			}
@@ -1013,10 +1014,10 @@
 
 					noteSrc = editor.trackBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
-						modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel] = *noteSrc++;
+						modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel] = *noteSrc++;
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 				else if (keyb.leftAltPressed)
 				{
@@ -1027,7 +1028,7 @@
 						editor.patternBuffer, sizeof (note_t) * (AMIGA_VOICES * MOD_ROWS));
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 				else if (keyb.leftCtrlPressed)
 				{
@@ -1037,7 +1038,7 @@
 					noteSrc = editor.cmdsBuffer;
 					for (i = 0; i < MOD_ROWS; i++)
 					{
-						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						noteDst->command = noteSrc->command;
 						noteDst->param = noteSrc->param;
 
@@ -1045,7 +1046,7 @@
 					}
 
 					updateWindowTitle(MOD_IS_MODIFIED);
-					editor.ui.updatePatternData = true;
+					ui.updatePatternData = true;
 				}
 			}
 		}
@@ -1071,7 +1072,7 @@
 				}
 				else if (keyb.leftCtrlPressed)
 				{
-					if (!editor.ui.samplerScreenShown)
+					if (!ui.samplerScreenShown)
 					{
 						editor.playMode = PLAY_MODE_PATTERN;
 						modPlay(modEntry->currPattern, DONT_SET_ORDER, editor.f6Pos);
@@ -1118,7 +1119,7 @@
 				}
 				else if (keyb.leftCtrlPressed)
 				{
-					if (!editor.ui.samplerScreenShown)
+					if (!ui.samplerScreenShown)
 					{
 						editor.playMode = PLAY_MODE_PATTERN;
 						modPlay(modEntry->currPattern, DONT_SET_ORDER, editor.f7Pos);
@@ -1165,7 +1166,7 @@
 				}
 				else if (keyb.leftCtrlPressed)
 				{
-					if (!editor.ui.samplerScreenShown)
+					if (!ui.samplerScreenShown)
 					{
 						editor.playMode = PLAY_MODE_PATTERN;
 						modPlay(modEntry->currPattern, DONT_SET_ORDER, editor.f8Pos);
@@ -1212,7 +1213,7 @@
 				}
 				else if (keyb.leftCtrlPressed)
 				{
-					if (!editor.ui.samplerScreenShown)
+					if (!ui.samplerScreenShown)
 					{
 						editor.playMode = PLAY_MODE_PATTERN;
 						modPlay(modEntry->currPattern, DONT_SET_ORDER, editor.f9Pos);
@@ -1259,7 +1260,7 @@
 				}
 				else if (keyb.leftCtrlPressed)
 				{
-					if (!editor.ui.samplerScreenShown)
+					if (!ui.samplerScreenShown)
 					{
 						editor.playMode = PLAY_MODE_PATTERN;
 						modPlay(modEntry->currPattern, DONT_SET_ORDER, editor.f10Pos);
@@ -1311,11 +1312,11 @@
 			{
 				editor.editMoveAdd = 0;
 				displayMsg("EDITSKIP = 0");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[9] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1336,11 +1337,11 @@
 			{
 				editor.editMoveAdd = 1;
 				displayMsg("EDITSKIP = 1");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[0] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1365,11 +1366,11 @@
 			{
 				editor.editMoveAdd = 2;
 				displayMsg("EDITSKIP = 2");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[1] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1394,11 +1395,11 @@
 			{
 				editor.editMoveAdd = 3;
 				displayMsg("EDITSKIP = 3");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[2] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1423,11 +1424,11 @@
 			{
 				editor.editMoveAdd = 4;
 				displayMsg("EDITSKIP = 4");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[3] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1448,11 +1449,11 @@
 			{
 				editor.editMoveAdd = 5;
 				displayMsg("EDITSKIP = 5");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[4] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1469,11 +1470,11 @@
 			{
 				editor.editMoveAdd = 6;
 				displayMsg("EDITSKIP = 6");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[5] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1490,11 +1491,11 @@
 			{
 				editor.editMoveAdd = 7;
 				displayMsg("EDITSKIP = 7");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[6] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1511,11 +1512,11 @@
 			{
 				editor.editMoveAdd = 8;
 				displayMsg("EDITSKIP = 8");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[7] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1532,11 +1533,11 @@
 			{
 				editor.editMoveAdd = 9;
 				displayMsg("EDITSKIP = 9");
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else if (keyb.shiftPressed)
 			{
-				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + editor.cursor.channel];
+				noteSrc = &modEntry->patterns[modEntry->currPattern][(modEntry->currRow * AMIGA_VOICES) + cursor.channel];
 				editor.effectMacros[8] = (noteSrc->command << 8) | noteSrc->param;
 				displayMsg("COMMAND STORED!");
 			}
@@ -1562,7 +1563,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1581,7 +1582,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1600,7 +1601,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1619,7 +1620,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1638,7 +1639,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1657,7 +1658,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1676,7 +1677,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1695,7 +1696,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1714,7 +1715,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1727,11 +1728,11 @@
 
 		case SDL_SCANCODE_KP_ENTER:
 		{
-			if (editor.ui.askScreenShown)
+			if (ui.askScreenShown)
 			{
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
-				editor.ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
+				ui.askScreenShown = false;
 				handleAskYes();
 			}
 			else
@@ -1757,7 +1758,7 @@
 				updateCurrSample();
 				if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 				{
-					editor.ui.changingDrumPadNote = true;
+					ui.changingDrumPadNote = true;
 					setStatusMessage("SELECT NOTE", NO_CARRY);
 					pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 					break;
@@ -1795,7 +1796,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1814,7 +1815,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1833,7 +1834,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				break;
@@ -1852,7 +1853,7 @@
 			updateCurrSample();
 			if (keyb.leftAltPressed && editor.pNoteFlag > 0)
 			{
-				editor.ui.changingDrumPadNote = true;
+				ui.changingDrumPadNote = true;
 
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
@@ -1867,8 +1868,8 @@
 
 		case SDL_SCANCODE_KP_PERIOD:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_KILL_SAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_KILL_SAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("KILL SAMPLE ?", NO_CARRY);
 			renderAskDialog();
@@ -1880,18 +1881,18 @@
 			keyb.delayKey = false;
 			keyb.repeatKey = false;
 
-			if (editor.ui.diskOpScreenShown)
+			if (ui.diskOpScreenShown)
 			{
-				if (editor.diskop.numEntries > DISKOP_LINES)
+				if (diskop.numEntries > DISKOP_LINES)
 				{
-					editor.diskop.scrollOffset++;
+					diskop.scrollOffset++;
 					if (mouse.rightButtonPressed) // PT quirk: right mouse button speeds up scrolling even on keyb UP/DOWN
-						editor.diskop.scrollOffset += 3;
+						diskop.scrollOffset += 3;
 
-					if (editor.diskop.scrollOffset > editor.diskop.numEntries-DISKOP_LINES)
-						editor.diskop.scrollOffset = editor.diskop.numEntries-DISKOP_LINES;
+					if (diskop.scrollOffset > diskop.numEntries-DISKOP_LINES)
+						diskop.scrollOffset = diskop.numEntries-DISKOP_LINES;
 
-					editor.ui.updateDiskOpFileList = true;
+					ui.updateDiskOpFileList = true;
 				}
 
 				if (!keyb.repeatKey)
@@ -1900,7 +1901,7 @@
 				keyb.repeatKey = true;
 				keyb.delayKey = false;
 			}
-			else if (editor.ui.posEdScreenShown)
+			else if (ui.posEdScreenShown)
 			{
 				if (modEntry->currOrder != modEntry->head.orderCount-1)
 				{
@@ -1908,7 +1909,7 @@
 						modEntry->currOrder = modEntry->head.orderCount-1;
 
 					modSetPos(modEntry->currOrder, DONT_SET_ROW);
-					editor.ui.updatePosEd = true;
+					ui.updatePosEd = true;
 				}
 
 				if (!keyb.repeatKey)
@@ -1917,7 +1918,7 @@
 				keyb.repeatKey = true;
 				keyb.delayKey = true;
 			}
-			else if (!editor.ui.samplerScreenShown)
+			else if (!ui.samplerScreenShown)
 			{
 				if (editor.currMode != MODE_PLAY && editor.currMode != MODE_RECORD)
 					modSetPos(DONT_SET_ORDER, (modEntry->currRow + 1) & 0x3F);
@@ -1932,16 +1933,16 @@
 			keyb.delayKey  = false;
 			keyb.repeatKey = false;
 
-			if (editor.ui.diskOpScreenShown)
+			if (ui.diskOpScreenShown)
 			{
-				editor.diskop.scrollOffset--;
+				diskop.scrollOffset--;
 				if (mouse.rightButtonPressed) // PT quirk: right mouse button speeds up scrolling even on keyb UP/DOWN
-					editor.diskop.scrollOffset -= 3;
+					diskop.scrollOffset -= 3;
 
-				if (editor.diskop.scrollOffset < 0)
-					editor.diskop.scrollOffset = 0;
+				if (diskop.scrollOffset < 0)
+					diskop.scrollOffset = 0;
 
-				editor.ui.updateDiskOpFileList = true;
+				ui.updateDiskOpFileList = true;
 
 				if (!keyb.repeatKey)
 					keyb.delayCounter = 0;
@@ -1949,12 +1950,12 @@
 				keyb.repeatKey = true;
 				keyb.delayKey = false;
 			}
-			else if (editor.ui.posEdScreenShown)
+			else if (ui.posEdScreenShown)
 			{
 				if (modEntry->currOrder > 0)
 				{
 					modSetPos(modEntry->currOrder - 1, DONT_SET_ROW);
-					editor.ui.updatePosEd = true;
+					ui.updatePosEd = true;
 				}
 
 				if (!keyb.repeatKey)
@@ -1963,7 +1964,7 @@
 				keyb.repeatKey = true;
 				keyb.delayKey = true;
 			}
-			else if (!editor.ui.samplerScreenShown)
+			else if (!ui.samplerScreenShown)
 			{
 				if ((editor.currMode != MODE_PLAY) && (editor.currMode != MODE_RECORD))
 					modSetPos(DONT_SET_ORDER, (modEntry->currRow - 1) & 0x3F);
@@ -2067,7 +2068,7 @@
 			}
 			else if (keyb.leftCtrlPressed)
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 				{
 					samplerRangeAll();
 				}
@@ -2080,12 +2081,12 @@
 						editor.muted[2] = true;
 						editor.muted[3] = true;
 
-						editor.muted[editor.cursor.channel] = false;
+						editor.muted[cursor.channel] = false;
 						renderMuteButtons();
 						break;
 					}
 
-					editor.muted[editor.cursor.channel] ^= 1;
+					editor.muted[cursor.channel] ^= 1;
 					renderMuteButtons();
 				}
 			}
@@ -2101,9 +2102,9 @@
 			if (keyb.leftCtrlPressed)
 			{
 				// CTRL+B doesn't change the status message back, so do this:
-				if (editor.ui.introScreenShown)
+				if (ui.introScreenShown)
 				{
-					editor.ui.introScreenShown = false;
+					ui.introScreenShown = false;
 					statusAllRight();
 				}
 
@@ -2118,7 +2119,7 @@
 					editor.blockToPos = modEntry->currRow;
 				}
 
-				editor.ui.updateStatusText = true;
+				ui.updateStatusText = true;
 			}
 			else if (keyb.leftAltPressed)
 			{
@@ -2131,7 +2132,7 @@
 
 				boostSample(editor.currSample, true);
 
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					displaySample();
 			}
 			else
@@ -2149,7 +2150,7 @@
 			}
 			else if (keyb.leftCtrlPressed)
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 				{
 					samplerSamCopy();
 					return;
@@ -2165,7 +2166,7 @@
 				editor.blockBufferFlag = true;
 
 				for (i = 0; i < MOD_ROWS; i++)
-					editor.blockBuffer[i] = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					editor.blockBuffer[i] = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 				if (editor.blockFromPos > editor.blockToPos)
 				{
@@ -2209,12 +2210,12 @@
 			{
 				if (keyb.leftAltPressed)
 				{
-					if (!editor.ui.posEdScreenShown)
+					if (!ui.posEdScreenShown)
 					{
 						editor.blockMarkFlag = false;
 
-						editor.ui.diskOpScreenShown ^= 1;
-						if (!editor.ui.diskOpScreenShown)
+						ui.diskOpScreenShown ^= 1;
+						if (!ui.diskOpScreenShown)
 						{
 							pointerSetPreviousMode();
 							setPrevStatusMessage();
@@ -2222,7 +2223,7 @@
 						}
 						else
 						{
-							editor.ui.diskOpScreenShown = true;
+							ui.diskOpScreenShown = true;
 							renderDiskOpScreen();
 						}
 					}
@@ -2243,12 +2244,12 @@
 			}
 			else if (keyb.leftAltPressed)
 			{
-				if (!editor.ui.diskOpScreenShown && !editor.ui.posEdScreenShown)
+				if (!ui.diskOpScreenShown && !ui.posEdScreenShown)
 				{
-					if (editor.ui.editOpScreenShown)
-						editor.ui.editOpScreen = (editor.ui.editOpScreen + 1) % 3;
+					if (ui.editOpScreenShown)
+						ui.editOpScreen = (ui.editOpScreen + 1) % 3;
 					else
-						editor.ui.editOpScreenShown = true;
+						ui.editOpScreenShown = true;
 
 					renderEditOpScreen();
 				}
@@ -2262,11 +2263,11 @@
 				{
 					for (i = 62; i >= j; i--)
 					{
-						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
-						modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel] = *noteSrc;
+						noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
+						modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel] = *noteSrc;
 					}
 
-					noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel];
 					noteDst->period = 0;
 					noteDst->sample = 0;
 					noteDst->command = 0;
@@ -2276,7 +2277,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -2317,7 +2318,7 @@
 				}
 
 				filterSample(editor.currSample, true);
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					displaySample();
 			}
 			else
@@ -2331,8 +2332,8 @@
 		{
 			if (keyb.leftCtrlPressed)
 			{
-				editor.ui.askScreenShown = true;
-				editor.ui.askScreenType = ASK_BOOST_ALL_SAMPLES;
+				ui.askScreenShown = true;
+				ui.askScreenType = ASK_BOOST_ALL_SAMPLES;
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				setStatusMessage("BOOST ALL SAMPLES", NO_CARRY);
 				renderAskDialog();
@@ -2345,8 +2346,8 @@
 				else
 					displayMsg("REC MODE: SONG");
 
-				if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 1)
-					editor.ui.updateRecordText = true;
+				if (ui.editOpScreenShown && ui.editOpScreen == 1)
+					ui.updateRecordText = true;
 			}
 			else
 			{
@@ -2390,8 +2391,8 @@
 					{
 						for (j = 62; j >= modEntry->currRow; j--)
 						{
-							noteSrc = &modEntry->patterns[modEntry->currPattern][(j * AMIGA_VOICES) + editor.cursor.channel];
-							modEntry->patterns[modEntry->currPattern][((j + 1) * AMIGA_VOICES) + editor.cursor.channel] = *noteSrc;
+							noteSrc = &modEntry->patterns[modEntry->currPattern][(j * AMIGA_VOICES) + cursor.channel];
+							modEntry->patterns[modEntry->currPattern][((j + 1) * AMIGA_VOICES) + cursor.channel] = *noteSrc;
 						}
 					}
 				}
@@ -2402,7 +2403,7 @@
 					if (modEntry->currRow+i > 63)
 						break;
 
-					modEntry->patterns[modEntry->currPattern][((modEntry->currRow + i) * AMIGA_VOICES) + editor.cursor.channel]
+					modEntry->patterns[modEntry->currPattern][((modEntry->currRow + i) * AMIGA_VOICES) + cursor.channel]
 						= editor.blockBuffer[editor.buffFromPos + i];
 				}
 
@@ -2414,12 +2415,12 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else if (keyb.leftAltPressed)
 			{
 				editor.autoInsFlag ^= 1;
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else
 			{
@@ -2445,7 +2446,7 @@
 				patt = modEntry->patterns[modEntry->currPattern];
 				while (true)
 				{
-					noteDst = &patt[(j * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &patt[(j * AMIGA_VOICES) + cursor.channel];
 
 					if (editor.blockBuffer[i].period == 0 && editor.blockBuffer[i].sample == 0)
 					{
@@ -2472,7 +2473,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -2487,7 +2488,7 @@
 			{
 				for (i = 0; i < MOD_ROWS; i++)
 				{
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					if (noteSrc->sample == editor.currSample+1)
 					{
 						noteSrc->period = 0;
@@ -2498,7 +2499,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else if (keyb.leftCtrlPressed)
 			{
@@ -2510,7 +2511,7 @@
 					// kill to start
 					while (i >= 0)
 					{
-						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						noteDst->period = 0;
 						noteDst->sample = 0;
 						noteDst->command = 0;
@@ -2524,7 +2525,7 @@
 					// kill to end
 					while (i < MOD_ROWS)
 					{
-						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+						noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 						noteDst->period = 0;
 						noteDst->sample = 0;
 						noteDst->command = 0;
@@ -2535,7 +2536,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -2568,17 +2569,17 @@
 			if (keyb.leftCtrlPressed)
 			{
 				editor.multiFlag ^= 1;
-				editor.ui.updateTrackerFlags = true;
-				editor.ui.updateKeysText = true;
+				ui.updateTrackerFlags = true;
+				ui.updateKeysText = true;
 			}
 			else if (keyb.leftAltPressed)
 			{
 				if (keyb.shiftPressed)
-					editor.metroChannel = editor.cursor.channel + 1;
+					editor.metroChannel = cursor.channel + 1;
 				else
 					editor.metroFlag ^= 1;
 
-				editor.ui.updateTrackerFlags = true;
+				ui.updateTrackerFlags = true;
 			}
 			else
 			{
@@ -2614,12 +2615,12 @@
 				{
 					for (i = j; i < MOD_ROWS-1; i++)
 					{
-						noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel];
-						modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel] = *noteSrc;
+						noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel];
+						modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel] = *noteSrc;
 					}
 
 					// clear newly made row on very bottom
-					noteDst = &modEntry->patterns[modEntry->currPattern][(63 * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &modEntry->patterns[modEntry->currPattern][(63 * AMIGA_VOICES) + cursor.channel];
 					noteDst->period = 0;
 					noteDst->sample = 0;
 					noteDst->command = 0;
@@ -2629,7 +2630,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -2655,7 +2656,7 @@
 				patt = modEntry->patterns[modEntry->currPattern];
 				while (true)
 				{
-					noteDst = &patt[(j * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &patt[(j * AMIGA_VOICES) + cursor.channel];
 					*noteDst = editor.blockBuffer[i];
 
 					if (i == editor.buffToPos || i == 63 || j == 63)
@@ -2673,17 +2674,17 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else if (keyb.leftAltPressed)
 			{
-				if (!editor.ui.diskOpScreenShown)
+				if (!ui.diskOpScreenShown)
 				{
-					editor.ui.posEdScreenShown ^= 1;
-					if (editor.ui.posEdScreenShown)
+					ui.posEdScreenShown ^= 1;
+					if (ui.posEdScreenShown)
 					{
 						renderPosEdScreen();
-						editor.ui.updatePosEd = true;
+						ui.updatePosEd = true;
 					}
 					else
 					{
@@ -2714,8 +2715,8 @@
 			}
 			else if (keyb.leftAltPressed)
 			{
-				editor.ui.askScreenShown = true;
-				editor.ui.askScreenType = ASK_QUIT;
+				ui.askScreenShown = true;
+				ui.askScreenType = ASK_QUIT;
 
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				setStatusMessage("REALLY QUIT ?", NO_CARRY);
@@ -2746,8 +2747,8 @@
 			}
 			else if (keyb.leftAltPressed)
 			{
-				editor.ui.askScreenShown = true;
-				editor.ui.askScreenType = ASK_RESAMPLE;
+				ui.askScreenShown = true;
+				ui.askScreenType = ASK_RESAMPLE;
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				setStatusMessage("RESAMPLE?", NO_CARRY);
 				renderAskDialog();
@@ -2764,13 +2765,13 @@
 			if (keyb.leftCtrlPressed)
 			{
 				// if we're in sample load/save mode, set current dir to modules path
-				if (editor.diskop.mode == DISKOP_MODE_SMP)
+				if (diskop.mode == DISKOP_MODE_SMP)
 					UNICHAR_CHDIR(editor.modulesPathU);
 
 				saveModule(DONT_CHECK_IF_FILE_EXIST, DONT_GIVE_NEW_FILENAME);
 
 				// set current dir to samples path
-				if (editor.diskop.mode == DISKOP_MODE_SMP)
+				if (diskop.mode == DISKOP_MODE_SMP)
 					UNICHAR_CHDIR(editor.samplesPathU);
 			}
 			else if (keyb.leftAmigaPressed)
@@ -2824,14 +2825,14 @@
 			}
 			else if (keyb.leftCtrlPressed)
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 				{
 					samplerSamPaste();
 				}
 				else
 				{
-					editor.ui.askScreenShown = true;
-					editor.ui.askScreenType = ASK_FILTER_ALL_SAMPLES;
+					ui.askScreenShown = true;
+					ui.askScreenType = ASK_FILTER_ALL_SAMPLES;
 
 					pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 					setStatusMessage("FILTER ALL SAMPLS", NO_CARRY);
@@ -2872,7 +2873,7 @@
 				patt = modEntry->patterns[modEntry->currPattern];
 				while (true)
 				{
-					noteDst = &patt[(j * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &patt[(j * AMIGA_VOICES) + cursor.channel];
 					if (editor.blockBuffer[i].period == 0 && editor.blockBuffer[i].sample == 0)
 					{
 						noteDst->command = editor.blockBuffer[i].command;
@@ -2899,7 +2900,7 @@
 				}
 
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -2916,7 +2917,7 @@
 			}
 			else if (keyb.leftCtrlPressed)
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 				{
 					samplerSamDelete(SAMPLE_CUT);
 					return;
@@ -2933,7 +2934,7 @@
 				editor.blockBufferFlag = true;
 
 				for (i = 0; i < MOD_ROWS; i++)
-					editor.blockBuffer[i] = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					editor.blockBuffer[i] = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 				if (editor.blockFromPos > editor.blockToPos)
 				{
@@ -2948,7 +2949,7 @@
 
 				for (i = editor.buffFromPos; i <= editor.buffToPos; i++)
 				{
-					noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					noteDst->period = 0;
 					noteDst->sample = 0;
 					noteDst->command = 0;
@@ -2957,7 +2958,7 @@
 
 				statusAllRight();
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else
 			{
@@ -3001,8 +3002,8 @@
 
 				while (blockFrom < blockTo)
 				{
-					noteDst = &modEntry->patterns[modEntry->currPattern][(blockFrom * AMIGA_VOICES) + editor.cursor.channel];
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(blockTo * AMIGA_VOICES) + editor.cursor.channel];
+					noteDst = &modEntry->patterns[modEntry->currPattern][(blockFrom * AMIGA_VOICES) + cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(blockTo * AMIGA_VOICES) + cursor.channel];
 
 					noteTmp = *noteDst;
 					*noteDst = *noteSrc;
@@ -3014,12 +3015,12 @@
 
 				statusAllRight();
 				updateWindowTitle(MOD_IS_MODIFIED);
-				editor.ui.updatePatternData = true;
+				ui.updatePatternData = true;
 			}
 			else if (keyb.leftAltPressed)
 			{
-				editor.ui.askScreenShown = true;
-				editor.ui.askScreenType = ASK_SAVE_ALL_SAMPLES;
+				ui.askScreenShown = true;
+				ui.askScreenType = ASK_SAVE_ALL_SAMPLES;
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 				setStatusMessage("SAVE ALL SAMPLES?", NO_CARRY);
 				renderAskDialog();
@@ -3039,10 +3040,10 @@
 			}
 			else if (keyb.leftCtrlPressed)
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 				{
-					editor.ui.askScreenShown = true;
-					editor.ui.askScreenType = ASK_RESTORE_SAMPLE;
+					ui.askScreenShown = true;
+					ui.askScreenType = ASK_RESTORE_SAMPLE;
 
 					pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 					setStatusMessage("RESTORE SAMPLE ?", NO_CARRY);
@@ -3085,15 +3086,15 @@
 
 void movePatCurPrevCh(void)
 {
-	int8_t pos = ((editor.cursor.pos + 5) / 6) - 1;
+	int8_t pos = ((cursor.pos + 5) / 6) - 1;
 
-	editor.cursor.pos = (pos < 0) ? (3 * 6) : (pos * 6);
-	editor.cursor.mode = CURSOR_NOTE;
+	cursor.pos = (pos < 0) ? (3 * 6) : (pos * 6);
+	cursor.mode = CURSOR_NOTE;
 
-	     if (editor.cursor.pos <  6) editor.cursor.channel = 0;
-	else if (editor.cursor.pos < 12) editor.cursor.channel = 1;
-	else if (editor.cursor.pos < 18) editor.cursor.channel = 2;
-	else if (editor.cursor.pos < 24) editor.cursor.channel = 3;
+	     if (cursor.pos <  6) cursor.channel = 0;
+	else if (cursor.pos < 12) cursor.channel = 1;
+	else if (cursor.pos < 18) cursor.channel = 2;
+	else if (cursor.pos < 24) cursor.channel = 3;
 
 	updateCursorPos();
 }
@@ -3100,15 +3101,15 @@
 
 void movePatCurNextCh(void)
 {
-	int8_t pos = (editor.cursor.pos / 6) + 1;
+	int8_t pos = (cursor.pos / 6) + 1;
 
-	editor.cursor.pos = (pos == 4) ? 0 : (pos * 6);
-	editor.cursor.mode = CURSOR_NOTE;
+	cursor.pos = (pos == 4) ? 0 : (pos * 6);
+	cursor.mode = CURSOR_NOTE;
 
-	     if (editor.cursor.pos <  6) editor.cursor.channel = 0;
-	else if (editor.cursor.pos < 12) editor.cursor.channel = 1;
-	else if (editor.cursor.pos < 18) editor.cursor.channel = 2;
-	else if (editor.cursor.pos < 24) editor.cursor.channel = 3;
+	     if (cursor.pos <  6) cursor.channel = 0;
+	else if (cursor.pos < 12) cursor.channel = 1;
+	else if (cursor.pos < 18) cursor.channel = 2;
+	else if (cursor.pos < 24) cursor.channel = 3;
 
 	updateCursorPos();
 }
@@ -3115,27 +3116,27 @@
 
 void movePatCurRight(void)
 {
-	editor.cursor.pos = (editor.cursor.pos == 23) ? 0 : (editor.cursor.pos + 1);
+	cursor.pos = (cursor.pos == 23) ? 0 : (cursor.pos + 1);
 
-	     if (editor.cursor.pos <  6) editor.cursor.channel = 0;
-	else if (editor.cursor.pos < 12) editor.cursor.channel = 1;
-	else if (editor.cursor.pos < 18) editor.cursor.channel = 2;
-	else if (editor.cursor.pos < 24) editor.cursor.channel = 3;
+	     if (cursor.pos <  6) cursor.channel = 0;
+	else if (cursor.pos < 12) cursor.channel = 1;
+	else if (cursor.pos < 18) cursor.channel = 2;
+	else if (cursor.pos < 24) cursor.channel = 3;
 
-	editor.cursor.mode = editor.cursor.pos % 6;
+	cursor.mode = cursor.pos % 6;
 	updateCursorPos();
 }
 
 void movePatCurLeft(void)
 {
-	editor.cursor.pos = (editor.cursor.pos == 0) ? 23 : (editor.cursor.pos - 1);
+	cursor.pos = (cursor.pos == 0) ? 23 : (cursor.pos - 1);
 
-	     if (editor.cursor.pos <  6) editor.cursor.channel = 0;
-	else if (editor.cursor.pos < 12) editor.cursor.channel = 1;
-	else if (editor.cursor.pos < 18) editor.cursor.channel = 2;
-	else if (editor.cursor.pos < 24) editor.cursor.channel = 3;
+	     if (cursor.pos <  6) cursor.channel = 0;
+	else if (cursor.pos < 12) cursor.channel = 1;
+	else if (cursor.pos < 18) cursor.channel = 2;
+	else if (cursor.pos < 24) cursor.channel = 3;
 
-	editor.cursor.mode = editor.cursor.pos % 6;
+	cursor.mode = cursor.pos % 6;
 	updateCursorPos();
 }
 
@@ -3143,7 +3144,7 @@
 {
 	uint8_t repeatNum;
 
-	if (!keyb.repeatKey || (editor.ui.clearScreenShown || editor.ui.askScreenShown))
+	if (!keyb.repeatKey || (ui.clearScreenShown || ui.askScreenShown))
 	{
 		keyb.repeatFrac = 0;
 		keyb.repeatCounter = 0;
@@ -3164,7 +3165,7 @@
 			{
 				keyb.repeatCounter = 0;
 
-				if (editor.ui.posEdScreenShown)
+				if (ui.posEdScreenShown)
 				{
 					if (modEntry->currOrder-(POSED_LIST_SIZE-1) > 0)
 						modSetPos(modEntry->currOrder-(POSED_LIST_SIZE-1), DONT_SET_ROW);
@@ -3171,15 +3172,15 @@
 					else
 						modSetPos(0, DONT_SET_ROW);
 				}
-				else if (editor.ui.diskOpScreenShown)
+				else if (ui.diskOpScreenShown)
 				{
-					if (editor.ui.diskOpScreenShown)
+					if (ui.diskOpScreenShown)
 					{
-						editor.diskop.scrollOffset -= DISKOP_LINES-1;
-						if (editor.diskop.scrollOffset < 0)
-							editor.diskop.scrollOffset = 0;
+						diskop.scrollOffset -= DISKOP_LINES-1;
+						if (diskop.scrollOffset < 0)
+							diskop.scrollOffset = 0;
 
-						editor.ui.updateDiskOpFileList = true;
+						ui.updateDiskOpFileList = true;
 					}
 				}
 				else if (editor.currMode == MODE_IDLE || editor.currMode == MODE_EDIT)
@@ -3201,7 +3202,7 @@
 			{
 				keyb.repeatCounter = 0;
 
-				if (editor.ui.posEdScreenShown)
+				if (ui.posEdScreenShown)
 				{
 					if (modEntry->currOrder+(POSED_LIST_SIZE-1) <= modEntry->head.orderCount-1)
 						modSetPos(modEntry->currOrder+(POSED_LIST_SIZE-1), DONT_SET_ROW);
@@ -3208,15 +3209,15 @@
 					else
 						modSetPos(modEntry->head.orderCount - 1, DONT_SET_ROW);
 				}
-				else if (editor.ui.diskOpScreenShown)
+				else if (ui.diskOpScreenShown)
 				{
-					if (editor.diskop.numEntries > DISKOP_LINES)
+					if (diskop.numEntries > DISKOP_LINES)
 					{
-						editor.diskop.scrollOffset += DISKOP_LINES-1;
-						if (editor.diskop.scrollOffset > editor.diskop.numEntries-DISKOP_LINES)
-							editor.diskop.scrollOffset = editor.diskop.numEntries-DISKOP_LINES;
+						diskop.scrollOffset += DISKOP_LINES-1;
+						if (diskop.scrollOffset > diskop.numEntries-DISKOP_LINES)
+							diskop.scrollOffset = diskop.numEntries-DISKOP_LINES;
 
-						editor.ui.updateDiskOpFileList = true;
+						ui.updateDiskOpFileList = true;
 					}
 				}
 				else if (editor.currMode == MODE_IDLE || editor.currMode == MODE_EDIT)
@@ -3229,7 +3230,7 @@
 
 		case SDL_SCANCODE_LEFT:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				if (keyb.repeatCounter >= 4)
 				{
@@ -3279,7 +3280,7 @@
 
 		case SDL_SCANCODE_RIGHT:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				if (keyb.repeatCounter >= 4)
 				{
@@ -3329,23 +3330,23 @@
 
 		case SDL_SCANCODE_UP:
 		{
-			if (editor.ui.diskOpScreenShown)
+			if (ui.diskOpScreenShown)
 			{
 				if (keyb.repeatCounter >= 1)
 				{
 					keyb.repeatCounter = 0;
 
-					editor.diskop.scrollOffset--;
+					diskop.scrollOffset--;
 					if (mouse.rightButtonPressed) // PT quirk: right mouse button speeds up scrolling even on keyb UP/DOWN
-						editor.diskop.scrollOffset -= 3;
+						diskop.scrollOffset -= 3;
 
-					if (editor.diskop.scrollOffset < 0)
-						editor.diskop.scrollOffset = 0;
+					if (diskop.scrollOffset < 0)
+						diskop.scrollOffset = 0;
 
-					editor.ui.updateDiskOpFileList = true;
+					ui.updateDiskOpFileList = true;
 				}
 			}
-			else if (editor.ui.posEdScreenShown)
+			else if (ui.posEdScreenShown)
 			{
 				if (keyb.repeatCounter >= 3)
 				{
@@ -3353,11 +3354,11 @@
 					if (modEntry->currOrder > 0)
 					{
 						modSetPos(modEntry->currOrder - 1, DONT_SET_ROW);
-						editor.ui.updatePosEd = true;
+						ui.updatePosEd = true;
 					}
 				}
 			}
-			else if (!editor.ui.samplerScreenShown)
+			else if (!ui.samplerScreenShown)
 			{
 				if (editor.currMode != MODE_PLAY && editor.currMode != MODE_RECORD)
 				{
@@ -3379,26 +3380,26 @@
 
 		case SDL_SCANCODE_DOWN:
 		{
-			if (editor.ui.diskOpScreenShown)
+			if (ui.diskOpScreenShown)
 			{
 				if (keyb.repeatCounter >= 1)
 				{
 					keyb.repeatCounter = 0;
 
-					if (editor.diskop.numEntries > DISKOP_LINES)
+					if (diskop.numEntries > DISKOP_LINES)
 					{
-						editor.diskop.scrollOffset++;
+						diskop.scrollOffset++;
 						if (mouse.rightButtonPressed) // PT quirk: right mouse button speeds up scrolling even on keyb UP/DOWN
-							editor.diskop.scrollOffset += 3;
+							diskop.scrollOffset += 3;
 
-						if (editor.diskop.scrollOffset > editor.diskop.numEntries-DISKOP_LINES)
-							editor.diskop.scrollOffset = editor.diskop.numEntries-DISKOP_LINES;
+						if (diskop.scrollOffset > diskop.numEntries-DISKOP_LINES)
+							diskop.scrollOffset = diskop.numEntries-DISKOP_LINES;
 
-						editor.ui.updateDiskOpFileList = true;
+						ui.updateDiskOpFileList = true;
 					}
 				}
 			}
-			else if (editor.ui.posEdScreenShown)
+			else if (ui.posEdScreenShown)
 			{
 				if (keyb.repeatCounter >= 3)
 				{
@@ -3410,11 +3411,11 @@
 							modEntry->currOrder = modEntry->head.orderCount-1;
 
 						modSetPos(modEntry->currOrder, DONT_SET_ROW);
-						editor.ui.updatePosEd = true;
+						ui.updatePosEd = true;
 					}
 				}
 			}
-			else if (!editor.ui.samplerScreenShown)
+			else if (!ui.samplerScreenShown)
 			{
 				if (editor.currMode != MODE_PLAY && editor.currMode != MODE_RECORD)
 				{
@@ -3436,7 +3437,7 @@
 
 		case SDL_SCANCODE_BACKSPACE:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				// only repeat backspace while editing texts
 				if (keyb.repeatCounter >= 3)
@@ -3482,17 +3483,17 @@
 	note_t *noteSrc, noteTmp;
 
 	// SAMPLER SCREEN (volume box)
-	if (editor.ui.samplerVolBoxShown && !editor.ui.editTextFlag && scancode == SDL_SCANCODE_ESCAPE)
+	if (ui.samplerVolBoxShown && !ui.editTextFlag && scancode == SDL_SCANCODE_ESCAPE)
 	{
-		editor.ui.samplerVolBoxShown = false;
+		ui.samplerVolBoxShown = false;
 		removeSamplerVolBox();
 		return false;
 	}
 
 	// SAMPLER SCREEN (filters box)
-	if (editor.ui.samplerFiltersBoxShown && !editor.ui.editTextFlag && scancode == SDL_SCANCODE_ESCAPE)
+	if (ui.samplerFiltersBoxShown && !ui.editTextFlag && scancode == SDL_SCANCODE_ESCAPE)
 	{
-		editor.ui.samplerFiltersBoxShown = false;
+		ui.samplerFiltersBoxShown = false;
 		removeSamplerFiltersBox();
 		return false;
 	}
@@ -3502,16 +3503,16 @@
 	{
 		exitGetTextLine(EDIT_TEXT_UPDATE);
 		editor.mixFlag = false;
-		editor.ui.updateMixText = true;
+		ui.updateMixText = true;
 		return false;
 	}
 
 	// EDIT OP. SCREEN #4
-	if (editor.ui.changingChordNote)
+	if (ui.changingChordNote)
 	{
 		if (scancode == SDL_SCANCODE_ESCAPE)
 		{
-			editor.ui.changingChordNote = false;
+			ui.changingChordNote = false;
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
 			return false;
@@ -3525,28 +3526,28 @@
 		rawKey = keyToNote(scancode);
 		if (rawKey >= 0)
 		{
-			if (editor.ui.changingChordNote == 1)
+			if (ui.changingChordNote == 1)
 			{
 				editor.note1 = rawKey;
-				editor.ui.updateNote1Text = true;
+				ui.updateNote1Text = true;
 			}
-			else if (editor.ui.changingChordNote == 2)
+			else if (ui.changingChordNote == 2)
 			{
 				editor.note2 = rawKey;
-				editor.ui.updateNote2Text = true;
+				ui.updateNote2Text = true;
 			}
-			else if (editor.ui.changingChordNote == 3)
+			else if (ui.changingChordNote == 3)
 			{
 				editor.note3 = rawKey;
-				editor.ui.updateNote3Text = true;
+				ui.updateNote3Text = true;
 			}
-			else if (editor.ui.changingChordNote == 4)
+			else if (ui.changingChordNote == 4)
 			{
 				editor.note4 = rawKey;
-				editor.ui.updateNote4Text = true;
+				ui.updateNote4Text = true;
 			}
 
-			editor.ui.changingChordNote = false;
+			ui.changingChordNote = false;
 			recalcChordLength();
 
 			setPrevStatusMessage();
@@ -3557,11 +3558,11 @@
 	}
 
 	// CHANGE DRUMPAD NOTE
-	if (editor.ui.changingDrumPadNote)
+	if (ui.changingDrumPadNote)
 	{
 		if (scancode == SDL_SCANCODE_ESCAPE)
 		{
-			editor.ui.changingDrumPadNote = false;
+			ui.changingDrumPadNote = false;
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
 			return false;
@@ -3576,7 +3577,7 @@
 		if (rawKey >= 0)
 		{
 			pNoteTable[editor.currSample] = rawKey;
-			editor.ui.changingDrumPadNote = false;
+			ui.changingDrumPadNote = false;
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
 		}
@@ -3585,12 +3586,12 @@
 	}
 
 	// SAMPLER SCREEN
-	if (editor.ui.changingSmpResample)
+	if (ui.changingSmpResample)
 	{
 		if (scancode == SDL_SCANCODE_ESCAPE)
 		{
-			editor.ui.changingSmpResample = false;
-			editor.ui.updateResampleNote = true;
+			ui.changingSmpResample = false;
+			ui.updateResampleNote = true;
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
 			return false;
@@ -3605,8 +3606,8 @@
 		if (rawKey >= 0)
 		{
 			editor.resampleNote = rawKey;
-			editor.ui.changingSmpResample = false;
-			editor.ui.updateResampleNote = true;
+			ui.changingSmpResample = false;
+			ui.updateResampleNote = true;
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
 		}
@@ -3615,22 +3616,22 @@
 	}
 
 	// DISK OP. SCREEN
-	if (editor.diskop.isFilling)
+	if (diskop.isFilling)
 	{
-		if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_QUIT)
+		if (ui.askScreenShown && ui.askScreenType == ASK_QUIT)
 		{
 			if (keycode == SDLK_y)
 			{
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
+				ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
 				handleAskYes();
 			}
 			else if (keycode == SDLK_n)
 			{
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = true;
-				editor.ui.answerYes = false;
+				ui.askScreenShown = false;
+				ui.answerNo = true;
+				ui.answerYes = false;
 				handleAskNo();
 			}
 		}
@@ -3641,7 +3642,7 @@
 	// if MOD2WAV is ongoing, only react to ESC and Y/N on exit ask dialog
 	if (editor.isWAVRendering)
 	{
-		if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_QUIT)
+		if (ui.askScreenShown && ui.askScreenType == ASK_QUIT)
 		{
 			if (keycode == SDLK_y)
 			{
@@ -3648,17 +3649,17 @@
 				editor.isWAVRendering = false;
 				SDL_WaitThread(editor.mod2WavThread, NULL);
 
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
+				ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
 
 				handleAskYes();
 			}
 			else if (keycode == SDLK_n)
 			{
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = true;
-				editor.ui.answerYes = false;
+				ui.askScreenShown = false;
+				ui.answerNo = true;
+				ui.answerYes = false;
 
 				handleAskNo();
 
@@ -3691,7 +3692,7 @@
 			{
 				for (i = 0; i < MOD_ROWS; i++)
 				{
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					noteTmp = modEntry->patterns[modEntry->currPattern][i * AMIGA_VOICES];
 
 					modEntry->patterns[modEntry->currPattern][i * AMIGA_VOICES] = *noteSrc;
@@ -3709,7 +3710,7 @@
 			{
 				for (i = 0; i < MOD_ROWS; i++)
 				{
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					noteTmp = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 1];
 
 					modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 1] = *noteSrc;
@@ -3727,7 +3728,7 @@
 			{
 				for (i = 0; i < MOD_ROWS; i++)
 				{
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					noteTmp = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 2];
 
 					modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 2] = *noteSrc;
@@ -3745,7 +3746,7 @@
 			{
 				for (i = 0; i < MOD_ROWS; i++)
 				{
-					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+					noteSrc = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 					noteTmp = modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 3];
 
 					modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + 3] = *noteSrc;
@@ -3766,9 +3767,9 @@
 	}
 
 	// YES/NO ASK DIALOG
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		if (editor.ui.pat2SmpDialogShown)
+		if (ui.pat2SmpDialogShown)
 		{
 			// PAT2SMP specific ask dialog
 			switch (keycode)
@@ -3777,9 +3778,9 @@
 				case SDLK_RETURN:
 				case SDLK_h:
 				{
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = true;
-					editor.ui.answerYes = false;
+					ui.askScreenShown = false;
+					ui.answerNo = true;
+					ui.answerYes = false;
 					editor.pat2SmpHQ = true;
 					handleAskYes();
 				}
@@ -3787,9 +3788,9 @@
 
 				case SDLK_l:
 				{
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = false;
-					editor.ui.answerYes = true;
+					ui.askScreenShown = false;
+					ui.answerNo = false;
+					ui.answerYes = true;
 					editor.pat2SmpHQ = false;
 					handleAskYes();
 					// pointer/status is updated by the 'yes handler'
@@ -3800,9 +3801,9 @@
 				case SDLK_a:
 				case SDLK_n:
 				{
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = true;
-					editor.ui.answerYes = false;
+					ui.askScreenShown = false;
+					ui.answerNo = true;
+					ui.answerYes = false;
 					handleAskNo();
 				}
 				break;
@@ -3818,9 +3819,9 @@
 				case SDLK_ESCAPE:
 				case SDLK_n:
 				{
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = true;
-					editor.ui.answerYes = false;
+					ui.askScreenShown = false;
+					ui.answerNo = true;
+					ui.answerYes = false;
 					handleAskNo();
 				}
 				break;
@@ -3829,9 +3830,9 @@
 				case SDLK_RETURN:
 				case SDLK_y:
 				{
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = false;
-					editor.ui.answerYes = true;
+					ui.askScreenShown = false;
+					ui.answerNo = false;
+					ui.answerYes = true;
 					handleAskYes();
 					// pointer/status is updated by the 'yes handler'
 				}
@@ -3845,13 +3846,13 @@
 	}
 
 	// CLEAR SCREEN DIALOG
-	if (editor.ui.clearScreenShown)
+	if (ui.clearScreenShown)
 	{
 		switch (keycode)
 		{
 			case SDLK_s:
 			{
-				editor.ui.clearScreenShown = false;
+				ui.clearScreenShown = false;
 				removeClearScreen();
 
 				modStop();
@@ -3867,7 +3868,7 @@
 
 			case SDLK_o:
 			{
-				editor.ui.clearScreenShown = false;
+				ui.clearScreenShown = false;
 				removeClearScreen();
 
 				modStop();
@@ -3883,7 +3884,7 @@
 
 			case SDLK_a:
 			{
-				editor.ui.clearScreenShown = false;
+				ui.clearScreenShown = false;
 				removeClearScreen();
 
 				modStop();
@@ -3900,7 +3901,7 @@
 			case SDLK_c:
 			case SDLK_ESCAPE:
 			{
-				editor.ui.clearScreenShown = false;
+				ui.clearScreenShown = false;
 				removeClearScreen();
 
 				editor.currMode = MODE_IDLE;
@@ -3936,50 +3937,50 @@
 	if (textChar < ' ' || textChar > '~')
 		return;
 
-	// a..z -> A..Z
-	if (textChar >= 'a' && textChar <= 'z')
-		textChar = toupper(textChar);
+	// A..Z -> a..z
+	if (textChar >= 'A' && textChar <= 'Z')
+		textChar = (char)tolower(textChar);
 
-	if (editor.ui.editTextType == TEXT_EDIT_STRING)
+	if (ui.editTextType == TEXT_EDIT_STRING)
 	{
-		if (editor.ui.editPos < editor.ui.textEndPtr)
+		if (ui.editPos < ui.textEndPtr)
 		{
 			if (!editor.mixFlag)
 			{
-				readTmp = editor.ui.textEndPtr;
-				while (readTmp > editor.ui.editPos)
+				readTmp = ui.textEndPtr;
+				while (readTmp > ui.editPos)
 				{
 					readTmpPrev = *--readTmp;
 					*(readTmp + 1) = readTmpPrev;
 				}
 
-				*editor.ui.textEndPtr = '\0';
-				*editor.ui.editPos++ = textChar;
+				*ui.textEndPtr = '\0';
+				*ui.editPos++ = textChar;
 
 				textMarkerMoveRight();
 			}
 			else if ((textChar >= '0' && textChar <= '9') || (textChar >= 'A' && textChar <= 'F'))
 			{
-				if (editor.ui.dstPos == 14) // hack for sample mix text
+				if (ui.dstPos == 14) // hack for sample mix text
 				{
-					*editor.ui.editPos = textChar;
+					*ui.editPos = textChar;
 				}
 				else
 				{
-					*editor.ui.editPos++ = textChar;
+					*ui.editPos++ = textChar;
 					textMarkerMoveRight();
 
-					if (editor.ui.dstPos == 9) // hack for sample mix text
+					if (ui.dstPos == 9) // hack for sample mix text
 					{
 						for (i = 0; i < 4; i++)
 						{
-							editor.ui.editPos++;
+							ui.editPos++;
 							textMarkerMoveRight();
 						}
 					}
-					else if (editor.ui.dstPos == 6) // hack for sample mix text
+					else if (ui.dstPos == 6) // hack for sample mix text
 					{
-						editor.ui.editPos++;
+						ui.editPos++;
 						textMarkerMoveRight();
 					}
 				}
@@ -3988,79 +3989,79 @@
 	}
 	else
 	{
-		if (editor.ui.editTextType == TEXT_EDIT_DECIMAL)
+		if (ui.editTextType == TEXT_EDIT_DECIMAL)
 		{
 			if (textChar >= '0' && textChar <= '9')
 			{
 				textChar -= '0';
 
-				if (editor.ui.numLen == 4)
+				if (ui.numLen == 4)
 				{
-					number = *editor.ui.numPtr16;
+					number = *ui.numPtr16;
 					digit4 = number % 10; number /= 10;
 					digit3 = number % 10; number /= 10;
 					digit2 = number % 10; number /= 10;
 					digit1 = (uint8_t)number;
 
-					     if (editor.ui.dstPos == 0) *editor.ui.numPtr16 = (textChar * 1000) + (digit2 * 100) + (digit3 * 10) + digit4;
-					else if (editor.ui.dstPos == 1) *editor.ui.numPtr16 = (digit1 * 1000) + (textChar * 100) + (digit3 * 10) + digit4;
-					else if (editor.ui.dstPos == 2) *editor.ui.numPtr16 = (digit1 * 1000) + (digit2 * 100) + (textChar * 10) + digit4;
-					else if (editor.ui.dstPos == 3) *editor.ui.numPtr16 = (digit1 * 1000) + (digit2 * 100) + (digit3 * 10) + textChar;
+					     if (ui.dstPos == 0) *ui.numPtr16 = (textChar * 1000) + (digit2 * 100) + (digit3 * 10) + digit4;
+					else if (ui.dstPos == 1) *ui.numPtr16 = (digit1 * 1000) + (textChar * 100) + (digit3 * 10) + digit4;
+					else if (ui.dstPos == 2) *ui.numPtr16 = (digit1 * 1000) + (digit2 * 100) + (textChar * 10) + digit4;
+					else if (ui.dstPos == 3) *ui.numPtr16 = (digit1 * 1000) + (digit2 * 100) + (digit3 * 10) + textChar;
 				}
-				else if (editor.ui.numLen == 3)
+				else if (ui.numLen == 3)
 				{
-					number = *editor.ui.numPtr16;
+					number = *ui.numPtr16;
 					digit3 = number % 10; number /= 10;
 					digit2 = number % 10; number /= 10;
 					digit1 = (uint8_t)number;
 
-					     if (editor.ui.dstPos == 0) *editor.ui.numPtr16 = (textChar * 100) + (digit2 * 10) + digit3;
-					else if (editor.ui.dstPos == 1) *editor.ui.numPtr16 = (digit1 * 100) + (textChar * 10) + digit3;
-					else if (editor.ui.dstPos == 2) *editor.ui.numPtr16 = (digit1 * 100) + (digit2 * 10) + textChar;
+					     if (ui.dstPos == 0) *ui.numPtr16 = (textChar * 100) + (digit2 * 10) + digit3;
+					else if (ui.dstPos == 1) *ui.numPtr16 = (digit1 * 100) + (textChar * 10) + digit3;
+					else if (ui.dstPos == 2) *ui.numPtr16 = (digit1 * 100) + (digit2 * 10) + textChar;
 				}
-				else if (editor.ui.numLen == 2)
+				else if (ui.numLen == 2)
 				{
-					number = *editor.ui.numPtr16;
+					number = *ui.numPtr16;
 					digit2 = number % 10; number /= 10;
 					digit1 = (uint8_t)number;
 
-					     if (editor.ui.dstPos == 0) *editor.ui.numPtr16 = (textChar * 10) + digit2;
-					else if (editor.ui.dstPos == 1) *editor.ui.numPtr16 = (digit1 * 10) + textChar;
+					     if (ui.dstPos == 0) *ui.numPtr16 = (textChar * 10) + digit2;
+					else if (ui.dstPos == 1) *ui.numPtr16 = (digit1 * 10) + textChar;
 				}
 
 				textMarkerMoveRight();
-				if (editor.ui.dstPos >= editor.ui.numLen)
+				if (ui.dstPos >= ui.numLen)
 					exitGetTextLine(EDIT_TEXT_UPDATE);
 			}
 		}
 		else
 		{
-			if ((textChar >= '0' && textChar <= '9') || (textChar >= 'A' && textChar <= 'F'))
+			if ((textChar >= '0' && textChar <= '9') || (textChar >= 'a' && textChar <= 'f'))
 			{
 				if (textChar <= '9')
 					textChar -= '0';
-				else if (textChar <= 'F')
-					textChar -= 'A'-10;
+				else if (textChar <= 'f')
+					textChar -= 'a'-10;
 
-				if (editor.ui.numBits == 16)
+				if (ui.numBits == 16)
 				{
-					*editor.ui.numPtr16 &= ~(0xF000 >> (editor.ui.dstPos << 2));
-					*editor.ui.numPtr16 |= (textChar << (12 - (editor.ui.dstPos << 2)));
+					*ui.numPtr16 &= ~(0xF000 >> (ui.dstPos << 2));
+					*ui.numPtr16 |= (textChar << (12 - (ui.dstPos << 2)));
 				}
-				else if (editor.ui.numBits == 8)
+				else if (ui.numBits == 8)
 				{
-					*editor.ui.numPtr8 &= ~(0xF0 >> (editor.ui.dstPos << 2));
-					*editor.ui.numPtr8 |= (textChar << (4 - (editor.ui.dstPos << 2)));
+					*ui.numPtr8 &= ~(0xF0 >> (ui.dstPos << 2));
+					*ui.numPtr8 |= (textChar << (4 - (ui.dstPos << 2)));
 				}
 
 				textMarkerMoveRight();
-				if (editor.ui.dstPos >= editor.ui.numLen)
+				if (ui.dstPos >= ui.numLen)
 					exitGetTextLine(EDIT_TEXT_UPDATE);
 			}
 		}
 	}
 
-	updateTextObject(editor.ui.editObject);
+	updateTextObject(ui.editObject);
 
 	if (!keyb.repeatKey)
 		keyb.delayCounter = 0;
@@ -4081,7 +4082,7 @@
 		case SDL_SCANCODE_ESCAPE:
 		{
 			editor.blockMarkFlag = false;
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				exitGetTextLine(EDIT_TEXT_NO_UPDATE);
 				return false;
@@ -4091,9 +4092,9 @@
 
 		case SDL_SCANCODE_HOME:
 		{
-			if (editor.ui.editTextFlag && !editor.mixFlag)
+			if (ui.editTextFlag && !editor.mixFlag)
 			{
-				while (editor.ui.editPos > editor.ui.showTextPtr)
+				while (ui.editPos > ui.showTextPtr)
 					textCharPrevious();
 			}
 		}
@@ -4101,12 +4102,12 @@
 
 		case SDL_SCANCODE_END:
 		{
-			if (editor.ui.editTextFlag && !editor.mixFlag)
+			if (ui.editTextFlag && !editor.mixFlag)
 			{
-				if (editor.ui.editTextType != TEXT_EDIT_STRING)
+				if (ui.editTextType != TEXT_EDIT_STRING)
 					break;
 
-				while (!editor.ui.dstOffsetEnd)
+				while (!ui.dstOffsetEnd)
 					textCharNext();
 			}
 		}
@@ -4114,7 +4115,7 @@
 
 		case SDL_SCANCODE_LEFT:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				textCharPrevious();
 				if (!keyb.repeatKey)
@@ -4133,7 +4134,7 @@
 
 		case SDL_SCANCODE_RIGHT:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
 				textCharNext();
 				if (!keyb.repeatKey)
@@ -4152,13 +4153,13 @@
 
 		case SDL_SCANCODE_DELETE:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
-				if (editor.mixFlag || editor.ui.editTextType != TEXT_EDIT_STRING)
+				if (editor.mixFlag || ui.editTextType != TEXT_EDIT_STRING)
 					break;
 
-				readTmp = editor.ui.editPos;
-				while (readTmp < editor.ui.textEndPtr)
+				readTmp = ui.editPos;
+				while (readTmp < ui.textEndPtr)
 				{
 					readTmpNext = *(readTmp + 1);
 					*readTmp++ = readTmpNext;
@@ -4165,8 +4166,8 @@
 				}
 
 				// kludge to prevent cloning last character if the song/sample name has one character too much
-				if (editor.ui.editObject == PTB_SONGNAME || editor.ui.editObject == PTB_SAMPLENAME)
-					 *editor.ui.textEndPtr = '\0';
+				if (ui.editObject == PTB_SONGNAME || ui.editObject == PTB_SAMPLENAME)
+					 *ui.textEndPtr = '\0';
 
 				if (!keyb.repeatKey)
 					keyb.delayCounter = 0;
@@ -4174,7 +4175,7 @@
 				keyb.repeatKey = true;
 				keyb.delayKey = false;
 
-				updateTextObject(editor.ui.editObject);
+				updateTextObject(ui.editObject);
 			}
 		}
 		break;
@@ -4181,17 +4182,17 @@
 
 		case SDL_SCANCODE_BACKSPACE:
 		{
-			if (editor.ui.editTextFlag)
+			if (ui.editTextFlag)
 			{
-				if (editor.mixFlag || editor.ui.editTextType != TEXT_EDIT_STRING)
+				if (editor.mixFlag || ui.editTextType != TEXT_EDIT_STRING)
 					break;
 
-				if (editor.ui.editPos > editor.ui.dstPtr)
+				if (ui.editPos > ui.dstPtr)
 				{
-					editor.ui.editPos--;
+					ui.editPos--;
 
-					readTmp = editor.ui.editPos;
-					while (readTmp < editor.ui.textEndPtr)
+					readTmp = ui.editPos;
+					while (readTmp < ui.textEndPtr)
 					{
 						readTmpNext = *(readTmp + 1);
 						*readTmp++ = readTmpNext;
@@ -4198,11 +4199,11 @@
 					}
 
 					// kludge to prevent cloning last character if the song/sample name has one character too much
-					if (editor.ui.editObject == PTB_SONGNAME || editor.ui.editObject == PTB_SAMPLENAME)
-						*editor.ui.textEndPtr = '\0';
+					if (ui.editObject == PTB_SONGNAME || ui.editObject == PTB_SAMPLENAME)
+						*ui.textEndPtr = '\0';
 
 					textMarkerMoveLeft();
-					updateTextObject(editor.ui.editObject);
+					updateTextObject(ui.editObject);
 				}
 
 				if (!keyb.repeatKey)
@@ -4213,7 +4214,7 @@
 			}
 			else
 			{
-				if (editor.ui.diskOpScreenShown)
+				if (ui.diskOpScreenShown)
 				{
 #ifdef _WIN32
 					diskOpSetPath(L"..", DISKOP_CACHE);
@@ -4245,7 +4246,7 @@
 							}
 
 							modEntry->currRow--;
-							editor.ui.updatePatternData = true;
+							ui.updatePatternData = true;
 						}
 					}
 					else
@@ -4254,8 +4255,8 @@
 						{
 							for (i = modEntry->currRow-1; i < MOD_ROWS-1; i++)
 							{
-								noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + editor.cursor.channel];
-								noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + editor.cursor.channel];
+								noteSrc = &modEntry->patterns[modEntry->currPattern][((i + 1) * AMIGA_VOICES) + cursor.channel];
+								noteDst = &modEntry->patterns[modEntry->currPattern][(i * AMIGA_VOICES) + cursor.channel];
 
 								if (keyb.leftCtrlPressed)
 								{
@@ -4269,7 +4270,7 @@
 							}
 
 							// clear newly made row on very bottom
-							noteDst = &modEntry->patterns[modEntry->currPattern][(63 * AMIGA_VOICES) + editor.cursor.channel];
+							noteDst = &modEntry->patterns[modEntry->currPattern][(63 * AMIGA_VOICES) + cursor.channel];
 							noteDst->period = 0;
 							noteDst->sample = 0;
 							noteDst->command = 0;
@@ -4276,7 +4277,7 @@
 							noteDst->param = 0;
 
 							modEntry->currRow--;
-							editor.ui.updatePatternData = true;
+							ui.updatePatternData = true;
 						}
 					}
 				}
@@ -4295,13 +4296,13 @@
 		default: break;
 	}
 
-	if (editor.ui.editTextFlag)
+	if (ui.editTextFlag)
 	{
 		if (scancode == SDL_SCANCODE_RETURN || scancode == SDL_SCANCODE_KP_ENTER)
 		{
 			// dirty hack
-			if (editor.ui.editObject == PTB_SAMPLES)
-				editor.ui.tmpDisp8++;
+			if (ui.editObject == PTB_SAMPLES)
+				ui.tmpDisp8++;
 
 			exitGetTextLine(EDIT_TEXT_UPDATE);
 
@@ -4308,7 +4309,7 @@
 			if (editor.mixFlag)
 			{
 				editor.mixFlag = false;
-				editor.ui.updateMixText = true;
+				ui.updateMixText = true;
 				doMix();
 			}
 		}
--- a/src/pt2_keyboard.h
+++ b/src/pt2_keyboard.h
@@ -17,6 +17,6 @@
 void keyDownHandler(SDL_Scancode scancode, SDL_Keycode keycode);
 void handleTextEditInputChar(char textChar);
 
-#ifdef _WIN32
+#if defined _WIN32 && !defined _DEBUG
 LRESULT CALLBACK lowLevelKeyboardProc(int32_t nCode, WPARAM wParam, LPARAM lParam);
 #endif
--- a/src/pt2_main.c
+++ b/src/pt2_main.c
@@ -35,8 +35,8 @@
 #include "pt2_audio.h"
 
 #define CRASH_TEXT "Oh no!\nThe ProTracker 2 clone has crashed...\n\nA backup .mod was hopefully " \
-                   "saved to the current module directory.\n\nPlease report this to 8bitbubsy " \
-                   "(IRC or olav.sorensen@live.no).\nTry to mention what you did before the crash happened."
+                   "saved to the current module directory.\n\nPlease report this bug if you can.\n" \
+                   "Try to mention what you did before the crash happened."
 
 module_t *modEntry = NULL; // globalized
 
@@ -46,9 +46,11 @@
 #define SYSMSG_FILE_ARG (WM_USER + 1)
 #define ARGV_SHARED_MEM_MAX_LEN ((MAX_PATH * 2) + 2)
 
-// for taking control over windows key and numlock on keyboard if app has focus
+#ifndef _DEBUG
 bool windowsKeyIsDown;
 HHOOK g_hKeyboardHook;
+#endif
+
 static HWND hWnd_to;
 static HANDLE oneInstHandle, hMapFile;
 static LPCTSTR sharedMemBuf;
@@ -125,8 +127,7 @@
 #ifdef _WIN32
 		showErrorMsgBox("SDL2.dll is not the expected version, the program will terminate.\n\n" \
 		                "Loaded dll version: %d.%d.%d\n" \
-		                "Required (compiled with) version: %d.%d.%d\n\n" \
-		                "The needed SDL2.dll is located in the .zip from 16-bits.org/pt2.php\n",
+		                "Required (compiled with) version: %d.%d.%d",
 		                sdlVer.major, sdlVer.minor, sdlVer.patch,
 		                SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL);
 #else
@@ -196,9 +197,11 @@
 #endif
 
 #ifdef _WIN32
-	// for taking control over windows key and numlock on keyboard if app has focus
+
+#ifndef _DEBUG
 	windowsKeyIsDown = false;
 	g_hKeyboardHook = SetWindowsHookEx(WH_KEYBOARD_LL, lowLevelKeyboardProc, GetModuleHandle(NULL), 0);
+#endif
 
 	makeSureDirIsProgramDir();
 #endif
@@ -305,8 +308,8 @@
 		updateMouseCounters();
 		handleKeyRepeat(keyb.lastRepKey);
 
-		if (!mouse.buttonWaiting && editor.ui.sampleMarkingPos == -1 &&
-			!editor.ui.forceSampleDrag && !editor.ui.forceVolDrag && !editor.ui.forceSampleEdit)
+		if (!mouse.buttonWaiting && ui.sampleMarkingPos == -1 &&
+			!ui.forceSampleDrag && !ui.forceVolDrag && !ui.forceSampleEdit)
 		{
 			handleGUIButtonRepeat();
 		}
@@ -353,7 +356,7 @@
 #ifdef _WIN32
 		handleSysMsg(event);
 #endif
-		if (editor.ui.editTextFlag && event.type == SDL_TEXTINPUT)
+		if (ui.editTextFlag && event.type == SDL_TEXTINPUT)
 		{
 			// text input when editing texts/numbers
 
@@ -392,34 +395,34 @@
 		{
 			mouseButtonUpHandler(event.button.button);
 
-			if (!editor.ui.askScreenShown && editor.ui.introScreenShown)
+			if (!ui.askScreenShown && ui.introScreenShown)
 			{
-				if (!editor.ui.clearScreenShown && !editor.ui.diskOpScreenShown)
+				if (!ui.clearScreenShown && !ui.diskOpScreenShown)
 					statusAllRight();
 
-				editor.ui.introScreenShown = false;
+				ui.introScreenShown = false;
 			}
 		}
 		else if (event.type == SDL_MOUSEBUTTONDOWN)
 		{
-			if (editor.ui.sampleMarkingPos == -1 &&
-				!editor.ui.forceSampleDrag && !editor.ui.forceVolDrag &&
-				!editor.ui.forceSampleEdit)
+			if (ui.sampleMarkingPos == -1 &&
+				!ui.forceSampleDrag && !ui.forceVolDrag &&
+				!ui.forceSampleEdit)
 			{
 				mouseButtonDownHandler(event.button.button);
 			}
 		}
 
-		if (editor.ui.throwExit)
+		if (ui.throwExit)
 		{
 			editor.programRunning = false;
 
-			if (editor.diskop.isFilling)
+			if (diskop.isFilling)
 			{
-				editor.diskop.isFilling = false;
+				diskop.isFilling = false;
 
-				editor.diskop.forceStopReading = true;
-				SDL_WaitThread(editor.diskop.fillThread, NULL);
+				diskop.forceStopReading = true;
+				SDL_WaitThread(diskop.fillThread, NULL);
 			}
 
 			if (editor.isWAVRendering)
@@ -504,11 +507,11 @@
 	editor.multiModeNext[1] = 3;
 	editor.multiModeNext[2] = 4;
 	editor.multiModeNext[3] = 1;
-	editor.ui.introScreenShown = true;
+	ui.introScreenShown = true;
 	editor.normalizeFiltersFlag = true;
 	editor.markStartOfs = -1;
-	editor.ui.sampleMarkingPos = -1;
-	editor.ui.previousPointerMode = editor.ui.pointerMode;
+	ui.sampleMarkingPos = -1;
+	ui.previousPointerMode = ui.pointerMode;
 
 	// setup GUI text pointers
 	editor.vol1Disp = &editor.vol1;
@@ -546,8 +549,8 @@
 			SDL_RaiseWindow(video.window);
 		}
 
-		editor.ui.askScreenShown = true;
-		editor.ui.askScreenType = ASK_QUIT;
+		ui.askScreenShown = true;
+		ui.askScreenType = ASK_QUIT;
 
 		pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 		setStatusMessage("REALLY QUIT ?", NO_CARRY);
@@ -555,7 +558,7 @@
 	}
 	else
 	{
-		editor.ui.throwExit = true;
+		ui.throwExit = true;
 	}
 }
 
@@ -874,7 +877,9 @@
 
 #ifdef _WIN32
 	freeWin32Usleep();
+#ifndef _DEBUG
 	UnhookWindowsHookEx(g_hKeyboardHook);
+#endif
 	if (oneInstHandle != NULL) CloseHandle(oneInstHandle);
 #endif
 }
--- a/src/pt2_mod2wav.c
+++ b/src/pt2_mod2wav.c
@@ -13,6 +13,7 @@
 #include "pt2_textout.h"
 #include "pt2_visuals.h"
 #include "pt2_mod2wav.h"
+#include "pt2_structs.h"
 
 #define TICKS_PER_RENDER_CHUNK 32
 
@@ -75,7 +76,7 @@
 			if (++loopCounter >= 8)
 			{
 				loopCounter = 0;
-				editor.ui.updateMod2WavDialog = true;
+				ui.updateMod2WavDialog = true;
 			}
 		}
 
@@ -112,8 +113,8 @@
 	fwrite(&wavHeader, sizeof (wavHeader_t), 1, f);
 	fclose(f);
 
-	editor.ui.mod2WavFinished = true;
-	editor.ui.updateMod2WavDialog = true;
+	ui.mod2WavFinished = true;
+	ui.updateMod2WavDialog = true;
 
 	return true;
 }
@@ -127,8 +128,8 @@
 	{
 		if (stat(fileName, &statBuffer) == 0)
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_MOD2WAV_OVERWRITE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_MOD2WAV_OVERWRITE;
 
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("OVERWRITE FILE?", NO_CARRY);
@@ -139,11 +140,11 @@
 		}
 	}
 
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		editor.ui.askScreenShown = false;
-		editor.ui.answerNo = false;
-		editor.ui.answerYes = false;
+		ui.askScreenShown = false;
+		ui.answerNo = false;
+		ui.answerYes = false;
 	}
 
 	fOut = fopen(fileName, "wb");
@@ -171,7 +172,7 @@
 	pointerSetMode(POINTER_MODE_MSG2, NO_CARRY);
 	setStatusMessage("RENDERING MOD...", NO_CARRY);
 
-	editor.ui.disableVisualizer = true;
+	ui.disableVisualizer = true;
 	editor.isWAVRendering = true;
 	renderMOD2WAVDialog();
 
@@ -188,7 +189,7 @@
 	{
 		free(mod2WavBuffer);
 
-		editor.ui.disableVisualizer = false;
+		ui.disableVisualizer = false;
 		editor.isWAVRendering = false;
 
 		displayErrorMsg("THREAD ERROR");
--- a/src/pt2_modloader.c
+++ b/src/pt2_modloader.c
@@ -49,8 +49,8 @@
 
 void showSongUnsavedAskBox(int8_t askScreenType)
 {
-	editor.ui.askScreenShown = true;
-	editor.ui.askScreenType = askScreenType;
+	ui.askScreenShown = true;
+	ui.askScreenType = askScreenType;
 
 	pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 	setStatusMessage("SONG IS UNSAVED !", NO_CARRY);
@@ -158,9 +158,9 @@
 	displayMsg("MODULE SAVED !");
 	setMsgPointer();
 
-	editor.diskop.cached = false;
-	if (editor.ui.diskOpScreenShown)
-		editor.ui.updateDiskOpFileList = true;
+	diskop.cached = false;
+	if (ui.diskOpScreenShown)
+		ui.updateDiskOpFileList = true;
 
 	updateWindowTitle(MOD_NOT_MODIFIED);
 	return true;
@@ -419,7 +419,7 @@
 			fixZeroesInString(s->text, 22);
 		}
 
-		s->length = ((mgetc(m) << 8) | mgetc(m)) * 2;
+		s->length = (uint16_t)(((mgetc(m) << 8) | mgetc(m)) * 2);
 
 		/* Only late versions of Ultimate SoundTracker could have samples larger than 9999 bytes.
 		** If found, we know for sure that this is a late STK module.
@@ -758,7 +758,7 @@
 			loopOverflowVal = (s->loopStart + s->loopLength) - s->length;
 			if (s->length+loopOverflowVal <= MAX_SAMPLE_LEN)
 			{
-				s->length += loopOverflowVal; // this is safe, we're allocating 65534 bytes per sample slot
+				s->length = (uint16_t)(s->length + loopOverflowVal); // this is safe, we're allocating 65534 bytes per sample slot
 			}
 			else
 			{
@@ -772,7 +772,7 @@
 	free(modBuffer);
 
 	for (i = 0; i < AMIGA_VOICES; i++)
-		newMod->channels[i].n_chanindex = i;
+		newMod->channels[i].n_chanindex = (int8_t)i;
 
 	return newMod;
 
@@ -893,8 +893,8 @@
 	{
 		if (stat(fileName, &statBuffer) == 0)
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_SAVEMOD_OVERWRITE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_SAVEMOD_OVERWRITE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("OVERWRITE FILE ?", NO_CARRY);
 			renderAskDialog();
@@ -902,11 +902,11 @@
 		}
 	}
 
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		editor.ui.answerNo = false;
-		editor.ui.answerYes = false;
-		editor.ui.askScreenShown = false;
+		ui.answerNo = false;
+		ui.answerYes = false;
+		ui.askScreenShown = false;
 	}
 
 	return modSave(fileName);
@@ -1013,7 +1013,7 @@
 			buf->_eof = true;
 		}
 
-		buf->_cnt = (buf->_base + buf->_bufsiz) - buf->_ptr;
+		buf->_cnt = (uint32_t)((buf->_base + buf->_bufsiz) - buf->_ptr);
 	}
 }
 
@@ -1154,7 +1154,7 @@
 	editor.currLengthDisp = &modEntry->head.orderCount;
 
 	// calculate MOD size
-	editor.ui.updateSongSize = true;
+	ui.updateSongSize = true;
 
 	editor.muted[0] = false;
 	editor.muted[1] = false;
@@ -1188,7 +1188,7 @@
 	uint32_t filenameLen;
 	UNICHAR *filenameU;
 
-	editor.ui.introScreenShown = false;
+	ui.introScreenShown = false;
 	statusAllRight();
 
 	filenameLen = (uint32_t)strlen(arg);
@@ -1265,8 +1265,8 @@
 	UNICHAR *fullPathU;
 
 	// don't allow drag n' drop if the tracker is busy
-	if (editor.ui.pointerMode == POINTER_MODE_MSG1 || editor.diskop.isFilling ||
-		editor.isWAVRendering || editor.ui.samplerFiltersBoxShown || editor.ui.samplerVolBoxShown)
+	if (ui.pointerMode == POINTER_MODE_MSG1 || diskop.isFilling ||
+		editor.isWAVRendering || ui.samplerFiltersBoxShown || ui.samplerVolBoxShown)
 	{
 		return;
 	}
@@ -1450,7 +1450,7 @@
 	editor.currPosEdPattDisp = &newMod->head.order[0];
 	editor.currLengthDisp = &newMod->head.orderCount;
 
-	editor.ui.updateSongSize = true;
+	ui.updateSongSize = true;
 	return newMod;
 
 oom:
--- a/src/pt2_modloader.h
+++ b/src/pt2_modloader.h
@@ -4,6 +4,7 @@
 #include <stdbool.h>
 #include "pt2_header.h"
 #include "pt2_unicode.h"
+#include "pt2_structs.h"
 
 void showSongUnsavedAskBox(int8_t askScreenType);
 void loadModFromArg(char *arg);
--- a/src/pt2_modplayer.c
+++ b/src/pt2_modplayer.c
@@ -88,11 +88,10 @@
 
 void setPattern(int16_t pattern)
 {
-	modPattern = pattern;
-	if (modPattern > MAX_PATTERNS-1)
-		modPattern = MAX_PATTERNS-1;
+	if (pattern > MAX_PATTERNS-1)
+		pattern = MAX_PATTERNS-1;
 
-	modEntry->currPattern = modPattern;
+	modEntry->currPattern = modPattern = (int8_t)pattern;
 }
 
 void storeTempVariables(void) // this one is accessed in other files, so non-static
@@ -306,7 +305,7 @@
 static void volumeChange(moduleChannel_t *ch)
 {
 	ch->n_volume = ch->n_cmd & 0xFF;
-	if ((uint8_t)ch->n_volume > 64) /* unsigned comparison is important here */
+	if ((uint8_t)ch->n_volume > 64)
 		ch->n_volume = 64;
 }
 
@@ -313,7 +312,7 @@
 static void patternBreak(moduleChannel_t *ch)
 {
 	pBreakPosition = (((ch->n_cmd & 0xF0) >> 4) * 10) + (ch->n_cmd & 0x0F);
-	if ((uint8_t)pBreakPosition > 63) /* unsigned comparison is important here */
+	if ((uint8_t)pBreakPosition > 63)
 		pBreakPosition = 0;
 
 	posJumpAssert = true;
@@ -350,7 +349,7 @@
 
 	if (arpTick == 1)
 	{
-		arpNote = ch->n_cmd >> 4;
+		arpNote = (uint8_t)(ch->n_cmd >> 4);
 	}
 	else if (arpTick == 2)
 	{
@@ -940,7 +939,7 @@
 
 				modEntry->currOrder = 0;
 				modEntry->currRow = modEntry->row = 0;
-				modEntry->currPattern = modPattern = modEntry->head.order[0];
+				modEntry->currPattern = modPattern = (int8_t)modEntry->head.order[0];
 
 				editor.currPatternDisp = &modEntry->currPattern;
 				editor.currPosEdPattDisp = &modEntry->currPattern;
@@ -947,16 +946,16 @@
 				editor.currPatternDisp = &modEntry->currPattern;
 				editor.currPosEdPattDisp = &modEntry->currPattern;
 
-				if (editor.ui.posEdScreenShown)
-					editor.ui.updatePosEd = true;
+				if (ui.posEdScreenShown)
+					ui.updatePosEd = true;
 
-				editor.ui.updateSongPos = true;
-				editor.ui.updateSongPattern = true;
-				editor.ui.updateCurrPattText = true;
+				ui.updateSongPos = true;
+				ui.updateSongPattern = true;
+				ui.updateCurrPattText = true;
 			}
 		}
 
-		modPattern = modEntry->head.order[modOrder];
+		modPattern = (int8_t)modEntry->head.order[modOrder];
 		if (modPattern > MAX_PATTERNS-1)
 			modPattern = MAX_PATTERNS-1;
 
@@ -990,12 +989,12 @@
 				editor.currPatternDisp = patt;
 				editor.currPosEdPattDisp = patt;
 
-				if (editor.ui.posEdScreenShown)
-					editor.ui.updatePosEd = true;
+				if (ui.posEdScreenShown)
+					ui.updatePosEd = true;
 
-				editor.ui.updateSongPos = true;
-				editor.ui.updateSongPattern = true;
-				editor.ui.updateCurrPattText = true;
+				ui.updateSongPos = true;
+				ui.updateSongPattern = true;
+				ui.updateCurrPattText = true;
 			}
 		}
 	}
@@ -1040,7 +1039,7 @@
 		if (!editor.isWAVRendering && !editor.isSMPRendering)
 		{
 			modEntry->currRow = modEntry->row;
-			editor.ui.updatePatternData = true;
+			ui.updatePatternData = true;
 		}
 
 		if (!editor.stepPlayBackwards)
@@ -1069,7 +1068,7 @@
 		}
 
 		if (editor.blockMarkFlag)
-			editor.ui.updateStatusText = true;
+			ui.updateStatusText = true;
 
 		if (editor.stepPlayEnabled)
 		{
@@ -1076,11 +1075,11 @@
 			doStopIt(true);
 
 			modEntry->currRow = modEntry->row & 0x3F;
-			editor.ui.updatePatternData = true;
+			ui.updatePatternData = true;
 
 			editor.stepPlayEnabled = false;
 			editor.stepPlayBackwards = false;
-			editor.ui.updatePatternData = true;
+			ui.updatePatternData = true;
 
 			return true;
 		}
@@ -1118,7 +1117,7 @@
 {
 	modPattern = pattern;
 	modEntry->currPattern = modPattern;
-	editor.ui.updateCurrPattText = true;
+	ui.updateCurrPattText = true;
 }
 
 void modSetPos(int16_t order, int16_t row)
@@ -1140,19 +1139,19 @@
 		{
 			modOrder = order;
 			modEntry->currOrder = order;
-			editor.ui.updateSongPos = true;
+			ui.updateSongPos = true;
 
 			if (editor.currMode == MODE_PLAY && editor.playMode == PLAY_MODE_NORMAL)
 			{
-				modPattern = modEntry->head.order[order];
+				modPattern = (int8_t)modEntry->head.order[order];
 				if (modPattern > MAX_PATTERNS-1)
 					modPattern = MAX_PATTERNS-1;
 
 				modEntry->currPattern = modPattern;
-				editor.ui.updateCurrPattText = true;
+				ui.updateCurrPattText = true;
 			}
 
-			editor.ui.updateSongPattern = true;
+			ui.updateSongPattern = true;
 			editor.currPatternDisp = &modEntry->head.order[modOrder];
 
 			posEdPos = modEntry->currOrder;
@@ -1161,15 +1160,15 @@
 
 			editor.currPosEdPattDisp = &modEntry->head.order[posEdPos];
 
-			if (editor.ui.posEdScreenShown)
-				editor.ui.updatePosEd = true;
+			if (ui.posEdScreenShown)
+				ui.updatePosEd = true;
 		}
 	}
 
-	editor.ui.updatePatternData = true;
+	ui.updatePatternData = true;
 
 	if (editor.blockMarkFlag)
-		editor.ui.updateStatusText = true;
+		ui.updateStatusText = true;
 }
 
 void modSetTempo(uint16_t bpm)
@@ -1179,11 +1178,15 @@
 	if (bpm < 32)
 		return;
 
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
+		lockAudio();
+
 	modBPM = bpm;
 	if (!editor.isSMPRendering && !editor.isWAVRendering)
 	{
 		modEntry->currBPM = bpm;
-		editor.ui.updateSongBPM = true;
+		ui.updateSongBPM = true;
 	}
 
 	bpm -= 32; // 32..255 -> 0..223
@@ -1196,6 +1199,9 @@
 		smpsPerTick = audio.bpmTab[bpm];
 
 	mixerSetSamplesPerTick(smpsPerTick);
+
+	if (audioWasntLocked)
+		unlockAudio();
 }
 
 void modStop(void)
@@ -1246,8 +1252,8 @@
 
 	modEntry->currPattern = modPattern;
 
-	editor.ui.updatePatternData = true;
-	editor.ui.updateCurrPattText = true;
+	ui.updatePatternData = true;
+	ui.updateCurrPattText = true;
 }
 
 void decPatt(void)
@@ -1257,8 +1263,8 @@
 
 	modEntry->currPattern = modPattern;
 
-	editor.ui.updatePatternData = true;
-	editor.ui.updateCurrPattText = true;
+	ui.updatePatternData = true;
+	ui.updateCurrPattText = true;
 }
 
 void modPlay(int16_t patt, int16_t order, int8_t row)
@@ -1305,15 +1311,9 @@
 	}
 
 	if (patt >= 0 && patt <= MAX_PATTERNS-1)
-	{
-		modPattern = patt;
-		modEntry->currPattern = patt;
-	}
+		modEntry->currPattern = modPattern = (int8_t)patt;
 	else
-	{
-		modPattern = modEntry->head.order[modOrder];
-		modEntry->currPattern = modEntry->head.order[modOrder];
-	}
+		modEntry->currPattern = modPattern = (int8_t)modEntry->head.order[modOrder];
 
 	editor.currPatternDisp = &modEntry->head.order[modOrder];
 	editor.currPosEdPattDisp = &modEntry->head.order[modOrder];
@@ -1332,10 +1332,10 @@
 
 	if (!editor.isSMPRendering && !editor.isWAVRendering)
 	{
-		editor.ui.updateSongPos = true;
-		editor.ui.updatePatternData = true;
-		editor.ui.updateSongPattern = true;
-		editor.ui.updateCurrPattText = true;
+		ui.updateSongPos = true;
+		ui.updatePatternData = true;
+		ui.updateSongPattern = true;
+		ui.updateCurrPattText = true;
 	}
 }
 
@@ -1396,7 +1396,7 @@
 		setLEDFilter(false); // real PT doesn't do this there, but that's insane
 		updateCurrSample();
 
-		editor.ui.updateSongSize = true;
+		ui.updateSongSize = true;
 		renderMuteButtons();
 		updateWindowTitle(MOD_IS_MODIFIED);
 	}
@@ -1427,8 +1427,8 @@
 	editor.currSample = 0;
 	editor.keypadSampleOffset = 0;
 	editor.sampleZero = false;
-	editor.ui.editOpScreenShown = false;
-	editor.ui.aboutScreenShown = false;
+	ui.editOpScreenShown = false;
+	ui.aboutScreenShown = false;
 	editor.blockMarkFlag = false;
 
 	editor.samplePos = 0;
@@ -1453,8 +1453,8 @@
 	if (modEntry == NULL)
 		return; // not allocated
 
-	const bool wasLocked = audio.locked;
-	if (!wasLocked)
+	const bool audioWasntLocked = !audio.locked;
+	if (audioWasntLocked)
 		lockAudio();
 
 	turnOffVoices();
@@ -1471,7 +1471,7 @@
 	free(modEntry);
 	modEntry = NULL;
 
-	if (!wasLocked)
+	if (audioWasntLocked)
 		unlockAudio();
 }
 
@@ -1525,7 +1525,7 @@
 		modEntry->channels[i].n_chanindex = i;
 
 	modOrder = oldOrder;
-	modPattern = oldPattern;
+	modPattern = (int8_t)oldPattern;
 
 	modEntry->row = oldRow;
 	modEntry->currRow = oldRow;
--- a/src/pt2_mouse.c
+++ b/src/pt2_mouse.c
@@ -90,9 +90,9 @@
 {
 	assert(pointerMode <= 5);
 
-	editor.ui.pointerMode = pointerMode;
+	ui.pointerMode = pointerMode;
 	if (carry)
-		editor.ui.previousPointerMode = editor.ui.pointerMode;
+		ui.previousPointerMode = ui.pointerMode;
 
 	switch (pointerMode)
 	{
@@ -108,10 +108,10 @@
 
 void pointerSetPreviousMode(void)
 {
-	if (editor.ui.editTextFlag || editor.ui.askScreenShown || editor.ui.clearScreenShown)
+	if (ui.editTextFlag || ui.askScreenShown || ui.clearScreenShown)
 		pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 	else
-		pointerSetMode(editor.ui.previousPointerMode, NO_CARRY);
+		pointerSetMode(ui.previousPointerMode, NO_CARRY);
 }
 
 void setMsgPointer(void)
@@ -124,15 +124,15 @@
 	pointerSetColor(POINTER_RED);
 }
 
-bool setSystemCursor(SDL_Cursor *cursor)
+bool setSystemCursor(SDL_Cursor *cur)
 {
-	if (cursor == NULL)
+	if (cur == NULL)
 	{
 		SDL_SetCursor(SDL_GetDefaultCursor());
 		return false;
 	}
 
-	SDL_SetCursor(cursor);
+	SDL_SetCursor(cur);
 	return true;
 }
 
@@ -153,7 +153,7 @@
 {
 	freeMouseCursors();
 
-	uint8_t scaleFactor = video.yScale;
+	const uint32_t scaleFactor = video.yScale;
 
 	for (uint32_t i = 0; i < NUM_CURSORS; i++)
 	{
@@ -331,11 +331,11 @@
 	if (mouseButton == SDL_BUTTON_LEFT)
 	{
 		mouse.leftButtonPressed = false;
-		editor.ui.forceSampleDrag = false;
-		editor.ui.forceVolDrag = false;
-		editor.ui.leftLoopPinMoving = false;
-		editor.ui.rightLoopPinMoving = false;
-		editor.ui.sampleMarkingPos = -1;
+		ui.forceSampleDrag = false;
+		ui.forceVolDrag = false;
+		ui.leftLoopPinMoving = false;
+		ui.rightLoopPinMoving = false;
+		ui.sampleMarkingPos = -1;
 
 		switch (mouse.lastGUIButton)
 		{
@@ -342,13 +342,13 @@
 			case PTB_SLENGTHU:
 			case PTB_SLENGTHD:
 			{
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					redrawSample();
 
 				recalcChordLength();
 				updateSamplePos();
 
-				editor.ui.updateSongSize = true;
+				ui.updateSongSize = true;
 			}
 			break;
 
@@ -357,9 +357,9 @@
 			case PTB_PATTERNU:
 			case PTB_PATTERND:
 			{
-				editor.ui.updateSongSize = true;
-				if (editor.ui.posEdScreenShown)
-					editor.ui.updatePosEd = true;
+				ui.updateSongSize = true;
+				if (ui.posEdScreenShown)
+					ui.updatePosEd = true;
 			}
 			break;
 
@@ -374,7 +374,7 @@
 	if (mouseButton == SDL_BUTTON_RIGHT)
 	{
 		mouse.rightButtonPressed = false;
-		editor.ui.forceSampleEdit = false;
+		ui.forceSampleEdit = false;
 	}
 }
 
@@ -408,7 +408,7 @@
 		return;
 	}
 
-	if (editor.ui.samplerFiltersBoxShown)
+	if (ui.samplerFiltersBoxShown)
 	{
 		handleRepeatedSamplerFilterButtons();
 		return;
@@ -435,7 +435,7 @@
 	if (editor.note1 > 36)
 		editor.note1 = 36;
 
-	editor.ui.updateNote1Text = true;
+	ui.updateNote1Text = true;
 	recalcChordLength();
 }
 
@@ -449,7 +449,7 @@
 	if (editor.note1 < 0)
 		editor.note1 = 0;
 
-	editor.ui.updateNote1Text = true;
+	ui.updateNote1Text = true;
 	recalcChordLength();
 }
 
@@ -463,7 +463,7 @@
 	if (editor.note2 > 36)
 		editor.note2 = 36;
 
-	editor.ui.updateNote2Text = true;
+	ui.updateNote2Text = true;
 	recalcChordLength();
 }
 
@@ -477,7 +477,7 @@
 	if (editor.note2 < 0)
 		editor.note2 = 0;
 
-	editor.ui.updateNote2Text = true;
+	ui.updateNote2Text = true;
 	recalcChordLength();
 }
 
@@ -491,7 +491,7 @@
 	if (editor.note3 > 36)
 		editor.note3 = 36;
 
-	editor.ui.updateNote3Text = true;
+	ui.updateNote3Text = true;
 	recalcChordLength();
 }
 
@@ -505,7 +505,7 @@
 	if (editor.note3 < 0)
 		editor.note3 = 0;
 
-	editor.ui.updateNote3Text = true;
+	ui.updateNote3Text = true;
 	recalcChordLength();
 }
 
@@ -519,7 +519,7 @@
 	if (editor.note4 > 36)
 		editor.note4 = 36;
 
-	editor.ui.updateNote4Text = true;
+	ui.updateNote4Text = true;
 	recalcChordLength();
 }
 
@@ -533,7 +533,7 @@
 	if (editor.note4 < 0)
 		editor.note4 = 0;
 
-	editor.ui.updateNote4Text = true;
+	ui.updateNote4Text = true;
 	recalcChordLength();
 }
 
@@ -577,7 +577,7 @@
 	if (editor.samplePos > modEntry->samples[editor.currSample].length)
 		editor.samplePos = modEntry->samples[editor.currSample].length;
 
-	editor.ui.updatePosText = true;
+	ui.updatePosText = true;
 }
 
 void edPosDownButton(bool fast)
@@ -617,7 +617,7 @@
 		}
 	}
 
-	editor.ui.updatePosText = true;
+	ui.updatePosText = true;
 }
 
 void edModUpButton(void)
@@ -630,7 +630,7 @@
 	if (editor.modulateSpeed > 127)
 		editor.modulateSpeed = 127;
 
-	editor.ui.updateModText = true;
+	ui.updateModText = true;
 }
 
 void edModDownButton(void)
@@ -647,7 +647,7 @@
 	if (editor.modulateSpeed < -128)
 		editor.modulateSpeed = -128;
 
-	editor.ui.updateModText = true;
+	ui.updateModText = true;
 }
 
 void edVolUpButton(void)
@@ -665,7 +665,7 @@
 			editor.sampleVol++;
 	}
 
-	editor.ui.updateVolText = true;
+	ui.updateVolText = true;
 }
 
 void edVolDownButton(void)
@@ -683,7 +683,7 @@
 			editor.sampleVol--;
 	}
 
-	editor.ui.updateVolText = true;
+	ui.updateVolText = true;
 }
 
 void sampleUpButton(void)
@@ -720,7 +720,7 @@
 		modEntry->samples[editor.currSample].fineTune = 0;
 
 	recalcChordLength();
-	editor.ui.updateCurrSampleFineTune = true;
+	ui.updateCurrSampleFineTune = true;
 }
 
 void sampleFineTuneDownButton(void)
@@ -733,7 +733,7 @@
 		modEntry->samples[editor.currSample].fineTune = 0;
 
 	recalcChordLength();
-	editor.ui.updateCurrSampleFineTune = true;
+	ui.updateCurrSampleFineTune = true;
 }
 
 void sampleVolumeUpButton(void)
@@ -749,7 +749,7 @@
 		val = 64;
 
 	modEntry->samples[editor.currSample].volume = (uint8_t)val;
-	editor.ui.updateCurrSampleVolume = true;
+	ui.updateCurrSampleVolume = true;
 }
 
 void sampleVolumeDownButton(void)
@@ -765,7 +765,7 @@
 		val = 0;
 
 	modEntry->samples[editor.currSample].volume = (uint8_t)val;
-	editor.ui.updateCurrSampleVolume = true;
+	ui.updateCurrSampleVolume = true;
 }
 
 void sampleLengthUpButton(bool fast)
@@ -794,8 +794,8 @@
 	if (val > MAX_SAMPLE_LEN)
 		val = MAX_SAMPLE_LEN;
 
-	modEntry->samples[editor.currSample].length = val;
-	editor.ui.updateCurrSampleLength = true;
+	modEntry->samples[editor.currSample].length = (uint16_t)val;
+	ui.updateCurrSampleLength = true;
 }
 
 void sampleLengthDownButton(bool fast)
@@ -840,9 +840,9 @@
 			val = s->loopStart+s->loopLength;
 	}
 
-	s->length = val;
+	s->length = (uint16_t)val;
 
-	editor.ui.updateCurrSampleLength = true;
+	ui.updateCurrSampleLength = true;
 }
 
 void sampleRepeatUpButton(bool fast)
@@ -877,16 +877,16 @@
 	if (val > len-loopLen)
 		val = len-loopLen;
 
-	modEntry->samples[editor.currSample].loopStart = val;
-	editor.ui.updateCurrSampleRepeat = true;
+	modEntry->samples[editor.currSample].loopStart = (uint16_t)val;
+	ui.updateCurrSampleRepeat = true;
 
 	mixerUpdateLoops();
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 		setLoopSprites();
 
-	if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3) // sample chord editor
-		editor.ui.updateLengthText = true;
+	if (ui.editOpScreenShown && ui.editOpScreen == 3) // sample chord editor
+		ui.updateLengthText = true;
 }
 
 void sampleRepeatDownButton(bool fast)
@@ -920,16 +920,16 @@
 	if (val < 0)
 		val = 0;
 
-	modEntry->samples[editor.currSample].loopStart = val;
-	editor.ui.updateCurrSampleRepeat = true;
+	modEntry->samples[editor.currSample].loopStart = (uint16_t)val;
+	ui.updateCurrSampleRepeat = true;
 
 	mixerUpdateLoops();
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 		setLoopSprites();
 
-	if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3) // sample chord editor
-		editor.ui.updateLengthText = true;
+	if (ui.editOpScreenShown && ui.editOpScreen == 3) // sample chord editor
+		ui.updateLengthText = true;
 }
 
 void sampleRepeatLengthUpButton(bool fast)
@@ -964,16 +964,16 @@
 	if (val > len-loopStart)
 		val = len-loopStart;
 
-	modEntry->samples[editor.currSample].loopLength = val;
-	editor.ui.updateCurrSampleReplen = true;
+	modEntry->samples[editor.currSample].loopLength = (uint16_t)val;
+	ui.updateCurrSampleReplen = true;
 
 	mixerUpdateLoops();
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 		setLoopSprites();
 
-	if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3) // sample chord editor
-		editor.ui.updateLengthText = true;
+	if (ui.editOpScreenShown && ui.editOpScreen == 3) // sample chord editor
+		ui.updateLengthText = true;
 }
 
 void sampleRepeatLengthDownButton(bool fast)
@@ -1007,16 +1007,16 @@
 	if (val < 2)
 		val = 2;
 
-	modEntry->samples[editor.currSample].loopLength = val;
-	editor.ui.updateCurrSampleReplen = true;
+	modEntry->samples[editor.currSample].loopLength = (uint16_t)val;
+	ui.updateCurrSampleReplen = true;
 
 	mixerUpdateLoops();
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 		setLoopSprites();
 
-	if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3) // sample chord editor
-		editor.ui.updateLengthText = true;
+	if (ui.editOpScreenShown && ui.editOpScreen == 3) // sample chord editor
+		ui.updateLengthText = true;
 }
 
 void tempoUpButton(void)
@@ -1037,7 +1037,7 @@
 
 	modEntry->currBPM = val;
 	modSetTempo(modEntry->currBPM);
-	editor.ui.updateSongBPM = true;
+	ui.updateSongBPM = true;
 }
 
 void tempoDownButton(void)
@@ -1058,7 +1058,7 @@
 
 	modEntry->currBPM = val;
 	modSetTempo(modEntry->currBPM);
-	editor.ui.updateSongBPM = true;
+	ui.updateSongBPM = true;
 }
 
 void songLengthUpButton(void)
@@ -1081,7 +1081,7 @@
 		val = modEntry->head.orderCount-1;
 
 	editor.currPosEdPattDisp = &modEntry->head.order[val];
-	editor.ui.updateSongLength = true;
+	ui.updateSongLength = true;
 }
 
 void songLengthDownButton(void)
@@ -1103,7 +1103,7 @@
 		val = modEntry->head.orderCount-1;
 
 	editor.currPosEdPattDisp = &modEntry->head.order[val];
-	editor.ui.updateSongLength = true;
+	ui.updateSongLength = true;
 }
 
 void patternUpButton(void)
@@ -1120,10 +1120,10 @@
 
 	modEntry->head.order[modEntry->currOrder] = (uint8_t)val;
 
-	if (editor.ui.posEdScreenShown)
-		editor.ui.updatePosEd = true;
+	if (ui.posEdScreenShown)
+		ui.updatePosEd = true;
 
-	editor.ui.updateSongPattern = true;
+	ui.updateSongPattern = true;
 }
 
 void patternDownButton(void)
@@ -1140,10 +1140,10 @@
 
 	modEntry->head.order[modEntry->currOrder] = (uint8_t)val;
 
-	if (editor.ui.posEdScreenShown)
-		editor.ui.updatePosEd = true;
+	if (ui.posEdScreenShown)
+		ui.updatePosEd = true;
 
-	editor.ui.updateSongPattern = true;
+	ui.updateSongPattern = true;
 }
 
 void positionUpButton(void)
@@ -1187,13 +1187,13 @@
 
 	if (mouse.rightButtonPressed)
 	{
-		if (editor.ui.editTextFlag)
+		if (ui.editTextFlag)
 		{
 			exitGetTextLine(EDIT_TEXT_NO_UPDATE);
 		}
 		else
 		{
-			editor.ui.samplerVolBoxShown = false;
+			ui.samplerVolBoxShown = false;
 			removeSamplerVolBox();
 		}
 
@@ -1200,7 +1200,7 @@
 		return;
 	}
 
-	if (editor.ui.editTextFlag)
+	if (ui.editTextFlag)
 		return;
 
 	// check buttons
@@ -1207,7 +1207,7 @@
 	if (mouse.leftButtonPressed)
 	{
 		// restore sample ask dialog
-		if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_RESTORE_SAMPLE)
+		if (ui.askScreenShown && ui.askScreenType == ASK_RESTORE_SAMPLE)
 		{
 			if (mouse.y >= 71 && mouse.y <= 81)
 			{
@@ -1214,17 +1214,17 @@
 				if (mouse.x >= 171 && mouse.x <= 196)
 				{
 					// YES button
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = false;
-					editor.ui.answerYes = true;
+					ui.askScreenShown = false;
+					ui.answerNo = false;
+					ui.answerYes = true;
 					handleAskYes();
 				}
 				else if (mouse.x >= 234 && mouse.x <= 252)
 				{
 					// NO button
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = true;
-					editor.ui.answerYes = false;
+					ui.askScreenShown = false;
+					ui.answerNo = true;
+					ui.answerYes = false;
 					handleAskNo();
 				}
 			}
@@ -1233,7 +1233,7 @@
 		}
 
 		// MAIN SCREEN STOP
-		if (!editor.ui.diskOpScreenShown && !editor.ui.posEdScreenShown)
+		if (!ui.diskOpScreenShown && !ui.posEdScreenShown)
 		{
 			if (mouse.x >= 182 && mouse.x <= 243 && mouse.y >= 0 && mouse.y <= 10)
 			{
@@ -1277,7 +1277,7 @@
 		// VOLUME button (toggle)
 		if (mouse.x >= 96 && mouse.x <= 135 && mouse.y >= 244 && mouse.y <= 254)
 		{
-			editor.ui.samplerVolBoxShown = false;
+			ui.samplerVolBoxShown = false;
 			removeSamplerVolBox();
 			return;
 		}
@@ -1294,11 +1294,11 @@
 			// FROM NUM
 			if (mouse.y >= 154 && mouse.y <= 164)
 			{
-				editor.ui.tmpDisp16 = editor.vol1;
-				editor.vol1Disp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 3;
-				editor.ui.editTextPos = 6342; // (y * 40) + x
+				ui.tmpDisp16 = editor.vol1;
+				editor.vol1Disp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 3;
+				ui.editTextPos = 6342; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_SA_VOL_FROM_NUM);
 				return;
 			}
@@ -1306,11 +1306,11 @@
 			// TO NUM
 			else if (mouse.y >= 165 && mouse.y <= 175)
 			{
-				editor.ui.tmpDisp16 = editor.vol2;
-				editor.vol2Disp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 3;
-				editor.ui.editTextPos = 6782; // (y * 40) + x
+				ui.tmpDisp16 = editor.vol2;
+				editor.vol2Disp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 3;
+				ui.editTextPos = 6782; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_SA_VOL_TO_NUM);
 				return;
 			}
@@ -1369,8 +1369,8 @@
 					editor.vol2 = (uint16_t)((100 * 127) / sampleVol);
 				}
 
-				editor.ui.updateVolFromText = true;
-				editor.ui.updateVolToText = true;
+				ui.updateVolFromText = true;
+				ui.updateVolToText = true;
 
 				showVolFromSlider();
 				showVolToSlider();
@@ -1382,8 +1382,8 @@
 			{
 				editor.vol1 = 100;
 				editor.vol2 = 0;
-				editor.ui.updateVolFromText = true;
-				editor.ui.updateVolToText = true;
+				ui.updateVolFromText = true;
+				ui.updateVolToText = true;
 				showVolFromSlider();
 				showVolToSlider();
 				return;
@@ -1394,8 +1394,8 @@
 			{
 				editor.vol1 = 0;
 				editor.vol2 = 100;
-				editor.ui.updateVolFromText = true;
-				editor.ui.updateVolToText = true;
+				ui.updateVolFromText = true;
+				ui.updateVolToText = true;
 				showVolFromSlider();
 				showVolToSlider();
 				return;
@@ -1406,8 +1406,8 @@
 			{
 				editor.vol1 = 100;
 				editor.vol2 = 100;
-				editor.ui.updateVolFromText = true;
-				editor.ui.updateVolToText = true;
+				ui.updateVolFromText = true;
+				ui.updateVolToText = true;
 				showVolFromSlider();
 				showVolToSlider();
 				return;
@@ -1416,7 +1416,7 @@
 			// CANCEL
 			else if (mouse.x >= 174 && mouse.x <= 207)
 			{
-				editor.ui.samplerVolBoxShown = false;
+				ui.samplerVolBoxShown = false;
 				removeSamplerVolBox();
 				return;
 			}
@@ -1433,7 +1433,7 @@
 
 				if (editor.vol1 == 100 && editor.vol2 == 100)
 				{
-					editor.ui.samplerVolBoxShown = false;
+					ui.samplerVolBoxShown = false;
 					removeSamplerVolBox();
 					return;
 				}
@@ -1471,7 +1471,7 @@
 
 				fixSampleBeep(s);
 
-				editor.ui.samplerVolBoxShown = false;
+				ui.samplerVolBoxShown = false;
 				removeSamplerVolBox();
 
 				updateWindowTitle(MOD_IS_MODIFIED);
@@ -1507,7 +1507,7 @@
 			if (editor.lpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 				editor.lpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-			editor.ui.updateLPText = true;
+			ui.updateLPText = true;
 		}
 		break;
 
@@ -1528,7 +1528,7 @@
 					editor.lpCutOff = 0;
 			}
 
-			editor.ui.updateLPText = true;
+			ui.updateLPText = true;
 		}
 		break;
 
@@ -1552,7 +1552,7 @@
 			if (editor.hpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 				editor.hpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-			editor.ui.updateHPText = true;
+			ui.updateHPText = true;
 		}
 		break;
 
@@ -1573,7 +1573,7 @@
 					editor.hpCutOff = 0;
 			}
 
-			editor.ui.updateHPText = true;
+			ui.updateHPText = true;
 		}
 		break;
 
@@ -1586,17 +1586,17 @@
 	uint8_t i;
 	moduleSample_t *s;
 
-	if (mouse.rightButtonPressed && editor.ui.editTextFlag)
+	if (mouse.rightButtonPressed && ui.editTextFlag)
 	{
 		exitGetTextLine(EDIT_TEXT_NO_UPDATE);
 		return;
 	}
 
-	if (editor.ui.editTextFlag || mouse.lastSmpFilterButton > -1 || !mouse.leftButtonPressed)
+	if (ui.editTextFlag || mouse.lastSmpFilterButton > -1 || !mouse.leftButtonPressed)
 		return;
 
 	// restore sample ask dialog
-	if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_RESTORE_SAMPLE)
+	if (ui.askScreenShown && ui.askScreenType == ASK_RESTORE_SAMPLE)
 	{
 		if (mouse.y >= 71 && mouse.y <= 81)
 		{
@@ -1603,17 +1603,17 @@
 			if (mouse.x >= 171 && mouse.x <= 196)
 			{
 				// YES button
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
+				ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
 				handleAskYes();
 			}
 			else if ((mouse.x >= 234) && (mouse.x <= 252))
 			{
 				// NO button
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = true;
-				editor.ui.answerYes = false;
+				ui.askScreenShown = false;
+				ui.answerNo = true;
+				ui.answerYes = false;
 				handleAskNo();
 			}
 		}
@@ -1624,13 +1624,13 @@
 	// FILTERS button (toggle)
 	if (mouse.x >= 211 && mouse.x <= 245 && mouse.y >= 244 && mouse.y <= 254)
 	{
-		editor.ui.samplerFiltersBoxShown = false;
+		ui.samplerFiltersBoxShown = false;
 		removeSamplerFiltersBox();
 		return;
 	}
 
 	// MAIN SCREEN STOP
-	if (!editor.ui.diskOpScreenShown && !editor.ui.posEdScreenShown)
+	if (!ui.diskOpScreenShown && !ui.posEdScreenShown)
 	{
 		if (mouse.x >= 182 && mouse.x <= 243 && mouse.y >= 0 && mouse.y <= 10)
 		{
@@ -1706,15 +1706,15 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.lpCutOff = 0;
-				editor.ui.updateLPText = true;
+				ui.updateLPText = true;
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = editor.lpCutOff;
-				editor.lpCutOffDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.editTextPos = 6341; // (y * 40) + x
+				ui.tmpDisp16 = editor.lpCutOff;
+				editor.lpCutOffDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.editTextPos = 6341; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_SA_FIL_LP_CUTOFF);
 			}
 
@@ -1743,7 +1743,7 @@
 			if (editor.lpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 				editor.lpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-			editor.ui.updateLPText = true;
+			ui.updateLPText = true;
 			return;
 		}
 
@@ -1766,7 +1766,7 @@
 					editor.lpCutOff = 0;
 			}
 
-			editor.ui.updateLPText = true;
+			ui.updateLPText = true;
 			return;
 		}
 	}
@@ -1787,15 +1787,15 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.hpCutOff = 0;
-				editor.ui.updateHPText = true;
+				ui.updateHPText = true;
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = editor.hpCutOff;
-				editor.hpCutOffDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.editTextPos = 6781; // (y * 40) + x
+				ui.tmpDisp16 = editor.hpCutOff;
+				editor.hpCutOffDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.editTextPos = 6781; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_SA_FIL_HP_CUTOFF);
 			}
 
@@ -1824,7 +1824,7 @@
 			if (editor.hpCutOff > (uint16_t)(FILTERS_BASE_FREQ/2))
 				editor.hpCutOff = (uint16_t)(FILTERS_BASE_FREQ/2);
 
-			editor.ui.updateHPText = true;
+			ui.updateHPText = true;
 			return;
 		}
 
@@ -1847,7 +1847,7 @@
 					editor.hpCutOff = 0;
 			}
 
-			editor.ui.updateHPText = true;
+			ui.updateHPText = true;
 			return;
 		}
 	}
@@ -1856,7 +1856,7 @@
 	if (mouse.x >= 76 && mouse.x <= 239 && mouse.y >= 174 && mouse.y <= 186)
 	{
 		editor.normalizeFiltersFlag ^= 1;
-		editor.ui.updateNormFlag = true;
+		ui.updateNormFlag = true;
 		return;
 	}
 
@@ -1863,7 +1863,7 @@
 	// EXIT
 	if (mouse.x >= 240 && mouse.x <= 250 && mouse.y >= 154 && mouse.y <= 186)
 	{
-		editor.ui.samplerFiltersBoxShown = false;
+		ui.samplerFiltersBoxShown = false;
 		removeSamplerFiltersBox();
 	}
 }
@@ -1884,9 +1884,9 @@
 int32_t checkGUIButtons(void)
 {
 	// these two makes *no other* buttons clickable
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		if (editor.ui.pat2SmpDialogShown)
+		if (ui.pat2SmpDialogShown)
 		{
 			TEST_BUTTONS(bPat2SmpAsk, PAT2SMP_ASK_BUTTONS);
 		}
@@ -1897,7 +1897,7 @@
 
 		return -1;
 	}
-	else if (editor.ui.clearScreenShown)
+	else if (ui.clearScreenShown)
 	{
 		TEST_BUTTONS(bClear, CLEAR_BUTTONS);
 		return -1;
@@ -1908,19 +1908,19 @@
 		return PTB_QUIT;
 
 	// top screen buttons
-	if (editor.ui.diskOpScreenShown)
+	if (ui.diskOpScreenShown)
 	{
 		TEST_BUTTONS(bDiskOp, DISKOP_BUTTONS);
 	}
 	else
 	{
-		if (editor.ui.posEdScreenShown)
+		if (ui.posEdScreenShown)
 		{
 			TEST_BUTTONS(bPosEd, POSED_BUTTONS);
 		}
-		else if (editor.ui.editOpScreenShown)
+		else if (ui.editOpScreenShown)
 		{
-			switch (editor.ui.editOpScreen)
+			switch (ui.editOpScreen)
 			{
 				default:
 				case 0: TEST_BUTTONS(bEditOp1, EDITOP1_BUTTONS); break;
@@ -1937,7 +1937,7 @@
 	TEST_BUTTONS(bMidScreen, MIDSCREEN_BUTTONS);
 
 	// bottom screen buttons
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 	{
 		TEST_BUTTONS(bSampler, SAMPLER_BUTTONS);
 	}
@@ -1952,12 +1952,12 @@
 void handleTextEditing(uint8_t mouseButton)
 {
 	char *tmpRead;
-	int16_t tmp16;
+	int32_t tmp32;
 
 	// handle mouse while editing text/numbers
-	if (editor.ui.editTextFlag)
+	if (ui.editTextFlag)
 	{
-		if (editor.ui.editTextType != TEXT_EDIT_STRING)
+		if (ui.editTextType != TEXT_EDIT_STRING)
 		{
 			if (mouseButton == SDL_BUTTON_RIGHT)
 				exitGetTextLine(EDIT_TEXT_NO_UPDATE);
@@ -1964,29 +1964,29 @@
 		}
 		else if (mouseButton == SDL_BUTTON_LEFT && !editor.mixFlag)
 		{
-			tmp16 = mouse.y - editor.ui.lineCurY;
-			if (tmp16 <= 2 && tmp16 >= -9)
+			tmp32 = mouse.y - ui.lineCurY;
+			if (tmp32 <= 2 && tmp32 >= -9)
 			{
-				tmp16 = (uint16_t)((mouse.x - editor.ui.lineCurX) + 4) >> 3;
-				while (tmp16 != 0) // 0 = pos we want
+				tmp32 = (uint32_t)((mouse.x - ui.lineCurX) + 4) >> 3;
+				while (tmp32 != 0) // 0 = pos we want
 				{
-					if (tmp16 > 0)
+					if (tmp32 > 0)
 					{
-						if (editor.ui.editPos < editor.ui.textEndPtr && *editor.ui.editPos != '\0')
+						if (ui.editPos < ui.textEndPtr && *ui.editPos != '\0')
 						{
-							editor.ui.editPos++;
+							ui.editPos++;
 							textMarkerMoveRight();
 						}
-						tmp16--;
+						tmp32--;
 					}
-					else if (tmp16 < 0)
+					else if (tmp32 < 0)
 					{
-						if (editor.ui.editPos > editor.ui.dstPtr)
+						if (ui.editPos > ui.dstPtr)
 						{
-							editor.ui.editPos--;
+							ui.editPos--;
 							textMarkerMoveLeft();
 						}
-						tmp16++;
+						tmp32++;
 					}
 				}
 			}
@@ -2001,34 +2001,34 @@
 			{
 				exitGetTextLine(EDIT_TEXT_UPDATE);
 				editor.mixFlag = false;
-				editor.ui.updateMixText = true;
+				ui.updateMixText = true;
 			}
 			else
 			{
-				tmpRead = editor.ui.dstPtr;
-				while (tmpRead < editor.ui.textEndPtr)
+				tmpRead = ui.dstPtr;
+				while (tmpRead < ui.textEndPtr)
 					*tmpRead++ = '\0';
 
-				*editor.ui.textEndPtr = '\0';
+				*ui.textEndPtr = '\0';
 
 				// don't exit text edit mode if the disk op. path was about to be deleted
-				if (editor.ui.editObject == PTB_DO_DATAPATH)
+				if (ui.editObject == PTB_DO_DATAPATH)
 				{
 					// move text cursor to pos 0
-					while (editor.ui.editPos > editor.ui.dstPtr)
+					while (ui.editPos > ui.dstPtr)
 					{
-						editor.ui.editPos--;
+						ui.editPos--;
 						textMarkerMoveLeft();
 					}
 
-					editor.ui.updateDiskOpPathText = true;
+					ui.updateDiskOpPathText = true;
 				}
 				else
 				{
-					if (editor.ui.editObject == PTB_SONGNAME)
-						editor.ui.updateSongName = true;
-					else if (editor.ui.editObject == PTB_SAMPLENAME)
-						editor.ui.updateCurrSampleName = true;
+					if (ui.editObject == PTB_SONGNAME)
+						ui.updateSongName = true;
+					else if (ui.editObject == PTB_SAMPLENAME)
+						ui.updateCurrSampleName = true;
 
 					exitGetTextLine(EDIT_TEXT_UPDATE);
 				}
@@ -2039,26 +2039,26 @@
 
 void mouseWheelUpHandler(void)
 {
-	if (editor.ui.editTextFlag || editor.ui.askScreenShown || editor.ui.clearScreenShown || editor.swapChannelFlag)
+	if (ui.editTextFlag || ui.askScreenShown || ui.clearScreenShown || editor.swapChannelFlag)
 		return;
 
 	if (mouse.y < 121)
 	{
 		// upper part of screen
-		if (editor.ui.diskOpScreenShown)
+		if (ui.diskOpScreenShown)
 		{
-			if (editor.diskop.scrollOffset > 0)
+			if (diskop.scrollOffset > 0)
 			{
-				editor.diskop.scrollOffset--;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset--;
+				ui.updateDiskOpFileList = true;
 			}
 		}
-		else if (editor.ui.posEdScreenShown && modEntry->currOrder > 0)
+		else if (ui.posEdScreenShown && modEntry->currOrder > 0)
 		{
 			modSetPos(modEntry->currOrder - 1, DONT_SET_ROW);
 		}
 	}
-	else if (editor.ui.samplerScreenShown)
+	else if (ui.samplerScreenShown)
 	{
 		samplerZoomInMouseWheel(); // lower part of screen
 	}
@@ -2070,26 +2070,26 @@
 
 void mouseWheelDownHandler(void)
 {
-	if (editor.ui.editTextFlag || editor.ui.askScreenShown || editor.ui.clearScreenShown || editor.swapChannelFlag)
+	if (ui.editTextFlag || ui.askScreenShown || ui.clearScreenShown || editor.swapChannelFlag)
 		return;
 
 	if (mouse.y < 121)
 	{
 		// upper part of screen
-		if (editor.ui.diskOpScreenShown)
+		if (ui.diskOpScreenShown)
 		{
-			if (editor.diskop.numEntries > DISKOP_LINES && editor.diskop.scrollOffset < editor.diskop.numEntries-DISKOP_LINES)
+			if (diskop.numEntries > DISKOP_LINES && diskop.scrollOffset < diskop.numEntries-DISKOP_LINES)
 			{
-				editor.diskop.scrollOffset++;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset++;
+				ui.updateDiskOpFileList = true;
 			}
 		}
-		else if (editor.ui.posEdScreenShown && modEntry->currOrder < modEntry->head.orderCount-1)
+		else if (ui.posEdScreenShown && modEntry->currOrder < modEntry->head.orderCount-1)
 		{
 			modSetPos(modEntry->currOrder + 1, DONT_SET_ROW);
 		}
 	}
-	else if (editor.ui.samplerScreenShown)
+	else if (ui.samplerScreenShown)
 	{
 		samplerZoomOutMouseWheel(); // lower part of screen
 	}
@@ -2114,9 +2114,9 @@
 	}
 
 	// close clear dialog with right mouse button
-	if (editor.ui.clearScreenShown)
+	if (ui.clearScreenShown)
 	{
-		editor.ui.clearScreenShown = false;
+		ui.clearScreenShown = false;
 		setPrevStatusMessage();
 		pointerSetPreviousMode();
 
@@ -2130,21 +2130,21 @@
 	}
 
 	// close ask dialogs with right mouse button
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		editor.ui.askScreenShown = false;
-		editor.ui.answerNo = true;
-		editor.ui.answerYes = false;
+		ui.askScreenShown = false;
+		ui.answerNo = true;
+		ui.answerYes = false;
 		handleAskNo(); // mouse pointer is set to error (red) in here
 		return true;
 	}
 
 	// toggle channel muting with right mouse button
-	if (editor.ui.visualizerMode == VISUAL_QUADRASCOPE && mouse.y >= 55 && mouse.y <= 87)
+	if (ui.visualizerMode == VISUAL_QUADRASCOPE && mouse.y >= 55 && mouse.y <= 87)
 	{
-		if (!editor.ui.posEdScreenShown && !editor.ui.editOpScreenShown && !editor.ui.diskOpScreenShown &&
-			!editor.ui.aboutScreenShown && !editor.ui.samplerVolBoxShown &&
-			!editor.ui.samplerFiltersBoxShown && !editor.isWAVRendering)
+		if (!ui.posEdScreenShown && !ui.editOpScreenShown && !ui.diskOpScreenShown &&
+			!ui.aboutScreenShown && !ui.samplerVolBoxShown &&
+			!ui.samplerFiltersBoxShown && !editor.isWAVRendering)
 		{
 			     if (mouse.x > 127 && mouse.x <= 167) editor.muted[0] ^= 1;
 			else if (mouse.x > 175 && mouse.x <= 215) editor.muted[1] ^= 1;
@@ -2156,8 +2156,8 @@
 	}
 
 	// sample hand drawing
-	if (mouse.y >= 138 && mouse.y <= 201 && editor.ui.samplerScreenShown &&
-		!editor.ui.samplerVolBoxShown && !editor.ui.samplerFiltersBoxShown)
+	if (mouse.y >= 138 && mouse.y <= 201 && ui.samplerScreenShown &&
+		!ui.samplerVolBoxShown && !ui.samplerFiltersBoxShown)
 	{
 		samplerEditSample(false);
 	}
@@ -2169,11 +2169,11 @@
 {
 	int32_t guiButton;
 
-	if (editor.swapChannelFlag || editor.ui.editTextFlag)
+	if (editor.swapChannelFlag || ui.editTextFlag)
 		return false;
 
 	// handle volume toolbox in sampler screen
-	if (editor.ui.samplerVolBoxShown)
+	if (ui.samplerVolBoxShown)
 	{
 		handleSamplerVolumeBox();
 		return true;
@@ -2180,7 +2180,7 @@
 	}
 
 	// handle filters toolbox in sampler
-	else if (editor.ui.samplerFiltersBoxShown)
+	else if (ui.samplerFiltersBoxShown)
 	{
 		handleSamplerFiltersBox();
 		return true;
@@ -2187,7 +2187,7 @@
 	}
 
 	// "downsample before loading sample" ask dialog
-	if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_LOAD_DOWNSAMPLE)
+	if (ui.askScreenShown && ui.askScreenType == ASK_LOAD_DOWNSAMPLE)
 	{
 		if (mouse.y >= 83 && mouse.y <= 93)
 		{
@@ -2194,9 +2194,9 @@
 			if (mouse.x >= 179 && mouse.x <= 204)
 			{
 				// YES button
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
+				ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
 				handleAskYes();
 				return true;
 			}
@@ -2203,9 +2203,9 @@
 			else if (mouse.x >= 242 && mouse.x <= 260)
 			{
 				// NO button
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = true;
-				editor.ui.answerYes = false;
+				ui.askScreenShown = false;
+				ui.answerNo = true;
+				ui.answerYes = false;
 				handleAskNo();
 				return true;
 			}
@@ -2215,19 +2215,19 @@
 	}
 
 	// cancel note input gadgets with left/right mouse button
-	if (editor.ui.changingSmpResample || editor.ui.changingChordNote || editor.ui.changingDrumPadNote)
+	if (ui.changingSmpResample || ui.changingChordNote || ui.changingDrumPadNote)
 	{
 		if (mouse.leftButtonPressed || mouse.rightButtonPressed)
 		{
-			editor.ui.changingSmpResample = false;
-			editor.ui.changingChordNote = false;
-			editor.ui.changingDrumPadNote = false;
+			ui.changingSmpResample = false;
+			ui.changingChordNote = false;
+			ui.changingDrumPadNote = false;
 
-			editor.ui.updateResampleNote = true;
-			editor.ui.updateNote1Text = true;
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateResampleNote = true;
+			ui.updateNote1Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
@@ -2240,9 +2240,9 @@
 		return false;
 
 	// handle QUIT ask dialog while Disk Op. filling is ongoing
-	if (editor.diskop.isFilling)
+	if (diskop.isFilling)
 	{
-		if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_QUIT)
+		if (ui.askScreenShown && ui.askScreenType == ASK_QUIT)
 		{
 			if (mouse.y >= 71 && mouse.y <= 81)
 			{
@@ -2249,17 +2249,17 @@
 				if (mouse.x >= 171 && mouse.x <= 196)
 				{
 					// YES button
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = false;
-					editor.ui.answerYes = true;
+					ui.askScreenShown = false;
+					ui.answerNo = false;
+					ui.answerYes = true;
 					handleAskYes();
 				}
 				else if (mouse.x >= 234 && mouse.x <= 252)
 				{
 					// NO button
-					editor.ui.askScreenShown = false;
-					editor.ui.answerNo = true;
-					editor.ui.answerYes = false;
+					ui.askScreenShown = false;
+					ui.answerNo = true;
+					ui.answerYes = false;
 					handleAskNo();
 				}
 			}
@@ -2271,7 +2271,7 @@
 	// CANCEL and YES/NO (ask exit) buttons while MOD2WAV is ongoing
 	if (editor.isWAVRendering)
 	{
-		if (editor.ui.askScreenShown && editor.ui.askScreenType == ASK_QUIT)
+		if (ui.askScreenShown && ui.askScreenType == ASK_QUIT)
 		{
 			if (mouse.x >= 171 && mouse.x <= 196)
 			{
@@ -2279,17 +2279,17 @@
 				editor.isWAVRendering = false;
 				SDL_WaitThread(editor.mod2WavThread, NULL);
 
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = false;
-				editor.ui.answerYes = true;
+				ui.askScreenShown = false;
+				ui.answerNo = false;
+				ui.answerYes = true;
 				handleAskYes();
 			}
 			else if (mouse.x >= 234 && mouse.x <= 252)
 			{
 				// NO button
-				editor.ui.askScreenShown = false;
-				editor.ui.answerNo = true;
-				editor.ui.answerYes = false;
+				ui.askScreenShown = false;
+				ui.answerNo = true;
+				ui.answerYes = false;
 				handleAskNo();
 
 				pointerSetMode(POINTER_MODE_MSG2, NO_CARRY);
@@ -2330,9 +2330,9 @@
 			editor.errorMsgCounter = 0;
 
 			// don't reset status text/mouse color during certain modes
-			if (!editor.ui.askScreenShown && !editor.ui.clearScreenShown &&
-				!editor.ui.pat2SmpDialogShown && !editor.ui.changingChordNote &&
-				!editor.ui.changingDrumPadNote && !editor.ui.changingSmpResample &&
+			if (!ui.askScreenShown && !ui.clearScreenShown &&
+				!ui.pat2SmpDialogShown && !ui.changingChordNote &&
+				!ui.changingDrumPadNote && !ui.changingSmpResample &&
 				!editor.swapChannelFlag)
 			{
 				pointerSetPreviousMode();
@@ -2363,9 +2363,9 @@
 
 		case PTB_PAT2SMP:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_PAT2SMP;
-			editor.ui.pat2SmpDialogShown = true;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_PAT2SMP;
+			ui.pat2SmpDialogShown = true;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 
 			if (editor.songPlaying)
@@ -2381,10 +2381,10 @@
 		// Edit Op. All Screens
 		case PTB_EO_TITLEBAR:
 		{
-			     if (editor.ui.editOpScreen == 0) editor.sampleAllFlag ^= 1;
-			else if (editor.ui.editOpScreen == 1) editor.trackPattFlag = (editor.trackPattFlag + 1) % 3;
-			else if (editor.ui.editOpScreen == 2) editor.halfClipFlag ^= 1;
-			else if (editor.ui.editOpScreen == 3) editor.newOldFlag ^= 1;
+			     if (ui.editOpScreen == 0) editor.sampleAllFlag ^= 1;
+			else if (ui.editOpScreen == 1) editor.trackPattFlag = (editor.trackPattFlag + 1) % 3;
+			else if (ui.editOpScreen == 2) editor.halfClipFlag ^= 1;
+			else if (ui.editOpScreen == 3) editor.newOldFlag ^= 1;
 
 			renderEditOpMode();
 		}
@@ -2392,7 +2392,7 @@
 
 		case PTB_EO_1:
 		{
-			editor.ui.editOpScreen = 0;
+			ui.editOpScreen = 0;
 			renderEditOpScreen();
 		}
 		break;
@@ -2399,7 +2399,7 @@
 
 		case PTB_EO_2:
 		{
-			editor.ui.editOpScreen = 1;
+			ui.editOpScreen = 1;
 			renderEditOpScreen();
 		}
 		break;
@@ -2406,7 +2406,7 @@
 
 		case PTB_EO_3:
 		{
-			editor.ui.editOpScreen = 2;
+			ui.editOpScreen = 2;
 			renderEditOpScreen();
 		}
 		break;
@@ -2413,8 +2413,8 @@
 
 		case PTB_EO_EXIT:
 		{
-			editor.ui.aboutScreenShown = false;
-			editor.ui.editOpScreenShown = false;
+			ui.aboutScreenShown = false;
+			ui.editOpScreenShown = false;
 			displayMainScreen();
 		}
 		break;
@@ -2435,7 +2435,7 @@
 		case PTB_EO_RECORD:
 		{
 			editor.recordMode ^= 1;
-			editor.ui.updateRecordText = true;
+			ui.updateRecordText = true;
 		}
 		break;
 
@@ -2446,7 +2446,7 @@
 		case PTB_EO_FROM:
 		{
 			editor.sampleFrom = editor.currSample + 1;
-			editor.ui.updateFromText = true;
+			ui.updateFromText = true;
 		}
 		break;
 
@@ -2453,14 +2453,14 @@
 		case PTB_EO_TO:
 		{
 			editor.sampleTo = editor.currSample + 1;
-			editor.ui.updateToText = true;
+			ui.updateToText = true;
 		}
 		break;
 
 		case PTB_EO_KILL:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_KILL_SAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_KILL_SAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("KILL SAMPLE ?", NO_CARRY);
 			renderAskDialog();
@@ -2469,11 +2469,11 @@
 
 		case PTB_EO_QUANTIZE:
 		{
-			editor.ui.tmpDisp16 = config.quantizeValue;
-			editor.quantizeValueDisp = &editor.ui.tmpDisp16;
-			editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-			editor.ui.numLen = 2;
-			editor.ui.editTextPos = 2824; // (y * 40) + x
+			ui.tmpDisp16 = config.quantizeValue;
+			editor.quantizeValueDisp = &ui.tmpDisp16;
+			ui.numPtr16 = &ui.tmpDisp16;
+			ui.numLen = 2;
+			ui.editTextPos = 2824; // (y * 40) + x
 			getNumLine(TEXT_EDIT_DECIMAL, PTB_EO_QUANTIZE);
 		}
 		break;
@@ -2480,11 +2480,11 @@
 
 		case PTB_EO_METRO_1: // metronome speed
 		{
-			editor.ui.tmpDisp16 = editor.metroSpeed;
-			editor.metroSpeedDisp = &editor.ui.tmpDisp16;
-			editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-			editor.ui.numLen = 2;
-			editor.ui.editTextPos = 3261; // (y * 40) + x
+			ui.tmpDisp16 = editor.metroSpeed;
+			editor.metroSpeedDisp = &ui.tmpDisp16;
+			ui.numPtr16 = &ui.tmpDisp16;
+			ui.numLen = 2;
+			ui.editTextPos = 3261; // (y * 40) + x
 			getNumLine(TEXT_EDIT_DECIMAL, PTB_EO_METRO_1);
 		}
 		break;
@@ -2491,11 +2491,11 @@
 
 		case PTB_EO_METRO_2: // metronome channel
 		{
-			editor.ui.tmpDisp16 = editor.metroChannel;
-			editor.metroChannelDisp = &editor.ui.tmpDisp16;
-			editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-			editor.ui.numLen = 2;
-			editor.ui.editTextPos = 3264; // (y * 40) + x
+			ui.tmpDisp16 = editor.metroChannel;
+			editor.metroChannelDisp = &ui.tmpDisp16;
+			ui.numPtr16 = &ui.tmpDisp16;
+			ui.numLen = 2;
+			ui.editTextPos = 3264; // (y * 40) + x
 			getNumLine(TEXT_EDIT_DECIMAL, PTB_EO_METRO_2);
 		}
 		break;
@@ -2502,12 +2502,12 @@
 
 		case PTB_EO_FROM_NUM:
 		{
-			editor.ui.tmpDisp8 = editor.sampleFrom;
-			editor.sampleFromDisp = &editor.ui.tmpDisp8;
-			editor.ui.numPtr8 = &editor.ui.tmpDisp8;
-			editor.ui.numLen = 2;
-			editor.ui.numBits = 8;
-			editor.ui.editTextPos = 3273; // (y * 40) + x
+			ui.tmpDisp8 = editor.sampleFrom;
+			editor.sampleFromDisp = &ui.tmpDisp8;
+			ui.numPtr8 = &ui.tmpDisp8;
+			ui.numLen = 2;
+			ui.numBits = 8;
+			ui.editTextPos = 3273; // (y * 40) + x
 			getNumLine(TEXT_EDIT_HEX, PTB_EO_FROM_NUM);
 		}
 		break;
@@ -2514,12 +2514,12 @@
 
 		case PTB_EO_TO_NUM:
 		{
-			editor.ui.tmpDisp8 = editor.sampleTo;
-			editor.sampleToDisp = &editor.ui.tmpDisp8;
-			editor.ui.numPtr8 = &editor.ui.tmpDisp8;
-			editor.ui.numLen = 2;
-			editor.ui.numBits = 8;
-			editor.ui.editTextPos = 3713; // (y * 40) + x
+			ui.tmpDisp8 = editor.sampleTo;
+			editor.sampleToDisp = &ui.tmpDisp8;
+			ui.numPtr8 = &ui.tmpDisp8;
+			ui.numLen = 2;
+			ui.numBits = 8;
+			ui.editTextPos = 3713; // (y * 40) + x
 			getNumLine(TEXT_EDIT_HEX, PTB_EO_TO_NUM);
 		}
 		break;
@@ -2529,7 +2529,7 @@
 			if (editor.sampleFrom < 0x1F)
 			{
 				editor.sampleFrom++;
-				editor.ui.updateFromText = true;
+				ui.updateFromText = true;
 			}
 		}
 		break;
@@ -2539,7 +2539,7 @@
 			if (editor.sampleFrom > 0x00)
 			{
 				editor.sampleFrom--;
-				editor.ui.updateFromText = true;
+				ui.updateFromText = true;
 			}
 		}
 		break;
@@ -2549,7 +2549,7 @@
 			if (editor.sampleTo < 0x1F)
 			{
 				editor.sampleTo++;
-				editor.ui.updateToText = true;
+				ui.updateToText = true;
 			}
 		}
 		break;
@@ -2559,7 +2559,7 @@
 			if (editor.sampleTo > 0x00)
 			{
 				editor.sampleTo--;
-				editor.ui.updateToText = true;
+				ui.updateToText = true;
 			}
 		}
 		break;
@@ -2567,8 +2567,8 @@
 		case PTB_EO_KEYS:
 		{
 			editor.multiFlag ^= 1;
-			editor.ui.updateTrackerFlags = true;
-			editor.ui.updateKeysText = true;
+			ui.updateTrackerFlags = true;
+			ui.updateKeysText = true;
 		}
 		break;
 		// ----------------------------------------------------------
@@ -2580,13 +2580,13 @@
 			if (!mouse.rightButtonPressed)
 			{
 				editor.mixFlag = true;
-				editor.ui.showTextPtr = editor.mixText;
-				editor.ui.textEndPtr = editor.mixText + 15;
-				editor.ui.textLength = 16;
-				editor.ui.editTextPos = 1936; // (y * 40) + x
-				editor.ui.dstOffset = NULL;
-				editor.ui.dstOffsetEnd = false;
-				editor.ui.updateMixText = true;
+				ui.showTextPtr = editor.mixText;
+				ui.textEndPtr = editor.mixText + 15;
+				ui.textLength = 16;
+				ui.editTextPos = 1936; // (y * 40) + x
+				ui.dstOffset = NULL;
+				ui.dstOffsetEnd = false;
+				ui.updateMixText = true;
 				getTextLine(PTB_EO_MIX);
 			}
 			else
@@ -2651,7 +2651,7 @@
 				free(ptr8_4);
 
 				fixSampleBeep(s);
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					displaySample();
 
 				updateWindowTitle(MOD_IS_MODIFIED);
@@ -2724,7 +2724,7 @@
 			}
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2736,16 +2736,16 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.samplePos = 0;
-				editor.ui.updatePosText = true;
+				ui.updatePosText = true;
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = editor.samplePos;
-				editor.samplePosDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.numBits = 16;
-				editor.ui.editTextPos = 2391; // (y * 40) + x
+				ui.tmpDisp16 = editor.samplePos;
+				editor.samplePosDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.numBits = 16;
+				ui.editTextPos = 2391; // (y * 40) + x
 				getNumLine(TEXT_EDIT_HEX, PTB_EO_POS_NUM);
 			}
 		}
@@ -2764,7 +2764,7 @@
 			}
 
 			boostSample(editor.currSample, false);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2781,7 +2781,7 @@
 			}
 
 			filterSample(editor.currSample, false);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2793,7 +2793,7 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.modulateSpeed = 0;
-				editor.ui.updateModText = true;
+				ui.updateModText = true;
 			}
 		}
 		break;
@@ -2849,7 +2849,7 @@
 			free(ptr8_3);
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2887,7 +2887,7 @@
 			while (ptr8_1 < ptr8_2);
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2923,7 +2923,7 @@
 			while (ptr8_1 < ptr8_2);
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -2978,7 +2978,7 @@
 
 		case PTB_EO_CHORD:
 		{
-			editor.ui.editOpScreen = 3;
+			ui.editOpScreen = 3;
 			renderEditOpScreen();
 		}
 		break;
@@ -3011,7 +3011,7 @@
 			}
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -3050,7 +3050,7 @@
 			}
 
 			fixSampleBeep(s);
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				displaySample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -3066,8 +3066,8 @@
 				break;
 			}
 
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_UPSAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_UPSAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("UPSAMPLE ?", NO_CARRY);
 			renderAskDialog();
@@ -3083,8 +3083,8 @@
 				break;
 			}
 
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_DOWNSAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_DOWNSAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("DOWNSAMPLE ?", NO_CARRY);
 			renderAskDialog();
@@ -3096,15 +3096,15 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.sampleVol = 100;
-				editor.ui.updateVolText = true;
+				ui.updateVolText = true;
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = editor.sampleVol;
-				editor.sampleVolDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 3;
-				editor.ui.editTextPos = 3711; // (y * 40) + x
+				ui.tmpDisp16 = editor.sampleVol;
+				editor.sampleVolDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 3;
+				ui.editTextPos = 3711; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_EO_VOL_NUM);
 			}
 		}
@@ -3132,7 +3132,7 @@
 				}
 
 				fixSampleBeep(s);
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					displaySample();
 
 				updateWindowTitle(MOD_IS_MODIFIED);
@@ -3148,8 +3148,8 @@
 
 		case PTB_EO_DOCHORD:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_MAKE_CHORD;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_MAKE_CHORD;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("MAKE CHORD?", NO_CARRY);
 			renderAskDialog();
@@ -3177,9 +3177,9 @@
 
 			editor.note4 = 36;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3206,9 +3206,9 @@
 			if (editor.note3 >= 36) editor.note3 -= 12;
 			if (editor.note4 >= 36) editor.note4 -= 12;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3222,11 +3222,11 @@
 			}
 			else
 			{
-				editor.ui.changingChordNote = 1;
+				ui.changingChordNote = 1;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			}
-			editor.ui.updateNote1Text = true;
+			ui.updateNote1Text = true;
 		}
 		break;
 
@@ -3241,11 +3241,11 @@
 			}
 			else
 			{
-				editor.ui.changingChordNote = 2;
+				ui.changingChordNote = 2;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			}
-			editor.ui.updateNote2Text = true;
+			ui.updateNote2Text = true;
 		}
 		break;
 
@@ -3260,11 +3260,11 @@
 			}
 			else
 			{
-				editor.ui.changingChordNote = 3;
+				ui.changingChordNote = 3;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			}
-			editor.ui.updateNote3Text = true;
+			ui.updateNote3Text = true;
 		}
 		break;
 
@@ -3279,11 +3279,11 @@
 			}
 			else
 			{
-				editor.ui.changingChordNote = 4;
+				ui.changingChordNote = 4;
 				setStatusMessage("SELECT NOTE", NO_CARRY);
 				pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			}
-			editor.ui.updateNote4Text = true;
+			ui.updateNote4Text = true;
 		}
 		break;
 
@@ -3299,10 +3299,10 @@
 
 			editor.chordLengthMin = false;
 
-			editor.ui.updateNote1Text = true;
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote1Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3329,9 +3329,9 @@
 
 			editor.note4 = 36;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3358,9 +3358,9 @@
 			if (editor.note3 >= 36) editor.note3 -= 12;
 			if (editor.note4 >= 36) editor.note4 -= 12;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3373,10 +3373,10 @@
 			editor.note3 = editor.oldNote3;
 			editor.note4 = editor.oldNote4;
 
-			editor.ui.updateNote1Text = true;
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote1Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3403,9 +3403,9 @@
 
 			editor.note4 = 36;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3432,9 +3432,9 @@
 			if (editor.note3 >= 36) editor.note3 -= 12;
 			if (editor.note4 >= 36) editor.note4 -= 12;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3471,9 +3471,9 @@
 			if (editor.note3 >= 36) editor.note3 -= 12;
 			if (editor.note4 >= 36) editor.note4 -= 12;
 
-			editor.ui.updateNote2Text = true;
-			editor.ui.updateNote3Text = true;
-			editor.ui.updateNote4Text = true;
+			ui.updateNote2Text = true;
+			ui.updateNote3Text = true;
+			ui.updateNote4Text = true;
 
 			recalcChordLength();
 		}
@@ -3482,13 +3482,13 @@
 
 		case PTB_ABOUT:
 		{
-			editor.ui.aboutScreenShown ^= 1;
+			ui.aboutScreenShown ^= 1;
 
-			if (editor.ui.aboutScreenShown)
+			if (ui.aboutScreenShown)
 				renderAboutScreen();
-			else if (editor.ui.visualizerMode == VISUAL_QUADRASCOPE)
+			else if (ui.visualizerMode == VISUAL_QUADRASCOPE)
 				renderQuadrascopeBg();
-			else if (editor.ui.visualizerMode == VISUAL_SPECTRUM)
+			else if (ui.visualizerMode == VISUAL_SPECTRUM)
 				renderSpectrumAnalyzerBg();
 		}
 		break;
@@ -3497,15 +3497,15 @@
 		{
 			if (editor.currMode == MODE_IDLE || editor.currMode == MODE_EDIT)
 			{
-				editor.ui.tmpDisp16 = modEntry->currOrder;
-				if (editor.ui.tmpDisp16 > modEntry->head.orderCount-1)
-					editor.ui.tmpDisp16 = modEntry->head.orderCount-1;
+				ui.tmpDisp16 = modEntry->currOrder;
+				if (ui.tmpDisp16 > modEntry->head.orderCount-1)
+					ui.tmpDisp16 = modEntry->head.orderCount-1;
 
-				editor.ui.tmpDisp16 = modEntry->head.order[editor.ui.tmpDisp16];
-				editor.currPosEdPattDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 2;
-				editor.ui.editTextPos = 2180; // (y * 40) + x
+				ui.tmpDisp16 = modEntry->head.order[ui.tmpDisp16];
+				editor.currPosEdPattDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 2;
+				ui.editTextPos = 2180; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_PE_PATT);
 			}
 		}
@@ -3541,8 +3541,8 @@
 
 		case PTB_PE_EXIT:
 		{
-			editor.ui.aboutScreenShown = false;
-			editor.ui.posEdScreenShown = false;
+			ui.aboutScreenShown = false;
+			ui.posEdScreenShown = false;
 			displayMainScreen();
 		}
 		break;
@@ -3550,11 +3550,11 @@
 		case PTB_POS:
 		case PTB_POSED:
 		{
-			editor.ui.posEdScreenShown ^= 1;
-			if (editor.ui.posEdScreenShown)
+			ui.posEdScreenShown ^= 1;
+			if (ui.posEdScreenShown)
 			{
 				renderPosEdScreen();
-				editor.ui.updatePosEd = true;
+				ui.updatePosEd = true;
 			}
 			else
 			{
@@ -3572,16 +3572,16 @@
 					modEntry->currOrder = 0;
 					editor.currPatternDisp = &modEntry->head.order[modEntry->currOrder];
 
-					if (editor.ui.posEdScreenShown)
-						editor.ui.updatePosEd = true;
+					if (ui.posEdScreenShown)
+						ui.updatePosEd = true;
 				}
 				else
 				{
-					editor.ui.tmpDisp16 = modEntry->currOrder;
-					editor.currPosDisp = &editor.ui.tmpDisp16;
-					editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-					editor.ui.numLen = 3;
-					editor.ui.editTextPos = 169; // (y * 40) + x
+					ui.tmpDisp16 = modEntry->currOrder;
+					editor.currPosDisp = &ui.tmpDisp16;
+					ui.numPtr16 = &ui.tmpDisp16;
+					ui.numLen = 3;
+					ui.editTextPos = 169; // (y * 40) + x
 					getNumLine(TEXT_EDIT_DECIMAL, PTB_POSS);
 				}
 			}
@@ -3596,19 +3596,19 @@
 				{
 					modEntry->head.order[modEntry->currOrder] = 0;
 
-					editor.ui.updateSongSize = true;
+					ui.updateSongSize = true;
 					updateWindowTitle(MOD_IS_MODIFIED);
 
-					if (editor.ui.posEdScreenShown)
-						editor.ui.updatePosEd = true;
+					if (ui.posEdScreenShown)
+						ui.updatePosEd = true;
 				}
 				else
 				{
-					editor.ui.tmpDisp16 = modEntry->head.order[modEntry->currOrder];
-					editor.currPatternDisp = &editor.ui.tmpDisp16;
-					editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-					editor.ui.numLen = 2;
-					editor.ui.editTextPos = 610; // (y * 40) + x
+					ui.tmpDisp16 = modEntry->head.order[modEntry->currOrder];
+					editor.currPatternDisp = &ui.tmpDisp16;
+					ui.numPtr16 = &ui.tmpDisp16;
+					ui.numLen = 2;
+					ui.editTextPos = 610; // (y * 40) + x
 					getNumLine(TEXT_EDIT_DECIMAL, PTB_PATTERNS);
 				}
 			}
@@ -3629,19 +3629,19 @@
 
 					editor.currPosEdPattDisp = &modEntry->head.order[tmp16];
 
-					editor.ui.updateSongSize = true;
+					ui.updateSongSize = true;
 					updateWindowTitle(MOD_IS_MODIFIED);
 
-					if (editor.ui.posEdScreenShown)
-						editor.ui.updatePosEd = true;
+					if (ui.posEdScreenShown)
+						ui.updatePosEd = true;
 				}
 				else
 				{
-					editor.ui.tmpDisp16 = modEntry->head.orderCount;
-					editor.currLengthDisp = &editor.ui.tmpDisp16;
-					editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-					editor.ui.numLen = 3;
-					editor.ui.editTextPos = 1049; // (y * 40) + x
+					ui.tmpDisp16 = modEntry->head.orderCount;
+					editor.currLengthDisp = &ui.tmpDisp16;
+					ui.numPtr16 = &ui.tmpDisp16;
+					ui.numLen = 3;
+					ui.editTextPos = 1049; // (y * 40) + x
 					getNumLine(TEXT_EDIT_DECIMAL, PTB_LENGTHS);
 				}
 			}
@@ -3651,13 +3651,13 @@
 		case PTB_PATTBOX:
 		case PTB_PATTDATA:
 		{
-			if (!editor.ui.introScreenShown && (editor.currMode == MODE_IDLE || editor.currMode == MODE_EDIT || editor.playMode != PLAY_MODE_NORMAL))
+			if (!ui.introScreenShown && (editor.currMode == MODE_IDLE || editor.currMode == MODE_EDIT || editor.playMode != PLAY_MODE_NORMAL))
 			{
-				editor.ui.tmpDisp16 = modEntry->currPattern;
-				editor.currEditPatternDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 2;
-				editor.ui.editTextPos = 5121; // (y * 40) + x
+				ui.tmpDisp16 = modEntry->currPattern;
+				editor.currEditPatternDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 2;
+				ui.editTextPos = 5121; // (y * 40) + x
 				getNumLine(TEXT_EDIT_DECIMAL, PTB_PATTDATA);
 			}
 		}
@@ -3666,12 +3666,12 @@
 		case PTB_SAMPLES:
 		{
 			editor.sampleZero = false;
-			editor.ui.tmpDisp8 = editor.currSample;
-			editor.currSampleDisp = &editor.ui.tmpDisp8;
-			editor.ui.numPtr8 = &editor.ui.tmpDisp8;
-			editor.ui.numLen = 2;
-			editor.ui.numBits = 8;
-			editor.ui.editTextPos = 1930; // (y * 40) + x
+			ui.tmpDisp8 = editor.currSample;
+			editor.currSampleDisp = &ui.tmpDisp8;
+			ui.numPtr8 = &ui.tmpDisp8;
+			ui.numLen = 2;
+			ui.numBits = 8;
+			ui.editTextPos = 1930; // (y * 40) + x
 			getNumLine(TEXT_EDIT_HEX, PTB_SAMPLES);
 		}
 		break;
@@ -3684,12 +3684,12 @@
 			}
 			else
 			{
-				editor.ui.tmpDisp8 = modEntry->samples[editor.currSample].volume;
-				modEntry->samples[editor.currSample].volumeDisp = &editor.ui.tmpDisp8;
-				editor.ui.numPtr8 = &editor.ui.tmpDisp8;
-				editor.ui.numLen = 2;
-				editor.ui.numBits = 8;
-				editor.ui.editTextPos = 2370; // (y * 40) + x
+				ui.tmpDisp8 = modEntry->samples[editor.currSample].volume;
+				modEntry->samples[editor.currSample].volumeDisp = &ui.tmpDisp8;
+				ui.numPtr8 = &ui.tmpDisp8;
+				ui.numLen = 2;
+				ui.numBits = 8;
+				ui.editTextPos = 2370; // (y * 40) + x
 				getNumLine(TEXT_EDIT_HEX, PTB_SVOLUMES);
 			}
 		}
@@ -3710,10 +3710,10 @@
 						s->length = s->loopStart+s->loopLength;
 				}
 
-				editor.ui.updateSongSize = true;
-				editor.ui.updateCurrSampleLength = true;
+				ui.updateSongSize = true;
+				ui.updateCurrSampleLength = true;
 
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					redrawSample();
 
 				recalcChordLength();
@@ -3721,12 +3721,12 @@
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = modEntry->samples[editor.currSample].length;
-				modEntry->samples[editor.currSample].lengthDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.numBits = 16;
-				editor.ui.editTextPos = 2808; // (y * 40) + x
+				ui.tmpDisp16 = modEntry->samples[editor.currSample].length;
+				modEntry->samples[editor.currSample].lengthDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.numBits = 16;
+				ui.editTextPos = 2808; // (y * 40) + x
 				getNumLine(TEXT_EDIT_HEX, PTB_SLENGTHS);
 			}
 		}
@@ -3749,11 +3749,11 @@
 					s->loopStart = 0;
 				}
 
-				editor.ui.updateCurrSampleRepeat = true;
-				if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3)
-					editor.ui.updateLengthText = true;
+				ui.updateCurrSampleRepeat = true;
+				if (ui.editOpScreenShown && ui.editOpScreen == 3)
+					ui.updateLengthText = true;
 
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					setLoopSprites();
 
 				mixerUpdateLoops();
@@ -3761,12 +3761,12 @@
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = modEntry->samples[editor.currSample].loopStart;
-				modEntry->samples[editor.currSample].loopStartDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.numBits = 16;
-				editor.ui.editTextPos = 3248; // (y * 40) + x
+				ui.tmpDisp16 = modEntry->samples[editor.currSample].loopStart;
+				modEntry->samples[editor.currSample].loopStartDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.numBits = 16;
+				ui.editTextPos = 3248; // (y * 40) + x
 				getNumLine(TEXT_EDIT_HEX, PTB_SREPEATS);
 			}
 		}
@@ -3792,11 +3792,11 @@
 				if (s->loopLength < 2)
 					s->loopLength = 2;
 
-				editor.ui.updateCurrSampleReplen = true;
-				if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 3)
-					editor.ui.updateLengthText = true;
+				ui.updateCurrSampleReplen = true;
+				if (ui.editOpScreenShown && ui.editOpScreen == 3)
+					ui.updateLengthText = true;
 
-				if (editor.ui.samplerScreenShown)
+				if (ui.samplerScreenShown)
 					setLoopSprites();
 
 				mixerUpdateLoops();
@@ -3804,12 +3804,12 @@
 			}
 			else
 			{
-				editor.ui.tmpDisp16 = modEntry->samples[editor.currSample].loopLength;
-				modEntry->samples[editor.currSample].loopLengthDisp = &editor.ui.tmpDisp16;
-				editor.ui.numPtr16 = &editor.ui.tmpDisp16;
-				editor.ui.numLen = 4;
-				editor.ui.numBits = 16;
-				editor.ui.editTextPos = 3688; // (y * 40) + x
+				ui.tmpDisp16 = modEntry->samples[editor.currSample].loopLength;
+				modEntry->samples[editor.currSample].loopLengthDisp = &ui.tmpDisp16;
+				ui.numPtr16 = &ui.tmpDisp16;
+				ui.numLen = 4;
+				ui.numBits = 16;
+				ui.editTextPos = 3688; // (y * 40) + x
 				getNumLine(TEXT_EDIT_HEX, PTB_SREPLENS);
 			}
 		}
@@ -3817,16 +3817,16 @@
 
 		case PTB_EDITOP:
 		{
-			if (editor.ui.editOpScreenShown)
+			if (ui.editOpScreenShown)
 			{
-				if (editor.ui.editOpScreen == 3)
-					editor.ui.editOpScreen = 0;
+				if (ui.editOpScreen == 3)
+					ui.editOpScreen = 0;
 				else
-					editor.ui.editOpScreen = (editor.ui.editOpScreen + 1) % 3;
+					ui.editOpScreen = (ui.editOpScreen + 1) % 3;
 			}
 			else
 			{
-				editor.ui.editOpScreenShown = true;
+				ui.editOpScreenShown = true;
 			}
 
 			renderEditOpScreen();
@@ -3835,43 +3835,43 @@
 
 		case PTB_DO_LOADMODULE:
 		{
-			editor.diskop.mode = DISKOP_MODE_MOD;
+			diskop.mode = DISKOP_MODE_MOD;
 			setPathFromDiskOpMode();
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
-			editor.ui.updateDiskOpFileList = true;
-			editor.ui.updateLoadMode = true;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
+			ui.updateDiskOpFileList = true;
+			ui.updateLoadMode = true;
 		}
 		break;
 
 		case PTB_DO_LOADSAMPLE:
 		{
-			editor.diskop.mode = DISKOP_MODE_SMP;
+			diskop.mode = DISKOP_MODE_SMP;
 			setPathFromDiskOpMode();
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
-			editor.ui.updateDiskOpFileList = true;
-			editor.ui.updateLoadMode = true;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
+			ui.updateDiskOpFileList = true;
+			ui.updateLoadMode = true;
 		}
 		break;
 
 		case PTB_LOADSAMPLE: // "LOAD" button next to sample name
 		{
-			editor.ui.posEdScreenShown = false;
-			editor.diskop.mode = DISKOP_MODE_SMP;
+			ui.posEdScreenShown = false;
+			diskop.mode = DISKOP_MODE_SMP;
 			setPathFromDiskOpMode();
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
 
-			if (!editor.ui.diskOpScreenShown)
+			if (!ui.diskOpScreenShown)
 			{
-				editor.ui.diskOpScreenShown = true;
+				ui.diskOpScreenShown = true;
 				renderDiskOpScreen();
 			}
 			else
 			{
-				editor.ui.updateDiskOpFileList = true;
-				editor.ui.updateLoadMode = true;
+				ui.updateDiskOpFileList = true;
+				ui.updateLoadMode = true;
 			}
 		}
 		break;
@@ -3878,17 +3878,17 @@
 
 		case PTB_DO_SAVESAMPLE:
 		{
-			if (editor.diskop.mode != DISKOP_MODE_SMP)
+			if (diskop.mode != DISKOP_MODE_SMP)
 			{
-				editor.diskop.mode = DISKOP_MODE_SMP;
+				diskop.mode = DISKOP_MODE_SMP;
 				setPathFromDiskOpMode();
-				editor.diskop.scrollOffset = 0;
-				editor.diskop.cached = false;
-				editor.ui.updateLoadMode = true;
+				diskop.scrollOffset = 0;
+				diskop.cached = false;
+				ui.updateLoadMode = true;
 			}
 
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_SAVE_SAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_SAVE_SAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("SAVE SAMPLE ?", NO_CARRY);
 			renderAskDialog();
@@ -3897,8 +3897,8 @@
 
 		case PTB_MOD2WAV:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_MOD2WAV;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_MOD2WAV;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("RENDER WAV FILE?", NO_CARRY);
 			renderAskDialog();
@@ -3907,8 +3907,8 @@
 
 		case PTB_SA_RESAMPLENOTE:
 		{
-			editor.ui.changingSmpResample = true;
-			editor.ui.updateResampleNote = true;
+			ui.changingSmpResample = true;
+			ui.updateResampleNote = true;
 			setStatusMessage("SELECT NOTE", NO_CARRY);
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 		}
@@ -3916,8 +3916,8 @@
 
 		case PTB_SA_RESAMPLE:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_RESAMPLE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_RESAMPLE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("RESAMPLE?", NO_CARRY);
 			renderAskDialog();
@@ -3926,7 +3926,7 @@
 
 		case PTB_SA_SAMPLEAREA:
 		{
-			if (editor.ui.sampleMarkingPos == -1)
+			if (ui.sampleMarkingPos == -1)
 			{
 				samplerSamplePressed(MOUSE_BUTTON_NOT_HELD);
 				return true;
@@ -3937,7 +3937,7 @@
 		case PTB_SA_ZOOMBARAREA:
 		{
 			mouse.lastGUIButton = button;
-			if (!editor.ui.forceSampleDrag)
+			if (!ui.forceSampleDrag)
 			{
 				samplerBarPressed(MOUSE_BUTTON_NOT_HELD);
 				return true;
@@ -3963,7 +3963,7 @@
 
 		case PTB_SA_VOLUME:
 		{
-			editor.ui.samplerVolBoxShown = true;
+			ui.samplerVolBoxShown = true;
 			renderSamplerVolBox();
 		}
 		break;
@@ -3970,7 +3970,7 @@
 
 		case PTB_SA_FILTERS:
 		{
-			editor.ui.samplerFiltersBoxShown = true;
+			ui.samplerFiltersBoxShown = true;
 			renderSamplerFiltersBox();
 			fillSampleFilterUndoBuffer();
 		}
@@ -3985,39 +3985,39 @@
 
 		case PTB_DO_REFRESH:
 		{
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
-			editor.ui.updateDiskOpFileList = true;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
+			ui.updateDiskOpFileList = true;
 		}
 		break;
 
 		// TODO: Find a PowerPacker packer and enable this
-		// case PTB_DO_PACKMOD: editor.diskop.modPackFlg ^= 1; break;
+		// case PTB_DO_PACKMOD: diskop.modPackFlg ^= 1; break;
 
 		case PTB_DO_SAMPLEFORMAT:
 		{
-			editor.diskop.smpSaveType = (editor.diskop.smpSaveType + 1) % 3;
-			editor.ui.updateSaveFormatText = true;
+			diskop.smpSaveType = (diskop.smpSaveType + 1) % 3;
+			ui.updateSaveFormatText = true;
 		}
 		break;
 
 		case PTB_DO_MODARROW:
 		{
-			editor.diskop.mode = DISKOP_MODE_MOD;
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
-			editor.ui.updateDiskOpFileList = true;
-			editor.ui.updateLoadMode = true;
+			diskop.mode = DISKOP_MODE_MOD;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
+			ui.updateDiskOpFileList = true;
+			ui.updateLoadMode = true;
 		}
 		break;
 
 		case PTB_DO_SAMPLEARROW:
 		{
-			editor.diskop.mode = DISKOP_MODE_SMP;
-			editor.diskop.scrollOffset = 0;
-			editor.diskop.cached = false;
-			editor.ui.updateDiskOpFileList = true;
-			editor.ui.updateLoadMode = true;
+			diskop.mode = DISKOP_MODE_SMP;
+			diskop.scrollOffset = 0;
+			diskop.cached = false;
+			ui.updateDiskOpFileList = true;
+			ui.updateLoadMode = true;
 		}
 		break;
 
@@ -4037,12 +4037,12 @@
 
 				updateWindowTitle(MOD_IS_MODIFIED);
 
-				editor.ui.updateSongSize = true;
-				editor.ui.updateSongLength = true;
-				editor.ui.updateSongPattern = true;
+				ui.updateSongSize = true;
+				ui.updateSongLength = true;
+				ui.updateSongPattern = true;
 
-				if (editor.ui.posEdScreenShown)
-					editor.ui.updatePosEd = true;
+				if (ui.posEdScreenShown)
+					ui.updatePosEd = true;
 			}
 		}
 		break;
@@ -4061,12 +4061,12 @@
 
 				updateWindowTitle(MOD_IS_MODIFIED);
 
-				editor.ui.updateSongSize = true;
-				editor.ui.updateSongLength = true;
-				editor.ui.updateSongPattern = true;
+				ui.updateSongSize = true;
+				ui.updateSongLength = true;
+				ui.updateSongPattern = true;
 
-				if (editor.ui.posEdScreenShown)
-					editor.ui.updatePosEd = true;
+				if (ui.posEdScreenShown)
+					ui.updatePosEd = true;
 			}
 		}
 		break;
@@ -4073,17 +4073,17 @@
 
 		case PTB_DO_SAVEMODULE:
 		{
-			if (editor.diskop.mode != DISKOP_MODE_MOD)
+			if (diskop.mode != DISKOP_MODE_MOD)
 			{
-				editor.diskop.mode = DISKOP_MODE_MOD;
+				diskop.mode = DISKOP_MODE_MOD;
 				setPathFromDiskOpMode();
-				editor.diskop.scrollOffset = 0;
-				editor.diskop.cached = false;
-				editor.ui.updateLoadMode = true;
+				diskop.scrollOffset = 0;
+				diskop.cached = false;
+				ui.updateLoadMode = true;
 			}
 
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_SAVE_MODULE;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_SAVE_MODULE;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("SAVE MODULE ?", NO_CARRY);
 			renderAskDialog();
@@ -4095,15 +4095,15 @@
 			if (mouse.rightButtonPressed)
 			{
 				memset(editor.currPath, 0, PATH_MAX + 1);
-				editor.ui.updateDiskOpPathText = true;
+				ui.updateDiskOpPathText = true;
 			}
 
-			editor.ui.showTextPtr = editor.currPath;
-			editor.ui.textEndPtr = &editor.currPath[PATH_MAX - 1];
-			editor.ui.textLength = 26;
-			editor.ui.editTextPos = 1043; // (y * 40) + x
-			editor.ui.dstOffset = &editor.textofs.diskOpPath;
-			editor.ui.dstOffsetEnd = false;
+			ui.showTextPtr = editor.currPath;
+			ui.textEndPtr = &editor.currPath[PATH_MAX - 1];
+			ui.textLength = 26;
+			ui.editTextPos = 1043; // (y * 40) + x
+			ui.dstOffset = &ui.diskOpPathTextOffset;
+			ui.dstOffsetEnd = false;
 			getTextLine(PTB_DO_DATAPATH);
 		}
 		break;
@@ -4113,17 +4113,17 @@
 			if (mouse.rightButtonPressed)
 			{
 				memset(modEntry->head.moduleTitle, 0, sizeof (modEntry->head.moduleTitle));
-				editor.ui.updateSongName = true;
+				ui.updateSongName = true;
 				updateWindowTitle(MOD_IS_MODIFIED);
 			}
 			else
 			{
-				editor.ui.showTextPtr = modEntry->head.moduleTitle;
-				editor.ui.textEndPtr = modEntry->head.moduleTitle + 19;
-				editor.ui.textLength = 20;
-				editor.ui.editTextPos = 4133; // (y * 40) + x
-				editor.ui.dstOffset = NULL;
-				editor.ui.dstOffsetEnd = false;
+				ui.showTextPtr = modEntry->head.moduleTitle;
+				ui.textEndPtr = modEntry->head.moduleTitle + 19;
+				ui.textLength = 20;
+				ui.editTextPos = 4133; // (y * 40) + x
+				ui.dstOffset = NULL;
+				ui.dstOffsetEnd = false;
 				getTextLine(PTB_SONGNAME);
 			}
 		}
@@ -4134,17 +4134,17 @@
 			if (mouse.rightButtonPressed)
 			{
 				memset(modEntry->samples[editor.currSample].text, 0, sizeof (modEntry->samples[editor.currSample].text));
-				editor.ui.updateCurrSampleName = true;
+				ui.updateCurrSampleName = true;
 				updateWindowTitle(MOD_IS_MODIFIED);
 			}
 			else
 			{
-				editor.ui.showTextPtr = modEntry->samples[editor.currSample].text;
-				editor.ui.textEndPtr = modEntry->samples[editor.currSample].text + 21;
-				editor.ui.textLength = 22;
-				editor.ui.editTextPos = 4573; // (y * 40) + x
-				editor.ui.dstOffset = NULL;
-				editor.ui.dstOffsetEnd = false;
+				ui.showTextPtr = modEntry->samples[editor.currSample].text;
+				ui.textEndPtr = modEntry->samples[editor.currSample].text + 21;
+				ui.textLength = 22;
+				ui.editTextPos = 4573; // (y * 40) + x
+				ui.dstOffset = NULL;
+				ui.dstOffsetEnd = false;
 				getTextLine(PTB_SAMPLENAME);
 			}
 		}
@@ -4152,9 +4152,9 @@
 
 		case PTB_PAT2SMP_HI:
 		{
-			editor.ui.askScreenShown = false;
-			editor.ui.answerNo = false;
-			editor.ui.answerYes = true;
+			ui.askScreenShown = false;
+			ui.answerNo = false;
+			ui.answerYes = true;
 			editor.pat2SmpHQ = true;
 			handleAskYes();
 		}
@@ -4162,9 +4162,9 @@
 
 		case PTB_PAT2SMP_LO:
 		{
-			editor.ui.askScreenShown = false;
-			editor.ui.answerNo = false;
-			editor.ui.answerYes = true;
+			ui.askScreenShown = false;
+			ui.answerNo = false;
+			ui.answerYes = true;
 			editor.pat2SmpHQ = false;
 			handleAskYes();
 		}
@@ -4172,9 +4172,9 @@
 
 		case PTB_SUREY:
 		{
-			editor.ui.askScreenShown = false;
-			editor.ui.answerNo = false;
-			editor.ui.answerYes = true;
+			ui.askScreenShown = false;
+			ui.answerNo = false;
+			ui.answerYes = true;
 			handleAskYes();
 		}
 		break;
@@ -4182,9 +4182,9 @@
 		case PTB_PAT2SMP_ABORT:
 		case PTB_SUREN:
 		{
-			editor.ui.askScreenShown = false;
-			editor.ui.answerNo = true;
-			editor.ui.answerYes = false;
+			ui.askScreenShown = false;
+			ui.answerNo = true;
+			ui.answerYes = false;
 			handleAskNo();
 		}
 		break;
@@ -4191,20 +4191,20 @@
 
 		case PTB_VISUALS:
 		{
-			if (editor.ui.aboutScreenShown)
+			if (ui.aboutScreenShown)
 			{
-				editor.ui.aboutScreenShown = false;
+				ui.aboutScreenShown = false;
 			}
 			else if (!mouse.rightButtonPressed)
 			{
-				editor.ui.visualizerMode = (editor.ui.visualizerMode + 1) % 2;
-				if (editor.ui.visualizerMode == VISUAL_SPECTRUM)
+				ui.visualizerMode = (ui.visualizerMode + 1) % 2;
+				if (ui.visualizerMode == VISUAL_SPECTRUM)
 					memset((int8_t *)editor.spectrumVolumes, 0, sizeof (editor.spectrumVolumes));
 			}
 
-			if (editor.ui.visualizerMode == VISUAL_QUADRASCOPE)
+			if (ui.visualizerMode == VISUAL_QUADRASCOPE)
 				renderQuadrascopeBg();
-			else if (editor.ui.visualizerMode == VISUAL_SPECTRUM)
+			else if (ui.visualizerMode == VISUAL_SPECTRUM)
 				renderSpectrumAnalyzerBg();
 		}
 		break;
@@ -4211,8 +4211,8 @@
 
 		case PTB_QUIT:
 		{
-			editor.ui.askScreenShown = true;
-			editor.ui.askScreenType = ASK_QUIT;
+			ui.askScreenShown = true;
+			ui.askScreenType = ASK_QUIT;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("REALLY QUIT ?", NO_CARRY);
 			renderAskDialog();
@@ -4308,7 +4308,7 @@
 		case PTB_DISKOP:
 		{
 			editor.blockMarkFlag = false;
-			editor.ui.diskOpScreenShown = true;
+			ui.diskOpScreenShown = true;
 			renderDiskOpScreen();
 		}
 		break;
@@ -4315,8 +4315,8 @@
 
 		case PTB_DO_EXIT:
 		{
-			editor.ui.aboutScreenShown = false;
-			editor.ui.diskOpScreenShown = false;
+			ui.aboutScreenShown = false;
+			ui.diskOpScreenShown = false;
 			editor.blockMarkFlag = false;
 			pointerSetPreviousMode();
 			setPrevStatusMessage();
@@ -4326,10 +4326,10 @@
 
 		case PTB_DO_SCROLLUP:
 		{
-			if (editor.diskop.scrollOffset > 0)
+			if (diskop.scrollOffset > 0)
 			{
-				editor.diskop.scrollOffset--;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset--;
+				ui.updateDiskOpFileList = true;
 			}
 		}
 		break;
@@ -4336,17 +4336,17 @@
 
 		case PTB_DO_SCROLLTOP:
 		{
-			editor.diskop.scrollOffset = 0;
-			editor.ui.updateDiskOpFileList = true;
+			diskop.scrollOffset = 0;
+			ui.updateDiskOpFileList = true;
 		}
 		break;
 
 		case PTB_DO_SCROLLDOWN:
 		{
-			if (editor.diskop.numEntries > DISKOP_LINES && editor.diskop.scrollOffset < editor.diskop.numEntries-DISKOP_LINES)
+			if (diskop.numEntries > DISKOP_LINES && diskop.scrollOffset < diskop.numEntries-DISKOP_LINES)
 			{
-				editor.diskop.scrollOffset++;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset++;
+				ui.updateDiskOpFileList = true;
 			}
 		}
 		break;
@@ -4353,10 +4353,10 @@
 
 		case PTB_DO_SCROLLBOT:
 		{
-			if (editor.diskop.numEntries > DISKOP_LINES)
+			if (diskop.numEntries > DISKOP_LINES)
 			{
-				editor.diskop.scrollOffset = editor.diskop.numEntries - DISKOP_LINES;
-				editor.ui.updateDiskOpFileList = true;
+				diskop.scrollOffset = diskop.numEntries - DISKOP_LINES;
+				ui.updateDiskOpFileList = true;
 			}
 		}
 		break;
@@ -4403,7 +4403,7 @@
 
 		case PTB_EDIT:
 		{
-			if (!editor.ui.samplerScreenShown)
+			if (!ui.samplerScreenShown)
 			{
 				editor.playMode = PLAY_MODE_NORMAL;
 				modStop();
@@ -4416,7 +4416,7 @@
 
 		case PTB_RECORD:
 		{
-			if (!editor.ui.samplerScreenShown)
+			if (!ui.samplerScreenShown)
 			{
 				editor.playMode = PLAY_MODE_PATTERN;
 
@@ -4434,7 +4434,7 @@
 
 		case PTB_CLEAR:
 		{
-			editor.ui.clearScreenShown = true;
+			ui.clearScreenShown = true;
 			pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 			setStatusMessage("PLEASE SELECT", NO_CARRY);
 			renderClearScreen();
@@ -4443,7 +4443,7 @@
 
 		case PTB_CLEARSONG:
 		{
-			editor.ui.clearScreenShown = false;
+			ui.clearScreenShown = false;
 			removeClearScreen();
 			editor.playMode = PLAY_MODE_NORMAL;
 			modStop();
@@ -4456,7 +4456,7 @@
 
 		case PTB_CLEARSAMPLES:
 		{
-			editor.ui.clearScreenShown = false;
+			ui.clearScreenShown = false;
 			removeClearScreen();
 			editor.playMode = PLAY_MODE_NORMAL;
 			modStop();
@@ -4469,7 +4469,7 @@
 
 		case PTB_CLEARALL:
 		{
-			editor.ui.clearScreenShown = false;
+			ui.clearScreenShown = false;
 			removeClearScreen();
 			editor.playMode = PLAY_MODE_NORMAL;
 			modStop();
@@ -4482,7 +4482,7 @@
 
 		case PTB_CLEARCANCEL:
 		{
-			editor.ui.clearScreenShown = false;
+			ui.clearScreenShown = false;
 			removeClearScreen();
 			setPrevStatusMessage();
 			pointerSetPreviousMode();
@@ -4498,7 +4498,7 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.sampleZero = true;
-				editor.ui.updateCurrSampleNum = true;
+				ui.updateCurrSampleNum = true;
 			}
 			else
 			{
@@ -4512,7 +4512,7 @@
 			if (mouse.rightButtonPressed)
 			{
 				editor.sampleZero = true;
-				editor.ui.updateCurrSampleNum = true;
+				ui.updateCurrSampleNum = true;
 			}
 			else
 			{
@@ -4824,7 +4824,7 @@
 				if (editor.sampleFrom < 0x1F)
 				{
 					editor.sampleFrom++;
-					editor.ui.updateFromText = true;
+					ui.updateFromText = true;
 				}
 			}
 		}
@@ -4838,7 +4838,7 @@
 				if (editor.sampleFrom > 0x00)
 				{
 					editor.sampleFrom--;
-					editor.ui.updateFromText = true;
+					ui.updateFromText = true;
 				}
 			}
 		}
@@ -4852,7 +4852,7 @@
 				if (editor.sampleTo < 0x1F)
 				{
 					editor.sampleTo++;
-					editor.ui.updateToText = true;
+					ui.updateToText = true;
 				}
 			}
 		}
@@ -4866,7 +4866,7 @@
 				if (editor.sampleTo > 0x00)
 				{
 					editor.sampleTo--;
-					editor.ui.updateToText = true;
+					ui.updateToText = true;
 				}
 			}
 		}
@@ -4880,7 +4880,7 @@
 				if (!mouse.rightButtonPressed)
 					sampleUpButton();
 				else
-					editor.ui.updateCurrSampleNum = true;
+					ui.updateCurrSampleNum = true;
 			}
 		}
 		break;
@@ -4893,7 +4893,7 @@
 				if (!mouse.rightButtonPressed)
 					sampleDownButton();
 				else
-					editor.ui.updateCurrSampleNum = true;
+					ui.updateCurrSampleNum = true;
 			}
 		}
 		break;
@@ -5106,14 +5106,14 @@
 			{
 				mouse.repeatCounter = 0;
 
-				editor.diskop.scrollOffset--;
+				diskop.scrollOffset--;
 				if (mouse.rightButtonPressed)
-					editor.diskop.scrollOffset -= 3;
+					diskop.scrollOffset -= 3;
 
-				if (editor.diskop.scrollOffset < 0)
-					editor.diskop.scrollOffset = 0;
+				if (diskop.scrollOffset < 0)
+					diskop.scrollOffset = 0;
 
-				editor.ui.updateDiskOpFileList = true;
+				ui.updateDiskOpFileList = true;
 			}
 		}
 		break;
@@ -5124,16 +5124,16 @@
 			{
 				mouse.repeatCounter = 0;
 
-				if (editor.diskop.numEntries > DISKOP_LINES)
+				if (diskop.numEntries > DISKOP_LINES)
 				{
-					editor.diskop.scrollOffset++;
+					diskop.scrollOffset++;
 					if (mouse.rightButtonPressed)
-						editor.diskop.scrollOffset += 3;
+						diskop.scrollOffset += 3;
 
-					if (editor.diskop.scrollOffset > editor.diskop.numEntries-DISKOP_LINES)
-						editor.diskop.scrollOffset = editor.diskop.numEntries-DISKOP_LINES;
+					if (diskop.scrollOffset > diskop.numEntries-DISKOP_LINES)
+						diskop.scrollOffset = diskop.numEntries-DISKOP_LINES;
 
-					editor.ui.updateDiskOpFileList = true;
+					ui.updateDiskOpFileList = true;
 				}
 			}
 		}
@@ -5144,7 +5144,7 @@
 			if (mouse.repeatCounter >= 4)
 			{
 				mouse.repeatCounter = 0;
-				if (!editor.ui.forceSampleDrag)
+				if (!ui.forceSampleDrag)
 					samplerBarPressed(MOUSE_BUTTON_NOT_HELD);
 			}
 		}
--- a/src/pt2_mouse.h
+++ b/src/pt2_mouse.h
@@ -262,7 +262,7 @@
 void setErrPointer(void);
 void pointerSetMode(uint8_t pointerMode, bool carry);
 void pointerSetPreviousMode(void);
-bool setSystemCursor(SDL_Cursor *cursor);
+bool setSystemCursor(SDL_Cursor *cur);
 void freeMouseCursors(void);
 bool createMouseCursors(void);
 
--- a/src/pt2_palette.c
+++ b/src/pt2_palette.c
@@ -1,5 +1,5 @@
+#include "pt2_structs.h"
 #include "pt2_palette.h"
-#include "pt2_header.h"
 
 void setDefaultPalette(void)
 {
--- a/src/pt2_pat2smp.c
+++ b/src/pt2_pat2smp.c
@@ -21,7 +21,7 @@
 {
 	moduleSample_t *s;
 
-	editor.ui.pat2SmpDialogShown = false;
+	ui.pat2SmpDialogShown = false;
 
 	editor.pat2SmpBuf = (int16_t *)malloc(MAX_SAMPLE_LEN * sizeof (int16_t));
 	if (editor.pat2SmpBuf == NULL)
@@ -66,7 +66,7 @@
 	s = &modEntry->samples[editor.currSample];
 
 	// quantize to 8-bit
-	for (uint32_t i = 0; i < editor.pat2SmpPos; i++)
+	for (int32_t i = 0; i < editor.pat2SmpPos; i++)
 		modEntry->sampleData[s->offset+i] = editor.pat2SmpBuf[i] >> 8;
 
 	// clear the rest of the sample
@@ -87,7 +87,7 @@
 		s->fineTune = 1;
 	}
 
-	s->length = editor.pat2SmpPos;
+	s->length = (uint16_t)editor.pat2SmpPos;
 	s->volume = 64;
 	s->loopStart = 0;
 	s->loopLength = 2;
--- a/src/pt2_patternviewer.c
+++ b/src/pt2_patternviewer.c
@@ -4,6 +4,7 @@
 #include "pt2_palette.h"
 #include "pt2_tables.h"
 #include "pt2_textout.h"
+#include "pt2_structs.h"
 
 #define MIDDLE_ROW 7
 #define VISIBLE_ROWS 15
--- a/src/pt2_sampleloader.c
+++ b/src/pt2_sampleloader.c
@@ -194,7 +194,7 @@
 	uint8_t *audioDataU8;
 	int16_t *audioDataS16, tempVol, smp16;
 	uint16_t audioFormat, numChannels, bitsPerSample;
-	int32_t *audioDataS32, smp32, smp32_l, smp32_r;
+	int32_t *audioDataS32, smp32;
 	uint32_t *audioDataU32, i, nameLen, chunkID, chunkSize;
 	uint32_t sampleLength, sampleRate, filesize, loopFlags;
 	uint32_t loopStart, loopEnd, dataPtr, dataLen, fmtPtr, endOfChunk, bytesRead;
@@ -417,10 +417,10 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp16 = (audioDataU8[(i * 2) + 0] - 128) + (audioDataU8[(i * 2) + 1] - 128);
+				smp16 = (audioDataU8[(i << 1) + 0] - 128) + (audioDataU8[(i << 1) + 1] - 128);
 				smp16 = 128 + (smp16 >> 1);
 				audioDataU8[i] = (uint8_t)smp16;
 			}
@@ -432,9 +432,9 @@
 			if (config.sampleLowpass)
 				lowPassSample8BitUnsigned(audioDataU8, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataU8[i] = audioDataU8[i * 2];
+				audioDataU8[i] = audioDataU8[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -453,7 +453,7 @@
 	}
 	else if (bitsPerSample == 16) // 16-BIT INTEGER SAMPLE
 	{
-		sampleLength /= 2;
+		sampleLength >>= 1;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -477,10 +477,10 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32 = (audioDataS16[(i * 2) + 0] + audioDataS16[(i * 2) + 1]) >> 1;
+				smp32 = (audioDataS16[(i << 1) + 0] + audioDataS16[(i << 1) + 1]) >> 1;
 				audioDataS16[i] = (int16_t)smp32;
 			}
 		}
@@ -491,9 +491,9 @@
 			if (config.sampleLowpass)
 				lowPassSample16Bit(audioDataS16, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS16[i] = audioDataS16[i * 2];
+				audioDataS16[i] = audioDataS16[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -538,12 +538,11 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32_l = audioDataS32[(i * 2) + 0] >> 1;
-				smp32_r = audioDataS32[(i * 2) + 1] >> 1;
-				audioDataS32[i] = smp32_l + smp32_r;
+				int64_t smp = ((int64_t)audioDataS32[(i << 1) + 0] + audioDataS32[(i << 1) + 1]) >> 1;
+				audioDataS32[i] = (int32_t)smp;
 			}
 		}
 
@@ -553,9 +552,9 @@
 			if (config.sampleLowpass)
 				lowPassSample32Bit(audioDataS32, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS32[i] = audioDataS32[i * 2];
+				audioDataS32[i] = audioDataS32[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -576,7 +575,7 @@
 	}
 	else if (audioFormat == WAV_FORMAT_PCM && bitsPerSample == 32) // 32-BIT INTEGER SAMPLE
 	{
-		sampleLength /= 4;
+		sampleLength >>= 2;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -600,13 +599,11 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32_l = audioDataS32[(i * 2) + 0] >> 1;
-				smp32_r = audioDataS32[(i * 2) + 1] >> 1;
-
-				audioDataS32[i] = smp32_l + smp32_r;
+				int64_t smp = ((int64_t)audioDataS32[(i << 1) + 0] + audioDataS32[(i << 1) + 1]) >> 1;
+				audioDataS32[i] = (int32_t)smp;
 			}
 		}
 
@@ -616,9 +613,9 @@
 			if (config.sampleLowpass)
 				lowPassSample32Bit(audioDataS32, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS32[i] = audioDataS32[i * 2];
+				audioDataS32[i] = audioDataS32[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -639,7 +636,7 @@
 	}
 	else if (audioFormat == WAV_FORMAT_IEEE_FLOAT && bitsPerSample == 32) // 32-BIT FLOATING POINT SAMPLE
 	{
-		sampleLength /= 4;
+		sampleLength >>= 2;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -665,7 +662,7 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
 				fSmp = (fAudioDataFloat[(i * 2) + 0] + fAudioDataFloat[(i * 2) + 1]) * 0.5f;
@@ -679,9 +676,9 @@
 			if (config.sampleLowpass)
 				lowPassSampleFloat(fAudioDataFloat, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				fAudioDataFloat[i] = fAudioDataFloat[i * 2];
+				fAudioDataFloat[i] = fAudioDataFloat[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -708,7 +705,7 @@
 	}
 	else if (audioFormat == WAV_FORMAT_IEEE_FLOAT && bitsPerSample == 64) // 64-BIT FLOATING POINT SAMPLE
 	{
-		sampleLength /= 8;
+		sampleLength >>= 3;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -734,7 +731,7 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
 				dSmp = (dAudioDataDouble[(i * 2) + 0] + dAudioDataDouble[(i * 2) + 1]) * 0.5;
@@ -748,9 +745,9 @@
 			if (config.sampleLowpass)
 				lowPassSampleDouble(dAudioDataDouble, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				dAudioDataDouble[i] = dAudioDataDouble[i * 2];
+				dAudioDataDouble[i] = dAudioDataDouble[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -783,7 +780,7 @@
 			sampleLength = MAX_SAMPLE_LEN;
 	}
 
-	s->length = sampleLength;
+	s->length = (uint16_t)sampleLength;
 	s->fineTune = 0;
 	s->volume = 64;
 	s->loopStart = 0;
@@ -803,8 +800,8 @@
 		if (forceDownSampling)
 		{
 			// we already downsampled 2x, so we're half the original length
-			loopStart /= 2;
-			loopEnd /= 2;
+			loopStart >>= 1;
+			loopEnd >>= 1;
 		}
 
 		loopStart &= 0xFFFFFFFE;
@@ -814,8 +811,8 @@
 		{
 			if (loopStart+(loopEnd-loopStart) <= s->length)
 			{
-				s->loopStart = loopStart;
-				s->loopLength = loopEnd - loopStart;
+				s->loopStart = (uint16_t)loopStart;
+				s->loopLength = (uint16_t)(loopEnd - loopStart);
 
 				if (s->loopLength < 2)
 				{
@@ -838,7 +835,7 @@
 		if (tempVol > 256)
 			tempVol = 256;
 
-		s->volume = (int8_t)(tempVol / 4);
+		s->volume = (int8_t)(tempVol >> 2);
 	}
 	// ---------------------------
 
@@ -869,7 +866,7 @@
 	{
 		nameLen = (uint32_t)strlen(entryName);
 		for (i = 0; i < 21; i++)
-			s->text[i] = (i < nameLen) ? toupper(entryName[i]) : '\0';
+			s->text[i] = (i < nameLen) ? (char)toupper(entryName[i]) : '\0';
 
 		s->text[21] = '\0';
 		s->text[22] = '\0';
@@ -1001,7 +998,7 @@
 	if (sampleVolume > 65536)
 		sampleVolume = 65536;
 
-	sampleVolume = (int32_t)((sampleVolume / 1024.0) + 0.5);
+	sampleVolume = (sampleVolume + 512) / 1024; // rounded
 	if (sampleVolume > 64)
 		sampleVolume = 64;
 
@@ -1034,9 +1031,9 @@
 
 	if (is16Bit)
 	{
-		sampleLength /= 2;
-		sampleLoopStart /= 2;
-		sampleLoopLength /= 2;
+		sampleLength >>= 1;
+		sampleLoopStart >>= 1;
+		sampleLoopLength >>= 1;
 	}
 
 	sampleLength &= 0xFFFFFFFE;
@@ -1075,7 +1072,7 @@
 	fseek(f, bodyPtr, SEEK_SET);
 	if (is16Bit) // FT2 specific 16SV format (little-endian samples)
 	{
-		fread(sampleData, 1, sampleLength * 2, f);
+		fread(sampleData, 1, sampleLength << 1, f);
 
 		ptr16 = (int16_t *)sampleData;
 		for (i = 0; i < sampleLength; i++)
@@ -1096,11 +1093,11 @@
 	free(sampleData);
 
 	// set sample attributes
-	s->volume = sampleVolume;
+	s->volume = (int8_t)sampleVolume;
 	s->fineTune = 0;
-	s->length = sampleLength;
-	s->loopStart = sampleLoopStart;
-	s->loopLength = sampleLoopLength;
+	s->length = (uint16_t)sampleLength;
+	s->loopStart = (uint16_t)sampleLoopStart;
+	s->loopLength = (uint16_t)sampleLoopLength;
 
 	// read name
 	if (namePtr != 0 && nameLen > 0)
@@ -1133,7 +1130,7 @@
 			nameLen = 21;
 
 		for (i = 0; i < nameLen; i++)
-			s->text[i] = toupper(tmpCharBuf[i]);
+			s->text[i] = (char)toupper(tmpCharBuf[i]);
 	}
 	else
 	{
@@ -1142,7 +1139,7 @@
 			nameLen = 21;
 
 		for (i = 0; i < nameLen; i++)
-			s->text[i] = toupper(entryName[i]);
+			s->text[i] = (char)toupper(entryName[i]);
 	}
 
 	// remove .iff from end of sample name (if present)
@@ -1195,7 +1192,7 @@
 	// set sample attributes
 	s->volume = 64;
 	s->fineTune = 0;
-	s->length = fileSize;
+	s->length = (uint16_t)fileSize;
 	s->loopStart = 0;
 	s->loopLength = 2;
 
@@ -1202,7 +1199,7 @@
 	// copy over sample name
 	nameLen = (uint32_t)strlen(entryName);
 	for (i = 0; i < 21; i++)
-		s->text[i] = (i < nameLen) ? toupper(entryName[i]) : '\0';
+		s->text[i] = (i < nameLen) ? (char)toupper(entryName[i]) : '\0';
 
 	s->text[21] = '\0';
 	s->text[22] = '\0';
@@ -1238,17 +1235,19 @@
 
 bool loadAIFFSample(UNICHAR *fileName, char *entryName, int8_t forceDownSampling)
 {
+	bool unsigned8bit;
 	char compType[4];
 	int8_t *audioDataS8;
 	uint8_t *audioDataU8, sampleRateBytes[10];
 	int16_t *audioDataS16, smp16;
 	uint16_t bitDepth, numChannels;
-	int32_t filesize, *audioDataS32, smp32, smp32_l, smp32_r;
+	int32_t filesize, *audioDataS32, smp32;
 	uint32_t nameLen, i, offset, sampleRate, sampleLength, blockName, blockSize;
 	uint32_t commPtr, commLen, ssndPtr, ssndLen;
 	FILE *f;
 	moduleSample_t *s;
 
+	unsigned8bit = false;
 	loadedFileWasAIFF = true;
 
 	if (forceDownSampling == -1)
@@ -1421,10 +1420,16 @@
 			return false;
 		}
 
+		if (unsigned8bit)
+		{
+			for (i = 0; i < sampleLength; i++)
+				audioDataS8[i] ^= 0x80;
+		}
+
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
 				smp16 = (audioDataS8[(i * 2) + 0] + audioDataS8[(i * 2) + 1]) >> 1;
@@ -1438,9 +1443,9 @@
 			if (config.sampleLowpass)
 				lowPassSample8Bit(audioDataS8, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS8[i] = audioDataS8[i * 2];
+				audioDataS8[i] = audioDataS8[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -1459,7 +1464,7 @@
 	}
 	else if (bitDepth == 16) // 16-BIT INTEGER SAMPLE
 	{
-		sampleLength /= 2;
+		sampleLength >>= 1;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -1487,10 +1492,10 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32 = (audioDataS16[(i * 2) + 0] + audioDataS16[(i * 2) + 1]) >> 1;
+				smp32 = (audioDataS16[(i << 1) + 0] + audioDataS16[(i << 1) + 1]) >> 1;
 				audioDataS16[i] = (int16_t)(smp32);
 			}
 		}
@@ -1501,9 +1506,9 @@
 			if (config.sampleLowpass)
 				lowPassSample16Bit(audioDataS16, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS16[i] = audioDataS16[i * 2];
+				audioDataS16[i] = audioDataS16[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -1528,7 +1533,7 @@
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
-		audioDataS32 = (int32_t *)malloc((sampleLength * 2) * sizeof (int32_t));
+		audioDataS32 = (int32_t *)malloc(sampleLength * sizeof (int32_t));
 		if (audioDataS32 == NULL)
 		{
 			fclose(f);
@@ -1537,7 +1542,7 @@
 		}
 
 		// read sample data
-		if (fread(&audioDataS32[sampleLength / 4], 3, sampleLength, f) != sampleLength)
+		if (fread(&audioDataS32[sampleLength >> 2], 3, sampleLength, f) != sampleLength)
 		{
 			fclose(f);
 			free(audioDataS32);
@@ -1556,12 +1561,11 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32_l = audioDataS32[(i * 2) + 0] >> 1;
-				smp32_r = audioDataS32[(i * 2) + 1] >> 1;
-				audioDataS32[i] = smp32_l + smp32_r;
+				int64_t smp = ((int64_t)audioDataS32[(i << 1) + 0] + audioDataS32[(i << 1) + 1]) >> 1;
+				audioDataS32[i] = (int32_t)smp;
 			}
 		}
 
@@ -1571,9 +1575,9 @@
 			if (config.sampleLowpass)
 				lowPassSample32Bit(audioDataS32, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS32[i] = audioDataS32[i * 2];
+				audioDataS32[i] = audioDataS32[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -1594,7 +1598,7 @@
 	}
 	else if (bitDepth == 32) // 32-BIT INTEGER SAMPLE
 	{
-		sampleLength /= 4;
+		sampleLength >>= 2;
 		if (sampleLength > MAX_SAMPLE_LEN*4)
 			sampleLength = MAX_SAMPLE_LEN*4;
 
@@ -1622,13 +1626,11 @@
 		// convert from stereo to mono (if needed)
 		if (numChannels == 2)
 		{
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 0; i < sampleLength-1; i++) // add right channel to left channel
 			{
-				smp32_l = audioDataS32[(i * 2) + 0] >> 1;
-				smp32_r = audioDataS32[(i * 2) + 1] >> 1;
-
-				audioDataS32[i] = smp32_l + smp32_r;
+				int64_t smp = ((int64_t)audioDataS32[(i << 1) + 0] + audioDataS32[(i << 1) + 1]) >> 1;
+				audioDataS32[i] = (int32_t)smp;
 			}
 		}
 
@@ -1638,9 +1640,9 @@
 			if (config.sampleLowpass)
 				lowPassSample32Bit(audioDataS32, sampleLength, sampleRate, sampleRate / DOWNSAMPLE_CUTOFF_FACTOR);
 
-			sampleLength /= 2;
+			sampleLength >>= 1;
 			for (i = 1; i < sampleLength; i++)
-				audioDataS32[i] = audioDataS32[i * 2];
+				audioDataS32[i] = audioDataS32[i << 1];
 		}
 
 		if (sampleLength > MAX_SAMPLE_LEN)
@@ -1667,7 +1669,7 @@
 			sampleLength = MAX_SAMPLE_LEN;
 	}
 
-	s->length = sampleLength;
+	s->length = (uint16_t)sampleLength;
 	s->fineTune = 0;
 	s->volume = 64;
 	s->loopStart = 0;
@@ -1678,7 +1680,7 @@
 	// copy over sample name
 	nameLen = (uint32_t)strlen(entryName);
 	for (i = 0; i < 21; i++)
-		s->text[i] = (i < nameLen) ? toupper(entryName[i]) : '\0';
+		s->text[i] = (i < nameLen) ? (char)toupper(entryName[i]) : '\0';
 
 	s->text[21] = '\0';
 	s->text[22] = '\0';
@@ -1753,6 +1755,13 @@
 				fclose(f);
 				return loadAIFFSample(fileName, entryName, -1);
 			}
+
+			else if (ID == 0x43464941) // "AIFC" (compressed AIFF)
+			{
+				fclose(f);
+				displayErrorMsg("UNSUPPORTED AIFF!");
+				return false;
+			}
 		}
 	}
 
@@ -1817,7 +1826,7 @@
 	
 	removeWavIffExt(fileName);
 
-	switch (editor.diskop.smpSaveType)
+	switch (diskop.smpSaveType)
 	{
 		case DISKOP_SMP_WAV: strcat(fileName, ".wav"); break;
 		case DISKOP_SMP_IFF: strcat(fileName, ".iff"); break;
@@ -1850,7 +1859,7 @@
 					sprintf(fileName, "%s-%d", tmpBuffer, j);
 				}
 
-				switch (editor.diskop.smpSaveType)
+				switch (diskop.smpSaveType)
 				{
 					default: case DISKOP_SMP_WAV: strcat(fileName, ".wav"); break;
 					         case DISKOP_SMP_IFF: strcat(fileName, ".iff"); break;
@@ -1865,8 +1874,8 @@
 
 	if (checkIfFileExist && stat(fileName, &statBuffer) == 0)
 	{
-		editor.ui.askScreenShown = true;
-		editor.ui.askScreenType = ASK_SAVESMP_OVERWRITE;
+		ui.askScreenShown = true;
+		ui.askScreenType = ASK_SAVESMP_OVERWRITE;
 		pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 		setStatusMessage("OVERWRITE FILE ?", NO_CARRY);
 		renderAskDialog();
@@ -1873,11 +1882,11 @@
 		return -1;
 	}
 
-	if (editor.ui.askScreenShown)
+	if (ui.askScreenShown)
 	{
-		editor.ui.answerNo = false;
-		editor.ui.answerYes = false;
-		editor.ui.askScreenShown = false;
+		ui.answerNo = false;
+		ui.answerYes = false;
+		ui.askScreenShown = false;
 	}
 
 	f = fopen(fileName, "wb");
@@ -1889,7 +1898,7 @@
 
 	sampleSize = modEntry->samples[editor.currSample].length;
 
-	switch (editor.diskop.smpSaveType)
+	switch (diskop.smpSaveType)
 	{
 		default:
 		case DISKOP_SMP_WAV:
@@ -2005,9 +2014,9 @@
 
 	fclose(f);
 
-	editor.diskop.cached = false;
-	if (editor.ui.diskOpScreenShown)
-		editor.ui.updateDiskOpFileList = true;
+	diskop.cached = false;
+	if (ui.diskOpScreenShown)
+		ui.updateDiskOpFileList = true;
 
 	displayMsg("SAMPLE SAVED !");
 	setMsgPointer();
--- a/src/pt2_sampler.c
+++ b/src/pt2_sampler.c
@@ -17,6 +17,8 @@
 #include "pt2_blep.h"
 #include "pt2_mouse.h"
 #include "pt2_scopes.h"
+#include "pt2_sampler.h"
+#include "pt2_structs.h"
 
 #define CENTER_LINE_COLOR 0x303030
 #define MARK_COLOR_1 0x666666 /* inverted background */
@@ -32,6 +34,8 @@
 	uint32_t posFrac, delta;
 } sampleMixer_t;
 
+sampler_t sampler; // globalized
+
 static int32_t samOffsetScaled, lastDrawX, lastDrawY;
 static uint32_t waveInvertTable[8];
 
@@ -43,9 +47,6 @@
 	-127,-126,-118,-106, -91, -71, -49, -25
 };
 
-void setLoopSprites(void);
-void fixSampleBeep(moduleSample_t *s);
-
 void upSample(void)
 {
 	moduleSample_t *s = &modEntry->samples[editor.currSample];
@@ -78,7 +79,7 @@
 	fixSampleBeep(s);
 	updateCurrSample();
 
-	editor.ui.updateSongSize = true;
+	ui.updateSongSize = true;
 	updateWindowTitle(MOD_IS_MODIFIED);
 }
 
@@ -102,7 +103,7 @@
 		ptr8_2[i<<1] = ptr8_2[i];
 	}
 
-	s->length = newLength;
+	s->length = (uint16_t)newLength;
 
 	if (s->loopLength > 2)
 	{
@@ -122,7 +123,7 @@
 	fixSampleBeep(s);
 	updateCurrSample();
 
-	editor.ui.updateSongSize = true;
+	ui.updateSongSize = true;
 	updateWindowTitle(MOD_IS_MODIFIED);
 }
 
@@ -142,10 +143,10 @@
 
 static void updateSamOffset(void)
 {
-	if (editor.sampler.samDisplay == 0)
+	if (sampler.samDisplay == 0)
 		samOffsetScaled = 0;
 	else
-		samOffsetScaled = (editor.sampler.samOffset * SAMPLE_AREA_WIDTH) / editor.sampler.samDisplay; // truncate here
+		samOffsetScaled = (sampler.samOffset * SAMPLE_AREA_WIDTH) / sampler.samDisplay; // truncate here
 }
 
 void fixSampleBeep(moduleSample_t *s)
@@ -168,8 +169,8 @@
 		if (editor.samplePos > s->length)
 			editor.samplePos = s->length;
 
-		if (editor.ui.editOpScreenShown && editor.ui.editOpScreen == 2)
-			editor.ui.updatePosText = true;
+		if (ui.editOpScreenShown && ui.editOpScreen == 2)
+			ui.updatePosText = true;
 	}
 }
 
@@ -185,9 +186,9 @@
 	}
 }
 
-static void sampleLine(int16_t line_x1, int16_t line_x2, int16_t line_y1, int16_t line_y2)
+static void sampleLine(int32_t line_x1, int32_t line_x2, int32_t line_y1, int32_t line_y2)
 {
-	int16_t d, x, y, ax, ay, sx, sy, dx, dy;
+	int32_t d, x, y, ax, ay, sx, sy, dx, dy;
 	uint32_t color = 0x01000000 | video.palette[PAL_QADSCP];
 
 	assert(line_x1 >= 0 || line_x2 >= 0 || line_x1 < SCREEN_W || line_x2 < SCREEN_W);
@@ -253,21 +254,21 @@
 	int32_t pos;
 	uint32_t *dstPtr, pixel, bgPixel;
 
-	if (editor.sampler.samLength > 0 && editor.sampler.samDisplay != editor.sampler.samLength)
+	if (sampler.samLength > 0 && sampler.samDisplay != sampler.samLength)
 	{
-		int32_t roundingBias = (uint32_t)editor.sampler.samLength / 2;
+		int32_t roundingBias = sampler.samLength >> 1;
 
 		// update drag bar coordinates
-		pos = ((editor.sampler.samOffset * 311) + roundingBias) / editor.sampler.samLength;
-		editor.sampler.dragStart = pos + 4;
-		editor.sampler.dragStart = CLAMP(editor.sampler.dragStart, 4, 315);
+		pos = ((sampler.samOffset * 311) + roundingBias) / sampler.samLength;
+		sampler.dragStart = (uint16_t)(pos + 4);
+		sampler.dragStart = CLAMP(sampler.dragStart, 4, 315);
 
-		pos = (((editor.sampler.samDisplay + editor.sampler.samOffset) * 311) + roundingBias) / editor.sampler.samLength;
-		editor.sampler.dragEnd = pos + 5;
-		editor.sampler.dragEnd = CLAMP(editor.sampler.dragEnd, 5, 316);
+		pos = (((sampler.samDisplay + sampler.samOffset) * 311) + roundingBias) / sampler.samLength;
+		sampler.dragEnd = (uint16_t)(pos + 5);
+		sampler.dragEnd = CLAMP(sampler.dragEnd, 5, 316);
 
-		if (editor.sampler.dragStart > editor.sampler.dragEnd-1)
-			editor.sampler.dragStart = editor.sampler.dragEnd-1;
+		if (sampler.dragStart > sampler.dragEnd-1)
+			sampler.dragStart = sampler.dragEnd-1;
 
 		// draw drag bar
 
@@ -279,7 +280,7 @@
 		{
 			for (int32_t x = 4; x < 316; x++)
 			{
-				if (x >= editor.sampler.dragStart && x <= editor.sampler.dragEnd)
+				if (x >= sampler.dragStart && x <= sampler.dragEnd)
 					dstPtr[x] = pixel; // drag bar
 				else
 					dstPtr[x] = bgPixel; // background
@@ -309,10 +310,10 @@
 {
 	const int8_t *ptr8;
 
-	if (editor.sampler.samLength <= 0 || index < 0 || index > editor.sampler.samLength)
+	if (sampler.samLength <= 0 || index < 0 || index > sampler.samLength)
 		return 0;
 
-	ptr8 = editor.sampler.samStart;
+	ptr8 = sampler.samStart;
 	if (ptr8 == NULL)
 		return 0;
 
@@ -321,12 +322,12 @@
 
 int32_t smpPos2Scr(int32_t pos) // sample pos -> screen x pos
 {
-	if (editor.sampler.samDisplay == 0)
+	if (sampler.samDisplay == 0)
 		return 0;
 
-	uint32_t roundingBias = (uint32_t)editor.sampler.samDisplay >> 1;
+	uint32_t roundingBias = (uint32_t)sampler.samDisplay >> 1;
 
-	pos = (((uint32_t)pos * SAMPLE_AREA_WIDTH) + roundingBias) / (uint32_t)editor.sampler.samDisplay; // rounded
+	pos = (((uint32_t)pos * SAMPLE_AREA_WIDTH) + roundingBias) / (uint32_t)sampler.samDisplay; // rounded
 	pos -= samOffsetScaled;
 
 	return pos;
@@ -334,7 +335,7 @@
 
 int32_t scr2SmpPos(int32_t x) // screen x pos -> sample pos
 {
-	if (editor.sampler.samDisplay == 0)
+	if (sampler.samDisplay == 0)
 		return 0;
 
 	if (x < 0)
@@ -341,10 +342,10 @@
 		x = 0;
 
 	x += samOffsetScaled;
-	x = (uint32_t)(x * editor.sampler.samDisplay) / SAMPLE_AREA_WIDTH; // truncate here
+	x = (uint32_t)(x * sampler.samDisplay) / SAMPLE_AREA_WIDTH; // truncate here
 
-	if (x > editor.sampler.samLength)
-		x = editor.sampler.samLength;
+	if (x > sampler.samLength)
+		x = sampler.samLength;
 
 	return x;
 }
@@ -399,11 +400,11 @@
 	}
 
 	// render sample data
-	if (editor.sampler.samDisplay >= 0 && editor.sampler.samDisplay <= MAX_SAMPLE_LEN)
+	if (sampler.samDisplay >= 0 && sampler.samDisplay <= MAX_SAMPLE_LEN)
 	{
 		y1 = SAMPLE_AREA_Y_CENTER - getScaledSample(scr2SmpPos(0));
 
-		if (editor.sampler.samDisplay <= SAMPLE_AREA_WIDTH)
+		if (sampler.samDisplay <= SAMPLE_AREA_WIDTH)
 		{
 			// 1:1 or zoomed in
 			for (x = 1; x < SAMPLE_AREA_WIDTH; x++)
@@ -427,8 +428,8 @@
 				smpNum = scr2SmpPos(x+1) - smpIdx;
 
 				// prevent look-up overflow (yes, this can happen near the end of the sample)
-				if (smpIdx+smpNum > editor.sampler.samLength)
-					smpNum = editor.sampler.samLength - smpNum;
+				if (smpIdx+smpNum > sampler.samLength)
+					smpNum = sampler.samLength - smpNum;
 
 				if (smpNum < 1)
 					smpNum = 1;
@@ -450,10 +451,10 @@
 	}
 
 	// render "sample display" text
-	if (editor.sampler.samStart == editor.sampler.blankSample)
+	if (sampler.samStart == sampler.blankSample)
 		printFiveDecimalsBg(272, 214, 0, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	else
-		printFiveDecimalsBg(272, 214, editor.sampler.samDisplay, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		printFiveDecimalsBg(272, 214, sampler.samDisplay, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 
 	setDragBar();
 	setLoopSprites();
@@ -470,7 +471,7 @@
 	start = smpPos2Scr(editor.markStartOfs);
 	end = smpPos2Scr(editor.markEndOfs);
 
-	if (editor.sampler.samDisplay < editor.sampler.samLength && (start >= SAMPLE_AREA_WIDTH || end < 0))
+	if (sampler.samDisplay < sampler.samLength && (start >= SAMPLE_AREA_WIDTH || end < 0))
 		return; // range is outside of view
 
 	start = CLAMP(start, 0, SAMPLE_AREA_WIDTH-1);
@@ -492,7 +493,7 @@
 
 void displaySample(void)
 {
-	if (!editor.ui.samplerScreenShown)
+	if (!ui.samplerScreenShown)
 		return;
 
 	renderSampleData();
@@ -499,7 +500,7 @@
 	if (editor.markStartOfs != -1)
 		invertRange();
 
-	editor.ui.update9xxPos = true;
+	ui.update9xxPos = true;
 }
 
 void redrawSample(void)
@@ -506,7 +507,7 @@
 {
 	moduleSample_t *s;
 
-	if (!editor.ui.samplerScreenShown)
+	if (!ui.samplerScreenShown)
 		return;
 
 	assert(editor.currSample >= 0 && editor.currSample <= 30);
@@ -514,33 +515,33 @@
 	{
 		editor.markStartOfs = -1;
 
-		editor.sampler.samOffset = 0;
+		sampler.samOffset = 0;
 		updateSamOffset();
 
 		s = &modEntry->samples[editor.currSample];
 		if (s->length > 0)
 		{
-			editor.sampler.samStart = &modEntry->sampleData[s->offset];
-			editor.sampler.samDisplay = s->length;
-			editor.sampler.samLength = s->length;
+			sampler.samStart = &modEntry->sampleData[s->offset];
+			sampler.samDisplay = s->length;
+			sampler.samLength = s->length;
 		}
 		else
 		{
 			// "blank sample" template
-			editor.sampler.samStart = editor.sampler.blankSample;
-			editor.sampler.samLength = SAMPLE_AREA_WIDTH;
-			editor.sampler.samDisplay = SAMPLE_AREA_WIDTH;
+			sampler.samStart = sampler.blankSample;
+			sampler.samLength = SAMPLE_AREA_WIDTH;
+			sampler.samDisplay = SAMPLE_AREA_WIDTH;
 		}
 
 		renderSampleData();
 		updateSamplePos();
 
-		editor.ui.update9xxPos = true;
-		editor.ui.lastSampleOffset = 0x900;
+		ui.update9xxPos = true;
+		ui.lastSampleOffset = 0x900;
 
 		// for quadrascope
-		editor.sampler.samDrawStart = s->offset;
-		editor.sampler.samDrawEnd = s->offset + s->length;
+		sampler.samDrawStart = s->offset;
+		sampler.samDrawEnd = s->offset + s->length;
 	}
 }
 
@@ -758,11 +759,11 @@
 	updateCurrSample();
 
 	// this routine can be called while the sampler toolboxes are open, so redraw them
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 	{
-		if (editor.ui.samplerVolBoxShown)
+		if (ui.samplerVolBoxShown)
 			renderSamplerVolBox();
-		else if (editor.ui.samplerFiltersBoxShown)
+		else if (ui.samplerFiltersBoxShown)
 			renderSamplerFiltersBox();
 	}
 }
@@ -797,10 +798,10 @@
 
 bool allocSamplerVars(void)
 {
-	editor.sampler.copyBuf = (int8_t *)malloc(MAX_SAMPLE_LEN);
-	editor.sampler.blankSample = (int8_t *)calloc(MAX_SAMPLE_LEN, 1);
+	sampler.copyBuf = (int8_t *)malloc(MAX_SAMPLE_LEN);
+	sampler.blankSample = (int8_t *)calloc(MAX_SAMPLE_LEN, 1);
 
-	if (editor.sampler.copyBuf == NULL || editor.sampler.blankSample == NULL)
+	if (sampler.copyBuf == NULL || sampler.blankSample == NULL)
 		return false;
 
 	return true;
@@ -808,16 +809,16 @@
 
 void deAllocSamplerVars(void)
 {
-	if (editor.sampler.copyBuf != NULL)
+	if (sampler.copyBuf != NULL)
 	{
-		free(editor.sampler.copyBuf);
-		editor.sampler.copyBuf = NULL;
+		free(sampler.copyBuf);
+		sampler.copyBuf = NULL;
 	}
 
-	if (editor.sampler.blankSample != NULL)
+	if (sampler.blankSample != NULL)
 	{
-		free(editor.sampler.blankSample);
-		editor.sampler.blankSample = NULL;
+		free(sampler.blankSample);
+		sampler.blankSample = NULL;
 	}
 
 	for (uint8_t i = 0; i < MOD_SAMPLES; i++)
@@ -973,10 +974,10 @@
 	if (editor.note4 == editor.note2) editor.note4 = 36;
 	if (editor.note3 == editor.note2) editor.note3 = 36;
 
-	editor.ui.updateNote1Text = true;
-	editor.ui.updateNote2Text = true;
-	editor.ui.updateNote3Text = true;
-	editor.ui.updateNote4Text = true;
+	ui.updateNote1Text = true;
+	ui.updateNote2Text = true;
+	ui.updateNote3Text = true;
+	ui.updateNote4Text = true;
 
 	// setup some variables
 
@@ -1222,7 +1223,7 @@
 		memset(&writeData[writePos], 0, MAX_SAMPLE_LEN - writeLength);
 
 	// update sample attributes
-	s->length = writeLength;
+	s->length = (uint16_t)writeLength;
 	s->fineTune = 0;
 
 	// scale loop points (and deactivate if overflowing)
@@ -1327,26 +1328,24 @@
 	}
 
 	turnOffVoices();
-	if (mixLength <= MAX_SAMPLE_LEN)
+
+	for (i = 0; i < mixLength; i++)
 	{
-		for (i = 0; i < mixLength; i++)
-		{
-			tmp16 = (i < s2->length) ? (fromPtr1[i] + fromPtr2[i]) : fromPtr1[i];
-			if (editor.halfClipFlag == 0)
-				tmp16 >>= 1;
+		tmp16 = (i < s2->length) ? (fromPtr1[i] + fromPtr2[i]) : fromPtr1[i];
+		if (editor.halfClipFlag == 0)
+			tmp16 >>= 1;
 
-			CLAMP8(tmp16);
-			mixPtr[i] = (int8_t)tmp16;
-		}
-
-		memcpy(&modEntry->sampleData[s3->offset], mixPtr, mixLength);
-		if (mixLength < MAX_SAMPLE_LEN)
-			memset(&modEntry->sampleData[s3->offset + mixLength], 0, MAX_SAMPLE_LEN - mixLength);
+		CLAMP8(tmp16);
+		mixPtr[i] = (int8_t)tmp16;
 	}
 
+	memcpy(&modEntry->sampleData[s3->offset], mixPtr, mixLength);
+	if (mixLength < MAX_SAMPLE_LEN)
+		memset(&modEntry->sampleData[s3->offset + mixLength], 0, MAX_SAMPLE_LEN - mixLength);
+
 	free(mixPtr);
 
-	s3->length = mixLength;
+	s3->length = (uint16_t)mixLength;
 	s3->volume = 64;
 	s3->fineTune = 0;
 	s3->loopStart = 0;
@@ -1361,7 +1360,7 @@
 }
 
 // this is actually treble increase
-void boostSample(int8_t sample, bool ignoreMark)
+void boostSample(int32_t sample, bool ignoreMark)
 {
 	int8_t *smpDat;
 	int16_t tmp16_0, tmp16_1, tmp16_2;
@@ -1417,7 +1416,7 @@
 }
 
 // this is actually treble decrease
-void filterSample(int8_t sample, bool ignoreMark)
+void filterSample(int32_t sample, bool ignoreMark)
 {
 	int8_t *smpDat;
 	int16_t tmp16;
@@ -1478,7 +1477,7 @@
 	{
 		// turn tuning tone on
 
-		editor.tuningChan = (editor.cursor.channel + 1) & 3;
+		editor.tuningChan = (cursor.channel + 1) & 3;
 
 		if (editor.tuningNote > 35)
 			editor.tuningNote = 35;
@@ -1519,11 +1518,11 @@
 		invertRange();
 		if (keyb.shiftPressed && editor.markStartOfs != -1)
 		{
-			editor.markStartOfs = editor.sampler.samOffset;
+			editor.markStartOfs = sampler.samOffset;
 		}
 		else
 		{
-			editor.markStartOfs = editor.sampler.samOffset;
+			editor.markStartOfs = sampler.samOffset;
 			editor.markEndOfs = editor.markStartOfs;
 		}
 		invertRange();
@@ -1550,7 +1549,7 @@
 	}
 	else
 	{
-		middlePos = editor.sampler.samOffset + ((editor.sampler.samDisplay + 1) / 2);
+		middlePos = sampler.samOffset + ((sampler.samDisplay + 1) / 2);
 
 		invertRange();
 		if (keyb.shiftPressed && editor.markStartOfs != -1)
@@ -1631,15 +1630,15 @@
 		return;
 	}
 
-	editor.sampler.copyBufSize = editor.markEndOfs - editor.markStartOfs;
+	sampler.copyBufSize = editor.markEndOfs - editor.markStartOfs;
 
-	if ((int32_t)(editor.markStartOfs + editor.sampler.copyBufSize) > MAX_SAMPLE_LEN)
+	if ((int32_t)(editor.markStartOfs + sampler.copyBufSize) > MAX_SAMPLE_LEN)
 	{
 		displayErrorMsg("COPY ERROR !");
 		return;
 	}
 
-	memcpy(editor.sampler.copyBuf, &modEntry->sampleData[s->offset+editor.markStartOfs], editor.sampler.copyBufSize);
+	memcpy(sampler.copyBuf, &modEntry->sampleData[s->offset+editor.markStartOfs], sampler.copyBufSize);
 }
 
 void samplerSamDelete(uint8_t cut)
@@ -1684,9 +1683,9 @@
 		invertRange();
 		editor.markStartOfs = -1;
 
-		editor.sampler.samStart = editor.sampler.blankSample;
-		editor.sampler.samDisplay = SAMPLE_AREA_WIDTH;
-		editor.sampler.samLength = SAMPLE_AREA_WIDTH;
+		sampler.samStart = sampler.blankSample;
+		sampler.samDisplay = SAMPLE_AREA_WIDTH;
+		sampler.samLength = SAMPLE_AREA_WIDTH;
 
 		s->length = 0;
 		s->loopStart = 0;
@@ -1733,25 +1732,25 @@
 
 	free(tmpBuf);
 
-	editor.sampler.samLength = copyLength;
-	if (editor.sampler.samOffset+editor.sampler.samDisplay >= editor.sampler.samLength)
+	sampler.samLength = copyLength;
+	if (sampler.samOffset+sampler.samDisplay >= sampler.samLength)
 	{
-		if (editor.sampler.samDisplay < editor.sampler.samLength)
+		if (sampler.samDisplay < sampler.samLength)
 		{
-			if (editor.sampler.samLength-editor.sampler.samDisplay < 0)
+			if (sampler.samLength-sampler.samDisplay < 0)
 			{
-				editor.sampler.samOffset = 0;
-				editor.sampler.samDisplay = editor.sampler.samLength;
+				sampler.samOffset = 0;
+				sampler.samDisplay = sampler.samLength;
 			}
 			else
 			{
-				editor.sampler.samOffset = editor.sampler.samLength - editor.sampler.samDisplay;
+				sampler.samOffset = sampler.samLength - sampler.samDisplay;
 			}
 		}
 		else
 		{
-			editor.sampler.samOffset = 0;
-			editor.sampler.samDisplay = editor.sampler.samLength;
+			sampler.samOffset = 0;
+			sampler.samDisplay = sampler.samLength;
 		}
 
 		updateSamOffset();
@@ -1791,15 +1790,15 @@
 
 	s->length = copyLength & 0xFFFE;
 
-	if (editor.sampler.samDisplay <= 2)
+	if (sampler.samDisplay <= 2)
 	{
-		editor.sampler.samStart = editor.sampler.blankSample;
-		editor.sampler.samLength = SAMPLE_AREA_WIDTH;
-		editor.sampler.samDisplay = SAMPLE_AREA_WIDTH;
+		sampler.samStart = sampler.blankSample;
+		sampler.samLength = SAMPLE_AREA_WIDTH;
+		sampler.samDisplay = SAMPLE_AREA_WIDTH;
 	}
 
 	invertRange();
-	if (editor.sampler.samDisplay == 0)
+	if (sampler.samDisplay == 0)
 	{
 		editor.markStartOfs = -1; // clear marking
 	}
@@ -1812,16 +1811,16 @@
 		invertRange();
 	}
 
-	editor.samplePos = editor.markStartOfs;
+	editor.samplePos = (uint16_t)editor.markStartOfs;
 	fixSampleBeep(s);
 	updateSamplePos();
 	recalcChordLength();
 	displaySample();
 
-	editor.ui.updateCurrSampleLength = true;
-	editor.ui.updateCurrSampleRepeat = true;
-	editor.ui.updateCurrSampleReplen = true;
-	editor.ui.updateSongSize = true;
+	ui.updateCurrSampleLength = true;
+	ui.updateCurrSampleRepeat = true;
+	ui.updateCurrSampleReplen = true;
+	ui.updateSongSize = true;
 
 	updateWindowTitle(MOD_IS_MODIFIED);
 }
@@ -1836,7 +1835,7 @@
 
 	assert(editor.currSample >= 0 && editor.currSample <= 30);
 
-	if (editor.sampler.copyBuf == NULL || editor.sampler.copyBufSize == 0)
+	if (sampler.copyBuf == NULL || sampler.copyBufSize == 0)
 	{
 		displayErrorMsg("BUFFER IS EMPTY");
 		return;
@@ -1853,7 +1852,7 @@
 	if (s->length == 0)
 		markStart = 0;
 
-	if (s->length+editor.sampler.copyBufSize > MAX_SAMPLE_LEN)
+	if (s->length+sampler.copyBufSize > MAX_SAMPLE_LEN)
 	{
 		displayErrorMsg("NOT ENOUGH ROOM");
 		return;
@@ -1868,7 +1867,7 @@
 
 	readPos = 0;
 	turnOffVoices();
-	wasZooming = (editor.sampler.samDisplay != editor.sampler.samLength);
+	wasZooming = (sampler.samDisplay != sampler.samLength);
 
 	// copy start part
 	if (markStart > 0)
@@ -1878,22 +1877,22 @@
 	}
 
 	// copy buffer
-	memcpy(&tmpBuf[readPos], editor.sampler.copyBuf, editor.sampler.copyBufSize);
+	memcpy(&tmpBuf[readPos], sampler.copyBuf, sampler.copyBufSize);
 
 	// copy end part
 	if (markStart >= 0)
 	{
-		readPos += editor.sampler.copyBufSize;
+		readPos += sampler.copyBufSize;
 
 		if (s->length-markStart > 0)
 			memcpy(&tmpBuf[readPos], &modEntry->sampleData[s->offset+markStart], s->length - markStart);
 	}
 
-	s->length = (s->length + editor.sampler.copyBufSize) & 0xFFFFFFFE;
-	if (s->length > MAX_SAMPLE_LEN)
-		s->length = MAX_SAMPLE_LEN;
+	int32_t newLength = (s->length + sampler.copyBufSize) & 0xFFFFFFFE;
+	if (newLength > MAX_SAMPLE_LEN)
+		newLength = MAX_SAMPLE_LEN;
 
-	editor.sampler.samLength = s->length;
+	sampler.samLength = (uint16_t)newLength;
 
 	if (s->loopLength > 2) // loop enabled?
 	{
@@ -1902,12 +1901,21 @@
 			if (markStart < s->loopStart+s->loopLength)
 			{
 				// we pasted data inside the loop, increase loop length
-				s->loopLength += editor.sampler.copyBufSize & 0xFFFFFFFE;
-				if (s->loopStart+s->loopLength > s->length)
+
+				if (s->loopLength+sampler.copyBufSize > MAX_SAMPLE_LEN)
 				{
 					s->loopStart = 0;
 					s->loopLength = 2;
 				}
+				else
+				{
+					s->loopLength = (uint16_t)(s->loopLength + sampler.copyBufSize) & 0xFFFE;
+					if (s->loopStart+s->loopLength > s->length)
+					{
+						s->loopStart = 0;
+						s->loopLength = 2;
+					}
+				}
 			}
 
 			// we pasted data after the loop, don't modify loop points
@@ -1915,12 +1923,20 @@
 		else
 		{
 			// we pasted data before the loop, adjust loop start point
-			s->loopStart = (s->loopStart + editor.sampler.copyBufSize) & 0xFFFFFFFE;
-			if (s->loopStart+s->loopLength > s->length)
+			if (s->loopStart+sampler.copyBufSize > MAX_SAMPLE_LEN)
 			{
 				s->loopStart = 0;
 				s->loopLength = 2;
 			}
+			else
+			{
+				s->loopStart = (uint16_t)(s->loopStart + sampler.copyBufSize) & 0xFFFE;
+				if (s->loopStart+s->loopLength > s->length)
+				{
+					s->loopStart = 0;
+					s->loopLength = 2;
+				}
+			}
 		}
 	}
 
@@ -1942,8 +1958,8 @@
 	else
 		redrawSample();
 
-	editor.ui.updateCurrSampleLength = true;
-	editor.ui.updateSongSize = true;
+	ui.updateCurrSampleLength = true;
+	ui.updateSongSize = true;
 
 	updateWindowTitle(MOD_IS_MODIFIED);
 }
@@ -1974,7 +1990,7 @@
 	else
 	{
 		ch->n_start = &modEntry->sampleData[s->offset + startOffset];
-		ch->n_length = (endOffset - startOffset) / 2;
+		ch->n_length = (uint16_t)((uint32_t)(endOffset - startOffset) >> 1);
 		ch->n_loopstart = &modEntry->sampleData[s->offset];
 		ch->n_replen = 1;
 	}
@@ -2009,15 +2025,15 @@
 
 void samplerPlayWaveform(void)
 {
-	playCurrSample(editor.cursor.channel, 0, 0, true);
+	playCurrSample(cursor.channel, 0, 0, true);
 }
 
 void samplerPlayDisplay(void)
 {
-	int32_t start = editor.sampler.samOffset;
-	int32_t end = editor.sampler.samOffset + editor.sampler.samDisplay;
+	int32_t start = sampler.samOffset;
+	int32_t end = sampler.samOffset + sampler.samDisplay;
 
-	playCurrSample(editor.cursor.channel, start, end, false);
+	playCurrSample(cursor.channel, start, end, false);
 }
 
 void samplerPlayRange(void)
@@ -2034,7 +2050,7 @@
 		return;
 	}
 
-	playCurrSample(editor.cursor.channel, editor.markStartOfs, editor.markEndOfs, false);
+	playCurrSample(cursor.channel, editor.markStartOfs, editor.markEndOfs, false);
 }
 
 void setLoopSprites(void)
@@ -2041,7 +2057,7 @@
 {
 	moduleSample_t *s;
 
-	if (!editor.ui.samplerScreenShown)
+	if (!ui.samplerScreenShown)
 	{
 		hideSprite(SPRITE_LOOP_PIN_LEFT);
 		hideSprite(SPRITE_LOOP_PIN_RIGHT);
@@ -2053,17 +2069,24 @@
 	s = &modEntry->samples[editor.currSample];
 	if (s->loopStart+s->loopLength > 2)
 	{
-		if (editor.sampler.samDisplay > 0)
+		if (sampler.samDisplay > 0)
 		{
-			editor.sampler.loopStartPos = smpPos2Scr(s->loopStart);
-			if (editor.sampler.loopStartPos >= 0 && editor.sampler.loopStartPos <= SAMPLE_AREA_WIDTH)
-				setSpritePos(SPRITE_LOOP_PIN_LEFT, editor.sampler.loopStartPos, 138);
+			sampler.loopStartPos = (int16_t)smpPos2Scr(s->loopStart);
+			if (sampler.loopStartPos >= 0 && sampler.loopStartPos <= SAMPLE_AREA_WIDTH)
+				setSpritePos(SPRITE_LOOP_PIN_LEFT, sampler.loopStartPos, 138);
 			else
 				hideSprite(SPRITE_LOOP_PIN_LEFT);
 
-			editor.sampler.loopEndPos = smpPos2Scr(s->loopStart + s->loopLength);
-			if (editor.sampler.loopEndPos >= 0 && editor.sampler.loopEndPos <= SAMPLE_AREA_WIDTH)
-				setSpritePos(SPRITE_LOOP_PIN_RIGHT, editor.sampler.loopEndPos + 3, 138);
+			sampler.loopEndPos = (int16_t)smpPos2Scr(s->loopStart + s->loopLength);
+
+			/* nasty kludge for where the right loop pin would sometimes disappear
+			** when zoomed in and scrolled all the way to the right.
+			*/
+			if (sampler.loopEndPos == SAMPLE_AREA_WIDTH+1)
+				sampler.loopEndPos = SAMPLE_AREA_WIDTH;
+
+			if (sampler.loopEndPos >= 0 && sampler.loopEndPos <= SAMPLE_AREA_WIDTH)
+				setSpritePos(SPRITE_LOOP_PIN_RIGHT, sampler.loopEndPos + 3, 138);
 			else
 				hideSprite(SPRITE_LOOP_PIN_RIGHT);
 		}
@@ -2070,8 +2093,8 @@
 	}
 	else
 	{
-		editor.sampler.loopStartPos = 0;
-		editor.sampler.loopEndPos = 0;
+		sampler.loopStartPos = 0;
+		sampler.loopEndPos = 0;
 
 		hideSprite(SPRITE_LOOP_PIN_LEFT);
 		hideSprite(SPRITE_LOOP_PIN_RIGHT);
@@ -2082,27 +2105,27 @@
 
 void samplerShowAll(void)
 {
-	if (editor.sampler.samDisplay == editor.sampler.samLength)
+	if (sampler.samDisplay == sampler.samLength)
 		return; // don't attempt to show all if already showing all! }
 
-	editor.sampler.samOffset = 0;
-	editor.sampler.samDisplay = editor.sampler.samLength;
+	sampler.samOffset = 0;
+	sampler.samDisplay = sampler.samLength;
 
 	updateSamOffset();
 	displaySample();
 }
 
-static void samplerZoomIn(int32_t step, int16_t x)
+static void samplerZoomIn(int32_t step, int32_t x)
 {
 	int32_t tmpDisplay, tmpOffset;
 
-	if (modEntry->samples[editor.currSample].length == 0 || editor.sampler.samDisplay <= 2)
+	if (modEntry->samples[editor.currSample].length == 0 || sampler.samDisplay <= 2)
 		return;
 
 	if (step < 1)
 		step = 1;
 
-	tmpDisplay = editor.sampler.samDisplay - (step * 2);
+	tmpDisplay = sampler.samDisplay - (step << 1);
 	if (tmpDisplay < 2)
 		tmpDisplay = 2;
 
@@ -2110,35 +2133,35 @@
 
 	step += (((x - (SCREEN_W / 2)) * step) + roundingBias) / (SCREEN_W / 2);
 
-	tmpOffset = editor.sampler.samOffset + step;
+	tmpOffset = sampler.samOffset + step;
 	if (tmpOffset < 0)
 		tmpOffset = 0;
 
-	if (tmpOffset+tmpDisplay > editor.sampler.samLength)
-		tmpOffset = editor.sampler.samLength-tmpDisplay;
+	if (tmpOffset+tmpDisplay > sampler.samLength)
+		tmpOffset = sampler.samLength-tmpDisplay;
 
-	editor.sampler.samOffset = tmpOffset;
-	editor.sampler.samDisplay = tmpDisplay;
+	sampler.samOffset = tmpOffset;
+	sampler.samDisplay = tmpDisplay;
 
 	updateSamOffset();
 	displaySample();
 }
 
-static void samplerZoomOut(int32_t step, int16_t x)
+static void samplerZoomOut(int32_t step, int32_t x)
 {
 	int32_t tmpDisplay, tmpOffset;
 
-	if (modEntry->samples[editor.currSample].length == 0 || editor.sampler.samDisplay == editor.sampler.samLength)
+	if (modEntry->samples[editor.currSample].length == 0 || sampler.samDisplay == sampler.samLength)
 		return;
 
 	if (step < 1)
 		step = 1;
 
-	tmpDisplay = editor.sampler.samDisplay + (step * 2);
-	if (tmpDisplay > editor.sampler.samLength)
+	tmpDisplay = sampler.samDisplay + (step << 1);
+	if (tmpDisplay > sampler.samLength)
 	{
 		tmpOffset  = 0;
-		tmpDisplay = editor.sampler.samLength;
+		tmpDisplay = sampler.samLength;
 	}
 	else
 	{
@@ -2146,16 +2169,16 @@
 
 		step += (((x - (SCREEN_W / 2)) * step) + roundingBias) / (SCREEN_W / 2);
 
-		tmpOffset = editor.sampler.samOffset - step;
+		tmpOffset = sampler.samOffset - step;
 		if (tmpOffset < 0)
 			tmpOffset = 0;
 
-		if (tmpOffset+tmpDisplay > editor.sampler.samLength)
-			tmpOffset = editor.sampler.samLength-tmpDisplay;
+		if (tmpOffset+tmpDisplay > sampler.samLength)
+			tmpOffset = sampler.samLength-tmpDisplay;
 	}
 
-	editor.sampler.samOffset = tmpOffset;
-	editor.sampler.samDisplay = tmpDisplay;
+	sampler.samOffset = tmpOffset;
+	sampler.samDisplay = tmpDisplay;
 
 	updateSamOffset();
 	displaySample();
@@ -2163,17 +2186,17 @@
 
 void samplerZoomInMouseWheel(void)
 {
-	samplerZoomIn((editor.sampler.samDisplay + 5) / 10, mouse.x);
+	samplerZoomIn((sampler.samDisplay + 5) / 10, mouse.x);
 }
 
 void samplerZoomOutMouseWheel(void)
 {
-	samplerZoomOut((editor.sampler.samDisplay + 5) / 10, mouse.x);
+	samplerZoomOut((sampler.samDisplay + 5) / 10, mouse.x);
 }
 
 void samplerZoomOut2x(void)
 {
-	samplerZoomOut((editor.sampler.samDisplay + 1) / 2, SCREEN_W / 2);
+	samplerZoomOut((sampler.samDisplay + 1) / 2, SCREEN_W / 2);
 }
 
 void samplerRangeAll(void)
@@ -2191,8 +2214,8 @@
 	else
 	{
 		invertRange();
-		editor.markStartOfs = editor.sampler.samOffset;
-		editor.markEndOfs = editor.sampler.samOffset + editor.sampler.samDisplay;
+		editor.markStartOfs = sampler.samOffset;
+		editor.markEndOfs = sampler.samOffset + sampler.samDisplay;
 		invertRange();
 	}
 }
@@ -2222,11 +2245,11 @@
 		return;
 	}
 
-	editor.sampler.samDisplay = editor.markEndOfs - editor.markStartOfs;
-	editor.sampler.samOffset = editor.markStartOfs;
+	sampler.samDisplay = editor.markEndOfs - editor.markStartOfs;
+	sampler.samOffset = editor.markStartOfs;
 
-	if (editor.sampler.samDisplay+editor.sampler.samOffset > editor.sampler.samLength)
-		editor.sampler.samOffset = editor.sampler.samLength-editor.sampler.samDisplay;
+	if (sampler.samDisplay+sampler.samOffset > sampler.samLength)
+		sampler.samOffset = sampler.samLength-sampler.samDisplay;
 
 	updateSamOffset();
 
@@ -2244,27 +2267,27 @@
 	{
 		if (mouse.x >= 72 && mouse.x <= 173)
 		{
-			if (mouse.y >= 154 && mouse.y <= 174) editor.ui.forceVolDrag = 1;
-			if (mouse.y >= 165 && mouse.y <= 175) editor.ui.forceVolDrag = 2;
+			if (mouse.y >= 154 && mouse.y <= 174) ui.forceVolDrag = 1;
+			if (mouse.y >= 165 && mouse.y <= 175) ui.forceVolDrag = 2;
 		}
 	}
 	else
 	{
-		if (editor.sampler.lastMouseX != mouse.x)
+		if (sampler.lastMouseX != mouse.x)
 		{
-			editor.sampler.lastMouseX = mouse.x;
-			mouseX = CLAMP(editor.sampler.lastMouseX - 107, 0, 60);
+			sampler.lastMouseX = mouse.x;
+			mouseX = CLAMP(sampler.lastMouseX - 107, 0, 60);
 
-			if (editor.ui.forceVolDrag == 1)
+			if (ui.forceVolDrag == 1)
 			{
 				editor.vol1 = (int16_t)(((mouseX * 200) + (60/2)) / 60); // rounded
-				editor.ui.updateVolFromText = true;
+				ui.updateVolFromText = true;
 				showVolFromSlider();
 			}
-			else if (editor.ui.forceVolDrag == 2)
+			else if (ui.forceVolDrag == 2)
 			{
 				editor.vol2 = (int16_t)(((mouseX * 200) + (60/2)) / 60); // rounded
-				editor.ui.updateVolToText = true;
+				ui.updateVolToText = true;
 				showVolToSlider();
 			}
 		}
@@ -2279,16 +2302,16 @@
 	{
 		if (mouse.x >= 4 && mouse.x <= 315)
 		{
-			if (mouse.x < editor.sampler.dragStart)
+			if (mouse.x < sampler.dragStart)
 			{
-				tmp32 = editor.sampler.samOffset - editor.sampler.samDisplay;
+				tmp32 = sampler.samOffset - sampler.samDisplay;
 				if (tmp32 < 0)
 					tmp32 = 0;
 
-				if (tmp32 == editor.sampler.samOffset)
+				if (tmp32 == sampler.samOffset)
 					return;
 
-				editor.sampler.samOffset = tmp32;
+				sampler.samOffset = tmp32;
 
 				updateSamOffset();
 				displaySample();
@@ -2295,23 +2318,23 @@
 				return;
 			}
 
-			if (mouse.x > editor.sampler.dragEnd)
+			if (mouse.x > sampler.dragEnd)
 			{
-				tmp32 = editor.sampler.samOffset + editor.sampler.samDisplay;
-				if (tmp32+editor.sampler.samDisplay <= editor.sampler.samLength)
+				tmp32 = sampler.samOffset + sampler.samDisplay;
+				if (tmp32+sampler.samDisplay <= sampler.samLength)
 				{
-					if (tmp32 == editor.sampler.samOffset)
+					if (tmp32 == sampler.samOffset)
 						return;
 
-					editor.sampler.samOffset = tmp32;
+					sampler.samOffset = tmp32;
 				}
 				else
 				{
-					tmp32 = editor.sampler.samLength - editor.sampler.samDisplay;
-					if (tmp32 == editor.sampler.samOffset)
+					tmp32 = sampler.samLength - sampler.samDisplay;
+					if (tmp32 == sampler.samOffset)
 						return;
 
-					editor.sampler.samOffset = tmp32;
+					sampler.samOffset = tmp32;
 				}
 
 				updateSamOffset();
@@ -2319,35 +2342,35 @@
 				return;
 			}
 
-			editor.sampler.lastSamPos = mouse.x;
-			editor.sampler.saveMouseX = editor.sampler.lastSamPos - editor.sampler.dragStart;
+			sampler.lastSamPos = mouse.x;
+			sampler.saveMouseX = sampler.lastSamPos - sampler.dragStart;
 
-			editor.ui.forceSampleDrag = true;
+			ui.forceSampleDrag = true;
 		}
 	}
 
-	if (mouse.x != editor.sampler.lastSamPos)
+	if (mouse.x != sampler.lastSamPos)
 	{
-		editor.sampler.lastSamPos = mouse.x;
+		sampler.lastSamPos = mouse.x;
 
-		tmp32 = editor.sampler.lastSamPos - editor.sampler.saveMouseX - 4;
+		tmp32 = sampler.lastSamPos - sampler.saveMouseX - 4;
 		tmp32 = CLAMP(tmp32, 0, SAMPLE_AREA_WIDTH);
 
-		tmp32 = ((tmp32 * editor.sampler.samLength) + (311/2)) / 311; // rounded
-		if (tmp32+editor.sampler.samDisplay <= editor.sampler.samLength)
+		tmp32 = ((tmp32 * sampler.samLength) + (311/2)) / 311; // rounded
+		if (tmp32+sampler.samDisplay <= sampler.samLength)
 		{
-			if (tmp32 == editor.sampler.samOffset)
+			if (tmp32 == sampler.samOffset)
 				return;
 
-			editor.sampler.samOffset = tmp32;
+			sampler.samOffset = tmp32;
 		}
 		else
 		{
-			tmp32 = editor.sampler.samLength - editor.sampler.samDisplay;
-			if (tmp32 == editor.sampler.samOffset)
+			tmp32 = sampler.samLength - sampler.samDisplay;
+			if (tmp32 == sampler.samOffset)
 				return;
 
-			editor.sampler.samOffset = tmp32;
+			sampler.samOffset = tmp32;
 		}
 
 		updateSamOffset();
@@ -2400,26 +2423,26 @@
 		lastDrawX = scr2SmpPos(mx);
 		lastDrawY = mouseYToSampleY(my);
 
-		editor.ui.forceSampleEdit = true;
+		ui.forceSampleEdit = true;
 		updateWindowTitle(MOD_IS_MODIFIED);
 	}
-	else if (mx == editor.sampler.lastMouseX && my == editor.sampler.lastMouseY)
+	else if (mx == sampler.lastMouseX && my == sampler.lastMouseY)
 	{
 		return; // don't continue if we didn't move the mouse
 	}
 
-	if (mx != editor.sampler.lastMouseX)
+	if (mx != sampler.lastMouseX)
 		p = scr2SmpPos(mx);
 	else
 		p = lastDrawX;
 
-	if (!keyb.shiftPressed && my != editor.sampler.lastMouseY)
+	if (!keyb.shiftPressed && my != sampler.lastMouseY)
 		vl = mouseYToSampleY(my);
 	else
 		vl = lastDrawY;
 
-	editor.sampler.lastMouseX = mx;
-	editor.sampler.lastMouseY = my;
+	sampler.lastMouseX = mx;
+	sampler.lastMouseY = my;
 
 	r = p;
 	rvl = vl;
@@ -2494,20 +2517,20 @@
 	{
 		if (mouse.y < 142)
 		{
-			if (mouse.x >= editor.sampler.loopStartPos && mouse.x <= editor.sampler.loopStartPos+3)
+			if (mouse.x >= sampler.loopStartPos && mouse.x <= sampler.loopStartPos+3)
 			{
-				editor.ui.leftLoopPinMoving = true;
-				editor.ui.rightLoopPinMoving = false;
-				editor.ui.sampleMarkingPos = 1;
-				editor.sampler.lastMouseX = mouse.x;
+				ui.leftLoopPinMoving = true;
+				ui.rightLoopPinMoving = false;
+				ui.sampleMarkingPos = 1;
+				sampler.lastMouseX = mouse.x;
 				return;
 			}
-			else if (mouse.x >= editor.sampler.loopEndPos+3 && mouse.x <= editor.sampler.loopEndPos+6)
+			else if (mouse.x >= sampler.loopEndPos+3 && mouse.x <= sampler.loopEndPos+6)
 			{
-				editor.ui.rightLoopPinMoving = true;
-				editor.ui.leftLoopPinMoving = false;
-				editor.ui.sampleMarkingPos = 1;
-				editor.sampler.lastMouseX = mouse.x;
+				ui.rightLoopPinMoving = true;
+				ui.leftLoopPinMoving = false;
+				ui.sampleMarkingPos = 1;
+				sampler.lastMouseX = mouse.x;
 				return;
 			}
 		}
@@ -2517,11 +2540,11 @@
 
 	s = &modEntry->samples[editor.currSample];
 
-	if (editor.ui.leftLoopPinMoving)
+	if (ui.leftLoopPinMoving)
 	{
-		if (editor.sampler.lastMouseX != mouseX)
+		if (sampler.lastMouseX != mouseX)
 		{
-			editor.sampler.lastMouseX = mouseX;
+			sampler.lastMouseX = mouseX;
 
 			tmpPos = (scr2SmpPos(mouseX - 1) - s->loopStart) & 0xFFFFFFFE;
 			if (tmpPos > MAX_SAMPLE_LEN)
@@ -2534,16 +2557,16 @@
 			}
 			else
 			{
-				s->loopStart = s->loopStart + tmpPos;
+				s->loopStart = (uint16_t)(s->loopStart + tmpPos);
 
 				if (s->loopLength-tmpPos > 2)
-					s->loopLength -= tmpPos;
+					s->loopLength -= (uint16_t)tmpPos;
 				else
 					s->loopLength = 2;
 			}
 
-			editor.ui.updateCurrSampleRepeat = true;
-			editor.ui.updateCurrSampleReplen = true;
+			ui.updateCurrSampleRepeat = true;
+			ui.updateCurrSampleReplen = true;
 
 			setLoopSprites();
 			mixerUpdateLoops();
@@ -2553,11 +2576,11 @@
 		return;
 	}
 
-	if (editor.ui.rightLoopPinMoving)
+	if (ui.rightLoopPinMoving)
 	{
-		if (editor.sampler.lastMouseX != mouseX)
+		if (sampler.lastMouseX != mouseX)
 		{
-			editor.sampler.lastMouseX = mouseX;
+			sampler.lastMouseX = mouseX;
 
 			s = &modEntry->samples[editor.currSample];
 
@@ -2564,10 +2587,10 @@
 			tmpPos = (scr2SmpPos(mouseX - 4) - s->loopStart) & 0xFFFFFFFE;
 			tmpPos = CLAMP(tmpPos, 2, MAX_SAMPLE_LEN);
 
-			s->loopLength = tmpPos;
+			s->loopLength = (uint16_t)tmpPos;
 
-			editor.ui.updateCurrSampleRepeat = true;
-			editor.ui.updateCurrSampleReplen = true;
+			ui.updateCurrSampleRepeat = true;
+			ui.updateCurrSampleReplen = true;
 
 			setLoopSprites();
 			mixerUpdateLoops();
@@ -2582,8 +2605,8 @@
 		if (mouseX < 3 || mouseX >= SCREEN_W)
 			return;
 
-		editor.ui.sampleMarkingPos = (int16_t)mouseX;
-		editor.sampler.lastSamPos = editor.ui.sampleMarkingPos;
+		ui.sampleMarkingPos = (int16_t)mouseX;
+		sampler.lastSamPos = ui.sampleMarkingPos;
 
 		invertRange();
 		if (s->length == 0)
@@ -2592,8 +2615,8 @@
 		}
 		else
 		{
-			editor.markStartOfs = scr2SmpPos(editor.ui.sampleMarkingPos - 3);
-			editor.markEndOfs = scr2SmpPos(editor.ui.sampleMarkingPos - 3);
+			editor.markStartOfs = scr2SmpPos(ui.sampleMarkingPos - 3);
+			editor.markEndOfs = scr2SmpPos(ui.sampleMarkingPos - 3);
 
 			if (editor.markEndOfs > s->length)
 				editor.markEndOfs = s->length;
@@ -2621,9 +2644,9 @@
 
 	mouseX = CLAMP(mouseX, 3, SCREEN_W);
 
-	if (mouseX != editor.sampler.lastSamPos)
+	if (mouseX != sampler.lastSamPos)
 	{
-		editor.sampler.lastSamPos = (uint16_t)mouseX;
+		sampler.lastSamPos = (uint16_t)mouseX;
 
 		invertRange();
 		if (s->length == 0)
@@ -2632,15 +2655,15 @@
 		}
 		else
 		{
-			if (editor.sampler.lastSamPos > editor.ui.sampleMarkingPos)
+			if (sampler.lastSamPos > ui.sampleMarkingPos)
 			{
-				editor.markStartOfs = scr2SmpPos(editor.ui.sampleMarkingPos - 3);
-				editor.markEndOfs = scr2SmpPos(editor.sampler.lastSamPos - 3);
+				editor.markStartOfs = scr2SmpPos(ui.sampleMarkingPos - 3);
+				editor.markEndOfs = scr2SmpPos(sampler.lastSamPos - 3);
 			}
 			else
 			{
-				editor.markStartOfs = scr2SmpPos(editor.sampler.lastSamPos - 3);
-				editor.markEndOfs = scr2SmpPos(editor.ui.sampleMarkingPos - 3);
+				editor.markStartOfs = scr2SmpPos(sampler.lastSamPos - 3);
+				editor.markEndOfs = scr2SmpPos(ui.sampleMarkingPos - 3);
 			}
 
 			if (editor.markEndOfs > s->length)
@@ -2682,8 +2705,8 @@
 	{
 		// disable loop
 
-		editor.sampler.tmpLoopStart = s->loopStart;
-		editor.sampler.tmpLoopLength = s->loopLength;
+		sampler.tmpLoopStart = s->loopStart;
+		sampler.tmpLoopLength = s->loopLength;
 
 		s->loopStart = 0;
 		s->loopLength = 2;
@@ -2692,7 +2715,7 @@
 	{
 		// enable loop
 
-		if (editor.sampler.tmpLoopStart == 0 && editor.sampler.tmpLoopLength == 0)
+		if (sampler.tmpLoopStart == 0 && sampler.tmpLoopLength == 0)
 		{
 			s->loopStart = 0;
 			s->loopLength = s->length;
@@ -2699,8 +2722,8 @@
 		}
 		else
 		{
-			s->loopStart = editor.sampler.tmpLoopStart;
-			s->loopLength = editor.sampler.tmpLoopLength;
+			s->loopStart = (uint16_t)sampler.tmpLoopStart;
+			s->loopLength = (uint16_t)sampler.tmpLoopLength;
 
 			if (s->loopStart+s->loopLength > s->length)
 			{
@@ -2710,8 +2733,8 @@
 		}
 	}
 
-	editor.ui.updateCurrSampleRepeat = true;
-	editor.ui.updateCurrSampleReplen = true;
+	ui.updateCurrSampleRepeat = true;
+	ui.updateCurrSampleReplen = true;
 
 	displaySample();
 	mixerUpdateLoops();
@@ -2721,18 +2744,18 @@
 
 void exitFromSam(void)
 {
-	editor.ui.samplerScreenShown = false;
+	ui.samplerScreenShown = false;
 	memcpy(&video.frameBuffer[121 * SCREEN_W], &trackerFrameBMP[121 * SCREEN_W], 320 * 134 * sizeof (int32_t));
 
 	updateCursorPos();
 	setLoopSprites();
 
-	editor.ui.updateStatusText = true;
-	editor.ui.updateSongSize = true;
-	editor.ui.updateSongTiming = true;
-	editor.ui.updateSongBPM = true;
-	editor.ui.updateCurrPattText = true;
-	editor.ui.updatePatternData = true;
+	ui.updateStatusText = true;
+	ui.updateSongSize = true;
+	ui.updateSongTiming = true;
+	ui.updateSongBPM = true;
+	ui.updateCurrPattText = true;
+	ui.updatePatternData = true;
 
 	editor.markStartOfs = -1;
 }
@@ -2739,21 +2762,21 @@
 
 void samplerScreen(void)
 {
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 	{
 		exitFromSam();
 		return;
 	}
 
-	editor.ui.samplerScreenShown = true;
+	ui.samplerScreenShown = true;
 	memcpy(&video.frameBuffer[(121 * SCREEN_W)], samplerScreenBMP, 320 * 134 * sizeof (int32_t));
 	hideSprite(SPRITE_PATTERN_CURSOR);
 
-	editor.ui.updateStatusText = true;
-	editor.ui.updateSongSize = true;
-	editor.ui.updateSongTiming = true;
-	editor.ui.updateResampleNote = true;
-	editor.ui.update9xxPos = true;
+	ui.updateStatusText = true;
+	ui.updateSongSize = true;
+	ui.updateSongTiming = true;
+	ui.updateResampleNote = true;
+	ui.update9xxPos = true;
 
 	redrawSample();
 }
@@ -2764,7 +2787,7 @@
 	int32_t pos;
 
 	hideSprite(SPRITE_SAMPLING_POS_LINE);
-	if (!editor.ui.samplerScreenShown || editor.ui.samplerVolBoxShown || editor.ui.samplerFiltersBoxShown)
+	if (!ui.samplerScreenShown || ui.samplerVolBoxShown || ui.samplerFiltersBoxShown)
 		return;
 
 	for (i = 0; i < AMIGA_VOICES; i++)
--- a/src/pt2_sampler.h
+++ b/src/pt2_sampler.h
@@ -2,7 +2,21 @@
 
 #include <stdint.h>
 #include <stdbool.h>
+#include "pt2_structs.h"
 
+typedef struct sampler_t
+{
+	const int8_t *samStart;
+	int8_t *blankSample, *copyBuf;
+	int16_t loopStartPos, loopEndPos;
+	uint16_t dragStart, dragEnd;
+	int32_t samPointWidth, samOffset, samDisplay, samLength, saveMouseX, lastSamPos;
+	int32_t lastMouseX, lastMouseY, tmpLoopStart, tmpLoopLength;
+	uint32_t copyBufSize, samDrawStart, samDrawEnd;
+} sampler_t;
+
+extern sampler_t sampler; // pt2_sampler.c
+
 void downSample(void);
 void upSample(void);
 void createSampleMarkTable(void);
@@ -15,8 +29,8 @@
 void mixChordSample(void);
 void samplerResample(void);
 void doMix(void);
-void boostSample(int8_t sample, bool ignoreMark);
-void filterSample(int8_t sample, bool ignoreMark);
+void boostSample(int32_t sample, bool ignoreMark);
+void filterSample(int32_t sample, bool ignoreMark);
 void toggleTuningTone(void);
 void samplerSamDelete(uint8_t cut);
 void samplerSamPaste(void);
--- a/src/pt2_scopes.c
+++ b/src/pt2_scopes.c
@@ -16,6 +16,7 @@
 #include "pt2_sampler.h"
 #include "pt2_palette.h"
 #include "pt2_tables.h"
+#include "pt2_structs.h"
 
 // this uses code that is not entirely thread safe, but I have never had any issues so far...
 
@@ -27,7 +28,7 @@
 scopeChannel_t scope[AMIGA_VOICES]; // global
 scopeChannelExt_t scopeExt[AMIGA_VOICES]; // global
 
-int32_t getSampleReadPos(uint8_t ch, uint8_t smpNum)
+int32_t getSampleReadPos(int32_t ch, uint8_t smpNum)
 {
 	const int8_t *data;
 	int32_t pos;
@@ -58,7 +59,7 @@
 	return -1;
 }
 
-void setScopeDelta(uint8_t ch, uint32_t delta)
+void setScopeDelta(int32_t ch, uint32_t delta)
 {
 	scope[ch].delta = delta;
 }
@@ -197,7 +198,7 @@
 
 			smpPeak = ((smpPeak * 48) + (1 << 12)) >> 13; // rounded
 			if (smpPeak > editor.realVuMeterVolumes[i])
-				editor.realVuMeterVolumes[i] = smpPeak;
+				editor.realVuMeterVolumes[i] = (int8_t)smpPeak;
 		}
 	}
 }
@@ -212,7 +213,7 @@
 	scopeChannelExt_t *se;
 
 	scopesReading = true;
-	if (editor.ui.visualizerMode == VISUAL_QUADRASCOPE)
+	if (ui.visualizerMode == VISUAL_QUADRASCOPE)
 	{
 		// --- QUADRASCOPE ---
 
@@ -402,7 +403,7 @@
 	return true;
 }
 
-void stopScope(uint8_t ch)
+void stopScope(int32_t ch)
 {
 	while (scopesReading);
 	memset(&scopeExt[ch], 0, sizeof (scopeChannelExt_t));
--- a/src/pt2_scopes.h
+++ b/src/pt2_scopes.h
@@ -20,12 +20,12 @@
 	int32_t newLength, newLoopStart;
 } scopeChannelExt_t;
 
-void setScopeDelta(uint8_t ch, uint32_t delta);
-int32_t getSampleReadPos(uint8_t ch, uint8_t smpNum);
+void setScopeDelta(int32_t ch, uint32_t delta);
+int32_t getSampleReadPos(int32_t ch, uint8_t smpNum);
 void updateScopes(void);
 void drawScopes(void);
 bool initScopes(void);
-void stopScope(uint8_t ch);
+void stopScope(int32_t ch);
 void stopAllScopes(void);
 
 extern scopeChannel_t scope[AMIGA_VOICES];
--- /dev/null
+++ b/src/pt2_structs.c
@@ -1,0 +1,9 @@
+#include "pt2_structs.h"
+
+keyb_t keyb;
+mouse_t mouse;
+video_t video;
+editor_t editor;
+diskop_t diskop;
+cursor_t cursor;
+ui_t ui;
--- /dev/null
+++ b/src/pt2_structs.h
@@ -1,0 +1,243 @@
+#pragma once
+
+#ifdef _WIN32
+#define WIN32_MEAN_AND_LEAN
+#include <windows.h>
+#endif
+
+#include <stdint.h>
+#include <stdbool.h>
+#include "pt2_header.h"
+
+// for .WAV sample loading/saving
+typedef struct wavHeader_t
+{
+	uint32_t chunkID, chunkSize, format, subchunk1ID, subchunk1Size;
+	uint16_t audioFormat, numChannels;
+	uint32_t sampleRate, byteRate;
+	uint16_t blockAlign, bitsPerSample;
+	uint32_t subchunk2ID, subchunk2Size;
+} wavHeader_t;
+
+typedef struct sampleLoop_t
+{
+	uint32_t dwIdentifier, dwType, dwStart;
+	uint32_t dwEnd, dwFraction, dwPlayCount;
+} sampleLoop_t;
+
+typedef struct samplerChunk_t
+{
+	uint32_t chunkID, chunkSize, dwManufacturer, dwProduct;
+	uint32_t dwSamplePeriod, dwMIDIUnityNote, wMIDIPitchFraction;
+	uint32_t dwSMPTEFormat, dwSMPTEOffset, cSampleLoops, cbSamplerData;
+	sampleLoop_t loop;
+} samplerChunk_t;
+// -----------------------------------------
+
+typedef struct note_t
+{
+	uint8_t param, sample, command;
+	uint16_t period;
+} note_t;
+
+typedef struct moduleHeader_t
+{
+	char moduleTitle[20 + 1];
+	uint16_t order[MOD_ORDERS], orderCount;
+	uint16_t initialTempo; // used for STK/UST modules after module is loaded
+} moduleHeader_t;
+
+typedef struct moduleSample_t
+{
+	volatile int8_t *volumeDisp;
+	volatile uint16_t *lengthDisp, *loopStartDisp, *loopLengthDisp;
+	char text[22 + 1];
+	int8_t volume;
+	uint8_t fineTune;
+	uint16_t length, loopStart, loopLength;
+	int32_t offset;
+} moduleSample_t;
+
+typedef struct moduleChannel_t
+{
+	int8_t *n_start, *n_wavestart, *n_loopstart, n_chanindex, n_volume;
+	int8_t n_toneportdirec, n_vibratopos, n_tremolopos, n_pattpos, n_loopcount;
+	uint8_t n_wavecontrol, n_glissfunk, n_sampleoffset, n_toneportspeed;
+	uint8_t n_vibratocmd, n_tremolocmd, n_finetune, n_funkoffset, n_samplenum;
+	int16_t n_period, n_note, n_wantedperiod;
+	uint16_t n_cmd, n_length, n_replen;
+	uint32_t n_scopedelta;
+} moduleChannel_t;
+
+typedef struct module_t
+{
+	int8_t *sampleData, currRow, modified, row;
+	uint8_t currSpeed, moduleLoaded;
+	uint16_t currOrder, currPattern, currBPM;
+	uint32_t rowsCounter, rowsInTotal;
+	moduleHeader_t head;
+	moduleSample_t samples[MOD_SAMPLES];
+	moduleChannel_t channels[AMIGA_VOICES];
+	note_t *patterns[MAX_PATTERNS];
+} module_t;
+
+typedef struct keyb_t
+{
+	bool repeatKey, delayKey;
+	bool shiftPressed, leftCtrlPressed, leftAltPressed;
+	bool leftCommandPressed, leftAmigaPressed, keypadEnterPressed;
+	uint8_t repeatCounter, delayCounter;
+	uint64_t repeatFrac;
+	SDL_Scancode lastRepKey, lastKey;
+} keyb_t;
+
+typedef struct mouse_t
+{
+	volatile bool setPosFlag;
+	bool buttonWaiting, leftButtonPressed, rightButtonPressed;
+	uint8_t repeatCounter, buttonWaitCounter;
+	int32_t x, y, lastMouseX, setPosX, setPosY, lastGUIButton, lastSmpFilterButton, prevX, prevY;
+	uint32_t buttonState;
+} mouse_t;
+
+typedef struct video_t
+{
+	bool fullscreen, vsync60HzPresent, windowHidden;
+	int32_t renderX, renderY, renderW, renderH, displayW, displayH;
+	int32_t xScale, yScale;
+	double dMouseXMul, dMouseYMul;
+	SDL_PixelFormat *pixelFormat;
+	uint32_t *frameBuffer, *frameBufferUnaligned;
+
+	SDL_Window *window;
+	SDL_Renderer *renderer;
+	SDL_Texture  *texture;
+
+	uint32_t palette[PALETTE_NUM];
+
+#ifdef _WIN32
+	HWND hWnd;
+#endif
+} video_t;
+
+typedef struct editor_t
+{
+	volatile int8_t vuMeterVolumes[AMIGA_VOICES], spectrumVolumes[SPECTRUM_BAR_NUM];
+	volatile int8_t *sampleFromDisp, *sampleToDisp, *currSampleDisp, realVuMeterVolumes[AMIGA_VOICES];
+	volatile bool songPlaying, programRunning, isWAVRendering, isSMPRendering, smpRenderingDone;
+	volatile uint8_t modTick, modSpeed;
+	volatile uint16_t *quantizeValueDisp, *metroSpeedDisp, *metroChannelDisp, *sampleVolDisp;
+	volatile uint16_t *vol1Disp, *vol2Disp, *currEditPatternDisp, *currPosDisp, *currPatternDisp;
+	volatile uint16_t *currPosEdPattDisp, *currLengthDisp, *lpCutOffDisp, *hpCutOffDisp;
+	volatile uint16_t *samplePosDisp, *chordLengthDisp;
+
+	char mixText[16];
+	char *entryNameTmp, *currPath, *dropTempFileName;
+	UNICHAR *fileNameTmpU, *currPathU, *modulesPathU, *samplesPathU;
+
+	bool errorMsgActive, errorMsgBlock, multiFlag, metroFlag, keypadToggle8CFlag, normalizeFiltersFlag;
+	bool sampleAllFlag, halfClipFlag, newOldFlag, pat2SmpHQ, mixFlag, useLEDFilter;
+	bool modLoaded, autoInsFlag, repeatKeyFlag, sampleZero, tuningFlag;
+	bool stepPlayEnabled, stepPlayBackwards, blockBufferFlag, blockMarkFlag, didQuantize;
+	bool swapChannelFlag, configFound, abortMod2Wav, chordLengthMin, rowVisitTable[MOD_ORDERS * MOD_ROWS];
+	bool muted[AMIGA_VOICES];
+
+	int8_t smpRedoFinetunes[MOD_SAMPLES], smpRedoVolumes[MOD_SAMPLES], multiModeNext[4], trackPattFlag;
+	int8_t *smpRedoBuffer[MOD_SAMPLES], *tempSample, currSample, recordMode, sampleFrom, sampleTo, autoInsSlot;
+	int8_t keypadSampleOffset, note1, note2, note3, note4, oldNote1, oldNote2, oldNote3, oldNote4;
+	uint8_t playMode, currMode, tuningChan, tuningVol, errorMsgCounter, buffFromPos, buffToPos;
+	uint8_t blockFromPos, blockToPos, timingMode, f6Pos, f7Pos, f8Pos, f9Pos, f10Pos, keyOctave, pNoteFlag;
+	uint8_t tuningNote, resampleNote, initialTempo, initialSpeed, editMoveAdd;
+
+	int16_t *pat2SmpBuf, modulateSpeed;
+	uint16_t metroSpeed, metroChannel, sampleVol, samplePos, chordLength;
+	uint16_t effectMacros[10], oldTempo, currPlayNote, vol1, vol2, lpCutOff, hpCutOff;
+	uint16_t smpRedoLoopStarts[MOD_SAMPLES], smpRedoLoopLengths[MOD_SAMPLES], smpRedoLengths[MOD_SAMPLES];
+	int32_t modulatePos, modulateOffset, markStartOfs, markEndOfs, pat2SmpPos;
+	uint32_t musicTime, vblankTimeLen, vblankTimeLenFrac;
+	double dPerfFreq, dPerfFreqMulMicro;
+	note_t trackBuffer[MOD_ROWS], cmdsBuffer[MOD_ROWS], blockBuffer[MOD_ROWS];
+	note_t patternBuffer[MOD_ROWS * AMIGA_VOICES], undoBuffer[MOD_ROWS * AMIGA_VOICES];
+	SDL_Thread *mod2WavThread, *pat2SmpThread;
+} editor_t;
+
+typedef struct diskop_t
+{
+	volatile bool cached, isFilling, forceStopReading;
+	bool modPackFlg;
+	int8_t mode, smpSaveType;
+	int32_t numEntries, scrollOffset;
+	SDL_Thread *fillThread;
+} diskop_t;
+
+typedef struct cursor_t
+{
+	uint8_t lastPos, pos, mode, channel;
+	uint32_t bgBuffer[11 * 14];
+} cursor_t;
+
+typedef struct ui_t
+{
+	char statusMessage[18], prevStatusMessage[18];
+	char *dstPtr, *editPos, *textEndPtr, *showTextPtr;
+
+	bool answerNo, answerYes, throwExit, editTextFlag, askScreenShown, samplerScreenShown;
+	bool leftLoopPinMoving, rightLoopPinMoving, changingSmpResample, changingDrumPadNote;
+	bool forceSampleDrag, forceSampleEdit, introScreenShown;
+	bool aboutScreenShown, clearScreenShown, posEdScreenShown, diskOpScreenShown;
+	bool samplerVolBoxShown, samplerFiltersBoxShown, editOpScreenShown;
+
+	int8_t *numPtr8, tmpDisp8, pointerMode, editOpScreen, editTextType, askScreenType;
+	int8_t visualizerMode, previousPointerMode, forceVolDrag, changingChordNote;
+	uint8_t numLen, numBits;
+
+	// render/update flags
+	bool updateStatusText, updatePatternData;
+	bool updateSongName, updateMod2WavDialog, mod2WavFinished;
+
+	// edit op. #2
+	bool updateRecordText, updateQuantizeText, updateMetro1Text, updateMetro2Text;
+	bool updateFromText, updateKeysText, updateToText;
+
+	// edit op. #3
+	bool updateMixText, updatePosText, updateModText, updateVolText;
+
+	// edit op. #4 (sample chord editor)
+	bool updateLengthText, updateNote1Text, updateNote2Text;
+	bool updateNote3Text, updateNote4Text;
+
+	//sampler
+	bool updateResampleNote, updateVolFromText, updateVolToText, updateLPText;
+	bool updateHPText, updateNormFlag, update9xxPos;
+
+	// general
+	bool updateSongPos, updateSongPattern, updateSongLength, updateCurrSampleFineTune;
+	bool updateCurrSampleNum, updateCurrSampleVolume, updateCurrSampleLength;
+	bool updateCurrSampleRepeat, updateCurrSampleReplen, updateCurrSampleName;
+	bool updateSongSize, updateSongTiming, updateSongBPM;
+	bool updateCurrPattText, updateTrackerFlags, pat2SmpDialogShown;
+
+	// disk op.
+	bool updateLoadMode, updatePackText, updateSaveFormatText, updateDiskOpPathText;
+
+	// pos ed.
+	bool updatePosEd, updateDiskOpFileList;
+
+	// these are used when things are drawn on top, for example clear/ask dialogs
+	bool disablePosEd, disableVisualizer;
+
+	int16_t lineCurX, lineCurY, editObject, sampleMarkingPos;
+	uint16_t *numPtr16, tmpDisp16, *dstOffset, dstPos, textLength, editTextPos;
+	uint16_t dstOffsetEnd, lastSampleOffset, diskOpPathTextOffset;
+	int32_t askTempData;
+} ui_t;
+
+extern keyb_t keyb;
+extern mouse_t mouse;
+extern video_t video;
+extern editor_t editor;
+extern diskop_t diskop;
+extern cursor_t cursor;
+extern ui_t ui;
+
+extern module_t *modEntry; // pt_main.c
--- a/src/pt2_textout.c
+++ b/src/pt2_textout.c
@@ -6,6 +6,7 @@
 #include "pt2_tables.h"
 #include "pt2_palette.h"
 #include "pt2_visuals.h"
+#include "pt2_structs.h"
 
 void charOut(uint32_t xPos, uint32_t yPos, char ch, uint32_t color)
 {
@@ -647,8 +648,8 @@
 
 void setPrevStatusMessage(void)
 {
-	strcpy(editor.ui.statusMessage, editor.ui.prevStatusMessage);
-	editor.ui.updateStatusText = true;
+	strcpy(ui.statusMessage, ui.prevStatusMessage);
+	ui.updateStatusText = true;
 }
 
 void setStatusMessage(const char *msg, bool carry)
@@ -656,10 +657,10 @@
 	assert(msg != NULL);
 
 	if (carry)
-		strcpy(editor.ui.prevStatusMessage, msg);
+		strcpy(ui.prevStatusMessage, msg);
 
-	strcpy(editor.ui.statusMessage, msg);
-	editor.ui.updateStatusText = true;
+	strcpy(ui.statusMessage, msg);
+	ui.updateStatusText = true;
 }
 
 void displayMsg(const char *msg)
--- a/src/pt2_unicode.h
+++ b/src/pt2_unicode.h
@@ -14,7 +14,7 @@
 #define UNICHAR_STRNCMP(a, b, c)   wcsncmp(a, b, c)
 #define UNICHAR_STRNICMP(a, b, c) _wcsnicmp(a, L ## b, c)
 #define UNICHAR_STRCAT(a, b)       wcscat(a, b)
-#define UNICHAR_STRDUP(a)          wcsdup(a)
+#define UNICHAR_STRDUP(a)         _wcsdup(a)
 #define UNICHAR_FOPEN(a, b)       _wfopen(a, L ## b)
 #define UNICHAR_CHDIR(a)          _wchdir(a)
 #define UNICHAR_GETCWD(a, b)      _wgetcwd(a, b)
--- a/src/pt2_visuals.c
+++ b/src/pt2_visuals.c
@@ -159,32 +159,32 @@
 {
 	editor.mixFlag = false;
 	editor.swapChannelFlag = false;
-	editor.ui.clearScreenShown = false;
-	editor.ui.changingChordNote = false;
-	editor.ui.changingSmpResample = false;
-	editor.ui.pat2SmpDialogShown = false;
-	editor.ui.disablePosEd = false;
-	editor.ui.disableVisualizer = false;
+	ui.clearScreenShown = false;
+	ui.changingChordNote = false;
+	ui.changingSmpResample = false;
+	ui.pat2SmpDialogShown = false;
+	ui.disablePosEd = false;
+	ui.disableVisualizer = false;
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 	{
-		editor.ui.samplerVolBoxShown = false;
-		editor.ui.samplerFiltersBoxShown = false;
+		ui.samplerVolBoxShown = false;
+		ui.samplerFiltersBoxShown = false;
 
 		displaySample();
 	}
 
-	if (editor.ui.editTextFlag)
+	if (ui.editTextFlag)
 		exitGetTextLine(EDIT_TEXT_NO_UPDATE);
 }
 
 void removeAskDialog(void)
 {
-	if (!editor.ui.askScreenShown && !editor.isWAVRendering)
+	if (!ui.askScreenShown && !editor.isWAVRendering)
 		displayMainScreen();
 
-	editor.ui.disablePosEd = false;
-	editor.ui.disableVisualizer = false;
+	ui.disablePosEd = false;
+	ui.disableVisualizer = false;
 }
 
 void renderAskDialog(void)
@@ -192,12 +192,12 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr;
 
-	editor.ui.disablePosEd = true;
-	editor.ui.disableVisualizer = true;
+	ui.disablePosEd = true;
+	ui.disableVisualizer = true;
 
 	// render ask dialog
 
-	srcPtr = editor.ui.pat2SmpDialogShown ? pat2SmpDialogBMP : yesNoDialogBMP;
+	srcPtr = ui.pat2SmpDialogShown ? pat2SmpDialogBMP : yesNoDialogBMP;
 	dstPtr = &video.frameBuffer[(51 * SCREEN_W) + 160];
 
 	for (uint32_t y = 0; y < 39; y++)
@@ -214,8 +214,8 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr;
 
-	editor.ui.disablePosEd = true;
-	editor.ui.disableVisualizer = true;
+	ui.disablePosEd = true;
+	ui.disableVisualizer = true;
 
 	// render custom big ask dialog
 
@@ -233,8 +233,8 @@
 
 void showDownsampleAskDialog(void)
 {
-	editor.ui.askScreenShown = true;
-	editor.ui.askScreenType = ASK_LOAD_DOWNSAMPLE;
+	ui.askScreenShown = true;
+	ui.askScreenType = ASK_LOAD_DOWNSAMPLE;
 	pointerSetMode(POINTER_MODE_MSG1, NO_CARRY);
 	setStatusMessage("PLEASE SELECT", NO_CARRY);
 	renderBigAskDialog();
@@ -250,7 +250,7 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr;
 
-	if (editor.ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
+	if (ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
 		return;
 
 	srcPtr = vuMetersBg;
@@ -276,7 +276,7 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr;
 
-	if (editor.ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
+	if (ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
 		return;
 
 	srcPtr = &video.frameBuffer[(187 * SCREEN_W) + 55];
@@ -302,7 +302,7 @@
 	const uint32_t *srcPtr;
 	uint32_t h, *dstPtr;
 
-	if (editor.ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
+	if (ui.samplerScreenShown || editor.isWAVRendering || editor.isSMPRendering)
 		return;
 
 	fillToVuMetersBgBuffer();
@@ -336,33 +336,33 @@
 {
 	moduleSample_t *currSample;
 
-	if (editor.ui.diskOpScreenShown)
+	if (ui.diskOpScreenShown)
 		return;
 
 	currSample = &modEntry->samples[editor.currSample];
 
-	if (editor.ui.updateSongPos)
+	if (ui.updateSongPos)
 	{
-		editor.ui.updateSongPos = false;
+		ui.updateSongPos = false;
 		printThreeDecimalsBg(72, 3, *editor.currPosDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateSongPattern)
+	if (ui.updateSongPattern)
 	{
-		editor.ui.updateSongPattern = false;
+		ui.updateSongPattern = false;
 		printTwoDecimalsBg(80, 14, *editor.currPatternDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateSongLength)
+	if (ui.updateSongLength)
 	{
-		editor.ui.updateSongLength = false;
+		ui.updateSongLength = false;
 		if (!editor.isWAVRendering)
 			printThreeDecimalsBg(72, 25, *editor.currLengthDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateCurrSampleFineTune)
+	if (ui.updateCurrSampleFineTune)
 	{
-		editor.ui.updateCurrSampleFineTune = false;
+		ui.updateCurrSampleFineTune = false;
 
 		if (!editor.isWAVRendering)
 		{
@@ -384,9 +384,9 @@
 		}
 	}
 
-	if (editor.ui.updateCurrSampleNum)
+	if (ui.updateCurrSampleNum)
 	{
-		editor.ui.updateCurrSampleNum = false;
+		ui.updateCurrSampleNum = false;
 		if (!editor.isWAVRendering)
 		{
 			printTwoHexBg(80, 47,
@@ -394,29 +394,29 @@
 		}
 	}
 
-	if (editor.ui.updateCurrSampleVolume)
+	if (ui.updateCurrSampleVolume)
 	{
-		editor.ui.updateCurrSampleVolume = false;
+		ui.updateCurrSampleVolume = false;
 		if (!editor.isWAVRendering)
 			printTwoHexBg(80, 58, *currSample->volumeDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateCurrSampleLength)
+	if (ui.updateCurrSampleLength)
 	{
-		editor.ui.updateCurrSampleLength = false;
+		ui.updateCurrSampleLength = false;
 		if (!editor.isWAVRendering)
 			printFourHexBg(64, 69, *currSample->lengthDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateCurrSampleRepeat)
+	if (ui.updateCurrSampleRepeat)
 	{
-		editor.ui.updateCurrSampleRepeat = false;
+		ui.updateCurrSampleRepeat = false;
 		printFourHexBg(64, 80, *currSample->loopStartDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateCurrSampleReplen)
+	if (ui.updateCurrSampleReplen)
 	{
-		editor.ui.updateCurrSampleReplen = false;
+		ui.updateCurrSampleReplen = false;
 		printFourHexBg(64, 91, *currSample->loopLengthDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 }
@@ -427,16 +427,16 @@
 	int32_t secs, MI_TimeM, MI_TimeS, x, i;
 	moduleSample_t *currSample;
 
-	if (editor.ui.updateStatusText)
+	if (ui.updateStatusText)
 	{
-		editor.ui.updateStatusText = false;
+		ui.updateStatusText = false;
 
 		// clear background
 		textOutBg(88, 127, "                 ", video.palette[PAL_GENBKG], video.palette[PAL_GENBKG]);
 
 		// render status text
-		if (!editor.errorMsgActive && editor.blockMarkFlag && !editor.ui.askScreenShown
-			&& !editor.ui.clearScreenShown && !editor.swapChannelFlag)
+		if (!editor.errorMsgActive && editor.blockMarkFlag && !ui.askScreenShown
+			&& !ui.clearScreenShown && !editor.swapChannelFlag)
 		{
 			textOut(88, 127, "MARK BLOCK", video.palette[PAL_GENTXT]);
 			charOut(192, 127, '-', video.palette[PAL_GENTXT]);
@@ -455,27 +455,27 @@
 		}
 		else
 		{
-			textOut(88, 127, editor.ui.statusMessage, video.palette[PAL_GENTXT]);
+			textOut(88, 127, ui.statusMessage, video.palette[PAL_GENTXT]);
 		}
 	}
 
-	if (editor.ui.updateSongBPM)
+	if (ui.updateSongBPM)
 	{
-		editor.ui.updateSongBPM = false;
-		if (!editor.ui.samplerScreenShown)
+		ui.updateSongBPM = false;
+		if (!ui.samplerScreenShown)
 			printThreeDecimalsBg(32, 123, modEntry->currBPM, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateCurrPattText)
+	if (ui.updateCurrPattText)
 	{
-		editor.ui.updateCurrPattText = false;
-		if (!editor.ui.samplerScreenShown)
+		ui.updateCurrPattText = false;
+		if (!ui.samplerScreenShown)
 			printTwoDecimalsBg(8, 127, *editor.currEditPatternDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateTrackerFlags)
+	if (ui.updateTrackerFlags)
 	{
-		editor.ui.updateTrackerFlags = false;
+		ui.updateTrackerFlags = false;
 
 		charOutBg(1, 113, ' ', video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		charOutBg(8, 113, ' ', video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -537,9 +537,9 @@
 		printTwoDecimalsBg(296, 102, 59, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateSongName)
+	if (ui.updateSongName)
 	{
-		editor.ui.updateSongName = false;
+		ui.updateSongName = false;
 		for (x = 0; x < 20; x++)
 		{
 			tempChar = modEntry->head.moduleTitle[x];
@@ -550,9 +550,9 @@
 		}
 	}
 
-	if (editor.ui.updateCurrSampleName)
+	if (ui.updateCurrSampleName)
 	{
-		editor.ui.updateCurrSampleName = false;
+		ui.updateCurrSampleName = false;
 		currSample = &modEntry->samples[editor.currSample];
 
 		for (x = 0; x < 22; x++)
@@ -565,9 +565,9 @@
 		}
 	}
 
-	if (editor.ui.updateSongSize)
+	if (ui.updateSongSize)
 	{
-		editor.ui.updateSongSize = false;
+		ui.updateSongSize = false;
 
 		// clear background
 		textOutBg(264, 123, "      ", video.palette[PAL_GENBKG], video.palette[PAL_GENBKG]);
@@ -596,9 +596,9 @@
 		}
 	}
 
-	if (editor.ui.updateSongTiming)
+	if (ui.updateSongTiming)
 	{
-		editor.ui.updateSongTiming = false;
+		ui.updateSongTiming = false;
 		textOutBg(288, 130, (editor.timingMode == TEMPO_MODE_CIA) ? "CIA" : "VBL", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 }
@@ -605,8 +605,8 @@
 
 void updateCursorPos(void)
 {
-	if (!editor.ui.samplerScreenShown)
-		setSpritePos(SPRITE_PATTERN_CURSOR, cursorPosTable[editor.cursor.pos], 188);
+	if (!ui.samplerScreenShown)
+		setSpritePos(SPRITE_PATTERN_CURSOR, cursorPosTable[cursor.pos], 188);
 }
 
 void updateSampler(void)
@@ -614,7 +614,7 @@
 	int32_t tmpSampleOffset;
 	moduleSample_t *s;
 
-	if (!editor.ui.samplerScreenShown)
+	if (!ui.samplerScreenShown)
 		return;
 
 	assert(editor.currSample >= 0 && editor.currSample <= 30);
@@ -623,32 +623,32 @@
 	// update 9xx offset
 	if (mouse.y >= 138 && mouse.y <= 201 && mouse.x >= 3 && mouse.x <= 316)
 	{
-		if (!editor.ui.samplerVolBoxShown && !editor.ui.samplerFiltersBoxShown && s->length > 0)
+		if (!ui.samplerVolBoxShown && !ui.samplerFiltersBoxShown && s->length > 0)
 		{
 			tmpSampleOffset = (scr2SmpPos(mouse.x-3) + (1 << 7)) >> 8; // rounded
 			tmpSampleOffset = 0x900 + CLAMP(tmpSampleOffset, 0x00, 0xFF);
 
-			if (tmpSampleOffset != editor.ui.lastSampleOffset)
+			if (tmpSampleOffset != ui.lastSampleOffset)
 			{
-				editor.ui.lastSampleOffset = tmpSampleOffset;
-				editor.ui.update9xxPos = true;
+				ui.lastSampleOffset = (uint16_t)tmpSampleOffset;
+				ui.update9xxPos = true;
 			}
 		}
 	}
 
 	// display 9xx offset
-	if (editor.ui.update9xxPos)
+	if (ui.update9xxPos)
 	{
-		editor.ui.update9xxPos = false;
-		printThreeHexBg(288, 247, editor.ui.lastSampleOffset, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		ui.update9xxPos = false;
+		printThreeHexBg(288, 247, ui.lastSampleOffset, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateResampleNote)
+	if (ui.updateResampleNote)
 	{
-		editor.ui.updateResampleNote = false;
+		ui.updateResampleNote = false;
 
 		// show resample note
-		if (editor.ui.changingSmpResample)
+		if (ui.changingSmpResample)
 		{
 			textOutBg(288, 236, "---", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
@@ -661,37 +661,37 @@
 		}
 	}
 
-	if (editor.ui.samplerVolBoxShown)
+	if (ui.samplerVolBoxShown)
 	{
-		if (editor.ui.updateVolFromText)
+		if (ui.updateVolFromText)
 		{
-			editor.ui.updateVolFromText = false;
+			ui.updateVolFromText = false;
 			printThreeDecimalsBg(176, 157, *editor.vol1Disp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateVolToText)
+		if (ui.updateVolToText)
 		{
-			editor.ui.updateVolToText = false;
+			ui.updateVolToText = false;
 			printThreeDecimalsBg(176, 168, *editor.vol2Disp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 	}
-	else if (editor.ui.samplerFiltersBoxShown)
+	else if (ui.samplerFiltersBoxShown)
 	{
-		if (editor.ui.updateLPText)
+		if (ui.updateLPText)
 		{
-			editor.ui.updateLPText = false;
+			ui.updateLPText = false;
 			printFourDecimalsBg(168, 157, *editor.lpCutOffDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateHPText)
+		if (ui.updateHPText)
 		{
-			editor.ui.updateHPText = false;
+			ui.updateHPText = false;
 			printFourDecimalsBg(168, 168, *editor.hpCutOffDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateNormFlag)
+		if (ui.updateNormFlag)
 		{
-			editor.ui.updateNormFlag = false;
+			ui.updateNormFlag = false;
 
 			if (editor.normalizeFiltersFlag)
 				textOutBg(208, 179, "YES", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -765,8 +765,8 @@
 		dstPtr += SCREEN_W;
 	}
 
-	editor.ui.updateVolFromText = true;
-	editor.ui.updateVolToText = true;
+	ui.updateVolFromText = true;
+	ui.updateVolToText = true;
 	showVolFromSlider();
 	showVolToSlider();
 
@@ -799,9 +799,9 @@
 	textOut(200, 157, "HZ", video.palette[PAL_GENTXT]);
 	textOut(200, 168, "HZ", video.palette[PAL_GENTXT]);
 
-	editor.ui.updateLPText = true;
-	editor.ui.updateHPText = true;
-	editor.ui.updateNormFlag = true;
+	ui.updateLPText = true;
+	ui.updateHPText = true;
+	ui.updateNormFlag = true;
 
 	// hide loop sprites
 	hideSprite(SPRITE_LOOP_PIN_LEFT);
@@ -817,11 +817,11 @@
 {
 	memcpy(video.frameBuffer, diskOpScreenBMP, (99 * 320) * sizeof (int32_t));
 
-	editor.ui.updateDiskOpPathText = true;
-	editor.ui.updatePackText = true;
-	editor.ui.updateSaveFormatText = true;
-	editor.ui.updateLoadMode = true;
-	editor.ui.updateDiskOpFileList = true;
+	ui.updateDiskOpPathText = true;
+	ui.updatePackText = true;
+	ui.updateSaveFormatText = true;
+	ui.updateLoadMode = true;
+	ui.updateDiskOpFileList = true;
 }
 
 void updateDiskOp(void)
@@ -828,21 +828,21 @@
 {
 	char tmpChar;
 
-	if (!editor.ui.diskOpScreenShown || editor.ui.posEdScreenShown)
+	if (!ui.diskOpScreenShown || ui.posEdScreenShown)
 		return;
 
-	if (editor.ui.updateDiskOpFileList)
+	if (ui.updateDiskOpFileList)
 	{
-		editor.ui.updateDiskOpFileList = false;
+		ui.updateDiskOpFileList = false;
 		diskOpRenderFileList();
 	}
 
-	if (editor.ui.updateLoadMode)
+	if (ui.updateLoadMode)
 	{
-		editor.ui.updateLoadMode = false;
+		ui.updateLoadMode = false;
 
 		// draw load mode arrow
-		if (editor.diskop.mode == 0)
+		if (diskop.mode == 0)
 		{
 			charOutBg(147,14, ' ', video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]); // clear other box
 			charOutBg(147, 3, 0x3, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -854,28 +854,28 @@
 		}
 	}
 
-	if (editor.ui.updatePackText)
+	if (ui.updatePackText)
 	{
-		editor.ui.updatePackText = false;
-		textOutBg(120, 3, editor.diskop.modPackFlg ? "ON " : "OFF", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		ui.updatePackText = false;
+		textOutBg(120, 3, diskop.modPackFlg ? "ON " : "OFF", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateSaveFormatText)
+	if (ui.updateSaveFormatText)
 	{
-		editor.ui.updateSaveFormatText = false;
-		     if (editor.diskop.smpSaveType == DISKOP_SMP_WAV) textOutBg(120, 14, "WAV", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
-		else if (editor.diskop.smpSaveType == DISKOP_SMP_IFF) textOutBg(120, 14, "IFF", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
-		else if (editor.diskop.smpSaveType == DISKOP_SMP_RAW) textOutBg(120, 14, "RAW", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		ui.updateSaveFormatText = false;
+		     if (diskop.smpSaveType == DISKOP_SMP_WAV) textOutBg(120, 14, "WAV", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		else if (diskop.smpSaveType == DISKOP_SMP_IFF) textOutBg(120, 14, "IFF", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
+		else if (diskop.smpSaveType == DISKOP_SMP_RAW) textOutBg(120, 14, "RAW", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 	}
 
-	if (editor.ui.updateDiskOpPathText)
+	if (ui.updateDiskOpPathText)
 	{
-		editor.ui.updateDiskOpPathText = false;
+		ui.updateDiskOpPathText = false;
 
 		// print disk op. path
 		for (uint32_t i = 0; i < 26; i++)
 		{
-			tmpChar = editor.currPath[editor.textofs.diskOpPath+i];
+			tmpChar = editor.currPath[ui.diskOpPathTextOffset+i];
 			if (tmpChar == '\0')
 				tmpChar = '_';
 
@@ -890,12 +890,12 @@
 	int32_t x, y, y2;
 	uint32_t *dstPtr, bgPixel;
 
-	if (!editor.ui.posEdScreenShown || !editor.ui.updatePosEd)
+	if (!ui.posEdScreenShown || !ui.updatePosEd)
 		return;
 
-	editor.ui.updatePosEd = false;
+	ui.updatePosEd = false;
 
-	if (!editor.ui.disablePosEd)
+	if (!ui.disablePosEd)
 	{
 		bgPixel = video.palette[PAL_BACKGRD];
 
@@ -950,7 +950,7 @@
 		}
 
 		// kludge to fix bottom part of text edit marker in pos ed
-		if (editor.ui.editTextFlag && editor.ui.editObject == PTB_PE_PATT)
+		if (ui.editTextFlag && ui.editObject == PTB_PE_PATT)
 			renderTextEditMarker();
 	}
 }
@@ -977,7 +977,7 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr, srcPitch;
 
-	if (editor.ui.diskOpScreenShown || editor.ui.posEdScreenShown)
+	if (ui.diskOpScreenShown || ui.posEdScreenShown)
 		return;
 
 	dstPtr = &video.frameBuffer[(3 * SCREEN_W) + 310];
@@ -1012,8 +1012,8 @@
 	const uint32_t *srcPtr;
 	uint32_t *dstPtr;
 
-	editor.ui.disablePosEd = true;
-	editor.ui.disableVisualizer = true;
+	ui.disablePosEd = true;
+	ui.disableVisualizer = true;
 
 	srcPtr = clearDialogBMP;
 	dstPtr = &video.frameBuffer[(51 * SCREEN_W) + 160];
@@ -1031,41 +1031,41 @@
 {
 	displayMainScreen();
 
-	editor.ui.disablePosEd = false;
-	editor.ui.disableVisualizer = false;
+	ui.disablePosEd = false;
+	ui.disableVisualizer = false;
 }
 
 void updateCurrSample(void)
 {
-	editor.ui.updateCurrSampleName = true;
-	editor.ui.updateSongSize = true;
+	ui.updateCurrSampleName = true;
+	ui.updateSongSize = true;
 
-	if (!editor.ui.diskOpScreenShown)
+	if (!ui.diskOpScreenShown)
 	{
-		editor.ui.updateCurrSampleFineTune = true;
-		editor.ui.updateCurrSampleNum = true;
-		editor.ui.updateCurrSampleVolume = true;
-		editor.ui.updateCurrSampleLength = true;
-		editor.ui.updateCurrSampleRepeat = true;
-		editor.ui.updateCurrSampleReplen = true;
+		ui.updateCurrSampleFineTune = true;
+		ui.updateCurrSampleNum = true;
+		ui.updateCurrSampleVolume = true;
+		ui.updateCurrSampleLength = true;
+		ui.updateCurrSampleRepeat = true;
+		ui.updateCurrSampleReplen = true;
 	}
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 		redrawSample();
 
 	updateSamplePos();
 	recalcChordLength();
 
-	editor.sampler.tmpLoopStart = 0;
-	editor.sampler.tmpLoopLength = 0;
+	sampler.tmpLoopStart = 0;
+	sampler.tmpLoopLength = 0;
 }
 
 void updatePatternData(void)
 {
-	if (editor.ui.updatePatternData)
+	if (ui.updatePatternData)
 	{
-		editor.ui.updatePatternData = false;
-		if (!editor.ui.samplerScreenShown)
+		ui.updatePatternData = false;
+		if (!ui.samplerScreenShown)
 			redrawPattern();
 	}
 }
@@ -1074,12 +1074,12 @@
 {
 	uint32_t *dstPtr, pixel;
 
-	if (!editor.ui.editTextFlag)
+	if (!ui.editTextFlag)
 		return;
 
-	dstPtr = &video.frameBuffer[((editor.ui.lineCurY - 1) * SCREEN_W) + (editor.ui.lineCurX - 4)];
+	dstPtr = &video.frameBuffer[((ui.lineCurY - 1) * SCREEN_W) + (ui.lineCurX - 4)];
 
-	if (editor.ui.editObject == PTB_PE_PATT)
+	if (ui.editObject == PTB_PE_PATT)
 	{
 		// position editor text editing
 
@@ -1089,7 +1089,7 @@
 
 		// no need to clear the second row of pixels
 
-		editor.ui.updatePosEd = true;
+		ui.updatePosEd = true;
 	}
 	else
 	{
@@ -1110,10 +1110,10 @@
 {
 	uint32_t *dstPtr, pixel;
 
-	if (!editor.ui.editTextFlag)
+	if (!ui.editTextFlag)
 		return;
 
-	dstPtr = &video.frameBuffer[((editor.ui.lineCurY - 1) * SCREEN_W) + (editor.ui.lineCurX - 4)];
+	dstPtr = &video.frameBuffer[((ui.lineCurY - 1) * SCREEN_W) + (ui.lineCurX - 4)];
 	pixel = video.palette[PAL_TEXTMARK];
 
 	for (uint32_t y = 0; y < 2; y++)
@@ -1141,25 +1141,25 @@
 {
 	bool testMouseButtonRelease = false;
 
-	if (editor.ui.sampleMarkingPos >= 0)
+	if (ui.sampleMarkingPos >= 0)
 	{
 		samplerSamplePressed(MOUSE_BUTTON_HELD);
 		testMouseButtonRelease = true;
 	}
 
-	if (editor.ui.forceSampleDrag)
+	if (ui.forceSampleDrag)
 	{
 		samplerBarPressed(MOUSE_BUTTON_HELD);
 		testMouseButtonRelease = true;
 	}
 
-	if (editor.ui.forceSampleEdit)
+	if (ui.forceSampleEdit)
 	{
 		samplerEditSample(MOUSE_BUTTON_HELD);
 		testMouseButtonRelease = true;
 	}
 
-	if (editor.ui.forceVolDrag)
+	if (ui.forceVolDrag)
 	{
 		volBoxBarPressed(MOUSE_BUTTON_HELD);
 		testMouseButtonRelease = true;
@@ -1187,15 +1187,15 @@
 	int32_t tmpVol;
 	uint32_t *dstPtr, pixel;
 
-	if (editor.ui.disableVisualizer || editor.ui.diskOpScreenShown ||
-		editor.ui.posEdScreenShown  || editor.ui.editOpScreenShown ||
-		editor.ui.aboutScreenShown  || editor.ui.askScreenShown    ||
+	if (ui.disableVisualizer || ui.diskOpScreenShown ||
+		ui.posEdScreenShown  || ui.editOpScreenShown ||
+		ui.aboutScreenShown  || ui.askScreenShown    ||
 		editor.isWAVRendering)
 	{
 		return;
 	}
 
-	if (editor.ui.visualizerMode == VISUAL_SPECTRUM)
+	if (ui.visualizerMode == VISUAL_SPECTRUM)
 	{
 		// spectrum analyzer
 
@@ -1272,7 +1272,7 @@
 	const uint32_t *srcPtr;
 	uint32_t verStringX, *dstPtr;
 
-	if (!editor.ui.aboutScreenShown || editor.ui.diskOpScreenShown || editor.ui.posEdScreenShown || editor.ui.editOpScreenShown)
+	if (!ui.aboutScreenShown || ui.diskOpScreenShown || ui.posEdScreenShown || ui.editOpScreenShown)
 		return;
 
 	srcPtr = aboutScreenBMP;
@@ -1300,7 +1300,7 @@
 
 	// select what character box to render
 
-	switch (editor.ui.editOpScreen)
+	switch (ui.editOpScreen)
 	{
 		default:
 		case 0:
@@ -1343,7 +1343,7 @@
 	uint32_t *dstPtr;
 
 	// select which background to render
-	switch (editor.ui.editOpScreen)
+	switch (ui.editOpScreen)
 	{
 		default:
 		case 0: srcPtr = editOpScreen1BMP; break;
@@ -1365,40 +1365,40 @@
 	renderEditOpMode();
 
 	// render text and content
-	if (editor.ui.editOpScreen == 0)
+	if (ui.editOpScreen == 0)
 	{
 		textOut(128, 47, "  TRACK      PATTERN  ", video.palette[PAL_GENTXT]);
 	}
-	else if (editor.ui.editOpScreen == 1)
+	else if (ui.editOpScreen == 1)
 	{
 		textOut(128, 47, "  RECORD     SAMPLES  ", video.palette[PAL_GENTXT]);
 
-		editor.ui.updateRecordText = true;
-		editor.ui.updateQuantizeText = true;
-		editor.ui.updateMetro1Text = true;
-		editor.ui.updateMetro2Text = true;
-		editor.ui.updateFromText = true;
-		editor.ui.updateKeysText = true;
-		editor.ui.updateToText = true;
+		ui.updateRecordText = true;
+		ui.updateQuantizeText = true;
+		ui.updateMetro1Text = true;
+		ui.updateMetro2Text = true;
+		ui.updateFromText = true;
+		ui.updateKeysText = true;
+		ui.updateToText = true;
 	}
-	else if (editor.ui.editOpScreen == 2)
+	else if (ui.editOpScreen == 2)
 	{
 		textOut(128, 47, "    SAMPLE EDITOR     ", video.palette[PAL_GENTXT]);
 		charOut(272, 91, '%', video.palette[PAL_GENTXT]); // for Volume text
 
-		editor.ui.updatePosText = true;
-		editor.ui.updateModText = true;
-		editor.ui.updateVolText = true;
+		ui.updatePosText = true;
+		ui.updateModText = true;
+		ui.updateVolText = true;
 	}
-	else if (editor.ui.editOpScreen == 3)
+	else if (ui.editOpScreen == 3)
 	{
 		textOut(128, 47, " SAMPLE CHORD EDITOR  ", video.palette[PAL_GENTXT]);
 
-		editor.ui.updateLengthText = true;
-		editor.ui.updateNote1Text = true;
-		editor.ui.updateNote2Text = true;
-		editor.ui.updateNote3Text = true;
-		editor.ui.updateNote4Text = true;
+		ui.updateLengthText = true;
+		ui.updateNote1Text = true;
+		ui.updateNote2Text = true;
+		ui.updateNote3Text = true;
+		ui.updateNote4Text = true;
 	}
 }
 
@@ -1424,16 +1424,16 @@
 	int32_t barLength, percent;
 	uint32_t *dstPtr, bgPixel, pixel;
 
-	if (!editor.ui.updateMod2WavDialog)
+	if (!ui.updateMod2WavDialog)
 		return;
 
-	editor.ui.updateMod2WavDialog = false;
+	ui.updateMod2WavDialog = false;
 
 	if (editor.isWAVRendering)
 	{
-		if (editor.ui.mod2WavFinished)
+		if (ui.mod2WavFinished)
 		{
-			editor.ui.mod2WavFinished = false;
+			ui.mod2WavFinished = false;
 
 			resetSong();
 			pointerSetMode(POINTER_MODE_IDLE, DO_CARRY);
@@ -1493,58 +1493,58 @@
 
 void updateEditOp(void)
 {
-	if (!editor.ui.editOpScreenShown || editor.ui.posEdScreenShown || editor.ui.diskOpScreenShown)
+	if (!ui.editOpScreenShown || ui.posEdScreenShown || ui.diskOpScreenShown)
 		return;
 
-	if (editor.ui.editOpScreen == 1)
+	if (ui.editOpScreen == 1)
 	{
-		if (editor.ui.updateRecordText)
+		if (ui.updateRecordText)
 		{
-			editor.ui.updateRecordText = false;
+			ui.updateRecordText = false;
 			textOutBg(176, 58, (editor.recordMode == RECORD_PATT) ? "PATT" : "SONG", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateQuantizeText)
+		if (ui.updateQuantizeText)
 		{
-			editor.ui.updateQuantizeText = false;
+			ui.updateQuantizeText = false;
 			printTwoDecimalsBg(192, 69, *editor.quantizeValueDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateMetro1Text)
+		if (ui.updateMetro1Text)
 		{
-			editor.ui.updateMetro1Text = false;
+			ui.updateMetro1Text = false;
 			printTwoDecimalsBg(168, 80, *editor.metroSpeedDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateMetro2Text)
+		if (ui.updateMetro2Text)
 		{
-			editor.ui.updateMetro2Text = false;
+			ui.updateMetro2Text = false;
 			printTwoDecimalsBg(192, 80, *editor.metroChannelDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateFromText)
+		if (ui.updateFromText)
 		{
-			editor.ui.updateFromText = false;
+			ui.updateFromText = false;
 			printTwoHexBg(264, 80, *editor.sampleFromDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateKeysText)
+		if (ui.updateKeysText)
 		{
-			editor.ui.updateKeysText = false;
+			ui.updateKeysText = false;
 			textOutBg(160, 91, editor.multiFlag ? "MULTI " : "SINGLE", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateToText)
+		if (ui.updateToText)
 		{
-			editor.ui.updateToText = false;
+			ui.updateToText = false;
 			printTwoHexBg(264, 91, *editor.sampleToDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 	}
-	else if (editor.ui.editOpScreen == 2)
+	else if (ui.editOpScreen == 2)
 	{
-		if (editor.ui.updateMixText)
+		if (ui.updateMixText)
 		{
-			editor.ui.updateMixText = false;
+			ui.updateMixText = false;
 			if (editor.mixFlag)
 			{
 				textOutBg(128, 47, editor.mixText, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -1556,15 +1556,15 @@
 			}
 		}
 
-		if (editor.ui.updatePosText)
+		if (ui.updatePosText)
 		{
-			editor.ui.updatePosText = false;
+			ui.updatePosText = false;
 			printFourHexBg(248, 58, *editor.samplePosDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateModText)
+		if (ui.updateModText)
 		{
-			editor.ui.updateModText = false;
+			ui.updateModText = false;
 			printThreeDecimalsBg(256, 69,
 				(editor.modulateSpeed < 0) ? (0 - editor.modulateSpeed) : editor.modulateSpeed,
 				video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -1575,17 +1575,17 @@
 				charOutBg(248, 69, ' ', video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateVolText)
+		if (ui.updateVolText)
 		{
-			editor.ui.updateVolText = false;
+			ui.updateVolText = false;
 			printThreeDecimalsBg(248, 91, *editor.sampleVolDisp, video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 	}
-	else if (editor.ui.editOpScreen == 3)
+	else if (ui.editOpScreen == 3)
 	{
-		if (editor.ui.updateLengthText)
+		if (ui.updateLengthText)
 		{
-			editor.ui.updateLengthText = false;
+			ui.updateLengthText = false;
 
 			// clear background
 			textOutBg(168, 91, "    ", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
@@ -1602,9 +1602,9 @@
 			}
 		}
 
-		if (editor.ui.updateNote1Text)
+		if (ui.updateNote1Text)
 		{
-			editor.ui.updateNote1Text = false;
+			ui.updateNote1Text = false;
 			if (editor.note1 > 35)
 				textOutBg(256, 58, "---", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 			else
@@ -1612,9 +1612,9 @@
 					video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateNote2Text)
+		if (ui.updateNote2Text)
 		{
-			editor.ui.updateNote2Text = false;
+			ui.updateNote2Text = false;
 			if (editor.note2 > 35)
 				textOutBg(256, 69, "---", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 			else
@@ -1622,9 +1622,9 @@
 					video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 
-		if (editor.ui.updateNote3Text)
+		if (ui.updateNote3Text)
 		{
-			editor.ui.updateNote3Text = false;
+			ui.updateNote3Text = false;
 			if (editor.note3 > 35)
 				textOutBg(256, 80, "---", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 			else
@@ -1632,9 +1632,9 @@
 					video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 		}
 			
-		if (editor.ui.updateNote4Text)
+		if (ui.updateNote4Text)
 		{
-			editor.ui.updateNote4Text = false;
+			ui.updateNote4Text = false;
 			if (editor.note4 > 35)
 				textOutBg(256, 91, "---", video.palette[PAL_GENTXT], video.palette[PAL_GENBKG]);
 			else
@@ -1648,50 +1648,50 @@
 {
 	editor.blockMarkFlag = false;
 
-	editor.ui.updateSongName = true;
-	editor.ui.updateSongSize = true;
-	editor.ui.updateSongTiming = true;
-	editor.ui.updateTrackerFlags = true;
-	editor.ui.updateStatusText = true;
+	ui.updateSongName = true;
+	ui.updateSongSize = true;
+	ui.updateSongTiming = true;
+	ui.updateTrackerFlags = true;
+	ui.updateStatusText = true;
 
-	editor.ui.updateCurrSampleName = true;
+	ui.updateCurrSampleName = true;
 
-	if (!editor.ui.diskOpScreenShown)
+	if (!ui.diskOpScreenShown)
 	{
-		editor.ui.updateCurrSampleFineTune = true;
-		editor.ui.updateCurrSampleNum = true;
-		editor.ui.updateCurrSampleVolume = true;
-		editor.ui.updateCurrSampleLength = true;
-		editor.ui.updateCurrSampleRepeat = true;
-		editor.ui.updateCurrSampleReplen = true;
+		ui.updateCurrSampleFineTune = true;
+		ui.updateCurrSampleNum = true;
+		ui.updateCurrSampleVolume = true;
+		ui.updateCurrSampleLength = true;
+		ui.updateCurrSampleRepeat = true;
+		ui.updateCurrSampleReplen = true;
 	}
 
-	if (editor.ui.samplerScreenShown)
+	if (ui.samplerScreenShown)
 	{
-		if (!editor.ui.diskOpScreenShown)
+		if (!ui.diskOpScreenShown)
 			memcpy(video.frameBuffer, trackerFrameBMP, 320 * 121 * sizeof (int32_t));
 	}
 	else
 	{
-		if (!editor.ui.diskOpScreenShown)
+		if (!ui.diskOpScreenShown)
 			memcpy(video.frameBuffer, trackerFrameBMP, 320 * 255 * sizeof (int32_t));
 		else
 			memcpy(&video.frameBuffer[121 * SCREEN_W], &trackerFrameBMP[121 * SCREEN_W], 320 * 134 * sizeof (int32_t));
 
-		editor.ui.updateSongBPM = true;
-		editor.ui.updateCurrPattText = true;
-		editor.ui.updatePatternData  = true;
+		ui.updateSongBPM = true;
+		ui.updateCurrPattText = true;
+		ui.updatePatternData  = true;
 	}
 
-	if (editor.ui.diskOpScreenShown)
+	if (ui.diskOpScreenShown)
 	{
 		renderDiskOpScreen();
 	}
 	else
 	{
-		editor.ui.updateSongPos = true;
-		editor.ui.updateSongPattern = true;
-		editor.ui.updateSongLength = true;
+		ui.updateSongPos = true;
+		ui.updateSongPattern = true;
+		ui.updateSongLength = true;
 
 		// zeroes (can't integrate zeroes in the graphics, the palette entry is above the 2-bit range)
 		charOut(64,  3, '0', video.palette[PAL_GENTXT]);
@@ -1704,27 +1704,27 @@
 			textOut(64, 58, "00", video.palette[PAL_GENTXT]);
 		}
 
-		if (editor.ui.posEdScreenShown)
+		if (ui.posEdScreenShown)
 		{
 			renderPosEdScreen();
-			editor.ui.updatePosEd = true;
+			ui.updatePosEd = true;
 		}
 		else
 		{
-			if (editor.ui.editOpScreenShown)
+			if (ui.editOpScreenShown)
 			{
 				renderEditOpScreen();
 			}
 			else
 			{
-				if (editor.ui.aboutScreenShown)
+				if (ui.aboutScreenShown)
 				{
 					renderAboutScreen();
 				}
 				else
 				{
-					     if (editor.ui.visualizerMode == VISUAL_QUADRASCOPE) renderQuadrascopeBg();
-					else if (editor.ui.visualizerMode == VISUAL_SPECTRUM) renderSpectrumAnalyzerBg();
+					     if (ui.visualizerMode == VISUAL_QUADRASCOPE) renderQuadrascopeBg();
+					else if (ui.visualizerMode == VISUAL_SPECTRUM) renderSpectrumAnalyzerBg();
 				}
 			}
 
@@ -1744,9 +1744,9 @@
 
 void handleAskNo(void)
 {
-	editor.ui.pat2SmpDialogShown = false;
+	ui.pat2SmpDialogShown = false;
 
-	switch (editor.ui.askScreenType)
+	switch (ui.askScreenType)
 	{
 		case ASK_SAVEMOD_OVERWRITE:
 		{
@@ -1790,7 +1790,7 @@
 	uint32_t i;
 	moduleSample_t *s;
 
-	switch (editor.ui.askScreenType)
+	switch (ui.askScreenType)
 	{
 		case ASK_DISCARD_SONG:
 		{
@@ -1854,7 +1854,7 @@
 			for (i = 0; i < MOD_SAMPLES; i++)
 				boostSample(i, true);
 
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				redrawSample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -1868,7 +1868,7 @@
 			for (i = 0; i < MOD_SAMPLES; i++)
 				filterSample(i, true);
 
-			if (editor.ui.samplerScreenShown)
+			if (ui.samplerScreenShown)
 				redrawSample();
 
 			updateWindowTitle(MOD_IS_MODIFIED);
@@ -1908,7 +1908,7 @@
 			editor.samplePos = 0;
 			updateCurrSample();
 
-			editor.ui.updateSongSize = true;
+			ui.updateSongSize = true;
 			updateWindowTitle(MOD_IS_MODIFIED);
 		}
 		break;
@@ -1979,7 +1979,7 @@
 		case ASK_QUIT:
 		{
 			restoreStatusAndMousePointer();
-			editor.ui.throwExit = true;
+			ui.throwExit = true;
 		}
 		break;
 
@@ -2341,17 +2341,17 @@
 
 void freeSprites(void)
 {
-	for (uint8_t i = 0; i < SPRITE_NUM; i++)
+	for (int32_t i = 0; i < SPRITE_NUM; i++)
 		free(sprites[i].refreshBuffer);
 }
 
-void setSpritePos(uint8_t sprite, uint16_t x, uint16_t y)
+void setSpritePos(int32_t sprite, int32_t x, int32_t y)
 {
-	sprites[sprite].newX = x;
-	sprites[sprite].newY = y;
+	sprites[sprite].newX = (int16_t)x;
+	sprites[sprite].newY = (int16_t)y;
 }
 
-void hideSprite(uint8_t sprite)
+void hideSprite(int32_t sprite)
 {
 	sprites[sprite].newX = SCREEN_W;
 }
@@ -2555,9 +2555,10 @@
 void updateSpectrumAnalyzer(int8_t vol, int16_t period)
 {
 	const uint8_t maxHeight = SPECTRUM_BAR_HEIGHT + 1; // +1 because of audio latency - allows full height to be seen
-	int32_t scaledVol, scaledNote;
+	int8_t scaledVol;
+	int32_t scaledNote;
 
-	if (editor.ui.visualizerMode != VISUAL_SPECTRUM || vol <= 0)
+	if (ui.visualizerMode != VISUAL_SPECTRUM || vol <= 0)
 		return;
 
 	scaledVol = (vol * 24600L) >> 16; // scaledVol = (vol << 8) / 682
--- a/src/pt2_visuals.h
+++ b/src/pt2_visuals.h
@@ -74,5 +74,5 @@
 void renderVuMeters(void);
 void setupSprites(void);
 void freeSprites(void);
-void setSpritePos(uint8_t sprite, uint16_t x, uint16_t y);
-void hideSprite(uint8_t sprite);
+void setSpritePos(int32_t sprite, int32_t x, int32_t y);
+void hideSprite(int32_t sprite);
--- a/vs2019_project/pt2-clone/pt2-clone.vcxproj
+++ b/vs2019_project/pt2-clone/pt2-clone.vcxproj
@@ -26,16 +26,14 @@
   </PropertyGroup>
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
-    <UseDebugLibraries>true</UseDebugLibraries>
     <PlatformToolset>v142</PlatformToolset>
     <WholeProgramOptimization>true</WholeProgramOptimization>
-    <CharacterSet>MultiByte</CharacterSet>
+    <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
-    <UseDebugLibraries>true</UseDebugLibraries>
     <PlatformToolset>v142</PlatformToolset>
     <WholeProgramOptimization>true</WholeProgramOptimization>
-    <CharacterSet>MultiByte</CharacterSet>
+    <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
     <PlatformToolset>v142</PlatformToolset>
@@ -95,7 +93,6 @@
       <IntrinsicFunctions>true</IntrinsicFunctions>
       <StringPooling>true</StringPooling>
       <MinimalRebuild>false</MinimalRebuild>
-      <ExceptionHandling>false</ExceptionHandling>
       <BasicRuntimeChecks>Default</BasicRuntimeChecks>
       <FunctionLevelLinking>true</FunctionLevelLinking>
       <FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
@@ -103,34 +100,28 @@
       <DebugInformationFormat>None</DebugInformationFormat>
       <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
       <OmitFramePointers>true</OmitFramePointers>
-      <EnableParallelCodeGeneration>false</EnableParallelCodeGeneration>
-      <FloatingPointExceptions>false</FloatingPointExceptions>
-      <CompileAsManaged>false</CompileAsManaged>
       <CompileAsWinRT>false</CompileAsWinRT>
-      <ControlFlowGuard>false</ControlFlowGuard>
-      <CreateHotpatchableImage>false</CreateHotpatchableImage>
       <BufferSecurityCheck>false</BufferSecurityCheck>
+      <TreatWChar_tAsBuiltInType>false</TreatWChar_tAsBuiltInType>
       <RuntimeTypeInfo>false</RuntimeTypeInfo>
-      <OpenMPSupport>false</OpenMPSupport>
-      <LanguageStandard>stdcpplatest</LanguageStandard>
     </ClCompile>
     <Link>
       <SubSystem>Windows</SubSystem>
-      <AdditionalDependencies>SDL2main.lib;SDL2.lib;winmm.lib;libcmt.lib;libvcruntime.lib;libucrt.lib;%(AdditionalDependencies)</AdditionalDependencies>
+      <AdditionalDependencies>SDL2main.lib;SDL2.lib;winmm.lib;%(AdditionalDependencies)</AdditionalDependencies>
       <IgnoreAllDefaultLibraries>
       </IgnoreAllDefaultLibraries>
       <LinkTimeCodeGeneration>UseLinkTimeCodeGeneration</LinkTimeCodeGeneration>
       <AdditionalOptions>/NODEFAULTLIB:MSVCRT "notelemetry.obj" %(AdditionalOptions)</AdditionalOptions>
-      <IgnoreSpecificDefaultLibraries>
-      </IgnoreSpecificDefaultLibraries>
+      <IgnoreSpecificDefaultLibraries>%(IgnoreSpecificDefaultLibraries)</IgnoreSpecificDefaultLibraries>
       <TreatLinkerWarningAsErrors>true</TreatLinkerWarningAsErrors>
       <MinimumRequiredVersion>5.1</MinimumRequiredVersion>
       <OptimizeReferences>true</OptimizeReferences>
       <EnableCOMDATFolding>true</EnableCOMDATFolding>
-      <DataExecutionPrevention>false</DataExecutionPrevention>
       <LargeAddressAware>true</LargeAddressAware>
-      <ImageHasSafeExceptionHandlers>true</ImageHasSafeExceptionHandlers>
       <GenerateDebugInformation>false</GenerateDebugInformation>
+      <SetChecksum>true</SetChecksum>
+      <FixedBaseAddress>false</FixedBaseAddress>
+      <ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>
     </Link>
     <PostBuildEvent />
     <Manifest>
@@ -137,6 +128,9 @@
       <VerboseOutput>false</VerboseOutput>
       <EnableDpiAwareness>PerMonitorHighDPIAware</EnableDpiAwareness>
     </Manifest>
+    <ResourceCompile>
+      <PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ResourceCompile>
   </ItemDefinitionGroup>
   <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
     <ClCompile>
@@ -148,7 +142,6 @@
       <IntrinsicFunctions>true</IntrinsicFunctions>
       <StringPooling>true</StringPooling>
       <MinimalRebuild>false</MinimalRebuild>
-      <ExceptionHandling>false</ExceptionHandling>
       <BasicRuntimeChecks>Default</BasicRuntimeChecks>
       <FunctionLevelLinking>true</FunctionLevelLinking>
       <FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
@@ -156,32 +149,25 @@
       <DebugInformationFormat>None</DebugInformationFormat>
       <InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
       <OmitFramePointers>true</OmitFramePointers>
-      <EnableParallelCodeGeneration>false</EnableParallelCodeGeneration>
-      <FloatingPointExceptions>false</FloatingPointExceptions>
-      <CompileAsManaged>false</CompileAsManaged>
-      <CompileAsWinRT>false</CompileAsWinRT>
-      <ControlFlowGuard>false</ControlFlowGuard>
-      <CreateHotpatchableImage>false</CreateHotpatchableImage>
       <BufferSecurityCheck>false</BufferSecurityCheck>
       <RuntimeTypeInfo>false</RuntimeTypeInfo>
-      <OpenMPSupport>false</OpenMPSupport>
-      <LanguageStandard>stdcpplatest</LanguageStandard>
+      <TreatWChar_tAsBuiltInType>false</TreatWChar_tAsBuiltInType>
     </ClCompile>
     <Link>
       <SubSystem>Windows</SubSystem>
-      <AdditionalDependencies>SDL2main.lib;SDL2.lib;winmm.lib;libcmt.lib;libvcruntime.lib;libucrt.lib;%(AdditionalDependencies)</AdditionalDependencies>
+      <AdditionalDependencies>SDL2main.lib;SDL2.lib;winmm.lib;%(AdditionalDependencies)</AdditionalDependencies>
       <IgnoreAllDefaultLibraries>
       </IgnoreAllDefaultLibraries>
       <LinkTimeCodeGeneration>UseLinkTimeCodeGeneration</LinkTimeCodeGeneration>
       <AdditionalOptions>/NODEFAULTLIB:MSVCRT "notelemetry.obj" %(AdditionalOptions)</AdditionalOptions>
-      <IgnoreSpecificDefaultLibraries>
-      </IgnoreSpecificDefaultLibraries>
+      <IgnoreSpecificDefaultLibraries>%(IgnoreSpecificDefaultLibraries)</IgnoreSpecificDefaultLibraries>
       <TreatLinkerWarningAsErrors>true</TreatLinkerWarningAsErrors>
       <OptimizeReferences>true</OptimizeReferences>
       <EnableCOMDATFolding>true</EnableCOMDATFolding>
-      <DataExecutionPrevention>false</DataExecutionPrevention>
       <LargeAddressAware>true</LargeAddressAware>
       <GenerateDebugInformation>false</GenerateDebugInformation>
+      <FixedBaseAddress>false</FixedBaseAddress>
+      <SetChecksum>true</SetChecksum>
     </Link>
     <PostBuildEvent />
     <Manifest>
@@ -188,6 +174,9 @@
       <VerboseOutput>false</VerboseOutput>
       <EnableDpiAwareness>PerMonitorHighDPIAware</EnableDpiAwareness>
     </Manifest>
+    <ResourceCompile>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ResourceCompile>
   </ItemDefinitionGroup>
   <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
     <ClCompile>
@@ -299,6 +288,7 @@
     <ClInclude Include="..\..\src\pt2_sampleloader.h" />
     <ClInclude Include="..\..\src\pt2_sampler.h" />
     <ClInclude Include="..\..\src\pt2_scopes.h" />
+    <ClInclude Include="..\..\src\pt2_structs.h" />
     <ClInclude Include="..\..\src\pt2_tables.h" />
     <ClInclude Include="..\..\src\pt2_textout.h" />
     <ClInclude Include="..\..\src\pt2_unicode.h" />
@@ -343,6 +333,7 @@
     <ClCompile Include="..\..\src\pt2_sampleloader.c" />
     <ClCompile Include="..\..\src\pt2_sampler.c" />
     <ClCompile Include="..\..\src\pt2_scopes.c" />
+    <ClCompile Include="..\..\src\pt2_structs.c" />
     <ClCompile Include="..\..\src\pt2_tables.c" />
     <ClCompile Include="..\..\src\pt2_textout.c" />
     <ClCompile Include="..\..\src\pt2_unicode.c" />
--- a/vs2019_project/pt2-clone/pt2-clone.vcxproj.filters
+++ b/vs2019_project/pt2-clone/pt2-clone.vcxproj.filters
@@ -72,6 +72,9 @@
     <ClInclude Include="..\..\src\pt2_pat2smp.h">
       <Filter>headers</Filter>
     </ClInclude>
+    <ClInclude Include="..\..\src\pt2_structs.h">
+      <Filter>headers</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="..\..\src\pt2_audio.c" />
@@ -150,6 +153,7 @@
     </ClCompile>
     <ClCompile Include="..\..\src\pt2_mod2wav.c" />
     <ClCompile Include="..\..\src\pt2_pat2smp.c" />
+    <ClCompile Include="..\..\src\pt2_structs.c" />
   </ItemGroup>
   <ItemGroup>
     <ResourceCompile Include="..\..\src\pt2-clone.rc" />