Delphi-PRAXiS
Seite 7 von 9   « Erste     567 89      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Software-Projekte der Mitglieder (https://www.delphipraxis.net/26-software-projekte-der-mitglieder/)
-   -   Virtual Piano (https://www.delphipraxis.net/158944-virtual-piano.html)

EWeiss 19. Mai 2011 17:36

AW: Virtual Piano
 
Alle Noten egal welcher Art werden immer 12x12 gezeichnet und zwar so groß wie die Quadrate im Grid.
Wenn du eine Note in der länge änderst wird immer mit 12 hochgezählt.

Ich habe es jetzt anderes gemacht.
Ich denke es macht keinen Sinn wenn ich bei eingestellter 1/16 Note anfange zu zeichnen anschließend noch auf eine andere wechseln zu wollen.
Daher habe ich ein Flag eingebaut welches das Ändern des Grid\Note unterbindet.
Man kann aber weiterhin auf 3/4 4/4 usw.. schalten.

Man kann jederzeit die Note nachträglich noch ändern wenn man vorher abspeichert.
Die Datei neueinläd und dann ohne vorher zu zeichen auf 1/8 schaltet.
Wird dann neu gezeichnet bleibt die eingestellte Note auf 1/8.

Denke das ist eine lösung.
Werde dir demnächst mal den Quelltext zuschicken.
Vorrausgesetzt du hast D2009 UP..

gruss

Namenloser 19. Mai 2011 18:54

AW: Virtual Piano
 
Ich kann das Programm ja leider weiterhin nicht starten, aber auf dem Screenshot ist mir aufgefallen, dass alles geskinnt
ist bis auf die Scrollbars des Grids. Wirst du die eigentlich noch durch eigene ersetzen?

alfold 19. Mai 2011 18:59

AW: Virtual Piano
 
ok ebend 12x12, wo liegt aber das Problem?
1/4 ist 12pixel eine 4tel Note, 4 senkrechte striche pro Takt
1/8 ist 24pixel eine 4tel Note, 8 senkrechte striche pro Takt
1/16 ist 48pixel eine 4tel Note usw
1/32 ist 96pixel eine 4tel Note usw

Zweite darstellung: halbe Note
1/4 ist 24pixel eine halbe Note, 4 senkrechte striche pro Takt
1/8 ist 48pixel eine halbe Note, 8 senkrechte striche pro Takt
1/16 ist 96pixel eine halbe Note, usw
1/32 ist 192pixel eine halbe Note, usw

dritte Darstellung: ganze Note
1/4 ist 48pixel eine ganze Note, 4 senkrechte striche pro Takt
1/8 ist 96pixel eine ganze Note, 8 senkrechte striche pro Takt
1/16 ist 192pixel eine ganze Note, usw
1/32 ist 384pixel eine ganze Note, usw

und nun das ganze wieder zurückrechnen. von 1/32 zu 1/4. Dies ist nur die graphische Darstellung. Was Du intern machst, um daraus ne Note zu hören ist wieder was anderes.
Selbst wenn Du daraus die Note berechnest, bleibt es immer die dementsprechende graphische Note. Du musst also nicht mal was zwischenspeichern um das neu zu berechnen beim Zeichnen des Grids. Denn irgendwo musst Du ja die Daten sprich Noten haben!?

Natürlich müssen die Taktstriche und zwichenstriche auch dazu berechnet werden, klar. Hast Du ja schon:wink:
Ist aber alles x2 oder durch 2. Oder rechne ich da falsch!?

Will ja nicht unken, bin ja selber kein Profi, nonvcl schon gar nicht, aber
Zitat:

Man kann jederzeit die Note nachträglich noch ändern wenn man vorher abspeichert.
Die Datei neueinläd und dann ohne vorher zu zeichen auf 1/8 schaltet.
dies ist keine Profilösung:gruebel:
Leider habe ich nur D7 Enterprise:? und XP
Ob Dein Source darauf läuft? Würde gern das mit der Graphic für Dich machen. Weil so wie es ist ist es halt nicht gut:?
Zumal ich noch ein paar wichtige futures habe, was Du noch machen müstest!

Gruss

EWeiss 19. Mai 2011 19:41

AW: Virtual Piano
 
Zitat:

Zitat von NamenLozer (Beitrag 1101857)
Ich kann das Programm ja leider weiterhin nicht starten, aber auf dem Screenshot ist mir aufgefallen, dass alles geskinnt
ist bis auf die Scrollbars des Grids. Wirst du die eigentlich noch durch eigene ersetzen?

Das ist schade. :cry:

Eigentlich schon..
Aber das ist nicht so einfach muss mir da noch was einfallen lassen.

gruss

EWeiss 19. Mai 2011 20:06

AW: Virtual Piano
 
Zitat:

Zitat von alfold (Beitrag 1101858)
ok ebend 12x12, wo liegt aber das Problem?

Erst mal Danke für dein Interesse.

Das Problem liegt tiefer begraben man kann das so pauschal nicht auslegen.
Hast du mal die *.mtf Datei analysiert?

Wenn du eine einfache Note zeichnest ist das alles kein problem wenn du aber zwei in folge addierst rechnet sich das ganze so..

Eine Note.. bsp. 50
Erweiterst du diese dann bekommst du einen Eintrag von "50, 1050"
1050 steht für Fortgesetzte Note(rede jetzt nur vom Grid) in dem Fall hättest du dann 2x48 Ticks also ein halbe note 2/4.
Wobei 50 die StartNote und mit 1000 addiert die Folgenden sind.
"50, 1050, 1050, 1050" wäre dann eine ganze.

Wenn du dich nun im 1/16 Grid befindest und dort eine ganze Note zeichnest sieht das ganze so aus.
"91,1091,1091,1091,1091,1091,1091,1091,1091,1091,1 091,1091,1091,1091,1091,1091"

So jetzt schalte mal zurück nach 1/8 Note..
Was denkst du wie es dann aussieht
Dann halbiert ich das ganze schaltest du nun nach 1/4 dann wird alles das abgeschnitten was
im 1/4 Grid nicht mehr Anzeigbar ist so wie die 1/16 Note.

Es ist einfach mit meiner Grid auflösung nicht möglich in einem 1/4 grid 1/16 noten anzeigen zu lassen.

Zitat:

Ob Dein Source darauf läuft? Würde gern das mit der Graphic für Dich machen.
Zumal ich noch ein paar wichtige futures habe, was Du noch machen müstest!
Nein definitiv nicht denn der ist auf Unicode ausgelegt.

Zitat:

Weil so wie es ist ist es halt nicht gut
Gebe ich dir vollkommen Recht!
Finde aber im moment nicht die Lösung für das Problem.

gruss

alfold 19. Mai 2011 20:43

AW: Virtual Piano
 
Zitat:

Das Problem liegt tiefer begraben man kann das so pauschal nicht auslegen.
Hast du mal die *.mtf Datei analysiert?
Jo hab ich, mit 'ALLeMeineENTCHEN':wink: erkenne zwar die Noten, kann aber mit anderen Werten nix anfangen.
Und ich vermute genau Da, liegt der Hase im Pfeffer.
Du trennst die Daten nicht von deiner visuallisierung, sprich Grid. Was Du wie wo Speicherst, berechnest, passiert in deinem Programm.
Wie sieht es aus ohne Grid, einfach nur Play und schon wirst du feststellen, egal wie Du intern es berechnest oder speicherst, eigenes Format, interesiert niemand.
Die Anzeige muss richtig funcen, ohne die, wird es ne Qual.

Was du Anzeigen willst musst du halt so umsetzten wie ich es oben simpel beschrieben habe. Da kommst Du nicht drumrum.

Du wirst zwar für Dich glücklich mit Deinem Programm, aber andere greifen dann doch lieber auf andere FreeSoftware zurück und dies währe schade finde ich.
Gerade weil diese Prog nicht überladen ist.
Aber, es ist wichtig das die Anzeige so funktioniert, wie es nun mal sein muss.

Ob man nun unbedingt Akorde in einem Track haben muss, währe schön, ist aber nicht wichtig!
Die Anzeige schon!

EDIT:
Zitat:

Dann halbiert ich das ganze schaltest du nun nach 1/4 dann wird alles das abgeschnitten was
im 1/4 Grid nicht mehr Anzeigbar ist so wie die 1/16 Note.
ebend nicht! Hab ich Dir in #240 mal vorgezeigt.
Gruss alfold

EWeiss 19. Mai 2011 21:01

AW: Virtual Piano
 
Zitat:

Jo hab ich, mit 'ALLeMeineENTCHEN' erkenne zwar die Noten, kann aber mit anderen Werten nix anfangen.
Habe ich dir doch oben ausführlich beschrieben ;)

Zitat:

Und ich vermute genau Da, liegt der Hase im Pfeffer.
Du trennst die Daten nicht von deiner visuallisierung, sprich Grid. Was Du wie wo Speicherst, berechnest, passiert in deinem Programm.
Wie soll ich die Daten vom Grid trennen?
Also das ist beim besten willen nicht möglich.
Wie willst du sonst die Arrays mit Daten füttern wenn du quasi nichts hast?

Delphi-Quellcode:
Grid: array[0..15, 0..MAXNOTES] of integer;

0..15 die Spuren
0..MAXNOTES die Noten

Wie also soll ich ohne das Grid das Array füllen?
Wie soll ich ohne Grid die Noten Visualisieren ?
Wie willst du ohne Grid festlegen wann und welche Note gespielt wird?

Zitat:

ebend nicht! Hab ich Dir in #240 mal vorgezeigt.
Muss dir nochmal sagen ich habe pro Note einen bereich zum zeichnen von 12x12 pixel
Nichts drunter und nichts drüber.
Befindet sich die Note in einem bereich der nicht glatt durch 12 Teilbar
ist wird sie gelöscht und nicht angezeigt.
Habe dir in einem früheren Beitrag schon mal gesagt das ich 7.5 nicht durch 12 Teilen kann.


gruss

alfold 19. Mai 2011 22:34

AW: Virtual Piano
 
Zitat:

Habe ich dir doch oben ausführlich beschrieben
hab ich erst beim xten mal lesen verstanden:oops:
Wenn ich es richtig verstanden habe, speicherst du die gezeichnete Notenlänge in Deiner Datei ab?

Hast Du dir mal diesen LINK wirklich durchgelesen!

Zitat:

Wie soll ich die Daten vom Grid trennen?
Also das ist beim besten willen nicht möglich.
Wie willst du sonst die Arrays mit Daten füttern wenn du quasi nichts hast?
....
Wie also soll ich ohne das Grid das Array füllen?
Wie soll ich ohne Grid die Noten Visualisieren ?
Wie willst du ohne Grid festlegen wann und welche Note gespielt wird?
OK fangen wir hinten an!
Du liest eine Mid ein!
Was ist jetzt das Problem, die Noten kannst du in ein normales Array laden, auch ohne Grid.
Takt und BPM liegen auch vor.
Aus diesen Daten und noch andere, errechnet sich was eine 4tel note ist, halbe oder 16. als reiner Zahlenwert!
Würdest Du nun ne visualisierug mit Notenlienen machen ist es auch egal ob Du 40pixel für eine Note nimmst oder nur 10pixel. Enscheident ist jetzt, welche Note wo gezeichnet wird!

Ok zum Grid!
Wenn du beim einlesen von Middateien nun die reinen Notenwerte hast (die liegen in ein Array) kannst Du nun die Anzeige machen wie du willst! weil Du das Array nicht änderst sondern nur die Anzeige!

Ok editieren:
auch hier gibst Du Takt und BPM vor, Zeichnest die Note, egal in welcher Auflösung, siehe mein simpel Beispiel. Selbst daraus errechnet sich jetzt welche Note und wie lang sie ist.
Diesen wert speicherst Du im array, wie beim einlesen! Änderst Du jetzt die Auflösung wird die Note aus denm array geholt und gezeichnet! Auch hier wieder mein simpel Beispiel.

Das selbe gilt für das speichern deines Formates, du must nicht die Darstellung speichern(wenn ich es richtig verstanden habe) sondern nur die Note und ihre länge zum Takt und nicht wie lang sie gezeichnet werden muss!


Der rest ist dann so wie ich es beschrieben habe.
Ich befürchte aber das das umstellen schwerer sein wird als es so zu lassen! Weil Du dich auf 12x12 fixierst hast!

Gruss alfold

EWeiss 20. Mai 2011 01:10

AW: Virtual Piano
 
Zitat:

OK fangen wir hinten an!
Du liest eine Mid ein!
Was ist jetzt das Problem, die Noten kannst du in ein normales Array laden, auch ohne Grid.
Takt und BPM liegen auch vor.
Mache nichts anderes.
Nur das ich Sie nach dem einlesen in mein Array auf meinen DateiTyp anpasse (Parsen).
Zitat:

ist es auch egal ob Du 40pixel für eine Note nimmst oder nur 10pixel.
Enscheident ist jetzt, welche Note wo gezeichnet wird!
Ist nicht egal die Noten werden in einer Breite von 12 und einer höhe von 12 gezeichnet.
das mußt du doch sehen wenn du in einer reihe im Grid Klickst.
Nochmal..
0..15 Spur die legst du fest indem du auf EditTrack 1 klickst
0..1000 Noten.. Scroll das grid ganz runter wenn du nun in der Spalte 0 und Letzte Reihe(72) klickst dann wird im Array Grid die Note "C0" gespeichert
Wird diese erweitert also als halbe Note ausgelegt dann wird dem Array eine (1000 + 72) = 1072 hinzugefügt.
Im Array steht jetzt also 72, 1072. Start und Fortlaufende Note = eine 2/4 Note bei einem 4/4 Takt.
Diese Daten werden dann in der *.mtf Datei abgespeichert.

Zitat:

kannst Du nun die Anzeige machen wie du willst! weil Du das Array nicht änderst sondern nur die Anzeige!
Kann ich auch nicht.
Die Anzeige ist vorgegeben pro Note 12x12

Zitat:

Das selbe gilt für das speichern deines Formates, du must nicht die Darstellung speichern(wenn ich es richtig verstanden habe) sondern nur die Note und ihre länge zum Takt und nicht wie lang sie gezeichnet werden muss!
Genau das mache ich.
Aber du scheinst da irgend etwas nicht zu verstehen.
Ob ich meine Note nun in Hex oder Dezimal in meine Datei schreibe ist doch wurscht.
Die Frage ist doch wie ich die Daten nachher wieder einlese (Parse).
Und das es funktioniert wenn du mein Format liest siehst du doch.

Zitat:

Ich befürchte aber das das umstellen schwerer sein wird als es so zu lassen! Weil Du dich auf 12x12 fixierst hast!
Nö habe mich da nicht fixiert sondern das ist vorgegeben.
Ich habe das Prog so ausgelegt das die Noten nicht in Pixeln sondern in Quadern gezeichnet werden
und um das umzulegen auf Pixel da kann ich direkt alles wieder neu machen.
Und das scheinst du nicht zu verstehen.

Habe dir das schon 20 Beiträge vorher mitgeteilt.
Das ich im moment grenzen unterliege weil meine Grafik(Grid) auf eine feste größe ausgelegt ist.
Vielleicht verstehst du eins nicht das ist NonVCL es gibt keine komponente die man mal
ebend auf die Form klatscht sondern es ist alles Handgemacht mit GDI+.
Nur für das grid ca. 4 Wochen Arbeit(na ja ist Hobby).
Wenn ich das ändere muss ich quasi alles neu machen angefangen bei den Tool Button.

Im moment geht es eh nicht..
Da ich mit einer 6 Segment Anzeige von hand gezeichnet GDI+ beschäftigt bin.
Das hat vorrang da ich damit die Zeitanzeige verwirklichen will.
Passend zu meinem Design natürlich.
Das bedeutet Bilder zeichnen Quelltext schreiben und dann muss es auch noch funktionieren ;)

