블로그 이미지
내게 능력 주시는 자 안에서 내가 모든것을 할수 있느니라 - 빌립보서 4 : 13 - happydong

카테고리

Happydong (1363)
프로그래밍 (156)
MUSIC (16)
인물 (3)
Utility (10)
세미나 소식&내용 (22)
IT뉴스 (18)
운동 (830)
CAFE (10)
Life (282)
Total
Today
Yesterday



Get Microsoft Silverlight
 


ListBox Control
를 이용해서 간단한 위와 같이 만들어 보겠습니다. 전에 어떤 분이 훈스닷넷에 질문을 오려주신 내용인데요. 그때 만들었던 예제 소스입니다. 그럼 설명 필요 없이 소스부터 천천히 보면서 알아 보도록 하지요.

ListBox Control

<ListBox x:Name="DemoList" HorizontalAlignment="Left"  ScrollViewer.HorizontalScrollBarVisibility="Hidden" ScrollViewer.VerticalScrollBarVisibility="Hidden" VerticalAlignment="Stretch" Cursor="Hand" Style="{StaticResource DemoListBoxStyle}" ItemContainerStyle="{StaticResource DemoListBoxItemStyle}">

</ListBox>


 
일단 ListBox컨트롤을 하나 생성합니다. 저는 ScrollViewer의 속성을 다 Hidden으로 잡았습니다. 스크롤이 안보이도록 한거죠. 또 코드를 보시면 Style ItemContatinerStyle StaticResource로 스타일이 잡혀있는 것을 볼수가 있을 겁니다. 그럼 저 스타일쪽에 움직임의 답이 있지 않을까... 하는 생각이 바로 드실겁니다.^^ 그렇게 생각하셨던 분들이라면 역시 대단하신 분들이 아닐까 감히 생각해 봅니다.

그럼 일단 Style 소스를 보도록 하지요.

Style Source

<Style x:Key="DemoListBoxStyle" TargetType="ListBox">

<Setter Property="ItemsPanel">

<Setter.Value>

<ItemsPanelTemplate>

<!-- 리스트박스의 페널은 스텍페널 입니다. Orientation : Horizontal-->

<StackPanel Orientation="Horizontal"

VerticalAlignment="Stretch"

HorizontalAlignment="Center" />

</ItemsPanelTemplate>

</Setter.Value>

</Setter>

</Style>


Style 코드는 짧지요. 모.. 이정도쯤은 손으로 짜도 짤수 있지 않을까 생각해드네요. Style을 만들고 key 이름만 지어주고,TargetType 지정해주고, ItemsPanel 속성을 StackPanel로 지정하고...정말 눈으로 봐도 직관적 으로 알수 있지 안나요.  결론적으로 저는 ListBox ItemsPanel속성을 StackPanel Orientation Horizontal로 사용하고 있을 알수 있을 것입니다. 이렇게 한다면 리스트 아이템이 가로로 나타나겠지요.

그럼 이제 ItemContatinerStyle 소스를 보도록 하겠습니다.

ItemContatinerStyle Source

<Style x:Key="DemoListBoxItemStyle" TargetType="ListBoxItem">

<Setter Property="Padding" Value="1"/>

<Setter Property="HorizontalContentAlignment" Value="Left"/>

<Setter Property="VerticalContentAlignment" Value="Top"/>

<Setter Property="Background" Value="Transparent"/>

<Setter Property="BorderThickness" Value="1"/>

<Setter Property="TabNavigation" Value="Local"/>

<Setter Property="Template">

<Setter.Value>

<ControlTemplate TargetType="ListBoxItem">

<Grid x:Name="grid" Width="20" Background="{TemplateBinding Background}">

<vsm:VisualStateManager.VisualStateGroups>

<vsm:VisualStateGroup x:Name="CommonStates">

<vsm:VisualStateGroup.Transitions>

<vsm:VisualTransition GeneratedDuration="00:00:00.1000000"/>

<vsm:VisualTransition From="Normal" GeneratedDuration="00:00:00.1000000" To="MouseOver"/>

