티스토리 툴바


9월 16일 세미나 준비를 하는 중에, Local Connection이.. 좋긴 한데 확장성이 그닥 좋지 않은것을 알았습니다.


몇가지 실험 결과를 알려드립니다.

(1) 대소문자 구별.

 - 즉, Sender가 "ShortyLuv"였을 때, Receiver가 "shortyLuv"라면 전달루틴이 발생하지 않습니다.
   이건 예상 가능했기 때문에 그렇다 치죠.


(2) 2개 이상 등록 불가능

 - 가장 황당했던 에러입니다.


  그러니까, Sender가 1개, Receiver가 2개라고 했을 경우에 이 Receiver 2개는 각각 다른 식별키를 사용해야 한다는
  이야기죠. 즉 Sender에서도 LocalMessageSender를 2개를 등록해야 한다는 이야기가 나옵니다.

  ... 이럼... 이게 몹니까.. 그냥 Silverlight -> JavaScript -> Silverlight 와 다른 것이 없어보입니다.
  그것보다 1:1만 지원이 된다는 것이 좀 아쉽네요.
 

(3) HtmlPage 클래스의 함수 사용에 제약이 있는 듯 보입니다.

 

  글쎄요.. 혹시 LocalConnection 자체가 HtmlDom을 읽어들이지 못하는건가 생각해봤는데. 생성자에 Alert를 붙여보니
  그건 또 잘 동작하더군요. HtmlDom을 사용하는 루틴은 사용하지 못하는 듯 보입니다.

  다른 변수로 바꿔서 실행해봐도 그렇고, 따로 함수로 빼서 실행해봐도 결과는 같습니다.

  ... 왜이럴까요..


결론은 LocalConnection은 'XAP이 2개일때만 쓰자' 라는 것이 되겠네요.. 구글링을 해봐도
아직까지 Silverlight 3에 대한 이슈는 활성화되어있지 않은 모양입니다..

mms. 말 그대로 Windows Media Server를 이용하여 스트리밍으로 뿌려주는 프로토콜이지요.

이 mms를 실버라이트에서 쓰려고 할때, 잘 안되는 경우가 많습니다.


분명 웹페이지에 그냥 mms://어쩌고.. 쓰면 잘 나오던 것이 왜 실버라이트로 가면 안되는가..

구글링 끝에 해결이 되었습니다. (제 경우라 다양한 돌발상황에 대해서는 잘 모릅니다;;)


일단 보통 서버에는 IIS가 올라가있을 것입니다. 이게 포트 80번을 씁니다.

그런데 미디어서버를 설치하면. 이거 역시 포트 80번을 씁니다. (WMS HTTP Protocol)

실버라이트에서는 포트번호를 명시하지 않고 바로 MediaElement의 Source에 mms://어쩌고.. 를 바로 써주면

이 포트 80번의 충돌때문에 미디어가 동작하지 않는 것이지요..

즉.


이 WMS HTTP 서버 제어 프로토콜이 기본적으로 포트 80을 사용한다는 데에 문제가 있었습니다.

(그리고 아마 '사용 안함'으로 되어있을 것입니다. 그래서 포트를 설정해주고 '사용' 해주어야 합니다)


이 아이템을 클릭하면 바로 속성창이 나옵니다.


그래서 다른 포트 사용을 하셔서.. 사용하지 않는 포트 숫자를 적어줍니다. 서비스를 다시 실행시키고 나서

기존의 소스를 적용해봅니다.

     this.me_played.Source = new Uri("mms://xxxxxx:7870/xxxxxx.wmv", UriKind.Absolute);
     this.me_played.Play();        


그럼 적용이 잘 될 것입니다.

주의할 점은, 반드시 포트번호를 명시해주어야 한다는점. 그리고 이 경우의 7870이 방화벽에 막혀있음 안될 가능성도 있으니

방화벽 포트 예외 처리를 해주어야 한다는 점 등이 있습니다.