gruss

alfold 20. Mai 2011 14:35

AW: Virtual Piano
 
Zitat:

Eine Note.. bsp. 50
Erweiterst du diese dann bekommst du einen Eintrag von "50, 1050"
1050 steht für Fortgesetzte Note(rede jetzt nur vom Grid) in dem Fall hättest du dann 2x48 Ticks also ein halbe note 2/4.
Wobei 50 die StartNote und mit 1000 addiert die Folgenden sind.
"50, 1050, 1050, 1050" wäre dann eine ganze.

Wenn du dich nun im 1/16 Grid befindest und dort eine ganze Note zeichnest sieht das ganze so aus.
"91,1091,1091,1091,1091,1091,1091,1091,1091,10 91,1 091,1091,1091,1091,1091,1091"

So jetzt schalte mal zurück nach 1/8 Note..
Was denkst du wie es dann aussieht
Dann halbiert ich das ganze schaltest du nun nach 1/4 dann wird alles das abgeschnitten was
im 1/4 Grid nicht mehr Anzeigbar ist so wie die 1/16 Note.

Es ist einfach mit meiner Grid auflösung nicht möglich in einem 1/4 grid 1/16 noten anzeigen zu lassen.

Ok hiehr mal der richtige Ansatz
'...Fall hättest du dann 2x48 Ticks also ein halbe note 2/4.'
eine 32tel hat 3ticks
eine 16tel hat 6ticks
eine 8tel hat 12ticks
Eine 4tel hätte 24 ticks
eine halbe hätte 48 ticks
eine ganze hat 96 ticks