</vsm:VisualStateGroup.Transitions>

<vsm:VisualState x:Name="Normal"/>

<vsm:VisualState x:Name="MouseOver">

<Storyboard>

<DoubleAnimationUsingKeyFrames BeginTime="00:00:00" Duration="00:00:00.0010000" Storyboard.TargetName="grid" Storyboard.TargetProperty="(FrameworkElement.Width)">

<SplineDoubleKeyFrame KeyTime="00:00:00" Value="50"/>

</DoubleAnimationUsingKeyFrames>

</Storyboard>

</vsm:VisualState>

<vsm:VisualState x:Name="Disabled">

<Storyboard>

<DoubleAnimationUsingKeyFrames Storyboard.TargetName="contentPresenter" Storyboard.TargetProperty="Opacity">

<SplineDoubleKeyFrame KeyTime="0" Value=".55"/>

</DoubleAnimationUsingKeyFrames>

</Storyboard>

</vsm:VisualState>

</vsm:VisualStateGroup>

<vsm:VisualStateGroup x:Name="SelectionStates">

<vsm:VisualState x:Name="Unselected"/>

<vsm:VisualState x:Name="Selected">

<Storyboard/>

</vsm:VisualState>

</vsm:VisualStateGroup>

<vsm:VisualStateGroup x:Name="FocusStates">

<vsm:VisualState x:Name="Focused">

<Storyboard/>

</vsm:VisualState>

<vsm:VisualState x:Name="Unfocused"/>

</vsm:VisualStateGroup>

</vsm:VisualStateManager.VisualStateGroups>

<ContentPresenter HorizontalAlignment="Stretch" Margin="{TemplateBinding Padding}" x:Name="contentPresenter" VerticalAlignment="Stretch" Width="Auto" Content="{TemplateBinding Content}" ContentTemplate="{TemplateBinding ContentTemplate}"/>

</Grid>

</ControlTemplate>

</Setter.Value>

</Setter>

</Style>


~정말 소스가 기네요. 이정도면 손으로 작성하는것 보다는 블랜드를 이용하는 것이 좋겠네요. ItemContainerStyle은 아이템 항목 컨테이너에 적용될 스타일을 지정합니다. 일단 아래 그림을 통해 블랜드로 어떻게 만들었는지 확인 해보록 하지요.

그럼 아래 그림과 같이 Control들 중에서 ListBoxItem를 선택하도록 합니다.

 

사용자 삽입 이미지

ListBoxItem컨트롤을 더블 클릭하면 블랜드 화면에 생성된 것을 확인 하실수 있습니다. 그럼 마우스 오른쪽을 클릭해서 Edit Control Parts(Template) >> Edit a Copy.. 를 클릭합니다. (아래 그림 참고)

 

사용자 삽입 이미지

 

 

그럼 아래와 같은 화면이 나타날 텐데요.

 

사용자 삽입 이미지

 

Name(key)에 스타일을 이름을 설정해 주도록합니다. 그리고 Application쪽에 스타일을 둘 것인 것 아니면, 현재 페이제에 스타일을 둘 것인지를 선택합니다. 범용적으로 사용되어야 할 스타일이라면 Application쪽에 두는 것이 좋겠지요. 일단 아무데나 선택을 하고 OK를 클릭하세요.

 

사용자 삽입 이미지

 

위 그림과 같이 저는 필요없는 Rectangle을 잡아서 삭제 해버렸습니다. 그냥 ContentPresenter만 남겨두었지요. ContentPresenter는 지우면 안될 녀석입니다. 주의 하세요. 그리고 Grid를 선택하고 위의 MeuseOver상태일때와 Normal, Disabled 상태일때 각각의 크기를 지정해 주도록 합니다. 이렇게까지 하면 끝입니다.

 

이제 테스트 할 수 있는 아이템을 .cs단에서 만들어서 테스트 해보면 되겠네요.

테스트 아이템은 아래와 같습니다.

 

Test Code