감사합니다.
  

  쇼티예요.
  Silverlight Toolkit에 Chart가 있습니다. 제가 이번에 조사한 자료는 LineSeries에 대한 것입니다.
  (원문자료는 이곳입니다.)

  LineSeries Chart는. 다 아시겠지만 대충 이런 모양새입니다.
 

  말그대로 '라인'을 사용하는 '꺾은선 그래프'? 이정도의 느낌이지요.

  거두절미하고 그럼 한번 해보도록 하겠습니다. 고객에게 '어떤 책에 대한 베스트셀러 순위 조회'를 위한 꺾은선 그래프를
  만들어주세요~ 라는 요청을 받았다고 해보죠.

  프로토타입을 만듭니다. 일단 예상되는 데이터를 생성합니다.

 

  1주일 단위로, 순위가 10, 5, 2, 1, 1..정도로 되었다고 해보죠.
  Silverlight Toolkit의 차트 사용법은, 일단 XAML 내에 네임스페이스를 정의하고(보통 네임스페이스는 charting으로 많이
  하시더군요). 그래서 <charting:Chart> 태그를 올리고, 그 자식으로 <charting:___series>를 올려놓습니다.

  이경우는 Line 차트니까 LineSeries라고 올려놓으면 되겠군요.  
 

  주요 속성은.. DependentValue와 IndependentValue는 각각 '값', '범위' 설정이구요. 그냥 DataPointStyle의 색을
  바꾼 것 밖에 없습니다. 그리고 선 좌표값에 대한 설정은, 코드만 보셔도 이해하실 수 있으실 듯 해요.
 
  다 됐습니다. 
 

  근데 이 그래프를 받아본 고객사에서 항의전화가 왔습니다. 

  "왜 그래프가 이 모양이예요?"
  "뭐가 문제죠?"
  "아니 베스트셀러면. 1위가 제일 높은건데, 왜 점점 이 책이 가치가 없어지는듯한 그래프 모양을 하고 있죠?"
 
  "...."

  10이면 높은거고, 1이면 낮은게 맞는건데. 베스트 셀러같은. 어떤.. 순위를 매기는 그래프는 1이 높고
  10이 낮은것이지요. 이 그래프가 틀린건 아닌데, 일반 고객사에서 느끼기엔, 그 고객사의 고객을 관리하는 입장에서
  이런 그래프는 '용서받지 못할 그래프'가 되는거죠. 뒤집어주는 프로퍼티가 있음 좋은데 그게 있는것도 아니구요.

  어쩔 수 없지요. 편법을 써야합니다. 컨버터를 사용해서 일단 정수를 전부 음수로 해주는 과정을 진행합니다.
 

  간단하게, 이게 (int)형이면 -(int)로 바꿔줍니다. 그리고 XAML의 LineSeries에 컨버터를 답니다.
  또, 아래 역상 표시된 곳에 보시면 Minimum과 Maximum을 바꿔주고 있지요. 
 

  그러면 다음과 같이 나옵니다.
 

  이정도면 괜찮은 것 같습니다. 그러면 왼쪽에 -(int)와, 마우스 오버했을 때의 -(int)만 없애주면 되겠군요.
 

  보시면, 정규식으로 {}(0:0.#;0.#) 를 쓰는 것을 볼 수 있습니다. 정규식에 대한건 구글링해보세요 ^^
  이것을, LineDataPoint 형태로 Template을 잡아주시고, 밑에 AxisLabel에도 붙여주세요.
 

  정리하자면
 
  1. 컨버터로 일단 이 값을 음수화 시켜서, 그래프를 뒤집은 다음에
  2. 나타낼 때 수치를 컨버젼 시키시면 되겠습니다.

  감사합니다.

  
  

 


  쇼티예요.


  OC 툴팁 개발하다가 생긴 에러인데.. 이게 실버라이트 버그라고 하네요..

  관련포스트

 
  이거참.. ToolTip 커스터마이징 하기 두렵네요 ㅋㅋ;
 
  참고하세요 ^^

  쇼티예요.

  통상적인 방법으로는 동시 개발이 불가능하더군요. Virtual PC나 VmWare 등을 사용해서 쓰는
  법이 일반적입니다.

  이것도 Beta 버젼이 끝나는 때까지만 하면 되는 것이기때문에, 동시 개발환경을 구성하고 싶다
  면, 미리 앞서서 Virtual PC를 띄우는 것이 더 좋은 방법일 수가 있다는 것을 말씀드립니다.

  그래도. 난 절대로 한 컴퓨터에 동시 환경을 구성하고 싶다! 라고 하시는 분들께서는 
  이 포스팅을 주목해보세요.

  외국의 어떤 분이 배치파일을 만들어두셨더군요. 역시, 깔고 지우고 깔고 지우고..
  그냥 이런 노가다를 배치파일로 편하게 만들어두었습니다. ... 그래도 이렇게 만들어놓으니까
  일단 편하더군요.

  첨부된 배치파일(zip으로 압축이 되어있습니다)을 받으시고 다음 순서를 따라해주세요.

  1. 첨부 배치파일을 다운로드합니다.
  2. 실버라이트 2 툴을 다운로드 받습니다. (첨부파일과 동일 폴더에 둡니다)
  3. 실버라이트 3 툴을 다운로드 받습니다. (첨부파일과 동일 폴더에 둡니다)
  4. 다운로드 받은 두개의 툴을 인스톨합니다. (인스톨되었다면 스킵)
  5. 첨부파일의 압축을 풀어 Setup_SLTools_Util.bat 을 실행시킵니다.

 

  4번은. 일단 실버라이트 2를 인스톨 하시고, 3를 인스톨합니다. 이 과정중에서 3를 설치할 때
  실버라이트 2를 지운다는 로그메세지를 보실 수 있는데, 원래 그런거니까 넘어가시고..
  중요한건, 실버라이트 2 Tools를 Unavailable 시키는 것이지 파일 자체를 지운다는건 아니라는
  거지요.. (윈도우 폴더에 Silverlight 폴더 찾아보시면 v2.0과 v3.0이 둘다 있게 될것입니다)

  아무튼 5번 과정까지 끝나면, VS_3-to-2.bat과 VS_2-to-3.bat라는 파일이 생길 것입니다.
  (두개 더 생기긴 하는데, 혹시 여러분들이 Web Developer Express를 쓰신다면 그 배치파일을
   실행시켜야 합니다)
  
  다 됐습니다. 2를 개발하다가 3로 가시려면 2-to-3를 실행시키시면 되고, 
  3를 개발하다가 2로 가시려면 3-to-2를 실행시키시면 됩니다.

  정보를 언인스톨하고 새버젼으로 덮어씌우는 개념이기 때문에, 시간은 컴퓨터 사양에 따라 
  2~3분 정도 걸릴거예요. 
  
  좀 더 자세한 포스팅 자료에 대한 링크는 다음과 같습니다.

  jeff.wilcox 블로그
  dullard's 블로그 (전 이걸 보고 했어요..)
  wahlin의 오버뷰 (이건 dullard의 포스팅을 소개해주는 블로그예요)

  그래도 거듭 말씀드리지만, 예외는 언제나 존재하니까요..
  Virtual PC 등을 띄우시는 것을 추천합니다.


쇼티예요. 안녕하세요~
이 방법은 그냥 일반적으로 띄우는 데에도 도움이 될 듯 보여요.. ^^

보통 실버라이트에서 팝업을 띄우려고 하면, Navigate 함수나 PopupWindow 둘중에
하나를 써야하지요. 차이도 별로 없는 듯이 보이네요.
(둘을 비교해둔 글은 있더군요. 인자 컨버팅의 차이가 있는듯..)

하지만 이 둘은 '치명적인(?)' 결점이 있습니다. 팝업 제목으로 '주소값'이 들어간다는 점이지요..
크리덴셜이라도 붙어있는 팝업이라면 해킹의 원인이 될 가능성도 있다는 이야기입니다.

또, 이미지의 크기에 맞게 브라우저가 열리질 않습니다.
물론 sizeChanged 이벤트 함수나, BitmapImage.DownloadProgress 등을 쓰는 방법도 있는데
결국 제목이 저렇게 표시되지 않는다면 이는 실버라이트에서 어떻게 할 수 없다는 이야기가
되지요. (일전에 이 문제때문에 실버라이트 카페에 질문을 해봤었는데, 실버라이트 단에서는 불가능하다는 이야기가 나오더군요..)

그럼 어떻게 해야되나요.. 네. 눈물을 머금고 '자바스크립트'를 쓰는 수밖에 없더군요.
실제로 자바스크립트와 실버라이트의 연동은 많이 쓰이곤 합니다. 실버라이트가, 보여주는 쪽은
좋을 지 모르지만, .NET의 기능보다는 너무나 많이 부족한 것이 사실입니다.
(애초에 클라이언트로 xap이 다운로드 되어지는 방식이기때문에 당연할 지도 모르고.. 
 .NET 개발자분들의 기본 사고방식인 runat='server'가 아니라는 점이지요..)

일단.. js 파일을 만듭니다. 그리고 함수 하나를 생성하셔서 다음과 같이 코딩하십니다.
(지식인에서 이분의 포스팅을 가져왔음을 밝힙니다)

  <IVBasic_Script.js>

 function IV_PopupImageView(img_path, img_title) {

    var popSource = "";
    var obj = document.createElement("img");

    obj.src = img_path;
    obj.id = 'newimg';

    var p = window.open("", "", "toolbar=no");
    document.body.appendChild(obj);

    setTimeout(function() {

        popSource = "<html><head><title>" + img_title + "</title></head>";
        popSource += "<script> window.resizeTo( " + (obj.width + 8) + ", " + (obj.height + 30)
                             + " )</script>";
        obj.style.display = "none";
        popSource += "<body style='margin:0000'> <img src='" + img_path + "'
                              onclick='self.close()'></body></html>";   

        p.document.write(popSource);

    });
}


보시면 아시겠지만 인자값(링크, 타이틀)을 받아서, popup을 띄우고 바로 document.write로
써버리는 방식이지요. <html></html>로 구성되는 html 문서를 그냥 바로 적용시킨 결과지요.

그리고 resizeto를 사용하여, 간격 8 정도로 두고 width, height를 받아서 쓸 수 있게끔
되어있습니다.

그리고 실버라이트에서는, 일반적으로 Javascript 함수를 부르는 방식을 사용합니다.

  <page.xaml.cs / 혹은 다른 cs 파일>
// 선언을 해 두고
ScriptObject jfunc = (ScriptObject)HtmlPage.Window.GetProperty("IV_PopupImageView");

// '여기다!' 싶은 곳에서 함수 호출
jfunc.InvokeSelf(senderUri, senderTitle);

이렇게 되면, 바로 <title> 안에 인자를 대입하면서 제목도 들어가고, 이미지 크기에 맞게
팝업이 띄워지고, 클릭하면 팝업이 닫힙니다.

자바스크립트도 어쩔 수 없이 들어가야되듯 보이더군요 실버라이트 개발을 하면서..
아무튼. 이런 방법이 있다는걸 알려드리기 위해 포스팅을 했습니다. ^^

도움이 되셨길..


...음. 그러니까 이런 경우져.


그냥 배포서버에서 찍어본다면야 wsdl이 나오겠지만, 다른 컴퓨터에선 저 컴퓨터 이름을 알지 못하니.. 참조할 수가 없겠지요.

VS2008 의 Service Reference도 결과는 같습니다. 먹통이예요.

일단 바인딩이라는 것을 해줘야합니다. 따로 프로그램을 짜야하는 것은 아니고..
IIS 매니저의 기본 기능을 이용해야 하지요.

시작 -> 실행 -> inetmgr을 클릭하시고 변경하려는 서비스에서 속성을 클릭해주세요.


그러면 웹사이트 확인.. 이라고 그룹이 있고 옆에 고급이 있습니다. 그걸 누릅니다.


그리고.. 우리가 쓰려고 하는 도메인 명을 입력합니다.


그런데 이때 주의해야 할 점은, 이렇게만 하면 에러를 뱉는다는 거예요.

('이 컬렉션에는 스키마 http을(를) 가진 주소가 이미 있습니다. 이 컬렉션에서 스키마당 주소는 하나만 존재할 수 있습니다' - 라는 에러메시지)

반드시, wcf와 같이 배포되는 web.config에도 다음과 같이 prefix를 명시해주어야 합니다. ^^

 <system.serviceModel>
    <serviceHostingEnvironment aspNetCompatibilityEnabled="false" >
    <baseAddressPrefixFilters>
        <add prefix="http://xxxxxx.kaoni.com"/>
    </baseAddressPrefixFilters>
    </serviceHostingEnvironment>

보통 serviceHostingEnvironment는 한줄에 /> 이렇게 닫혀있으니까요.
그거 </serviceHostingEnvironment>로 빼신 다음에, 중간에 이렇게..
prefix를 추가시키는 과정을 해주시면 됩니다.

이렇게 매칭을 시키고 iisreset 한번 돌려주시고 다시 svc파일을 띄워보시면.


그리고 클릭해서, xsd 스키마도 들어가있나 확인하시면 됩니다.

이 이후에는.. service reference로 해봐도 제약 없이 잘 들어가지지요..
이제 그 다음, 디렉토리 권한, 익명, 기본인증.. 등의 개념에 대한 지식...등등은.

.... 이 포스트에서 다루기가 너무 힘드니..;;


아 그리고 이건 iis 6의 경우입니다.
iis 7의 경우는.. 훈스님이 잘 설명해주셨더군요..

iis 7 사용자분들께서는 그 포스트와 이 포스트를 비교해서. 한번 해결해보세요.. ^^
(http://blog.hoons.kr/blog_post_71.aspx)


쇼티예요. ^^

WCF를 쓰는 방법중에는 그냥 쓰는 방법도 있지만.. GAC에 등록해서 쓸 수도 있지요..
이게 일반 IIS면 상관이 없는데. MOSS, 즉 Sharepoint 2007 하에서 사용하려 하면
Virtual Path에 대한 에러가 나오더군요.

Sharepoint에서 GAC을 사용하려면 이 VirtualPath에 대한 Dll을 만들어서, 배포를 해야합니다.
(프로젝트를 만들어서.. cs파일 아무거나 만드셔서, dll로 만들고 GAC에다 끌어다놓으면 되요)

 public class WCFVirtualPathProvider: VirtualPathProvider
{
    public override bool FileExists(string virtualPath)
    {
        string fixedPath = virtualPath;
        if (fixedPath.StartsWith("~", StringComparison.Ordinal) && fixedPath.EndsWith
                                       (".svc", StringComparison.InvariantCultureIgnoreCase))
        {
            fixedPath = fixedPath.Remove(0, 1);
        }
        return Previous.FileExists(fixedPath);
    }

    public override string CombineVirtualPaths(string basePath, string relativePath)
    {
        return Previous.CombineVirtualPaths(basePath, relativePath);
    }

    public override System.Runtime.Remoting.ObjRef CreateObjRef(Type requestedType)
    {
        return Previous.CreateObjRef(requestedType);
    }

    public override bool DirectoryExists(string virtualDir)
    {
        return Previous.DirectoryExists(virtualDir);
    }

    public override System.Web.Caching.CacheDependency GetCacheDependency(string virtualPath, System.Collections.IEnumerable virtualPathDependencies, DateTime utcStart)
    {
        return Previous.GetCacheDependency
                 (virtualPath, virtualPathDependencies, utcStart);
    }

    public override string GetCacheKey(string virtualPath)
    {
        return Previous.GetCacheKey(virtualPath);
    }

    public override VirtualDirectory GetDirectory(string virtualDir)
    {
        return Previous.GetDirectory(virtualDir);
    }

    public override VirtualFile GetFile(string virtualPath)
    {
        return Previous.GetFile(virtualPath);
    }

    public override string GetFileHash(string virtualPath, System.Collections.IEnumerable virtualPathDependencies)
    {
        return Previous.GetFileHash(virtualPath, virtualPathDependencies);
    }

    protected override void Initialize()
    {
        base.Initialize();
    }
}


이때, VirtualPathProvider는 System.Web.Hosting에서 찾을 수 있습니다. (ctrl + . 치시면 되요)
그리고 이 클래스를 사용하여 이런 클래스를 또 만들어주시면 됩니다.

 public class WCFVirtualPathProviderRegistration : IHttpModule
{
    static bool _initialized = false;
    static object _locker = new object();

    public void Init(HttpApplication context)
    {
        if (!_initialized)
        {
            lock (_locker)
            {
                if (!_initialized)
                {
                    WCFVirtualPathProvider provider = new WCFVirtualPathProvider();
                    HostingEnvironment.RegisterVirtualPathProvider(provider);
                    _initialized = true;
                }
            }
        }
    }

    public void Dispose()
    {
    }
}

그리고, Web.Config (MOSS의 루트에 보면 있지요..)에서 다음을 추가해줍니다.

 <add name="WCFVirtualPathProviderRegistration"
     type="TST.WCFServices.WCFVirtualPathProviderRegistration, TST.WCFServices, Version=1.0.0.0, Culture=neutral, PublicKeyToken=28ec3cd925274d6c"> 
</add>

... 물론 이제 name이나 type, 기타 버전이나 토큰..같은것들은 상황에 맞게 바꿔주셔야겠지요.
아무튼 <HttpModules></> 안에 해주시면 됩니다.


이게 아마 '~' 가 화일 안에 들어가있어서, 그 문자를 지워주는 역할을 하는 듯 하네요..
저도 자세히는 잘 모르겠어요.. ^^;; 그런데 이렇게 하면 해결이 된다 합니다.


도움이 되셨길~ ^^

쇼티예요.

clientaccesspolicy.xml는 흔히 이렇게 알고 계시져.

 <?xml version="1.0" encoding="utf-8"?>
<access-policy>
  <cross-domain-access>
    <policy>
      <allow-from http-request-headers="*">
        <domain uri="*"/>
      </allow-from>
      <grant-to>
        <resource path="/" include-subpaths="true"/>
      </grant-to>
    </policy>
  </cross-domain-access>
</access-policy> 

듣기로도 '모든 도메인에서의 접근을 허용한다' 라고 많이 들어보셨을 꺼예요.
실제로도 맞아요. <domain uri="*" /> 이게, 모든 도메인을 허용한다는 이야기이지요.

궁금증이 생겼어요. "그럼 도메인 하나만 접근을 허용하고 싶을땐?"
이거까지는 구글링에 걸리더군요.

<domain uri = "http://xxx.com" />

그런데. '그럼 두개일땐?', '세개일땐?' 어떻게 해야될까요.
간단해요. 하나 더 써주시면 됩니다.

<domain uri = "http://xxx.com" />
<domain uri = "http://yyy.com" />

실험도 해봤어요. 공도님(http://gongdosoft.com)이 네이트온에서 직접 협조해주셔서 제 나름대로는 상당히 흥미로운 실험이었는데.

방법은. 제가 가용 가능한 도메인 한개에, 공도님이 다방면의 도메인에서 접근을 합니다.
저게 맞다는 가정하에, 이 도메인의 루트디렉토리 clientaccesspolicy.xml 를 다음과 같이 수정하였구요. 여기다가 test.png 한개를 두어서, 이 정책이 통과가 되면 접근이 되도록.

            <allow-from http-request-headers="*">
                <domain uri="http://a.com"/>
                <domain uri="http://b.com"/
            </allow-from>

공도님의 접근경로(?)를 이렇게 가정을 해보고.

http://a.com/test/
http://b.com/test/
http://c.com/test/

이 각각에는 실버라이트 어플리케이션이 들어있구요. (동일합니다) 


이렇게 해서 Open을 해봅니다.
확인 결과 c.com쪽에서 접근을 했었을 때 에러가 발생하더군요. 정확히.


나머지 a.com과 b.com은 이미지가 잘 보이네요.


정리하자면. 도메인을 두개 이상 허용하고 싶을 때는.

             <allow-from http-request-headers="*">
                <domain uri="http://a.com"/>
                <domain uri="http://b.com"/
            </allow-from>

이렇게 하시면 된다는 것입니다 ^^ 3개면 domain uri를 3개 쓰시면 되고.. *도 적절하게 섞어준다면 더 효과적이겠지요.

실험 도와주신 공도님께 감사드리며. 도움이 되셨길.. ^^
 예를 들어, 콤보박스 하나를 추가하고 이 콤보가 변할 때의 코딩은 보통 이런식으로 하지요..


 SelectionChanged 이벤트를 오버라이딩 시킨 후에
 List<Class> aa = e.AddedItems[0] as Class;

 
 근데.. 이게 만약 새로고침이나, 페이지가 옮겨질 때에 보면 예상범위 초과 에러가
 뜰 때가 있어요..

 이게 왜 일어나냐면, '새로고침(으로 통칭할께요)'이 일어나게 되도 SelectionChanged 이벤트가
 발생해버려서 그렇게 됩니다. 선택된 아이템이 없는데 [0]번째 값을 참조하려고 했기 때문이죠.

 저때, 디버그로 e 인자를 조회해보시면 아시겠지만, AddedItems는 0이고, RemovedItems에 1이
 되면서, 기존에 선택했던 아이템이 그쪽으로 갑니다. 즉, if 하나 씌워주면 이 문제는 해결되지요.

 if (e.AddedItems.Count != 0)
 { 
      List<Class> aa = e.AddedItems[0] as Class;
 }

 어쩔 수 없네요. 그때 이벤트가 발생해버리기 때문에 그렇게 되는데, 이렇게 해주면 막을 수
 있습니다.
  
- Posted By Shorty