eine Punktierte 4tel hätte demzufolge auch 48ticks nur so am rande

So speichern tutst Du nun
50 12 für ne 8tel oder
50 24 für ne 4tel oder
50 48 für ne halbe oder
50 96 für ne ganze
so sollten die dan in deinem Array drin stehen.
Das sind die tatsächliche gehörte länge einer Note!
Grid Ausgabe:
1/4 diesen wert musst Du ja auch irgendwo stehen haben!
nun kommt die Berechnung und dies hat nix mit VCL oder nonvcl zu tun

Deine graphiche länge ist 12, (die höhe lass ich mal weg)
Delphi-Quellcode:
if 1/4 and (notenticks >=24) then zeichnen
  notenticks 24 zeichne 12
  notenticks 48 zeichne 2x12
  notenticks 96 zeichne 4x12

if 1/8 and (notenticks >= 12 then zeichnen
   notenticks 12 zeichne 12
   notenticks 24 zeichne 2x12
   notenticks 48 zeichne 4x12

if 1/16 and (notenticks >=6) then zeichnen
   notenticks 6 zeichne 12
   notenticks 12 zeichne 2x12
   notenticks 24 zeichne 4x12
   notenticks 48 zeichne 8x12
usw.
Sieht im ersten Moment natürlich blöd aus, erklärt aber wie die Umsetzung vom prinzip geht!
Und jetzt sage mir das geht nicht!
Denn dies hat weder was mit vcl oder nonvcl zu tun
Das auslesen(beim editieren) was Du also irgend wo mit der Mouse gemacht hast,
must Du ja auch irgenwo herbekommen. Da steht auch irgenwo der Wert 1/4 oder 1/16
dann Zeichnest Du (oder wie du es bei nonvcl nennst)und diesen Wert rechnest Du zurück und speicherst es so ab wie oben beschrieben!

Das brauchst Du also nicht speichern
"91,1091,1091,1091,1091,1091,1091,1091,1091,10 91,1 091,1091,1091,1091,1091,1091"
bei einer Auflösung von 1/16
sondern so wie es sein sollte
91 96, entspricht eine ganze Note.

Du siehst also das dein eigener Ansatzt des speichern, falsch ist.
Sorry Bitte, wenn ich diesen Ansatz von Dir kritisiere.

Kannst mich jetzt auch Steinigen oder mir verbieten auf dieses Thema noch zu Antworten,
würde ich sogar verstehen.

Gruss alfold

EWeiss 20. Mai 2011 15:19

AW: Virtual Piano
 
Zitat:

Du siehst also das dein eigener Ansatzt des speichern, falsch ist.
Sorry Bitte, wenn ich diesen Ansatz von Dir kritisiere.

Kannst mich jetzt auch Steinigen oder mir verbieten auf dieses Thema noch zu Antworten,
würde ich sogar verstehen.
Warum sollte ich auf Konstruktive vorschläge aggressiv reagieren?
Ich werde mir deinen vorschlag mal notieren genau durchgehen und wenn ich zu dem Schluss
komme das es einfacher, Übersichtlicher ist es so zu machen dann tue ich es.

Solange wie ich im "moment" nicht meine Grid Operationen dadurch gefährde.

Meine aber das es letztendlich nicht von bedeutung ist was im array steht
und wie die Daten gespeichert werden.
Sondern nur wie lese ich sie ein bzw .. parse sie korrekt auf das MidiFormat(NOTE)
Theoretisch könnte ich sie für dich unleserlich machen A,AB,AB,AB aber am ende stehen die Daten
in einem für mein Grid bzw.. MidiDaten lauffähigen Format nach dem parsen.

ob ich jetzt
91 96 Note/Notenlänge so interpretiere
oder auf meiner weise
91, 1091, 1091 spielt dabei absolut keine rolle das ergebniss zählt was letztendlich heraus kommt. ;)
Auf die eine oder andere Weise.

