ListView mit bewegbaren Items (per Mausklick)



  • Guten Abend!

    Werde demnächst ein ListView-ähnliches Control brauchen, deren Items der User mit der Maus verschieben kann.

    Habt ihr ne Idee wie man sowas bewerkstelligen kann. Gibt's Tutorials?

    MfG,
    Aziz



  • *Push*

    Ist sehr wichtig. Wäre für Tipps sehr dankbar 😉



  • So wie auf dem Windows Desktop? Aber das ist doch ein ListView.



  • Hallo!

    Nein nicht mit den großen Icons. So wie in einem TreeView Control, aber ohne Hierarchie und Icons (naja wär nicht schlimm). Die Items bestehen nur aus Text und werden untereinander gestapelt..

    Z.B.:

    *----------*
    * |Text 1| *
    * |Text 2| *
    * |Text 3| *
    *----------*
    

    Ich möchte jetzt, dass der User die Items mit der Maus bewegen kann. Muss ich diese Funktionalität selber programmieren, oder gibt es etwas Fertiges, oder etwas anderes in der Richtung, w.z.B. ein Tutorial, das einen Ansatz zeigt?



  • Es gibt jede Menge Tutorials, die erklären wie man Items von einer ListBox in die andere per Drag&Drop verschieben kann.
    Ich möchte aber nur, dass die Items in der selben ListBox mit der Maus nach oben und nach unten verschiebbar sind.



  • Kommt schon Leute, hat noch nie jemand soetwas programmiert?



  • Glau nicht. Normale Styles und Funktionen gibts auf jeden Fall nicht. Musst Du manuell machen per Drag and Drop, die genau Position in der Liste des Mauszeigers "beim Loslassen" des Items holen und dort in die liste "einfügen"... etc.



  • Hallo allerseits!

    Ich poste wie immer die Lösung für ein Problem, das ich selber später lösen konnte:

    Entgegen der Behauptung von ChrisK gibt es eine Funtion, die für den Programmierer die Mühe abnimmt Drag&Drop-Funktionalität bei Listboxen zu implementieren.

    Man erzeugt eine simple ListBox und übergibt dessen Window-Handle folgender Funktion:

    BOOL MakeDragList(HWND hLB);
    

    Ich habe dazu ein Beispiel auf einer Seite gefunden, die nur in der japanischen Sprache verfügbar ist (deshalb auch diese merkwürdigen Fragezeichen im Code): http://www.kumei.ne.jp/c_lang/sdk3/sdk_215.htm

    //        draglst1.cpp
    
    #include <windows.h>
    #include <windowsx.h>
    #include <commctrl.h>
    
    LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
    ATOM InitApp(HINSTANCE);
    BOOL InitInstance(HINSTANCE, int);
    
    char szClassName[] = "draglst1";    //????????
    
    int WINAPI WinMain(HINSTANCE hCurInst, HINSTANCE hPrevInst,
                       LPSTR lpsCmdLine, int nCmdShow)
    {
        MSG msg;
    
        if (!InitApp(hCurInst))
            return FALSE;
        if (!InitInstance(hCurInst, nCmdShow)) 
            return FALSE;
        while (GetMessage(&msg, NULL, 0, 0)) {
            TranslateMessage(&msg);
            DispatchMessage(&msg);
        }
        return msg.wParam;
    }
    
    ATOM InitApp(HINSTANCE hInst)
    {
        WNDCLASSEX wc;
        wc.cbSize = sizeof(WNDCLASSEX);
        wc.style = CS_HREDRAW | CS_VREDRAW;
        wc.lpfnWndProc = WndProc;    //???????
        wc.cbClsExtra = 0;
        wc.cbWndExtra = 0;
        wc.hInstance = hInst;//??????
        wc.hIcon = LoadIcon(NULL, IDI_APPLICATION);
        wc.hCursor = LoadCursor(NULL, IDC_ARROW);
        wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
        wc.lpszMenuName = NULL;    //?????
        wc.lpszClassName = (LPCSTR)szClassName;
        wc.hIconSm = LoadIcon(NULL, IDI_APPLICATION);
        return (RegisterClassEx(&wc));
    }
    
    BOOL InitInstance(HINSTANCE hInst, int nCmdShow)
    {
        HWND hWnd;
    
        hWnd = CreateWindow(szClassName,
                "?????????????", //??????????????????
                WS_OVERLAPPEDWINDOW, //????????
                CW_USEDEFAULT,    //X??
                CW_USEDEFAULT,    //Y??
                230,//?
                140,//??
                NULL, //???????????????????NULL
                NULL, //??????????????????????NULL
                hInst, //??????????
                NULL);
        if (!hWnd)
            return FALSE;
        ShowWindow(hWnd, nCmdShow);
        UpdateWindow(hWnd);
        return TRUE;
    }
    
    //???????????
    
    LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
    {
        int id;
        static HWND hList;
        static HINSTANCE hInst;
        LPCREATESTRUCT lpc;
        INITCOMMONCONTROLSEX ic;
        static UINT drgMsg;
        static LPDRAGLISTINFO lpd;
        UINT nMsg;
        static int nDragItem = -1, nListID;
        char szData[64];
    
        if (msg == drgMsg) {
            lpd = (LPDRAGLISTINFO)lp;
            nMsg = lpd->uNotification;
            switch (nMsg) {
                case DL_BEGINDRAG:
                    nDragItem = LBItemFromPt(lpd->hWnd, lpd->ptCursor, TRUE);
                    return TRUE;
                case DL_DRAGGING:
                    nListID = LBItemFromPt(lpd->hWnd, lpd->ptCursor, TRUE);
                    DrawInsert(hWnd, lpd->hWnd, nListID);
                    if (nListID != -1) {
                        SetCursor(LoadCursor(hInst, "MYDRAG"));
                        return 0;
                    }
                    return DL_STOPCURSOR;
                case DL_CANCELDRAG:
                    nDragItem = -1;
                    break;
                case DL_DROPPED:
                    nListID = LBItemFromPt(lpd->hWnd, lpd->ptCursor, TRUE);
                    if (nListID != -1) {
                        ListBox_GetText(hList, nDragItem, szData);
                        ListBox_DeleteString(hList, nDragItem);
                        ListBox_InsertString(hList, nListID, szData);
                        ListBox_SetCurSel(hList, nListID);
                    }
                    DrawInsert(hWnd, lpd->hWnd, -1);
                    nDragItem = -1;
                    break;
            }
        }
        switch (msg) {
            case WM_CREATE:
                ic.dwSize = sizeof(INITCOMMONCONTROLSEX);
                ic.dwICC = ICC_WIN95_CLASSES;
                InitCommonControlsEx(&ic);
                lpc = (LPCREATESTRUCT)lp;
                hInst = lpc->hInstance;
                hList = CreateWindowEx(0, "LISTBOX", "",
                    WS_CHILD | WS_VISIBLE | WS_BORDER | WS_VSCROLL,
                    10, 10, 200, 100, hWnd, (HMENU)100, 
                    hInst, NULL);
                MakeDragList(hList);
                drgMsg = RegisterWindowMessage(DRAGLISTMSGSTRING);
                ListBox_AddString(hList, "1?????");
                ListBox_AddString(hList, "2?????");
                ListBox_AddString(hList, "3?????");
                ListBox_AddString(hList, "4?????");
                ListBox_AddString(hList, "5?????");
                ListBox_AddString(hList, "6?????");
                break;
            case WM_CLOSE:
                id = MessageBox(hWnd,
                    "??????????",
                    "????",
                    MB_YESNO | MB_ICONQUESTION);
                if (id == IDYES) {
                    DestroyWindow(hList);
                    DestroyWindow(hWnd);
                }
                break;
            case WM_DESTROY:
                PostQuitMessage(0);
                break;
            default:
                return (DefWindowProc(hWnd, msg, wp, lp));
        }
        return 0;
    }
    

    Näheres erfährt ihr in der MSDN; hier der Online-Link: http://msdn.microsoft.com/library/default.asp?url=/library/en-us/shellcc/platform/commctls/draglb/reflist.asp



  • Danke, das ist auch für mich interessant!
    Ich stoße auch total oft auf diese japanischen Seiten, aber die haben glaube ich so ziemlich alles dokumentiert, voll krass 🙂
    Die Japaner sind halt immer voraus...


Anmelden zum Antworten