DOBON.NET プログラミング道: .NET Framework, VB.NET, C#, Visual Basic, Visual Studio, インストーラ, ...

ウェブブラウザからDrag&DropされたリンクのURLと文字列を取得する

WebブラウザからドロップされたリンクのURLを取得する

まずはWebブラウザからドロップされたリンクのURLの取得方法から説明します。

基本的な考え方は、「Drag&Dropされたファイルのファイル名を取得」と変わりません。ただここでは、データをGetDataメソッドで取得する時にDataFormats.Textを指定し、また、DragEnterイベントハンドラでドロップされたデータを受け入れるかを判断する際、"UniformResourceLocator"形式であることを確認し、そうであればドロップ効果(e.Effect)をDragDropEffects.Linkとします。

次の例では、ウェブブラウザからTextBox1にドロップされたリンクのURLをTextBox1に表示しています。

VB.NET
コードを隠すコードを選択
'フォームのLoadイベントハンドラ
Private Sub Form1_Load(ByVal sender As Object, _
        ByVal e As EventArgs) Handles MyBase.Load
    'ドロップを受け入れる
    TextBox1.AllowDrop = True
    'DragEnterイベントハンドラを追加
    AddHandler TextBox1.DragEnter, AddressOf TextBox1_DragEnter
    'DragDropイベントハンドラを追加
    AddHandler TextBox1.DragDrop, AddressOf TextBox1_DragDrop
End Sub

Private Sub TextBox1_DragEnter( _
        ByVal sender As Object, ByVal e As DragEventArgs)
    'URLのみ受け入れる
    If e.Data.GetDataPresent("UniformResourceLocator") Then
        e.Effect = DragDropEffects.Link
    Else
        e.Effect = DragDropEffects.None
    End If
End Sub

Private Sub TextBox1_DragDrop( _
        ByVal sender As Object, ByVal e As DragEventArgs)
    'ドロップされたリンクのURLを取得する
    Dim url As String = e.Data.GetData(DataFormats.Text).ToString()
    '結果を表示
    TextBox1.Text = url
End Sub
C#
コードを隠すコードを選択
//フォームのLoadイベントハンドラ
private void Form1_Load(object sender, System.EventArgs e)
{
    //ドロップを受け入れる
    TextBox1.AllowDrop = true;
    //DragEnterイベントハンドラを追加
    TextBox1.DragEnter += new DragEventHandler(TextBox1_DragEnter);
    //DragDropイベントハンドラを追加
    TextBox1.DragDrop += new DragEventHandler(TextBox1_DragDrop);
}

private void TextBox1_DragEnter(object sender, DragEventArgs e)
{
    //URLのみ受け入れる
    if (e.Data.GetDataPresent("UniformResourceLocator"))
        e.Effect = DragDropEffects.Link;
    else
        e.Effect = DragDropEffects.None;
}

private void TextBox1_DragDrop(object sender, DragEventArgs e)
{
    //ドロップされたリンクのURLを取得する
    string url = e.Data.GetData(DataFormats.Text).ToString();
    //結果を表示
    TextBox1.Text = url;
}
補足:Internet ExplorerからリンクをDrag&Dropしようとすると、マウスポインタが赤い丸に斜線が引かれたアイコンになり、ドロップできない場合があります。これはInternet Explorerが保護モードで実行されているためです。保護モードを解除する方法は、「Internet Explorer の保護モードを解除したい」等をご覧ください。

Webブラウザからドロップされたリンクのテキストを取得する

ドロップされたリンクの文字列を取得するためには、ちょっと工夫が必要です。この方法については、次のページが参考になります。

これらのページで紹介されているコードでは日本語は文字化けします。日本語でもきちんと取得できるようにするには、Encodingクラスを使ってデコードする必要があります。

次の例では上記のコードに付け加えて、リンクの文字列も取得するようにしています。

VB.NET
コードを隠すコードを選択
'フォームのLoadイベントハンドラ
Private Sub Form1_Load(ByVal sender As Object, _
        ByVal e As EventArgs) Handles MyBase.Load
    'ドロップを受け入れる
    TextBox1.AllowDrop = True
    'DragEnterイベントハンドラを追加
    AddHandler TextBox1.DragEnter, AddressOf TextBox1_DragEnter
    'DragDropイベントハンドラを追加
    AddHandler TextBox1.DragDrop, AddressOf TextBox1_DragDrop
End Sub

Private Sub TextBox1_DragEnter( _
        ByVal sender As Object, ByVal e As DragEventArgs)
    'URLのみ受け入れる
    If e.Data.GetDataPresent("UniformResourceLocator") Then
        e.Effect = DragDropEffects.Link
    Else
        e.Effect = DragDropEffects.None
    End If