PS:
Meine Funktion zum Parsen ist Ausschlaggebend und nicht die art wie ich die Daten ablege.
gruss

EWeiss 20. Mai 2011 15:26

AW: Virtual Piano
 
Hier meine Parse Funktion

Delphi-Quellcode:
function TMidiTracker.ConvertMidiNote(MidiNote: TMIDINote; Ticks: Word; FirstNote: Bool) : Integer;
var
  TickValue: Integer;

begin
  Result := -1;

  TickValue := Ticks div SmallNoteData[SmallNDSelected].Value;

  if MidiNote.NoteNo > 0 then
    if (MidiNote.Length = TickValue) or (FirstNote = True) then
    begin
      Result := MidiNote.NoteNo;
      MidStartNote := False;
    end
    else if (MidiNote.Length > TickValue) then
      Result := 1000 + MidiNote.NoteNo
    else
    Result := MidiNote.NoteNo;

end;
Delphi-Quellcode:
procedure TMidiTracker.ImpMidiFile(MidiFile: Widestring);
var
  MIDIFileInfo: TMIDIFileInfo;
  MIDINote:    TMIDINote;
  IntI:        Integer;
  IntA:        Integer;
  IntB:        Integer;
  IntC:        Integer;
  NewNote:     Integer;
  TimeGap:     DWORD;
  Ticks:       Word;
  TmpGrid:     array of integer;
  TmpInstGrid: array of integer;
  PPQN:        Double;
  st:          string;

begin
  if not ReadMIDIFile(MidiFile, MIDIFileInfo) then
  begin
    MessageBox(Self.Handle, 'Not a valid MIDI file.', 'Confirm', MB_OK);
    exit;
  end;
  ClearGrids;

  Ticks := MIDIFileInfo.Ticks;

  // Array länge setzen
  SetLength(TmpGrid, MaxNotes);
  SetLength(TmpInstGrid, MaxNotes);

  // Blanke Noten einfügen
  for IntB := 0 to High(TmpGrid) do
  begin
    TmpGrid[IntB] := -1;
    TmpInstGrid[IntB] := 0;
  end;

  // erste Note Initialisieren
  NewNote := -1;

  for IntI := 0 to High(SmallNoteData) do
  begin
    if SmallNoteData[IntI].Ticks = Ticks then
    begin
      SmallNDSelected := IntI;
      SKAERO_SetCTLText(SKAERO_GetMainItem(MainHandle, ID_SMALLESTNOTELABELVAL),
      WideString(SmallNoteData[SmallNDSelected].Name));
      break;
    end;
  end;

  for IntI := 1 to MIDIFileInfo.Channels do
  begin
    for IntA := 0 to MIDIFileInfo.ChannelAttr[IntI].NoteCounter -1 do
    begin
      // Note einlesen
      MidiNote := MIDIFileInfo.MIDINotes[IntI, IntA];
      PPQN := MidiNote.Ppqn * 2;

      // Note Umdrehen
      MidiNote.NoteNo := (127 - MidiNote.NoteNo) + basenote;

      // Erste Note nicht an position 0
      // Blanke Noten einfügen
      if (IntA = 0) and (MIDIFileInfo.MIDINotes[IntI, IntA].StartTime > 0) then
      begin
        TimeGap := MidiNote.StartTime;
        IntB := (TimeGap div 12);
        if IntB > 0 then
        begin
          for IntC := 1 to IntB do
          begin
            inc(NewNote);
            TmpGrid[NewNote] := -1;
            TmpInstGrid[NewNote] := 0;
          end;
        end
      end;

      // Prüfen ob StartNote
      if not MidStartNote then
        MidStartNote := MidiNote.Length > (Ticks div SmallNoteData[SmallNDSelected].Value);

      // StartNote gefunden
      if MidStartNote then
      begin

       for IntB := 1 to round(PPQN) do
       begin
         Grid[IntI - 1, IntA] := ConvertMidiNote(MidiNote, Ticks, MidStartNote);

         SKAERO_SetTrackValue(TrackBarVol[IntI].Handle, MIDIFileInfo.ChannelAttr[IntI].Volume);

         inc(NewNote);
         if Grid[IntI - 1, IntA] < 1000 then
         begin
           TmpGrid[NewNote] := Grid[IntI - 1, IntA];
           TmpInstGrid[NewNote] := MidiNote.Instrument;;
         end;

         if Grid[IntI - 1, IntA] > 1000 then
         begin
           TmpGrid[NewNote] := Grid[IntI - 1, IntA];
           TmpInstGrid[NewNote] := MidiNote.Instrument;
         end;
       end;
      end else
      begin
        Grid[IntI - 1, IntA] := ConvertMidiNote(MidiNote, Ticks, MidStartNote);
        InstGrid[IntI - 1, IntA] := MidiNote.Instrument;

        SKAERO_SetTrackValue(TrackBarVol[IntI].Handle, MIDIFileInfo.ChannelAttr[IntI].Volume);

        inc(NewNote);
        TmpGrid[NewNote] := Grid[IntI - 1, IntA];
        TmpInstGrid[NewNote] := MidiNote.Instrument;
      end;

      if IntA < MIDIFileInfo.ChannelAttr[IntI].NoteCounter -1 then
      begin
        TimeGap := MIDIFileInfo.MIDINotes[IntI, IntA + 1].StartTime - (MidiNote.StartTime + MidiNote.Length);
        if TimeGap > 0 then
        begin
          IntB := (TimeGap div 12);
          if IntB > 0 then
          begin
            for IntC := 1 to IntB do
            begin
              inc(NewNote);
              TmpGrid[NewNote] := -1;
              TmpInstGrid[NewNote] := 0;
            end;
          end
        end;
      end;
    end;

    for IntA := 0 to High(TmpGrid) do
    begin
      Grid[IntI - 1, IntA] := TmpGrid[IntA];
      InstGrid[IntI - 1, IntA] := TmpInstGrid[IntA];
    end;

    // Blanke Noten für neu einlesenden Track einfügen
    for IntB := 0 to High(TmpGrid) do
    begin
      TmpGrid[IntB] := -1;
      TmpInstGrid[NewNote] := 0;
    end;

    NewNote := -1;

  end;

  // Temp Array löschen
  Fillchar(TmpGrid, sizeOf(TmpGrid), 0);
  // Default werte für das Grid setzen
  StartX := 0;
  EndX   := XSize;
  ColumnX := 0;

  // Grid zeichnen
  DrawGrid(Handle);

  // Spielgeschwindigkeit auf default wert setzen
  Tempo := round(300 / 127 * MidiNote.Velocity);
  SKAERO_SetKnobValue(SKAERO_GetMainItem(MainHandle, ID_KNOB_SPEED), trunc(Tempo));
  SKAERO_SetCTLText(SKAERO_GetMainItem(MainHandle, ID_SPEEDVALLABEL),
    WideString(IntToStr(trunc(Tempo))));

  MidiTracker.Tempo := Tempo;
  MidiTracker.ChangeVelocity;

  MidiTracker.SetTime(round(MIDIFileInfo.PlayTime));
  st := Format ('%02d:%02.2d:%02.2d.%02.2d', [fHours, fMins, fSecs, fCS]);
  MediaTimer.SetTime(trunc(MIDIFileInfo.PlayTime));
  SKAERO_SetCTLText(SKAERO_GetMainItem(MainHandle, ID_SOUNDTIME),
    WideString(st));

  //SetTimer(Handle, SONGTIME_TIMER, 250, nil);

