2010-05-25 4 views
0

Windows 용 WPF에서 text with icon links 케이스에 맞는 WPF 링크 컨트롤을 만들고 있습니다. 내가 원하는 것은 이미지의 오른쪽에 나타나는 하이퍼 링크 내에 텍스트를 넣는 것입니다.WPF에서 MouseOver를 시뮬레이트하는 방법

내 경우에는 이미지와 텍스트가 포함 된 하이퍼 링크가 포함 된 TextBlock을 사용하기 시작했습니다.

<TextBlock> 
    <Hyperlink> 
     <Rectangle Height="16" 
        Width="16" 
        Fill="{StaticResource MyIconBrush}" 
        Stretch="UniformToFill" 
        VerticalAlignment="Center" 
        HorizontalAlignment="Left" /> 
     <Run>My link text</Run> 
    </Hyperlink> 
</TextBlock> 

이 가진 문제

그러나 이미지 내 텍스트가 텍스트 아래에 정렬 된 효과보다 키가 생성되는 것으로 하였다. 불행히도 나는 TextBlock 내 또는 하이퍼 링크 내에서 수직 정렬을 제어 할 수있는 방법을 찾지 못했기 때문에 하이퍼 링크와 내 벡터 아이콘을 나타내는 사각형이 구분되도록 대체 레이아웃을 시도했습니다. 아래에 표시된 것과 같습니다. 이와

<StackPanel Orientation="Horizontal"> 
    <Rectangle Height="16" 
       Width="16" 
       Fill="{StaticResource MyIconBrush}" 
       Stretch="UniformToFill" 
       VerticalAlignment="Center" 
       HorizontalAlignment="Left" /> 
    <TextBlock VerticalAlignment="Center"><Hyperlink>My link text<Hyperlink></TextBlock> 
</StackPanel> 

문제는 그러나 나는 마우스가 내 아이콘과 바이스도 마찬가지 위에있을 때 지금 내 아이콘과 내 하이퍼 링크가 분리되어 있음을 내 링크의 내 마우스 오버 외모를 할 수 없다. 또한 내 하이퍼 링크에는 Command를 연결하는 옵션이 있지만 Rectangle 및 StackPanel은 사용하지 않으면 Hyperlink.Command 아이콘이 명령을 실행하지 않습니다.

그래서이 컨트롤을 마우스 오른쪽 단추로 클릭하면 상자에 MouseOver 효과가 나타나는 확인란을 사용하여 해당 컨트롤에 대해 MouseOver를 시뮬레이션 할 수 있습니다. 나는 HTML 세계에서 label element has a for 속성을 사용하여 기본적으로 내가 무엇을 찾고 있는지 레이블링하는 컨트롤을 지정하는 데 사용할 수 있습니다. 또한 나는 다른 시나리오에서 마우스를 가져 가면 해당 텍스트 상자가 보이고, 마우스를 클릭했을 때와 해당 클릭 상자에 포커스가있을 때처럼 해당 텍스트 상자가 표시되는 레이블을 사용하는 것이 좋습니다. 현재로서는 WPF에서 레이블이나 레이블 같은 요소를 가져 와서 해당 컨트롤에 대한 프록시 역할을 MouseOver 상태로하는 방법에 주로 관심이 있습니다. 또한 가능한 경우 XAML에서이 작업을 수행하려고합니다.

업데이트 : 다음을 시도했지만 성공하지 못했습니다. 내가 원하는 모양을 얻을 수 있지만 아이콘 아래의 링크가 마우스 이벤트를 얻기에 충분하지 않은 것으로 보입니다. 히트 테스트는 마우스가 실제로 컨트롤의 패딩에 관계없이 렌더링 된 텍스트 위에있을 때만 작동합니다.

<Grid> 
    <Rectangle Height="16" 
       Width="16" 
       Fill="{StaticResource MyIconBrush}" 
       Stretch="UniformToFill" 
       HorizontalAlignment="Left" 
       VerticalAlignment="Center" 
       IsHitTestVisible="False" 
       Focusable="False"/> 
    <TextBlock Padding="18,0,0,0" 
       VerticalAlignment="Center"><Hyperlink>Configure additional filters...</Hyperlink></TextBlock> 