List<Rectangle> items = new List<Rectangle>()

            {

                new Rectangle(){Fill = new SolidColorBrush(Colors.Red)},

                new Rectangle(){Fill = new SolidColorBrush(Colors.Yellow)},

                new Rectangle(){Fill = new SolidColorBrush(Colors.Orange)},

                new Rectangle(){Fill = new SolidColorBrush(Colors.Green)},

                new Rectangle(){Fill = new SolidColorBrush(Color.FromArgb(100,213,236,191))},

                new Rectangle(){Fill = new SolidColorBrush(Color.FromArgb(100,253,218,180))},

                new Rectangle(){Fill = new SolidColorBrush(Color.FromArgb(100,165,149,185))},

                new Rectangle(){Fill = new SolidColorBrush(Color.FromArgb(100,138,42,4))},

                new Rectangle(){Fill = new SolidColorBrush(Colors.Blue)},

                new Rectangle(){Fill = new SolidColorBrush(Colors.Black)}

            };

DemoList.ItemsSource = items;

 

여기까지 하셨다면 위와 같은 컨트롤이 만들어 졌을 겁니다.

지금까지 읽고 따라해주셔 감사합니다~!

Posted by happydong
, |



몇일전 회사에서 Silverlight를 이용해서 로그인 처리를 하고, 로그인에 대한 정보를 Silverlight에서 받을수 있도록 하는 간단한 샘플프로젝트를 해보라는 미션을 받게 되었습니다. 단, OpenID를 입력받아서 사용자 정보를 받아야 하는 것 이었습니다. 그래서 이래저래 Google링하는 도중 좋은 정보들을 찾을 수 있어서 공유하기 위한 목적으로 이렇게 포스팅 해봅니다.^^

OpenID란?

  OpenID란 간단하게 얘기하자면, 하나의 아이디로 여러 웹사이트에 로그인하기 위한 서비스라고 생각하시면 되겠습니다. 즉, 웹사이트에 따로 복잡한 회원가입 절차가 없이도, OpenID를 지원하다면 로그인을 할수 있도록 하는 것이지요.
 OpenID를 보시면 URL 주소로 되어 있는데요, 그것이 나만의 아이디로 쓰이게 되고요, 이미 가지고 계신 블로그나 홈피주소를 아이디로 쓸 수도 있어요.
 OpenID를 지원하는 웹사이트에 로긴하기 위해서는, 단지 사용자의 OpenID URL만 입력하면 되고요, 그럼 그 웹사이트에서는 인증을 위해 사용자의 OpenID를 제공하는 서버로 요청을 보냅니다. 그리고 인증이 끝나면 사용자 정보를 요청한 사이트에 인증된 사용자정보를 보내주므로서 로그인처리가 되는 것이지요.
OpenID더 궁금하신 내용이 있다면 아래 링크를 참고 하세요.

OpenID한국판사이트
OpenID적용된사이트목록


OepnID 적용해 보기

 먼저 OpenID가 없으신 분이라면, myID.net에서 만드시면 되겠습니다. (myID.net서비스에 대해 궁금하신 분들은 를 참고해서 보세요.)

 OpenID를 만드셨다면 이제 Visual Studio를 이용해 웹프로젝트를 하나 생성하도록 하겠습니다. 프로젝트를 만드셨다면 이제 .NET 기반의 OpenID공개 소스인 ExtremeSwank Library(ExtremeSwank OpenID)와 컨트롤 예제(ExtremeSwank OpenIDControl User Control)를 다운받도록 합니다.

로드

(ExtremeSwank Library .NET2.0기반으로 개발되어 있지만,3.0에서도 사용 가능하며, OpenID1.1 2.0을 모두 지원하고 있다는 장점도 가지고 있습니다.)

 

이렇게 두개의 파일을 다 받으셨다면 ExtremeSwank.OpenId.dll를 프로젝트에 추가 하시고, 컨트롤 파일을 추가해주시면 간단한 예제 프로젝트가 완성이 됩니다. 저 같은 경우 아래 그림과 같이 구성해 보았습니다.

 

사용자 삽입 이미지

 