end;
PPQN berechnet sich aus!
Delphi-Quellcode:
Info.MIDINotes[Channel_, N-1].Ppqn := Info.MIDINotes[Channel, N-1].Length / Info.Ticks;
gruss

alfold 20. Mai 2011 15:55

AW: Virtual Piano
 
2 Fragen dazu:wink:
An welcher Stelle berücksichtigst Du die Auflösung? (1/4 - 1/32)
Was passiert wenn man die Auflösung ändert? Wird die Datei neu eingelesene oder wie wird es bei Dir gemacht?

Das währe erstmal alles dazu.
Hab zwr noch nicht alles kappiert, ist klar, aber ich denke damit kommt man zurecht, um es nach meinem Vorschlag umzusetzten.(versuch):wink:

Gruss alfold

EWeiss 20. Mai 2011 16:15

AW: Virtual Piano
 
Zitat:

Zitat von alfold (Beitrag 1102017)
2 Fragen dazu:wink:
An welcher Stelle berücksichtigst Du die Auflösung? (1/4 - 1/32)
Was passiert wenn man die Auflösung ändert? Wird die Datei neu eingelesene oder wie wird es bei Dir gemacht?

Das währe erstmal alles dazu.
Hab zwr noch nicht alles kappiert, ist klar, aber ich denke damit kommt man zurecht, um es nach meinem Vorschlag umzusetzten.(versuch):wink:

Gruss alfold

Kleinste Note..
Delphi-Quellcode:
SmallNoteData[SmallNDSelected].Value);
Delphi-Quellcode:
    // Kleinste Noten
    SmallNoteData[0].Name := '1/4 Note';
    SmallNoteData[0].Value := 1;
    SmallNoteData[0].Nenner := 2;
    SmallNoteData[0].Ticks := 48;

    SmallNoteData[1].Name := '1/8 Note';
    SmallNoteData[1].Value := 2;
    SmallNoteData[1].Nenner := 3;
    SmallNoteData[1].Ticks := 24;

    SmallNoteData[2].Name := '1/16 Note';
    SmallNoteData[2].Value := 4;
    SmallNoteData[2].Nenner := 4;
    SmallNoteData[2].Ticks := 12;

    SmallNoteData[3].Name := '1/32 Note';
    SmallNoteData[3].Value := 8;
    SmallNoteData[3].Nenner := 5;
    SmallNoteData[3].Ticks := 6;

Wenn die Auflösung geändert wird passiert folgendes.. bzw wird diese Funktion aufgerufen.

Delphi-Quellcode:
MidiTracker.SetNewNoteLength(SmallNoteData[SmallNDSelected].Value);
Delphi-Quellcode:
procedure TMidiTracker.SetNewNoteLength(NewLenght: Integer);
var
  TmpGrid: array of Integer;
  Note:   Integer;

  IntA:   integer;
  IntB:   Integer;
  IntC:   Integer;
  NewNote: Integer;

begin

  FindEndOfSong;
  if SongLength > 0 then
  begin
    SetLength(TmpGrid, MaxNotes);
    MidiTracker.ChangeVelocity;

    NewNote:= -1;
  //if NewLenght div 2 = 0 then
  //  exit;

    // Altes Grid Speichern
    if not bOldGrid then
    begin
      for IntA := 0 to 15 do
        for IntB := 0 to High(TmpGrid) do
          OldGrid[IntA, IntB] := Grid[IntA, IntB];

      bOldGrid := True;
    end;

    if bOldGrid then
    begin
      // Altes Grid füllen zum erneuten Parsen
      for IntA := 0 to 15 do
        for IntB := 0 to High(TmpGrid) do
        begin
          Grid[IntA, IntB] := OldGrid[IntA, IntB];
          TmpGrid[IntB] := -1;
        end;
    end;

    for IntA := 0 to 15 do
    begin
      for IntB := 0 to SongLength do
      begin
        Note := Grid[IntA, IntB];

        if Note < 1000 then
        begin
          for IntC := 0 to NewLenght - 1 do
          begin
            if NewNote < High(TmpGrid) then
            begin
              inc(NewNote);
              TmpGrid[NewNote] := Note;
              if Note < 0 then
                Note := -1
              else
              Note := 1000 + Note;
            end;
          end;
        end else
        begin
          if Note > 1000 then
          for IntC := 0 to NewLenght - 1 do
          begin
            if NewNote < High(TmpGrid) then
            begin
              inc(NewNote);
              TmpGrid[NewNote] := Note;
            end;
          end;
        end;
      end;

      for IntB := 0 to High(TmpGrid) do
        Grid[IntA, IntB] := TmpGrid[IntB];

      // Blanke Noten einfügen
      for IntB := 0 to High(TmpGrid) do
        TmpGrid[IntB] := -1;


      NewNote:= -1;
    end;
  end;

end;
gruss

alfold 21. Mai 2011 22:51

AW: Virtual Piano
 
So bin wieder da.
Muss doch noch nachfragen. Will ja nur das umändern was du nicht brauchst, bei meinem Vorschlag.

MIDIFileInfo
MidiNote
Währe schön wenn Du mir die den Aufbau gibst.

Ist es MIDIFileInfo wo Du alles ablegst und zur Laufzeit für die Audioausgabe ausliest, vermute ich mal.

Code:
// Spielgeschwindigkeit auf default wert setzen
Tempo := round(300 / 127 * MidiNote.Velocity);
Velocity ist doch die Anschlagsdynamic, bzw kann man auch für NoteOn bzw NoteOff benutzten
Frage mich wie dies mit dem Tempo zusammenhängt?:gruebel:

EDIT:
Stelle fest das es dochn nicht so einfach ist Deine Variant anzupassen:gruebel:
Bei meinem Vorschlag muss ich ja nicht Prufen ob eine note >1000 ist
ConvertMidiNote? warscheinlich auch nicht!
Code:
for IntA := 0 to High(TmpGrid) do
begin
      Grid[IntI - 1, IntA] := TmpGrid[IntA];//<--Grid[array] füllen, Was zur anzeige kommt?
      InstGrid[IntI - 1, IntA] := TmpInstGrid[IntA];//<---????
end;
Es stellen sich also mehr Fragen als Lösungen an:?
Denn
// Grid zeichnen
DrawGrid(Handle);
müsste ja auch angepasst werden!

Auch wenn es bei mir nicht läuft, währe es besser ich könnte den code sehen, als hier tausend Fragen zu stellen. dann passe ich es als demo an mit meinem Vorschlag und Du kannst es testen:wink:
Gruss alfold

EWeiss 3. Jun 2011 12:34

AW: Virtual Piano
 
sorry konnte nicht vorher Antworten.
Lag die letzten zwei wochen mit Gehinblutung im Krankenhaus.

Velocity = Geschwindigkeit ;)

Werde den Quelltext die Tage hochladen muss meine 6 Segment Anzeige erst noch fertig machen
kam ja leider zu nichts mehr.

