スクロールバーについてです。

[戻る]
あきら 2006/01/10(火) 11:09:34
スクロールバーを使って別のウィンドウをスクロールさせたいのですけど
そのような事は可能ですか?

環境はXPでVC++6.0です。

KING・王 2006/01/10(火) 12:42:29
あまり詳しくないのですが、可能だと思います。

スクロールバーのあるウィンドウをAウィンドウ、別のウィンドウをBウィンドウとした場合、
Aウィンドウで、スクロールバーを移動させたときのメッセージの処理を、
デフォルトにしないで、オーバーライドして、Bウィンドウにメッセージを投げるようにすれ
ば、
おそらく可能だと思います。

#詳細は、識者の方々、フォローをお願いします。

あきら 2006/01/10(火) 18:27:25
ありがとうございます。参考にしながら作成していて、
 GetForegroundWindow()でBのハンドルを取り
 GetScrollInfo(Bのハンドル , SB_VERT , &scr);で情報を取り
 Aでボタンを押すとSetScrollInfo(Bのハンドル , SB_VERT , &scr  , TRUE);
とすればBウィンドウをスクロールできるのかと思ったのですが何も起こりませんでし
た。
これだけではできないのでしょうか?どこかに1行ずらすような事を書かないといけない
とおもうのですがわかりませんでした。

たいちう 2006/01/10(火) 19:17:55
もしかして、ダイアログBにあるリストボックスのスクロールバーとか?
この場合リストボックスのハンドルが必要になると思う。

そうでない場合、詳しい情報宜しく。

1.
> GetScrollInfo(Bのハンドル , SB_VERT , &scr);で情報を取り
これは、成功してますか?(戻り値とかで判断して)

2.AとBの関係は?Modal?Modeless?
    Bのスクロールバーを直接マウスで操作することは可能ですか?

3.KING・王さんが書いている通りの方法だとどうなります?
(::SendMessageを使う)

Q 2006/01/12(木) 11:06:20
こんなのは参考になりますでしょうか?
http://cyberwing.versus.jp/pg/archives/000144.shtml

はずしてたらごめんなさい。

あきら 2006/01/16(月) 18:08:28
SendMessage(Bのハンドル,WM_VSCROLL,SB_LINEDOWN, 0);

こうすることでしょうか?後々を考えてボタンで行おうと思い
ボタンを押したらSendMessage()としてみたのですが何も起きませんでした。

あきら 2006/01/17(火) 09:10:01
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
    int id, i, len, dy;
    HDC hdc;
    PAINTSTRUCT ps;
    static SCROLLINFO si;
    static int dispno, pos;
    RECT rc;

    switch (msg) {
        case WM_SIZE:
            GetClientRect(hWnd, &rc);
            dispno = rc.bottom / LINESIZE;
            si.cbSize = sizeof(SCROLLINFO);
            si.fMask = SIF_POS | SIF_RANGE | SIF_PAGE;
            si.nMin = 0;
            si.nMax = MAXLINE;
            si.nPage = dispno;
            si.nPos = pos;
            SetScrollInfo(hWnd, SB_VERT, &si, TRUE);
            break;
        case WM_VSCROLL:
            switch (LOWORD(wp)) {
                case SB_LINEUP:
                    dy = -1;
                    break;
                case SB_LINEDOWN:
                    dy = 1;
                    break;
                default:
                    dy = 0;
                    break;
            }
            dy = max(-1 * si.nPos, min(dy, si.nMax - si.nPos));
            if (dy != 0) {
                si.nPos += dy;
                pos = si.nPos;
                SetScrollInfo(hWnd, SB_VERT, &si, TRUE);
                ScrollWindow(hWnd, 0, -dy * LINESIZE, NULL, NULL);
                UpdateWindow(hWnd);
            }
            break;
-----------------------------------------------------------------------
ボタンが押されたら
  PostMessage(hWnd,WM_VSCROLL,SB_LINEDOWN,lP);
というようにすると自分のウィンドウの中がスクロールされました。
だから他のウィンドウの中身がスクロールできるようにクリックした時に
  hOwner=GetForegroundWindow();
として
  PostMessage(hOwner,WM_VSCROLL,SB_LINEDOWN,lP);
に変更したら操作出来るかと思ったのですができませんでした。
メッセージを送るハンドルが間違ってるのでしょうか?
長くなってしまいすみません。

たいちう 2006/01/17(火) 09:20:06
状況が良くわかりませんが、GetForegroundWindow()で取れるのは、
ボタンの親ではないですか?
『他のウィンドウ』を作るときハンドルをグローバル変数にでも
保持しておいたら、どうなります?

あきら 2006/01/17(火) 17:45:42
グローバル変数としてhOwnerにハンドルは保持しておいたのですが何もおきませんでし
た。
そのまえに途中からやろうとしてた内容が変わったのを説明してなかったので
よくわからない文章になってしまいすみません。

私がしたいことは
SB_LINEUPとSB_LINEDOWNのメッセージを送るボタンがあるウィンドウを作成することで
常に非アクティブな状態にしています。

そして今現在は、■発言 の部分に文字入力のカーソルがあり長文になるとスクロールバ
ーが表示されるのですが、これを使わずに自分が作成したウィンドウのボタンをしようし
てスクロールを行いたいのです。

ブラウザに限らずスクロールバーがあるところには全て使えるようにしたいのですが、
どこを直すべきなのでしょうか?

たいちう 2006/01/17(火) 19:10:59
やりたいことがどんどん膨らんでいくのはいいのですが、
やれることはそう簡単には増えません。
比較的簡単なことを確実にできるようになってから、
次に手を出すべきでしょう。

と、ここまで納得してもらったとして、

ステップ1:
    1つの実行ファイルで2つのダイアログを出し、
    ダイアログAのボタンを押すことで、
    ダイアログBのリストボックスのスクロールを行う。

ステップ2:
    ダイアログAとBを別々の実行ファイルとして、
    ダイアログAのボタンを押すことで、
    ダイアログBのリストボックスのスクロールを行う。

ステップ3:
    自作はダイアログAだけとして、Aのボタンを押すことで、
    インターネットエクスプローラの一番外側のスクロールを行う。

私がお手伝いできるのは、多分この辺まで。
これ以上のステップは、より力のある回答者に期待しましょう。

いずれにしろ、このような手順で順々にやっていくのが最良だと思いますが、
いかがですか?神の降臨を待つのも手ですが。

古いスレッドには追加発言できません。