int SYNC2Pulse(ITZXDataBlock TZXDataBlock) { EarBit = EarBit ^ 64; TZXState.Next(); PulseCounter = 2; usedBits = 8; return(((TZXDataBlock[0] & 0x80) > 0) ? TZXDataBlock.OneLength : TZXDataBlock.ZeroLength); }
public TZXDataBlock(ITZXDataBlock sourceDataBlock) { pulseLength = sourceDataBlock.PulseLength; pulseToneLength = sourceDataBlock.PulseToneLength; sync1Length = sourceDataBlock.Sync1Length; sync2Length = sourceDataBlock.Sync2Length; zeroLength = sourceDataBlock.ZeroLength; oneLength = sourceDataBlock.OneLength; pauseLength = sourceDataBlock.PauseLength; usedBits = sourceDataBlock.UsedBits; }
int DataBytes(ITZXDataBlock TZXDataBlock) { EarBit = EarBit ^ 64; PulseCounter--; if (PulseCounter > 0) { return(((TZXCurrentByte & 0x80) == 0x80) ? TZXDataBlock.OneLength : TZXDataBlock.ZeroLength); } if (usedBits > 1) { usedBits--; PulseCounter = 2; TZXCurrentByte <<= 1; return(((TZXCurrentByte & 0x80) == 0x80) ? TZXDataBlock.OneLength : TZXDataBlock.ZeroLength); } TZXDataBlock.Progress++; TZXTapeCounter++; if (TZXDataBlock.Progress >= TZXDataBlock.TAPBlock.Length) { if (TZXDataBlock.PauseLength > 0) { TZXState.Next(); OnLoaded(); return(TZXDataBlock.PauseLength * 3500); } else { if (TZXTapeCounter > TZXFile.TZXLength) { TZXState.Next(); OnLoaded(); return(TZXDataBlock.PauseLength * 3500); } if (TZXTapeCounter != TZXFile.TZXLength) { TZXState.Reset(); return(GetNextBlock()); } } } OnProgress(TZXFile, TZXDataBlock.TAPBlock.Length, TZXTapeCounter, TZXDataBlock.Progress, Percent(TZXFile.TZXLength, TZXTapeCounter), Percent(TZXDataBlock.TAPBlock.Length - 1, TZXDataBlock.Progress), TZXDataBlock.ToString(), TZXDataBlock); usedBits = TZXDataBlock.UsedBits; PulseCounter = 2; if (TZXDataBlock.Progress < TZXDataBlock.TAPBlock.Data.Length) { TZXCurrentByte = TZXDataBlock.TAPBlock.Data[TZXDataBlock.Progress]; } return(((TZXCurrentByte & 0x80) == 0x80) ? TZXDataBlock.OneLength : TZXDataBlock.ZeroLength); }
int PilotTone(ITZXDataBlock TZXDataBlock) { EarBit = EarBit ^ 64; if (TZXDataBlock.Progress < TZXDataBlock.PulseToneLength) { TZXDataBlock.Progress++; return(TZXDataBlock.PulseLength); } else { TZXDataBlock.Progress = 0; TZXState.Next(); return(TZXDataBlock.Sync1Length); } }
void Draw(Graphics offScreenDC) { coords.Clear(); if (tZXFile == null) { return; } double fr = TZXFileLength; float x = 0; int cnt = 1; for (int i = 0; i < tZXFile.Blocks.Count; i++) { if (tZXFile.Blocks[i] is ITZXDataBlock) { ITZXDataBlock block = tZXFile.Blocks[i] as ITZXDataBlock; double dd = block.TAPBlock.Length; double pct = (((double)(((dd / fr) * 100d)))); float w = (float)(Width * pct / 100); RectangleF rf = new RectangleF(x, 0, w, Height); Rectangle r = new Rectangle((int)x, 0, (int)w, Height); string s = (block.Index * block.Index).ToString(); string s1 = ""; for (int xxx = 0; xxx < s.Length; xxx++) { s1 += (s[xxx] << 0x18).ToString(); } int a = s1.GetHashCode(); int R = (a >> 0x10) & 0xff; int G = (a >> 0x08) & 0xff; int B = (a & 0xff); Background = Color.FromArgb(R, G, B); //background = Color.FromArgb(block.ID.ToString().GetHashCode() & 0xff, block.BlockLength.ToString().GetHashCode() & 0xff, block.BlockLength.ToString().GetHashCode() & 0xff); offScreenDC.FillRectangle(GetBrush(Background), rf); coords.Add(new Coord(block, cnt++, rf)); x += (float)(w); if (CursorPen == null) { CursorPen = new Pen(new SolidBrush(GetContrast(Background))); } } } try { offScreenDC.DrawLine(CursorPen, CursorPosition, 0, CursorPosition, Height); } catch { } }
int NextPulseLength(ITZXDataBlock TZXDataBlock) { switch (TZXState.State) { case TZXStates.PilotTone: return(PilotTone(TZXDataBlock)); case TZXStates.SYNC1Pulse: return(SYNC1Pulse(TZXDataBlock)); case TZXStates.SYNC2Pulse: return(SYNC2Pulse(TZXDataBlock)); case TZXStates.DataBytes: return(DataBytes(TZXDataBlock)); case TZXStates.EndPause: return(GetNextBlock()); } return(0); }
private void TapeView_MouseMove(object sender, MouseEventArgs e) { Focus(); if (TZXFile == null) { return; } if (TZXFile.Blocks == null) { return; } if (TZXFile.Blocks.Count == 0) { return; } if (coords == null) { return; } if (e.X != this.lastX || e.Y != this.lastY) { foreach (Coord c in coords) { if (c.Rect.Contains(e.X, e.Y)) { ITZXDataBlock b = c.Block as ITZXDataBlock; if (TZXFile.Blocks.Count > 1) { tooltip.SetToolTip(this, "[" + c.BlockNo.ToString() + "] " + c.Block.ToString() + " {" + b.TAPBlock.Length.ToString() + "} Bytes"); } else { tooltip.SetToolTip(this, c.Block.ToString() + " {" + b.TAPBlock.Length.ToString() + "} Bytes"); } break; } } } this.lastX = e.X; this.lastY = e.Y; }
private void CassetteDeck_Progress(TZXFile tzxFile, int blocklength, int tapeCounter, int blockCounter, float overallProgress, float blockProgress, string block, ITZXDataBlock tZXDataBlock) { class11.SelectionStart = class11.SelectionEnd = 0; class11.SetSelectionForeColor(true, Color.Lime); class11.SetSelectionBackColor(true, SystemColors.WindowFrame); if (tzxFile != null) { ProgressText = "Block:" + blockCounter.ToString("0000000") + "/" + (blocklength - 1).ToString() + " Total: " + tapeCounter.ToString("0000000") + "/" + tzxFile.TZXLength.ToString(); } counter1.Value = tapeCounter + 1; if (panel1.Visible) { toolStripStatusLabel1.Text = blockCounter == 0 ? "Paused" : "Playing"; blockView.CursorPen = null; tapeView.CursorPen = null; blockView.Next(blockProgress); tapeView.CursorPen = blockView.CursorPen; tapeView.Next(overallProgress); } if (tZXDataBlock != null) { if (class11.Visible && tZXDataBlock is ITZXDataBlock) { int b = tZXDataBlock.Progress; string s = tZXDataBlock.Details; int charindex = s.IndexOf("TZXTAP Block:") + 16; // "TZXTAP Block: /r/n".Length charindex += 5; // " {\r\n".Length int row = b / 16; int col = (b % 16); charindex = charindex + (row * 57); charindex += 11; charindex += (col * 3) - 3; class11.GotoPosition(charindex); class11.SelectionStart = charindex; class11.SelectionEnd = charindex + 2; class11.SetSelectionBackColor(true, Color.Lime); class11.SetSelectionForeColor(true, SystemColors.WindowFrame); } } }
public static string Header(ITZXDataBlock block) { Filename = ""; string text = ""; if (block.TAPBlock.Length < 10) { return("Fragment Block {" + (block.TAPBlock.Data.Length - 1).ToString() + " Bytes}"); } for (int i = 2; i < 12; i++) { char c = (char)block.TAPBlock.Data[i]; if (block.TAPBlock.Data[i] < 32) { c = '?'; } if (block.TAPBlock.Data[i] > 127) { c = '?'; } Filename += c; } Filename = Filename.Trim() + " "; switch (block.TAPBlock.Data[0]) { case 0: // Header BlockType = "Program: "; DataLength = block.TAPBlock.Data[12] | (block.TAPBlock.Data[13] << 8); AutostartLine = block.TAPBlock.Data[14] | (block.TAPBlock.Data[15] << 8); ProgramLength = block.TAPBlock.Data[16] | (block.TAPBlock.Data[17] << 8); text = BlockType + "\"" + Filename.Trim() + "\"" + " LINE " + AutostartLine.ToString() + "; Header Block {" + (block.TAPBlock.Data.Length - 1).ToString() + " Bytes}"; break; case 1: // Numeric Array BlockType = "Numeric Array: "; VariableName = ((char)block.TAPBlock.Data[15]).ToString(); text = BlockType + Filename + " " + VariableName; break; case 2: // Alphanumeric Array BlockType = "Alphanumeric Array: "; VariableName = ((char)block.TAPBlock.Data[15]).ToString(); text = BlockType + Filename + " " + VariableName; break; case 3: // Byte header or SCREEN$ header DataLength = block.TAPBlock.Data[12] | (block.TAPBlock.Data[13] << 8); StartAddress = block.TAPBlock.Data[14] | (block.TAPBlock.Data[15] << 8); BlockType = "Bytes: "; if (StartAddress == 16384) { BlockType = "Screen$: "; } if (StartAddress == 22528) { BlockType = "Screen$: "; } text = BlockType + "\"" + Filename.Trim() + "\"" + " CODE " + StartAddress.ToString() + ", " + (DataLength + 1).ToString() + "; Header Block {" + (block.TAPBlock.Data.Length - 1).ToString() + " Bytes}"; break; default: text = "Data Block {" + (block.TAPBlock.Data.Length - 1).ToString() + " Bytes}"; break; } return(text); }
int SYNC1Pulse(ITZXDataBlock TZXDataBlock) { EarBit = EarBit ^ 64; TZXState.Next(); return(TZXDataBlock.Sync2Length); }
int GetNextBlock(bool increment) { if (TZXBlockIndex == 0) { TZXTapeCounter = 0; } if (increment) { TZXBlockIndex++; } if (TZXBlockIndex > TZXFile.Blocks.Count) { IsPlaying = false; OnLoaded(); return(0); } pulseLength = 0; TZXBlock = TZXFile.Blocks[TZXBlockIndex]; switch (TZXBlock.ID) { case TZXBlockType.TapeDataBlock: case TZXBlockType.StandardSpeedDataBlock: case TZXBlockType.TurboSpeedDataBlock: { ITZXDataBlock tZXBlock = TZXBlock as ITZXDataBlock; pulseLength = tZXBlock.PulseLength; tZXBlock.Progress = 0; usedBits = tZXBlock.UsedBits; TZXState.Reset(); TZXCurrentByte = tZXBlock.TAPBlock.FirstByte(); break; } case TZXBlockType.PureDataBlock: { PureDataBlock tZXBlock = TZXBlock as PureDataBlock; PulseCounter = 2; if ((tZXBlock[0] & 0x80) > 0) { pulseLength = tZXBlock.OneLength; } else { pulseLength = tZXBlock.ZeroLength; } usedBits = tZXBlock.UsedBits; tZXBlock.Progress = 0; TZXState.State = TZXStates.DataBytes; TZXCurrentByte = tZXBlock.TAPBlock.FirstByte(); break; } case TZXBlockType.PureTone: { PureTone tZXBlock = TZXBlock as PureTone; PulseToneLength = tZXBlock.numberOfPulses; pulseLength = tZXBlock.PulseLength; tZXBlock.Progress = 0; TZXState.Reset(); break; } case TZXBlockType.SequenceOfPulsesOfVariousLengths: { SequenceOfPulsesOfVariousLengths tZXBlock = TZXBlock as SequenceOfPulsesOfVariousLengths; PulseToneLength = tZXBlock.PulseToneLength; pulseLength = tZXBlock.PulsesLengths[0]; tZXBlock.Progress = 0; TZXState.Reset(); break; } case TZXBlockType.PauseSilenceOrStopTheTapeCommand: { PauseStopTheTape tZXBlock = TZXBlock as PauseStopTheTape; if (tZXBlock.PauseDuration == 0) { StartStopTheTape(); } else { pulseLength = tZXBlock.PauseDuration * 3500; TZXState.State = TZXStates.EndPause; } break; } case TZXBlockType.StopTheTapeIfIn48kMode: { StartStopTheTape(); break; } case TZXBlockType.JumpToBlock: { JumpToBlock tZXBlock = TZXBlock as JumpToBlock; sbyte n = (sbyte)tZXBlock.RelativeJumpValue; TZXBlockIndex += n; GetNextBlock(false); break; } case TZXBlockType.LoopStart: { LoopStart tZXBlock = TZXBlock as LoopStart; loopCounter = tZXBlock.NumberOfRepetitions; TZXBlockIndex++; loopNext = TZXBlockIndex; GetNextBlock(false); break; } case TZXBlockType.LoopEnd: { LoopEnd tZXBlock = TZXBlock as LoopEnd; loopCounter--; if (loopCounter > 0) { TZXBlockIndex = loopNext; } else { TZXBlockIndex++; } GetNextBlock(false); break; } case TZXBlockType.CallSequence: { CallSequence tZXBlock = TZXBlock as CallSequence; stack.Push(TZXBlockIndex); numberOfCalls = tZXBlock.NumberOfCallsToBeMade; callList = tZXBlock.ArrayOfCallBlockNumbers; callCounter = 0; sbyte n = (sbyte)tZXBlock.ArrayOfCallBlockNumbers[callCounter++]; TZXBlockIndex = TZXBlockIndex += n; GetNextBlock(false); break; } case TZXBlockType.ReturnFromSequence: { if (callCounter < numberOfCalls) { sbyte n = (sbyte)callList[callCounter++]; TZXBlockIndex = callSequenceOrigin + n; GetNextBlock(false); } else { if (stack != null) { if (stack.Count > 0) { TZXBlockIndex = stack.Pop(); } } GetNextBlock(); } break; } case TZXBlockType.EndOfFile: { IsPlaying = false; OnLoaded(); } break; default: GetNextBlock(); break; } return(pulseLength); }
public static void OnProgress(TZXFile tzxfile, int blocklength, int tapeCounter, int blockCounter, float overallProgress, float blockProgress, string block, ITZXDataBlock tZXDataBlock) { Progress?.Invoke(tzxfile, blocklength, tapeCounter, blockCounter, overallProgress, blockProgress, block, tZXDataBlock); }