gruss

Namenloser 3. Jun 2011 13:42

AW: Virtual Piano
 
Zitat:

Zitat von EWeiss (Beitrag 1104435)
sorry konnte nicht vorher Antworten.
Lag die letzten zwei wochen mit Gehinblutung im Krankenhaus.

Oha, na dann gute Besserung, auch wenn’s zwei Wochen zu spät kommt...

EWeiss 3. Jun 2011 16:35

AW: Virtual Piano
 
Zitat:

Zitat von NamenLozer (Beitrag 1104454)
Zitat:

Zitat von EWeiss (Beitrag 1104435)
sorry konnte nicht vorher Antworten.
Lag die letzten zwei wochen mit Gehinblutung im Krankenhaus.

Oha, na dann gute Besserung, auch wenn’s zwei Wochen zu spät kommt...

Jo ;)
Danke schön .. jetzt geht es wieder. (Ohne Schmerzen)

gruss

alfold 3. Jun 2011 19:10

AW: Virtual Piano
 
Na, dann wünsch ich Dir auch alles gute:thumb: und alles langsamer angehen:wink:

Zitat:

Velocity = Geschwindigkeit
Original Auszug....
Zitat:

Die Tastennummern bei MIDI reichen von 0-127. #0 steht für C-2,#12 ist demnach C-1,#24 ist C 0,#36 ist C 1,#37 ist C# 1 usw...
$8n Note Off
Statusbyte: $8n,1. Datenbyte Key#,2. Datenbyte Note Off Velocity. Key # ist die Tastennummer 0-127.

$9n Note On
Statusbyte: $9n,1. Datenbyte Key#,2. Datenbyte Note On Velocity. Key # ist die Tastennummer 0-127.

Die Velocity bedeutet die Lautstärke mit der eine Note angeschlagen wird, bzw. losgelassen wird
:gruebel:

Freu mich schon auf die neue(letzte) Version:-D
Gruss alfold

EWeiss 3. Jun 2011 20:10

AW: Virtual Piano
 
Zitat:

Original Auszug....
Muss mich da nochmal schlaumachen.. sowie ich gelesen habe wird es nicht nur für
Anschlagdynamic verwendet.

Im Anhang der Source und fehlende Bitmaps für Nummern.
Der Quelltext funktioniert nur mit oben ängehängten "Binären Archiv"

gruss

alfold 4. Jun 2011 11:53

AW: Virtual Piano
 
Hast du wirklich die aktuelle Version oben?
Oberfläche sieht nicht so aus wie bei Dir(Photo)!

Da ich jetzt erst mit XE anfange, wie bekomme ich alles zusammen?
ein Ordner Sample, ein Ordner Lib, bzw dein Bin Ordner:shock:

Gruss alfold

EWeiss 4. Jun 2011 19:15

AW: Virtual Piano
 
Zitat:

Zitat von alfold (Beitrag 1104564)
Hast du wirklich die aktuelle Version oben?
Oberfläche sieht nicht so aus wie bei Dir(Photo)!

Da ich jetzt erst mit XE anfange, wie bekomme ich alles zusammen?
ein Ordner Sample, ein Ordner Lib, bzw dein Bin Ordner:shock:

Gruss alfold

Nein!
Alte Binäre Dateien EXE,DLL

Du brauchst aber den Bin Ordner incl. der darin enthaltenen Skins/Background/Config Ordner.

Rootpfad.. Name egal.
Darin Bin, Lib und Sample Ordner so wie sie sind hinein kopieren.
Danach sollte es laufen.
Erst nach neuer Kompilierung der EXE incl. DLL sollte die Oberfläsche mit dem letzen Hochgeladenen Bild Identisch sein.
Alte DLL kennt die Unit(Interface) uMediaTimer noch nicht da ich diese neu geschrieben habe.

Für die Gruppe EXE/DLL "ProjectGroup1" im Sample Odner starten oder VirtualPiano.dproj für die EXE allein.
Die Project Datei der DLL befindet sich im Lib Odner.
Hab mal nen Shot hochgeladen.

PS:
Komponente mußt du keine Installieren.
Mindestanforderung D2009.

gruss

blackfin 4. Jun 2011 19:38

AW: Virtual Piano
 
Ich muss sagen, das ist eine der hübschsten Delphi-Anwendungen, die ich je gesehen habe! :thumb::thumb:
So eine GUI hätte damals mal mein selbstgebautes MIDI-Pult gebraucht :-D

EWeiss 4. Jun 2011 19:43

AW: Virtual Piano
 
Zitat:

Zitat von blackfin (Beitrag 1104609)
Ich muss sagen, das ist eine der hübschsten Delphi-Anwendungen, die ich je gesehen habe! :thumb::thumb:
So eine GUI hätte damals mal mein selbstgebautes MIDI-Pult gebraucht :-D

Hoffe du kannst damit etwas Anfangen ;)

gruss

blackfin 4. Jun 2011 20:55

AW: Virtual Piano
 
Mal gucken, ich bin verzückt am testen, auch wenn ich MIDI nicht mehr so oft verwende...

Was mir gerade aufgefallen ist, wenn ich den Skin ein paar mal hintereinander wechsle (zuerst von Standard => Black => Crystal), hängt sich das Programm beim Restart auf (nur noch ein Task im TM sichtbar) und muss über den Taskmanager beendet werden, bevor man es wieder starten kann.

System: Win 7 x64, Programm liegt NICHT in C:\ProgramFiles\

EWeiss 5. Jun 2011 08:59

AW: Virtual Piano
 
Zitat:

Zitat von blackfin (Beitrag 1104617)
Mal gucken, ich bin verzückt am testen, auch wenn ich MIDI nicht mehr so oft verwende...

Was mir gerade aufgefallen ist, wenn ich den Skin ein paar mal hintereinander wechsle (zuerst von Standard => Black => Crystal), hängt sich das Programm beim Restart auf (nur noch ein Task im TM sichtbar) und muss über den Taskmanager beendet werden, bevor man es wieder starten kann.


Vielleicht ein Timing problem..
Das problem habe ich selbst auch kann es aber nicht nachvollziehen
da es nur sporadisch auftritt.

Zitat:

liegt NICHT in C:\ProgramFiles\
Ist auch nicht nötig.
System ist bei mir das selbe.


gruss

alfold 5. Jun 2011 11:07

AW: Virtual Piano
 
Ein riesen Respekt für diese Arbeit:thumb::thumb:

Ich hoffe das Du noch am Ball bleibst, denn ich würde gern meine Ideen mit einbauen.
Die Kritikpunkte kennst Du ja:wink:

Den eigentlichen Konzeptfehler deinerseits (MidiTracker), hab ich schon gefunden.
Nun muss ich nur noch sehen an welchen Stellen im Prog das alles korregiert werden muss.
(Wenn ich darf)
Es währe schade, wenn dieses Prog sonst nur für Dich bleibt.
Ich persöhnlich finde es ja toll(weil klein und übersichtlich), aber etwas umständlich beim komponieren.
Darum würde ich gern die Änderungen machen. Geht aber nur, wenn ich halt die ganzen Stellen finde:!: und Du am Ball bleibst.

