Maus im Konsolen fenster IM VOLLBILDMODI ??? - Fortsetzung
-
Weil die zweite Seite des ursprünglichen Threads http://www.c-plusplus.net/forum/viewtopic-var-t-is-223597-and-start-is-0.html kaputt ist, soll hier die Fortsetzung statt finden.
Also, wie geht das nu mit der Verschieberei von Fenstern in der Konsole ?
-
kaputt ... wie schön ... da ich ja der ursprüngliche fragensteller bin muss ich jetz mal wieder länger auf irgendeine nützliche antwort warten ... und bitte nicht wieder i-welche programme ... code oder wnigstens eine erklärung für einen noob wären ausreichend ... danke
-
Hi!
Guck dir mal die Console Functions an. Für deinen Zweck insbesondere
WriteConsoleOutput und ReadConsoleOutput.Die folgende Demo arbeitet nach dem double-buffer Prinzip.
Die beiden Puffer sind ciConsoleRestore und ciWindow.
Die Puffer werden abwechselnd in der for-Schleife des main-Programms
in der Konsole gezeichnet und bewirken einen Animationseffekt.Ein 'richtiges' Verschieben des Fensters mit der Maus ist mit einigen
wenigen extra Zeilen machbar, wurde hier aber weggelassen.Guckst du hier:
/* Das unten stehende C-Programm demonstriert ein animiertes Fenster innerhalb des Standard-Konsolenfensters. In dieser Demo wird das Fenster in der main-Funktion in einer while-Schleife verschoben. Ein Linksklickt auf den 'CloseButton' schließt das Fenster. */ #include <stdio.h> #include <windows.h> // Die Console Functions werden gebraucht. // Fensterecken #define LO 201 #define RO 187 #define RU 188 #define LU 200 // Waagerechte und senkrechte Fensterbegrenzung #define SR 186 #define WR 205 // Close Button #define CLOSE 'x' // Konsolenhandles HANDLE hOut, hIn; // Koordinate, linke obere Ecke des animierten Fensters. int x, y; // Die Breite und die Höhe der Konsole in Buchstabenzellen. enum { ConsoleX = 80, ConsoleY = 25 }; // Konsolenpuffer CHAR_INFO ciConsole [ ConsoleX * ConsoleY ]; // Fensterbreite, Fensterhöhe des animierten Fensters. enum { width = 20, height = 10 }; // Fensterpuffer, für das animierte Fenster. CHAR_INFO ciWindow [ width * height ]; // Sichert und restauriert einen Ausschnitt aus dem Konsolenpuffer ciCosole :) CHAR_INFO ciConsoleRestore [ width * height ]; // Setzt den Konsolencursor an die Position x, y. int GotoXY ( int x, int y ) { COORD pos; pos.X = x; pos.Y = y; if ( ! SetConsoleCursorPosition( GetStdHandle( STD_OUTPUT_HANDLE ), pos )) return Err( "SetConsoleCursorPosition failed." ); return 0; } // Konsolencursor verstecken. int CursorHide () { CONSOLE_CURSOR_INFO cci = {0}; if ( FALSE == GetConsoleCursorInfo ( hOut, &cci )) return 1; cci.bVisible = FALSE; if ( FALSE == SetConsoleCursorInfo ( hOut, &cci )) return 1; return 0; } // Fehlermeldungen int Err ( char* e ) { CursorHide(); system( "CLS" ); while( !_kbhit() ) { Sleep ( 400 ); GotoXY ( 0, 0 ); SetConsoleTextAttribute( hOut, FOREGROUND_RED ); printf( "%s\n%s", e, "Zum Beenden Taste druecken." ); Sleep ( 400 ); GotoXY ( 0, 0 ); SetConsoleTextAttribute( hOut, FOREGROUND_BLUE|FOREGROUND_GREEN |FOREGROUND_RED|FOREGROUND_INTENSITY ); printf( "%s\n%s", e, "Zum Beenden Taste druecken." ); } return 1; } // Initialisiert das animierte Fenster und setzt Schrift- und Hintergrundfarbe. void InitWindow ( WORD BColor, WORD FColor ) { int x, y; // Fensterecken und 'Close Button' ciWindow[0].Char.AsciiChar = LO; // Ecke links oben; ciWindow[width-2].Char.AsciiChar = CLOSE; // 'Close Button' ciWindow[width-1].Char.AsciiChar = RO; // Ecke rechts oben; ciWindow[width*height-1].Char.AsciiChar = RU; // Ecke rechts unten ciWindow[width*(height-1)].Char.AsciiChar = LU; // Ecke links unten // Hintergrundfarbe, Schriftfarbe for ( y = 0; y < height; y++ ) for ( x = 0; x < width; x++ ) ciWindow[width*y+x].Attributes = BColor | FColor; // Waagerechte Fensterbegrenzung oben for ( x = 1; x < width -2; x++ ) ciWindow[x].Char.AsciiChar = WR; // Waagerechte Fensterbegrenzung unten for ( x = 1; x < width -1; x++ ) ciWindow[width*(height-1)+x].Char.AsciiChar = WR; // Senkrechte Fensterbegrenzungen rechts und links for ( y = 1; y < height-1; y++ ) { ciWindow[width*y].Char.AsciiChar = SR; ciWindow[width*y+width-1].Char.AsciiChar = SR; } } // Konsolencursor maximieren. int CursorMaximize() { CONSOLE_CURSOR_INFO cci = {0}; if ( FALSE == GetConsoleCursorInfo ( hOut, &cci )) return 1; cci.dwSize = 99; if ( FALSE == SetConsoleCursorInfo ( hOut, &cci )) return 1; return 0; } // Konsolencursor anzeigen int CursorShow () { CONSOLE_CURSOR_INFO cci = {0}; if ( FALSE == GetConsoleCursorInfo ( hOut, &cci )) return 1; cci.bVisible = TRUE; if ( FALSE == SetConsoleCursorInfo ( hOut, &cci )) return 1; return 0; } // Legt die Größe des Konsolenpuffers und die Größe des Konsolenfensters fest. int SetConsoleDimension( short x, short y ) { int xmin, ymin, xmax, ymax; SMALL_RECT sr = {0,0,x-1,y-1}; COORD screenBufSize = {x,y}; if ( FALSE == ( SetConsoleScreenBufferSize( hOut, screenBufSize )) ) return Err( "Failed on SetConsoleScreenBufferSize." ); if ( FALSE == SetConsoleWindowInfo( hOut, TRUE, &sr ) ) return Err( "Failed on SetConsoleWindowInfo." ); return 0; } // Zeigt die Member der CONSOLE_SCREEN_BUFFER_INFO an. int PrintConsoleScreenBufferInfo() { // Konsole Infos :) CONSOLE_SCREEN_BUFFER_INFO CSBI; COORD LargestConsoleWindowSize = {0}; COORD xy = { 0, ConsoleY-1 }; DWORD dummy; if ( FALSE == GetConsoleScreenBufferInfo( hOut, &CSBI )) return 1; puts ( "Here is your console screen buffer information:\n" ); printf ( "Size x: %d\n", CSBI.dwSize.X ); printf ( "Size y: %d\n" , CSBI.dwSize.Y ); printf ( "Cursor position x: %d\n", CSBI.dwCursorPosition.X ); printf ( "Cursor position y: %d\n", CSBI.dwCursorPosition.Y ); printf ( "Attributes: %d\n", CSBI.wAttributes ); printf ( "Window position x-left: %d\n", CSBI.srWindow.Left ); printf ( "Window position x-top: %d\n", CSBI.srWindow.Top ); printf ( "Window position x-right: %d\n", CSBI.srWindow.Right ); printf ( "Window position x-bottom: %d\n", CSBI.srWindow.Bottom ); printf ( "Window size max x: %d\n", CSBI.dwMaximumWindowSize.X ); printf ( "Window size max y: %d\n", CSBI.dwMaximumWindowSize.Y ); // Größt mögliche Fenstergröße ( in Buchstabenzellen ) LargestConsoleWindowSize = GetLargestConsoleWindowSize( hOut ); if ( LargestConsoleWindowSize.X && LargestConsoleWindowSize.Y ) { printf ( "Largest size x: %d\n", LargestConsoleWindowSize.X ); printf ( "Largest size y: %d\n", LargestConsoleWindowSize.Y ); } FillConsoleOutputCharacter( hOut, 1, ConsoleX, xy, &dummy ); return 0; } // Kopiert den Inhalt der Konsole in den Puffer ciConsole. int CopyConsoleContent() { COORD dwBufferSize = { ConsoleX, ConsoleY }; COORD dwBufferCoord = { 0, 0 }; SMALL_RECT ReadRegion = { 0, 0, ConsoleX-1, ConsoleY-1 }; if ( FALSE == ReadConsoleOutput( hOut, ciConsole, dwBufferSize, dwBufferCoord, &ReadRegion )) return Err ("ReadConsoleOutput failed."); return 0; } // Liest aus dem Puffer ciConsole ab Position x, y einen rechteckigen Block // der Höhe height und der Breite width und speichert diesen im Puffer // ciConsoleRestore int FillRestoreBuffer( int x, int y ) { COORD dwBufferSize = { width, height }; COORD dwBufferCoord = { 0, 0 }; SMALL_RECT ReadRegion = { x, y, x+width-1, y+height-1 }; if ( FALSE == ReadConsoleOutput( hOut, ciConsoleRestore, dwBufferSize, dwBufferCoord, &ReadRegion )) return Err ("ReadConsoleOutput failed."); return 0; } // Zeichnet den Inhalt von pci in die Konsole an der Position x, y. // pci ist abwechselnd das animierte Fenster ciWindow // und der gesicherte Ausschnitt des Konsolenpuffers ciConsoleRestore int DrawWindow ( int x, int y, CHAR_INFO* pci ) { COORD dwBufferSize; COORD dwBufferCoord = { 0, 0 }; SMALL_RECT WriteRegion; dwBufferSize.X = width; dwBufferSize.Y = height; WriteRegion.Left = x; WriteRegion.Top = y; if ( (width + x) > (ConsoleX -1) ) WriteRegion.Right = ConsoleX -1; else WriteRegion.Right = width + x; if ( (height + y) > (ConsoleY -1) ) WriteRegion.Bottom = ConsoleY -1; else WriteRegion.Bottom = height + y; if ( FALSE == WriteConsoleOutput ( hOut, pci, dwBufferSize, dwBufferCoord, &WriteRegion )) return Err ( "WriteConsoleOutput failed." ); return 0; } // Schließt animiertes Fenster. Der komplette Konsoleninhalt wird wieder // hergestellt. int CloseConsoleWindow() { COORD dwBufferSize = { ConsoleX, ConsoleY }; COORD dwBufferCoord = { 0, 0 }; SMALL_RECT WriteRegion = { ConsoleX-1, ConsoleY-1 }; if ( FALSE == WriteConsoleOutput ( hOut, ciConsole, dwBufferSize, dwBufferCoord, &WriteRegion )) return Err ( "WriteConsoleOutput failed." ); puts ( "\n\n\n\nWindow closed. Animation terminated." ); return 0; } // Forward declaration. Thread für die Mausabfrage. DWORD WINAPI ConsoleEventsThread( LPVOID pt ); // Thread und Fensterschleife int run = 1; // Demo animiertes Fenster :) int main( void ) { HANDLE hThread; // Für den ConsoleEvents-Thread. DWORD dwID; // Parameter für CreateThread, interessiert hier nicht. int speed = 500; // Legt die Geschwindigkeit des Fensters fest. SetConsoleTitle( "Big Brothers Animated Console Window Demo" ); // Konsolen Output Handle holen. if ( ( hOut = GetStdHandle( STD_OUTPUT_HANDLE ) ) == INVALID_HANDLE_VALUE ) return Err( "GetStdHandle failed." ); // Konsolen Input Handle holen, für den Thread, der die Maus abfragt. if ( ( hIn = GetStdHandle( STD_INPUT_HANDLE ) ) == INVALID_HANDLE_VALUE ) return Err( "GetStdHandle failed." ); // Den Thread, der die Maus abfragt, starten. if ( NULL == ( hThread = CreateThread ( NULL, 0, ConsoleEventsThread, NULL, 0, &dwID ))) return Err( "CreateThread failed." ); // Konsolencursor verstecken. if ( CursorHide () ) return Err( "HideCursor failed." ); // Breite und Höhe der Konsole festlegen. if ( SetConsoleDimension( ConsoleX, ConsoleY ) ) return Err( "SetConsoleDimension failed." ); // Konsoleninfos anzeigen. if ( PrintConsoleScreenBufferInfo () ) return Err( "PrintConsoleScreenBufferInfo failed." ); // Den Inhalt der Konsole in den Puffer ciConsole kopieren. if ( CopyConsoleContent () ) return Err( "CopyConsoleContent failed." ); // Das 'Animationsfenster' initialisieren. Das Aussehen des Fenster wird // im Puffer ciWindow festgelegt. InitWindow ( BACKGROUND_BLUE, // Blauer Hintergrund, weiße Schrift FOREGROUND_BLUE|FOREGROUND_GREEN|FOREGROUND_RED|FOREGROUND_INTENSITY ); // Fensterschleife. Hier wird das Fenster verschoben und gezeichnet. while ( run ) { // Den Ausschnitt des Konsoleninhalts, wo das Fenster gezeichnet wird // zur Wiederherstellung sichern. if ( FillRestoreBuffer ( x, y ) ) return Err( "FillRestoreBuffer failed." ); // Animiertes Fenster zeichnen. if ( DrawWindow ( x, y, ciWindow ) ) return Err( "DrawWindow failed." ); // Warten. Sleep ( speed ); // Konsoleninhalt wieder herstellen. Das animierte Fenster wird mit dem // Konsoleninhalt-Ausschnitt wieder hergestellt. if ( DrawWindow ( x, y, ciConsoleRestore ) ) return Err( "DrawWindow failed." ); x++; y++; if ( y == ConsoleY ) y = 0; if ( x == ConsoleX ) x = 0; } // for CloseConsoleWindow(); // Animiertes Fenster schließen. getchar(); return 0; } // Thread für die Abfrage der Mauskoordinaten. DWORD WINAPI ConsoleEventsThread( LPVOID pt ) { DWORD count = 0; INPUT_RECORD ir = {0}; // Speichert Konsolenereignisse. int mouseX, mouseY; // Mauskoordinaten. while( run ) { if ( 0 == ( ReadConsoleInput( hIn, &ir, 1, &count ) ) ) return Err( "ConsoleEventsThread: Failed on ReadConsoleInput.\n"); switch( ir.EventType ) { case MOUSE_EVENT: { switch( ir.Event.MouseEvent.dwButtonState ) { case FROM_LEFT_1ST_BUTTON_PRESSED: mouseX = ir.Event.MouseEvent.dwMousePosition.X; mouseY = ir.Event.MouseEvent.dwMousePosition.Y; if ( mouseX == x + width -2 && mouseY == y ) run = 0; // Beendet Thread und Fensterschleife break; } } } } return 0; }
Gruß,
B.B.
-
auf den ersten blick gut ... aber dr compiler gibt einen Pott Fehler aus ...
C:\Dokumente und Einstellungen\admin\Desktop\win.cpp In function `int GotoXY(int, int)': 55 C:\Dokumente und Einstellungen\admin\Desktop\win.cpp `Err' undeclared (first use this function) (Each undeclared identifier is reported only once for each function it appears in.) C:\Dokumente und Einstellungen\admin\Desktop\win.cpp In function `int Err(char*)': 73 C:\Dokumente und Einstellungen\admin\Desktop\win.cpp `int Err(char*)' used prior to declaration 77 C:\Dokumente und Einstellungen\admin\Desktop\win.cpp `_kbhit' undeclared (first use this function)
das waren alle ... ich benutze den Bloodshev Dev-C++ Compiler ... unter Windows ... is da was falsch ?
-
ok ... nach einigen überarbeitungen des anfangs sind alle fehler weg ... gut ... aber ich will dieses Blaue fenster mit der Maus ziehen können ... das soll sich nicht automatisch bewegen ... also wenn man mit der maus auf den rahmen klick das man es durchs fenster zieht ...
-
Ja, schon klar. Du kannst das ganze doch nach belieben ergänzen/ändern/umschreiben/etc.
Wo haperts?
-
ich hab keine ahnung wie
... sowas wie maus hab ich noch nie benutzt ... oder gesehen ... ich bin nur auf die idee gekommen weil ich im vollbildmodi immer einen mauszeiger hatte ... den will ich auchmal benutzen ... nur leider habe ich keine ahnung was ich abtippen muss ...
-
Mit SetConsoleCursorInfo kannst du die Größe des Cursors bestimmen.
Mit ReadConsoleInput fragst du Mauskoordinaten, Tastatur ab, etc.
Mit SetConsoleCursorPosition bestimmst du die Cursorposition, usw.Hast du die MSDN? Da sind diese und andere Funktionen beschrieben.
Gruß,
B.B.
-
MSDN ? ne ... ich hab Visual Studio seit 3 monaten nichtmehr ... aber ich versuch mal mein glück mit den funktionen ... danke
-
Gibt es ja auch online:
http://msdn.microsoft.com/en-us/library/ms682073(VS.85).aspx