</Grid> 

답변

1

첫 번째 코드는 이동하는 길입니다. Run 맞춤을 BaselineAlignment으로 제어 할 수 있습니다. Center으로 설정하면 원하는대로 링크가 작동합니다.

+0

이 내 원래 문제가 정렬에 관한하지만 눈치 해결하지 그것이 내 아이콘은 또한 밑줄 가져옵니다이 방법을 구현하고, 더 악화 후 밑줄 텍스트와 이미지 사이에 깨졌습니다. 근본적인 질문이 아직 남아있는 다른 전략, WPF에서 MouseOver를 시뮬레이트하는 방법을 찾아야한다고 생각합니다. – jpierson

1

실행 및 BaselineAlignment = "Center"를 사용하면 연결이 끊어집니다. 이와 같이 수평 스택 패널에 이미지와 텍스트 블록을 채 웁니다.

컨트롤을 보이게하려면 mouseover 이벤트를 다른 방식으로 사용하려면 기본적으로 controltemplate을 재정의해야합니다. 이것은 기존의 controltemplate을 취하여 필요에 맞게 수정하면 가장 쉽게 수행 할 수 있습니다. 예를 들어, 확인란의 컨트롤 템플릿은 다음에서 찾을 수 있습니다. http://msdn.microsoft.com/en-us/library/ms752319(v=VS.85).aspx 링크를 누르면 마우스 오버시 배경을 다른 색상으로 변경하는 방법이 있지만 하이퍼 링크를 시뮬레이트하기 위해 일부 내용 아래의 선을 색상으로 변경할 수도 있습니다.

+0

아, 깨진 링크는 깨진 밑줄을 의미해야합니다. 필자는 Julien Lebosquain의 제안을 시도한 후에도 이것을 보았습니다. – jpierson

+0

나는이 템플릿을 재정의 할 수 있다는 것을 알고 있지만 그 유형의 솔루션은 항상 내가 겪고있는 것에 대해 헤비급으로 보입니다. 컨트롤 위로 마우스를 이동하거나 적어도 컨트롤의 템플릿을 다시 정의 할 필요없이 MouseOver에서 일반적으로 발생하는 것과 동일한 반응 메커니즘을 트리거하지 않고 컨트롤의 MouseOver 상태를 제어하기 만하면됩니다. MouseOver가 읽기 전용이 아닌 경우 솔루션은 매우 간단하지만 왜 이것이 아닌지 이해할 수 있습니다. – jpierson

1

UI 요소에는 마우스 이벤트를 시뮬레이트하는 데 사용할 수있는 RaiseEvent 메서드가 있습니다.

XAML :

<Window x:Class="MouseOverTest.Window1" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    Height="300" Width="300"> 
    <StackPanel> 
     <TextBlock> 
      <Hyperlink MouseEnter="OnHyperlinkMouseEnter" Name="_hyperLink"> 
       <TextBlock Text="My link text" /> 
      </Hyperlink> 
     </TextBlock> 
     <Button Content="Simulate mouse enter" Click="OnButtonClick" /> 
    </StackPanel> 
</Window> 

코드 숨김

using System.Windows; 
using System.Windows.Input; 

namespace MouseOverTest 
{ 
    public partial class Window1 : Window 
    { 
     public Window1() 
     { 
      InitializeComponent(); 
     } 

     private void OnButtonClick(object sender, RoutedEventArgs e) 
     { 
      MouseEventArgs mouseEventArgs = new MouseEventArgs(Mouse.PrimaryDevice, 0); 
      mouseEventArgs.RoutedEvent = Mouse.MouseEnterEvent; 
      _hyperLink.RaiseEvent(mouseEventArgs); 
     } 

     private void OnHyperlinkMouseEnter(object sender, MouseEventArgs e) 
     { 
      MessageBox.Show("Mouse enter"); 
     } 
    } 
} 
+0

깔끔함! 순수한 XAML이 아니지만 이것은 지금까지 내가 실제로했던 것에 가장 가깝습니다. – jpierson

관련 문제