간단하게 MasterPage, UserControls 폴더를 따로 만들어서 해당 파일들을 넣어주고 URL만 변경해 주었지요. 이제 한번 실행해 보도록 하지요.

그림1.

사용자 삽입 이미지

그림2.
사용자 삽입 이미지
(위 그림에서 drum83.myid.net는 제 OpenID입니다.^^;;;)

그림3.
사용자 삽입 이미지
(요청한 사이트가 등록이 되어 있지 않다면 비밀번호를 입력해야 합니다.)

그림4.
사용자 삽입 이미지
(비밀번호를 입력하게 되면, 자신의 정보를 보여지게되고, 승인할것인지, 이번만 승인할것인지를 사용자가 직접 결정을 하게됩니다.)

그림5.
사용자 삽입 이미지
(이렇게 사용자가 인증을 하게되면 위와같이 해당 정보를 요청한사이트에 콜백해주게 됩니다.)

 ExtremeSwank Library를 이용하면 간단하게 OpenID를 적용할수가 있으며, 지금 사용한 컨트롤만 웹사이트에 맞게 커스터마이징하시면 쉽게 OpenID를 적용한 웹사이트를 만들수 있을 거예요. 그리고 아래 주소를 가고시면  ExtremeSwank Library 문서도 MSDN같이 잘나와 있어서 적용하는데 큰 무리는 없을 듯 해요.
ExtremeSwank Library 문서

위에 만든 예제파일도 첨부했으니 받아보실분은 다운로드 받으세요~^^




Posted by happydong
, |



  Dependency Property (의존 속성)

실버라이트 2에서는 기존의 CLR(공용 언어 런타임)속성의 확장인 Dependency Property(의존 속성)를 이용해서 매번 자동적으로 속성의 값이 변경시킬수 있도록 지원해 줍니다.즉, 부모의 값이 변경이 되면 자식의 값이 같이 변경될수 있도록 할수 있는 것이라고 할수 있겠군요. 이런 방법을 이용해 Silverlight Application를 구현하면 바인딩모델로 만들어 쉽게 값을 설정하고 변경할 수 있으며, 개발자 입장에서는 유지보수가 편리할수 있습니다.
 Dependency Property는 기존의 CLR속성으로 노출되며, 내부적으로는 DependencyProperty구현 되어 있어 외부에서는 모를수 있습니다. 그러나 실버라이트 컨트롤들은 거의 대부분이 DependencyProperty로 구현되어 있어 리소스 및 스타일이라든지, 애니메이션, 기타값을 설정하는 부분에 바인딩으로 처리될 수 있습니다.

 Dependency Property의 주요 특징

 . 매번 자동적으로 속성의 값을 바꾼다. (다른 외부적인 값에 의존해서 값이 결정됨)
 . 기존의 CLR의 확장

 Dependency Property를 이용한 CustomComtrol

 간단하게 Dependency Property를 이용한 커스텀컨트롤을 만들어 보았습니다. UserNameCustomComtrol인데요, 사용자의 이름을 입력 받는 커스텀컨트롤이 될 것 입니다. 그럼 하나하나 코드를 보면서 알아보도록 하겠습니다.

Property 선언

public class UserNameCustomControl : Control

{

public String UserName

{

get { return (String)GetValue(UserNameProperty); }

set { SetValue(UserNameProperty, value); }

}

...나머지 코드는 아래에서

}


DependencyProperty의 값을 설정하거나 반환하기위해서는 DependencyObjectSetValue메소드와 GetValue메소드를 이용하여 값을 설정해 주거나 반환해 주어야 합니다. 그렇다면 DependencyObject는 어디에서 받아올지 궁금해 할수가 있겠군요.  실버라이트에서 거의 모든 컨트롤들이 UIElement를 상속받는데, UIElement를 DependencyObject를 상속 받아 구현된 클래스입니다. 즉, 제가 예제로 만든 UserNameCustomControl는 Control을 상속받아 구현됐는데요, Control클래스는 FrameworkElement 클래스를 상속을 받고, FrameworkElement 클래스는 UIElement 클래스를 상속을 받지요. (아래 그림 참고)