End Sub

Private Sub TextBox1_DragDrop( _
        ByVal sender As Object, ByVal e As DragEventArgs)
    'ドロップされたリンクのURLを取得する
    Dim url As String = e.Data.GetData(DataFormats.Text).ToString()

    'リンクの文字列
    Dim txt As String = Nothing
    If url.IndexOf("\"c) > -1 Then
        '(*3)によると、一部のブラウザは、URLと文字列が
        '一緒に取得されるらしい
        Dim ss As String() = url.Split("\"c)
        url = ss(0)
        txt = ss(1)
    Else
        'FILEGROUPDESCRIPTOR構造体のデータをMemoryStreamで取得
        Dim ms As MemoryStream = _
            CType(e.Data.GetData("FileGroupDescriptor"), MemoryStream)
        'cFileNameの長さを取得
        ms.Seek(76, SeekOrigin.Begin)
        Dim len As Integer = 0
        While ms.ReadByte() > 0
            len += 1
        End While
        'cFileNameの部分をbyte配列に取得
        Dim bs(len - 1) As Byte
        ms.Seek(76, SeekOrigin.Begin)
        ms.Read(bs, 0, len)
        ms.Close()
        'Shift JISでデコードする
        '(*1)によると、.NET Server 2003ではUnicodeとなるらしい
        txt = System.Text.Encoding.GetEncoding("Shift_JIS").GetString(bs)
        '最後が.urlか確認し、.urlをとる
        If txt.ToLower().EndsWith(".url") Then
            txt = txt.Substring(0, txt.Length - 4)
        End If
    End If

    '結果を表示
    TextBox1.Text = txt + " - " + url
End Sub
C#
コードを隠すコードを選択
//フォームのLoadイベントハンドラ
private void Form1_Load(object sender, System.EventArgs e)
{
    //ドロップを受け入れる
    TextBox1.AllowDrop = true;
    //DragEnterイベントハンドラを追加
    TextBox1.DragEnter += new DragEventHandler(TextBox1_DragEnter);
    //DragDropイベントハンドラを追加
    TextBox1.DragDrop += new DragEventHandler(TextBox1_DragDrop);
}

private void TextBox1_DragEnter(object sender, DragEventArgs e)
{
    //URLのみ受け入れる
    if (e.Data.GetDataPresent("UniformResourceLocator"))
        e.Effect = DragDropEffects.Link;
    else
        e.Effect = DragDropEffects.None;
}

private void TextBox1_DragDrop(object sender, DragEventArgs e)
{
    //ドロップされたリンクのURLを取得する
    string url = e.Data.GetData(DataFormats.Text).ToString();

    //リンクの文字列
    string txt = null;
    if (url.IndexOf('\\') > -1)
    {
        //(*3)によると、一部のブラウザは、URLと文字列が
        //一緒に取得されるらしい
        string[] ss = url.Split('\\');
        url = ss[0];
        txt = ss[1];
    }
    else
    {
        //FILEGROUPDESCRIPTOR構造体のデータをMemoryStreamで取得
        MemoryStream ms =
            (MemoryStream) e.Data.GetData("FileGroupDescriptor");
        //cFileNameの長さを取得
        ms.Seek(76, SeekOrigin.Begin);
        int len = 0;
        while (ms.ReadByte() > 0)
            len++;
        //cFileNameの部分をbyte配列に取得
        byte[] bs = new byte[len];
        ms.Seek(76, SeekOrigin.Begin);
        ms.Read(bs, 0, len);
        ms.Close();
        //Shift JISでデコードする
        //(*1)によると、.NET Server 2003ではUnicodeとなるらしい
        txt = System.Text.Encoding.GetEncoding("Shift_JIS").GetString(bs);
        //最後が.urlか確認し、.urlをとる
        if (txt.ToLower().EndsWith(".url"))
            txt = txt.Substring(0, txt.Length - 4);
    }

    //結果を表示
    TextBox1.Text = txt + " - " + url;
}
  • 履歴:
  • 2012/02/08 Internet Exploreが保護モードの時はドロップできない説明を追加(掲示板の投稿を参考にさせていただきました)。

注意:この記事では、基本的な事柄の説明が省略されているかもしれません。初心者の方は、特に以下の点にご注意ください。

  • このサイトで紹介されているコードの多くは、例外処理が省略されています。例外処理については、こちらをご覧ください。
  • イベントハンドラの意味が分からない、C#のコードをそのまま書いても動かないという方は、こちらをご覧ください。
  • .NET Tipsをご利用いただく際は、注意事項をお守りください。