/*
*********************************************************************
*
*	The Essence of OLE
*
*	Source code sample
*
*	Copyright (c) 1996, Rolling Thunder Computing, Ipswich MA
*
*	e-mail: essence@rollthunder.com
*	CompuServe: 73540,3430
*	Web: http://www.rollthunder.com
*
*********************************************************************
*/

#include "stdafx.h"
#include "resource.h"
#include "ctrlholder.h"
#include "scriptsite.h"
#include "activscp.h"
#include "msscript.h"
#include "scripterrordlg.h"

#include <string.h>

static const GUID IID_IActiveScript = {0xbb1a2ae1, 0xa4f9, 0x11cf, {0x8f, 0x20, 0x0, 0x80, 0x5f, 0x2c, 0xd0, 0x64}} ;

// {BB1A2AE2-A4F9-11cf-8F20-00805F2CD064}
static const GUID IID_IActiveScriptParse = {0xbb1a2ae2, 0xa4f9, 0x11cf, {0x8f, 0x20, 0x0, 0x80, 0x5f, 0x2c, 0xd0, 0x64}};

// {DB01A1E3-A42B-11cf-8F20-00805F2CD064}
static const GUID IID_IActiveScriptSite = {0xdb01a1e3, 0xa42b, 0x11cf, {0x8f, 0x20, 0x0, 0x80, 0x5f, 0x2c, 0xd0, 0x64}};

// {D10F6761-83E9-11cf-8F20-00805F2CD064}
static const GUID IID_IActiveScriptSiteWindow = {0xd10f6761, 0x83e9, 0x11cf, {0x8f, 0x20, 0x0, 0x80, 0x5f, 0x2c, 0xd0, 0x64}};

extern	CCtrlHolder*	g_pControl1 ;


CActiveScriptSite::CActiveScriptSite ( )
{
	m_RefCount = 1 ;
}

CActiveScriptSite::~CActiveScriptSite ( )
{

}


STDMETHODIMP CActiveScriptSite::GetItemInfo(LPCOLESTR   pName,
  DWORD       dwReturnMask,  IUnknown**  ppDispOut,  ITypeInfo** ppTypeInfoOut)
{
	HRESULT hr;
	USES_CONVERSION

/*
See if the script engine is asking for our Grid object.
*/

	if (_wcsicmp (pName, L"Control1") == 0)
	{
/*
See if they are asking for the object pointer
*/

		if (dwReturnMask & SCRIPTINFO_IUNKNOWN)
		{
			hr = g_pControl1->GetDispatch ((IDispatch **)ppDispOut) ;
		}

/*
See if the are also/otherwise asking for the type info.
*/
		if (dwReturnMask & SCRIPTINFO_ITYPEINFO)
		{
			hr = g_pControl1->GetTypeInfo (ppTypeInfoOut) ;
		}

		return hr ;
	}
		
	MessageBox (NULL, W2A(pName), "Unknown object", 0) ;
	return TYPE_E_ELEMENTNOTFOUND;
}


STDMETHODIMP CActiveScriptSite::RequestItems(void)
{
	return S_OK ;
}

STDMETHODIMP CActiveScriptSite::RequestTypeLibs(void)
{
	return S_OK ;
}


STDMETHODIMP CActiveScriptSite::OnScriptError(IActiveScriptError *pse)
{
	HRESULT   hr;
  
/*
Get the EXCEPINFO structure describing the error
*/
	EXCEPINFO ei;

	hr = pse->GetExceptionInfo(&ei) ;

/*
Get the position in the source code at which the error took plac
*/

	DWORD context,line ;
	LONG CharPos ;

	hr = pse->GetSourcePosition(&context, &line, &CharPos) ;

/*
Get the text of the source line that failed
*/

	BSTR bstrLine ;
	hr = pse->GetSourceLineText(&bstrLine);

/*
Format and display error for user.
*/
	CScriptErrorDlg dlg ;

	dlg.m_ErrorName = ei.bstrDescription ;
	dlg.m_AppName = ei.bstrSource ;
	dlg.m_ErrorStatement = bstrLine ;
	dlg.m_HelpFile = ei.bstrHelpFile ;
	dlg.m_HelpContext = ei.dwHelpContext ;

	int i = dlg.DoModal( ) ;

	SysFreeString (ei.bstrDescription) ;
	SysFreeString (ei.bstrSource) ;
	SysFreeString (ei.bstrHelpFile) ;
	SysFreeString (bstrLine) ;

/*
Based on user's choice, Ignore, Debug, or Quit
*/

	if (i == IDC_ABORT)
	{
		return E_FAIL ;
	}
	else if (i == IDC_DEBUG)
	{
		return S_FALSE ;
	}
	else
	{
		return S_OK ;
	}
}

/*
Stub out unused methods.
*/

STDMETHODIMP CActiveScriptSite::OnStateChange(SCRIPTSTATE ssScriptState)
{
	return S_OK;
}

STDMETHODIMP CActiveScriptSite::GetLCID(LCID *plcid)
{
	return E_NOTIMPL;     
}


STDMETHODIMP CActiveScriptSite::OnEnterScript(void)
{
  return S_OK;
}

STDMETHODIMP CActiveScriptSite::OnLeaveScript(void)
{
  return S_OK;
}

STDMETHODIMP CActiveScriptSite::GetDocVersionString(BSTR *pbstrVersion)
{
	return E_NOTIMPL;  
}

STDMETHODIMP CActiveScriptSite::OnScriptTerminate(const VARIANT   *pvarResult,
  const EXCEPINFO *pexcepinfo)
{
	return S_OK;
}

STDMETHODIMP CActiveScriptSite::EnableModeless (BOOL bModeless)
{
	return S_OK ;	
}

STDMETHODIMP CActiveScriptSite::GetWindow(HWND *phWnd)
{
	if (phWnd) 
	{
		*phWnd = AfxGetApp( )->m_pMainWnd->m_hWnd ;
	}
	return S_OK ;
}


STDMETHODIMP CActiveScriptSite::QueryInterface(REFIID  riid,
  LPVOID* ppOut)
{

  if (riid == IID_IUnknown || riid == IID_IActiveScriptSite)
  {
    *ppOut = (IActiveScriptSite *) this ;
	AddRef( ) ;
	return S_OK ;
  }
  else if (riid == IID_IActiveScriptSiteWindow)
  {
	*ppOut = (IActiveScriptSiteWindow *)this ;
	AddRef ( ) ;
	return S_OK ;
  }
  else
  {
	  *ppOut = NULL ;
	  return E_NOINTERFACE;
  }
}


//---------------------------------------------------------------------------
// 
//---------------------------------------------------------------------------
STDMETHODIMP_(ULONG) CActiveScriptSite::AddRef(void)
{
  return ++m_RefCount;
}


STDMETHODIMP_(ULONG) CActiveScriptSite::Release(void)
{
  m_RefCount -- ;
  
  if (m_RefCount == 0)
  {
      delete this;
      return 0;
  }
  return m_RefCount ;
}