사용자 삽입 이미지


UserNameProperty는 DependencyProperty에서 선언된 필드명 입니다. 그럼 DenpendencyProperty 함수 선언은 어떻게 하는지 알아 보도록 하지요. 코드는 아래와 같습니다.

DenpendencyProperty 함수 선언

public static readonly DependencyProperty UserNameProperty =

DependencyProperty.Register(

"UserName",

typeof(String),

typeof(UserNameCustomControl),

new PropertyMetadata(new PropertyChangedCallback(UserNameCustomControl.OnUserNamePropertyChanged)));


 첫번째 라인에 보면 Static으로 선언하고, 정적일 것이기에 readonly로 지정하여 DependencyProperty를 생성한는 것을 보실수 있을겁니다.
 두번째 라인부터는 DependencyProperty 클래스의 Static메소드인 Register메소드를 호출하여 Silverlight속성 시스템에 등록 하는 코드입니다. Register함수는 4개의 파라미터를 선언해 주어야하는데요, 아래 표를 참고 하셔서 보시면 될 것 같습니다.

속성

설명

Name

등록할 속성의 이름

PropertyType

속성의 타입

ownerType

속성을 포함한 부모의 타입

typeMetadata

속성 메타데이터 지정

(보통 콜백(Callback) 함수를 지정함)


마지막에 typeMetadata는 지정하지 않을수도 있습니다. 즉, null로 지정이 가능합니다.그리고 필요에 따라 CallBack함수를 만들어서 사용할 수도 있습니다. 그럼 다음은 CallBeck함수를 어떻게 지정하는지 알아 보도록 하겠습니다.

CallBeck 함수

private static void OnUserNamePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)

{

UserNameCustomControl userNamecontrol = d as UserNameCustomControl;

string newUserName = (string)e.NewValue;

string oldUserName = (string)e.OldValue;

}


위 코드를 보시면 OnUserNamePropertyChanged함수에는 2개의 파라미터(Parameter)를 받을수 있음을 확인 하실수 있을 것 입니다. 그리고 다음 코드를 보면 DependencyObject를  UserNameCustomControl로 캐스팅하는 코드인데요, 이렇게 캐스팅한 컨트롤을 이용하여 값이 변경되었을때 필요한 일들을 정의하면 되겠습니다. 그리고 DependencyPropertyChangedEventArgs함수에서는 NewValue함수와 OldValue함수가 있어서 현재 변경된값과 변경되지 전의 값을 확인 할수도 있습니다. 이렇게 해서 UserNameCustomControl이 어느정도 완성이 되었습니다. 이제 원하는데로OnUserNamePropertyChanged에서 값을 변경해 주거나 설정해 주면 되겠습니다.

아래 코드는 위의 코드들을 하나로 나타낸 코드입니다.(참고)

전체 코드 보기

public class UserNameCustomControl : Control

{

public String UserName

{

get { return (String)GetValue(UserNameProperty); }

set { SetValue(UserNameProperty, value); }

}

 

// Using a DependencyProperty as the backing store for UserName.  This enables animation, styling, binding, etc...

public static readonly DependencyProperty UserNameProperty =

DependencyProperty.Register(

"UserName",

typeof(String),

typeof(UserNameCustomControl),

new PropertyMetadata(new PropertyChangedCallback(UserNameCustomControl.OnUserNamePropertyChanged)));

 

private static void OnUserNamePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)

{

UserNameCustomControl userNamecontrol = d as UserNameCustomControl;

string newUserName = (string)e.NewValue;

string oldUserName = (string)e.OldValue;

}

}



처음으로 실버라이트를 접하는 사람들에게는 정말 이해하기 힘든 부분일수 있습니다.(저 역시 그랬으니까요) 그러나 실버라이트를 제대로 공부 하려면 정말 꼭꼭 알아야하는 내용입니다. 이렇게 알고 DependencyProperty를 잘 이용하면 바인딩모델로 구현하는데 쉽고, 편하게 구현할 수 있을 것 입니다.
Posted by happydong
, |