Gruss alfold

EWeiss 5. Jun 2011 11:59

AW: Virtual Piano
 
Zitat:

Zitat von alfold (Beitrag 1104659)
Ein riesen Respekt für diese Arbeit:thumb::thumb:

Ich hoffe das Du noch am Ball bleibst, denn ich würde gern meine Ideen mit einbauen.
Die Kritikpunkte kennst Du ja:wink:

Den eigentlichen Konzeptfehler deinerseits (MidiTracker), hab ich schon gefunden.
Nun muss ich nur noch sehen an welchen Stellen im Prog das alles korregiert werden muss.
(Wenn ich darf)
Es währe schade, wenn dieses Prog sonst nur für Dich bleibt.
Ich persöhnlich finde es ja toll(weil klein und übersichtlich), aber etwas umständlich beim komponieren.
Darum würde ich gern die Änderungen machen. Geht aber nur, wenn ich halt die ganzen Stellen finde:!: und Du am Ball bleibst.

Gruss alfold

Es würde mich freuen wenn du dich an dem Projekt beteiligst.
Eigentlich war es dazu gedacht um die Funktionalität der Library zu dokumentieren.
Das es nun solche ausmaße angenommen hat .. hat mich dann doch selbst überrascht ;)

Ich werde mal warten was du so umsetzt. also änderst.
Gleichzeitig am aktuellen Source änderungen vorzunehmen würde nichts bringen.
Natürlich werde ich am Ball bleiben und helfen wenn du probleme beim auffinden von Funktionen hast.

Hier meine letzten änderungen der LIB
und ein einfaches Window Sample das als Basis für spätere oder andere Anwendungen verwendet werden kann.

Lib Ordner ersetzen und den WinSample Ordner in den Rootpfad kopieren.

gruss Emil

alfold 7. Jun 2011 09:38

AW: Virtual Piano
 
So, nicht das Du denkst ich mach nichts mehr:wink:

Ich bin voll dabei, hier schon mal 1 von vielen, was ich anders mache:
Original
Delphi-Quellcode:
if FVisible then
begin
    // Aktualisiere die labels
    for IntA := StartX to StartX + XSize do
    begin
        if (IntA mod Value) = 0 then
        begin
            GetClientRect(TopBarFrame.Handle, rc);
            DC := GetDC(TopBarFrame.Handle);
            GDIP_CreateFromHDC(DC, Graphics);

            SKAERO_SplitColorARGB($000000, Alpha, Red, Green, Blue);
            GDIP_FillRect(Graphics, (IntA - StartX) * 16, rc.Top, rc.Right, rc.Bottom,
                 SKAERO_ColorARGB(254, RGB(Red, Green, Blue)));

            SKAERO_DrawTextToDC(DC, IntToStr((IntA div Value) + 1), (IntA - StartX) *
                  12 + TopBarOffset,
                       rc.Top - 2, SKAERO_BTNTEXTCOLOR, SKAERO_TEXTFONT, 10, 0, 0);

            GDIP_DeleteGraphics(Graphics);
            ReleaseDC(SideBarFrame.Handle, DC);
        end;
    end;
end;
Und hier mal das geänderte:
Delphi-Quellcode:
if FVisible then
begin
    // Aktualisiere die labels
    GetClientRect(TopBarFrame.Handle, rc);
    DC := GetDC(TopBarFrame.Handle);
    GDIP_CreateFromHDC(DC, Graphics);

    SKAERO_SplitColorARGB($000000, Alpha, Red, Green, Blue);

    GDIP_FillRect(Graphics, rc.Left, rc.Top, rc.Right, rc.Bottom,
          SKAERO_ColorARGB(254, RGB(Red, Green, Blue)));

    for IntA := StartX to StartX + XSize do
    begin
        if (IntA mod GridZahlenPos) = 0 then
        begin

            SKAERO_DrawTextToDC(DC, IntToStr((IntA div GridZahlenPos) + 1), (IntA - StartX) *
                24 + TopBarOffset,
                   rc.Top - 2, SKAERO_BTNTEXTCOLOR, SKAERO_TEXTFONT, 10, 0, 0);

        end;
    end;
    GDIP_DeleteGraphics(Graphics);
    ReleaseDC(SideBarFrame.Handle, DC);
end;
Durch diese Veränderung wird dein Prog natürlich schneller beim neuzeichnen!

Am schwersten ist natürlich Deine magische 12 und 1000:wink:
Aber die hab ich zum Teil schon auseinandergenommen 8-)
Für die neue Umsetztung ist diese magische 12 nicht mehr so wichtig, da bei der neuen Variante nun auch 32tel bei 1/4 zu sehen sind

Bis auf weiteres
Gruss alfold

EWeiss 7. Jun 2011 10:44

AW: Virtual Piano
 
Zitat:

Durch diese Veränderung wird dein Prog natürlich schneller beim neuzeichnen!
Jup war nicht die beste lösung das DC innerhalb der Schleife jedesmal neu zu erstellen.
Aber vergess bitte nicht bzw. schau mal wie lange ich an dem Projekt arbeite (alleine)
da passieren schon mal solche flüchtigkeitsfehler.

Nebenbei sehe ich hier ein Speicherleck!
Delphi-Quellcode:
DC := GetDC(TopBarFrame.Handle);

Delphi-Quellcode:
ReleaseDC(SideBarFrame.Handle, DC);


DC darf nur freigegeben werden wenn es auch vorher eingeholt wurde..
SideBarFrame.Handle ist also falsch das muß TopBarFrame.Handle sein.
Es wird also ein DC freigegeben das gar nicht existiert!.

Zitat:

Am schwersten ist natürlich Deine magische 12 und 1000
Aber die hab ich zum Teil schon auseinandergenommen
Für die neue Umsetztung ist diese magische 12 nicht mehr so wichtig, da bei der neuen Variante nun auch 32tel bei 1/4 zu sehen sind
Lass mich überraschen ;)


PS:
Hab noch nen neuen Skin erstellt .. Radio

EDIT:
Warum du hier!
Delphi-Quellcode:
12 + TopBarOffset,


die 12 mit 24 ersetzt hast ist mir unverständlich :?:
Du änderst damit den offset der Grid Zahlen Position
Was bedeutet das die Zahlen beim scrollen nicht immer direkt hinter der Dicken vertikalen Linie stehen.
Teste es selbst in dem du auf 1/8 schaltest und Song.mtf abspielst.
Magische 12! breite der NotenSpalte

gruss

Namenloser 7. Jun 2011 12:31

AW: Virtual Piano
 
Nur mal so ’ne Anregung, da der Source ja jetzt anscheinend eh öffentlich ist: Wollt ihr nicht vielleicht ein richtiges Repository dafür aufsetzen, statt immer den Code hin- und herzukopieren? Google Code wäre z.B. eine Möglichkeit (man hat die Wahl zwischen SVN und Mercurial – ich würde letzteres empfehlen wegen des einfacheren Mergings) oder auch SourceForge. Wäre denke ich deutlich eleganter und weniger Arbeit für euch beide...

EWeiss 7. Jun 2011 12:43

AW: Virtual Piano
 
Zitat:

Zitat von NamenLozer (Beitrag 1105036)
Nur mal so ’ne Anregung, da der Source ja jetzt anscheinend eh öffentlich ist: Wollt ihr nicht vielleicht ein richtiges Repository dafür aufsetzen, statt immer den Code hin- und herzukopieren? Google Code wäre z.B. eine Möglichkeit (man hat die Wahl zwischen SVN und Mercurial – ich würde letzteres empfehlen wegen des einfacheren Mergings) oder auch SourceForge. Wäre denke ich deutlich eleganter und weniger Arbeit für euch beide...

Wäre eine überlegung wert. ;)

gruss

blackfin 7. Jun 2011 12:46

AW: Virtual Piano
 
vor allem könnt ihr dann gleichzeitig dran rumwerkeln und müsst nicht immer auf den anderen warten :-)

EWeiss 7. Jun 2011 12:48

AW: Virtual Piano
 
Zitat:

Zitat von blackfin (Beitrag 1105039)
vor allem könnt ihr dann gleichzeitig dran rumwerkeln und müsst nicht immer auf den anderen warten :-)

Ist aber auch streßig wenn man nicht über genügend englisch kenntnisse verfügt ;)
Und Sourceforce spamt mir jetzt schon mein Postfach voll.
Nach der erstellung von BassVis_Wrapper..

EDIT:
Oder darf ich hier nicht mehr posten? :cry:

gruss

alfold 7. Jun 2011 13:53

AW: Virtual Piano
 
Naja, so schlimm wird es ja nicht!
Ich brauch ja ne ganze weile. Erst wenn ich soweit fertig bin schick ich ihm die überarbeitete zu. EWeiss wird selbst nichts ändern, in meinem Sinne. Würde ich auch nicht verlangen, da es ja so schon funktioniert:wink:

Es ging Ihm ja auch nicht darum was ich möchte, sondern um zu zeigen das man auch ohne VCL tolle Oberflächen gestallten kann. :thumb:

Es wird also kein Codegespame in dieser hinsicht geben:wink:

Der Rest erfolgt eh per Mail:P

@NamenLozer: Idee ist gut, nur wie man sowas macht:gruebel:
@blackfin: Warten muss er eh, bin ja nicht der schnellste:zwinker:
Gruss alfold

EWeiss 7. Jun 2011 13:55

AW: Virtual Piano
 
Zitat:

Warten muss er eh, bin ja nicht der schnellste
Kein problem für mich.

gruss

EWeiss 18. Jun 2011 18:07

AW: Virtual Piano
 
@NamenLozer

Wenn du zeit hast kannst nochmal testen ob die Listbox jetzt bei dir funktioniert?
Hab da einiges umgestellt vor allem was das ansprechen der ClientProc aus der DLL angeht.
Zusätzlich noch einen visuellen Rect erstellt für Selektierte Auswahl.

gruss

Namenloser 18. Jun 2011 19:50

AW: Virtual Piano
 
Liste der Anhänge anzeigen (Anzahl: 1)
Leider nein :(
Beim Start kommt jetzt die Meldung im Anhang (vorher passierte gar nichts, und das Programm hing nur).

EWeiss 18. Jun 2011 22:20

AW: Virtual Piano
 
Zitat:

Zitat von NamenLozer (Beitrag 1107228)
Leider nein :(
Beim Start kommt jetzt die Meldung im Anhang (vorher passierte gar nichts, und das Programm hing nur).

Hmm das hilft mir nicht wirklich weiter.
Kann mit dem Skin bzw.. dem einlesen der Instrumentenlisten zu tun haben wenn die nicht
korrekt sind. (Alte Version)

Danke für's testen.

Das linken auf die WinProc der Hauptanwendung sollte eigentlich so OK sein!

Delphi-Quellcode:
  FClientInstance,
  FPrevClientProc: TFNWndProc;
nachdem ich das Handle habe initialisiere ich die Subclass

Delphi-Quellcode:
SubClass(FHandle);


Delphi-Quellcode:
procedure TSkinListBox.SubClass(WinHandle: HWND);
begin
  FClientInstance := MakeObjectInstance(ClientWndProc);

  FPrevClientProc := Pointer(GetWindowLong(WinHandle, GWL_WNDPROC));
  SetWindowLong(WinHandle, GWL_WNDPROC, Integer(FClientInstance));
end;
Delphi-Quellcode:
procedure TSkinListBox.ClientWndProc(var Message: TMessage);

begin
  with Message do
  begin
    case Msg of
      WM_ERASEBKGND:
        Result := ListBoxProc(FHandle, integer(Msg), Message.WParam, Message.LParam);
      WM_MOUSEWHEEL:
        Result := ListBoxProc(FHandle, integer(Msg), Message.WParam, Message.LParam);
      WM_PAINT:
        Result := ListBoxProc(FHandle, integer(Msg), Message.WParam, Message.LParam);
      WM_LBUTTONUP:
        Result := ListBoxProc(FHandle, integer(Msg), Message.WParam, Message.LParam);
      WM_KILLFOCUS:
        Result := ListBoxProc(FHandle, integer(Msg), Message.WParam, Message.LParam);
    end;

    if (Result = 0) then
      Result := CallWindowProc(FPrevClientProc, FHandle, Msg, wParam, lParam);
  end;
end;


und dann.. bla bla

Delphi-Quellcode:
function TSkinListBox.ListBoxProc(WinHandle: HWND; Msg: UINT; wP: WParam; lP: LParam): LRESULT; stdcall;
begin
  ...
  Result := CallWindowProc(Pointer(FPrevClientProc), WinHandle, Msg, wP, lP);
end;
Kann mir jetzt nicht vorstellen das es daran liegen könnte (vermutung)
das die ListBoxProc privat deklariert ist.


gruss

Namenloser 18. Jun 2011 22:37

AW: Virtual Piano
 
Moment mal – deine WndProc ist eine Methode eines Objekts? Woher soll denn dann der implizite Parameter
Delphi-Quellcode:
self
kommen, wenn die WndProc von Windows aufgerufen wird? Das könnte durchaus der Grund für den Crash sein.

Änder doch mal die Deklaration in
Delphi-Quellcode:
class procedure TSkinListBox.ClientWndProc(var Message: TMessage); static;
. Das ist dann quasi wie eine „normale“ Procedure, nur in einer Klasse deklariert.



edit: Okay, sorry, kannte
Delphi-Quellcode:
MakeObjectInstance
nicht. Gerade nachgelesen, was das ist – damit sollte es wohl doch in Ordnung sein.

edit 2: Allerdings könnte es sein, dass diese Methode mit der Datenausführungsverhinderung DEP (die ich aktiviert habe) in Konflikt gerät. Denn anscheinend wird dabei Code on-the-fly generiert/alloziiert, allerdings konnte ich nirgends sehen, dass für den Speicherbereich das
Delphi-Quellcode:
PAGE_EXECUTE
-Flag gesetzt würde. Vielleicht könntest du es ja doch mal so probieren, wie ich oben vorgeschlagen habe?


Alle Zeitangaben in WEZ +1. Es ist jetzt 01:54 Uhr.
Seite 7 von 9   « Erste     567 89      

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz