コード例 #1
0
/*----------------------------------------------------------------------------------------------
	Set up the crawler to work on a given database connection.

	@param stuServerName - name of the database server
	@param stuDatabase - name of the database
	@param pstrmLog - pointer to the log stream (may be NULL)
	@param padvi3 - pointer to the progress report object (defaults to NULL)
----------------------------------------------------------------------------------------------*/
bool DbStringCrawler::Init(IOleDbEncap * pode, IStream *pstrmLog, IAdvInd3 * padvi3)
{
	m_qodeDb = pode;
	SmartBstr sbstrServer;
	StrUni stuServer;
	CheckHr(pode->get_Server(&sbstrServer));
	stuServer.Assign(sbstrServer.Chars(), sbstrServer.Length());
	SmartBstr sbstrDatabase;
	StrUni stuDatabase;
	CheckHr(pode->get_Database(&sbstrDatabase));
	stuDatabase.Assign(sbstrDatabase.Chars(), sbstrDatabase.Length());
	return Init(stuServer, stuDatabase, pstrmLog, padvi3);
}
コード例 #2
0
ファイル: FwGr.cpp プロジェクト: bbriggs/FieldWorks
/*----------------------------------------------------------------------------------------------
	Return the ISO-639-3 language code, cast to an unsigned int.
----------------------------------------------------------------------------------------------*/
isocode FwGrTxtSrc::getLanguage(toffset ich)
{
	LgCharRenderProps lgchrp;
	int ichMinBogus, ichLimBogus;
	GrResult res = (GrResult)m_qts->GetCharProps(GrToVwOffset(ich), &lgchrp, &ichMinBogus, &ichLimBogus);

	int ws = lgchrp.ws;

	ILgWritingSystemFactoryPtr qwsf;
	ILgWritingSystemPtr qws;
	CheckHr(m_qts->GetWsFactory(&qwsf));
	AssertPtr(qwsf);
	CheckHr(qwsf->get_EngineOrNull(ws, &qws));

	isocode code;
	if (!qws)
	{
		memset(code.rgch, 0, sizeof(char) * 4);
		return code;
	}

	SmartBstr bstrLang;
	CheckHr(qws->get_ISO3(&bstrLang));

	for (int i = 0; i < 4; i++)
		code.rgch[i] = (char)(i >= bstrLang.Length() ? 0 : bstrLang[i]);
	return code;
}
コード例 #3
0
/*----------------------------------------------------------------------------------------------
	Draw to the given clip rectangle.
	@param hdc
	@param rcpClip the given clip rectangle

	TODO: use views code to display the field contents!
----------------------------------------------------------------------------------------------*/
void AfDeFeEdBoxBut::Draw(HDC hdc, const Rect & rcpClip)
{
	Assert(hdc);
	int ws;
	SmartBstr sbstr;
	if (m_qtss)
	{
		CheckHr(m_qtss->get_Text(&sbstr));
		int nVar;
		ITsTextPropsPtr qttp;
		CheckHr(m_qtss->get_PropertiesAt(0, &qttp));
		CheckHr(qttp->GetIntPropValues(ktptWs, &nVar, &ws));
		MakeCharProps(ws);
		CreateFont();
}

	AfGfx::FillSolidRect(hdc, rcpClip, m_chrp.clrBack);
	COLORREF clrBgOld = AfGfx::SetBkColor(hdc, m_chrp.clrBack);
	COLORREF clrFgOld = AfGfx::SetTextColor(hdc, m_chrp.clrFore);
	HFONT hfontOld = AfGdi::SelectObjectFont(hdc, m_hfont);
#if 1
	UINT uAlignPrev = ::GetTextAlign(hdc);
	if (m_fRtl)
	{
		::SetTextAlign(hdc, (uAlignPrev & ~(TA_CENTER|TA_LEFT)) | TA_RIGHT | TA_RTLREADING);
		::TextOutW(hdc, rcpClip.right - 19, rcpClip.top + 1, sbstr.Chars(), sbstr.Length());
	}
	else
	{
		::SetTextAlign(hdc, (uAlignPrev & ~(TA_CENTER|TA_RIGHT)) | TA_LEFT);
		::TextOutW(hdc, rcpClip.left + 2, rcpClip.top + 1, sbstr.Chars(), sbstr.Length());
	}
	::SetTextAlign(hdc, uAlignPrev);
#else
	::TextOutW(hdc, rcpClip.left + 2, rcpClip.top + 1, sbstr.Chars(), sbstr.Length());
#endif
	AfGdi::SelectObjectFont(hdc, hfontOld, AfGdi::OLD);
	AfGfx::SetBkColor(hdc, clrBgOld);
	AfGfx::SetTextColor(hdc, clrFgOld);
}
コード例 #4
0
/*----------------------------------------------------------------------------------------------
	Change all the occurrences of the old styles names to the new names, and delete any
	obsolete names.
----------------------------------------------------------------------------------------------*/
bool FwDbMergeStyles::ProcessFormatting(ComVector<ITsTextProps> & vqttp,
	StrUni stuDelete)
{
	bool fAnyChanged = false;
	for (int ittp = 0; ittp < vqttp.Size(); ittp++)
	{
		SmartBstr sbstr;
		HRESULT hr;
		CheckHr(hr = vqttp[ittp]->GetStrPropValue(ktptNamedStyle, &sbstr));
		if (hr == S_OK && sbstr.Length() > 0)
		{
			ITsPropsBldrPtr qtpb = NULL;
			StrUni stuOld(sbstr.Chars());
			StrUni stuNew;
			if (Delete(stuOld))
			{
				CheckHr(vqttp[ittp]->GetBldr(&qtpb));
				if (stuDelete.Length() == 0)
				{
					// If the style name to delete is empty, we want to pass null
					// so that the named style string property is removed.
					CheckHr(qtpb->SetStrPropValue(ktptNamedStyle, NULL));
				}
				else
					CheckHr(qtpb->SetStrPropValue(ktptNamedStyle, stuDelete.Bstr()));

			}
			else if (Rename(stuOld, stuNew))
			{
				CheckHr(vqttp[ittp]->GetBldr(&qtpb));
				CheckHr(qtpb->SetStrPropValue(ktptNamedStyle, stuNew.Bstr()));
			}

			if (qtpb)
			{
				ITsTextPropsPtr qttpNew;
				CheckHr(qtpb->GetTextProps(&qttpNew));
				vqttp[ittp] = qttpNew;
				fAnyChanged = true;
			}
		}
	}

	return fAnyChanged;
}
コード例 #5
0
ファイル: VwBaseVc.cpp プロジェクト: agran147/FieldWorks
/*----------------------------------------------------------------------------------------------
	Insert material as appropriate to display the specified object.
	This method has not yet been tested...maybe not even compiled?
----------------------------------------------------------------------------------------------*/
STDMETHODIMP VwBaseVc::DisplayEmbeddedObject(IVwEnv * pvwenv, HVO hvo)
{
	BEGIN_COM_METHOD;
	ChkComArgPtr(pvwenv);
	// See if it is a CmPicture.
	ISilDataAccessPtr qsda;
	CheckHr(pvwenv->get_DataAccess(&qsda));
	int clsid;
	CheckHr(qsda->get_IntProp(hvo, kflidCmObject_Class, &clsid));
	if (clsid != kclidCmPicture)
		return S_OK; // don't know how to deal with it.
	StrUni stuRootDir = DirectoryFinder::FwRootDataDir();
	HVO hvoFile;
	CheckHr(qsda->get_ObjectProp(hvo, kflidCmPicture_PictureFile, &hvoFile));
	if (hvoFile == 0)
		return S_OK;
	SmartBstr sbstrFileName;
	CheckHr(qsda->get_UnicodeProp(hvoFile, kflidCmFile_InternalPath, &sbstrFileName));
	if (sbstrFileName.Length() == 0)
		return S_OK;
	StrUni stuPath;
	stuPath.Format(L"%s,%s,%s", stuRootDir.Chars(), L"\\", sbstrFileName.Chars());
	IPicturePtr qpic;
	try
	{
		IStreamPtr qstrm;
		FileStream::Create(stuPath, STGM_READ, &qstrm);
		STATSTG stg;
		CheckHr(qstrm->Stat(&stg, STATFLAG_NONAME));
		LONG cbdata = (LONG)stg.cbSize.QuadPart;
		CheckHr(::OleLoadPicture(qstrm, cbdata, FALSE, IID_IPicture, (LPVOID *)&qpic));
		CheckHr(pvwenv->AddPicture(qpic, ktagNotAnAttr, 0, 0));
	}
	catch (...)
	{
		return S_OK; // if anything goes wrong (e.g., file not found), just give up for now.
		// Todo: insert a 'file XXX not found string.
	}
	// Todo: also add the caption.

	END_COM_METHOD(g_fact, IID_IVwViewConstructor);
}
コード例 #6
0
/*----------------------------------------------------------------------------------------------
	Save data in the cache, to the database.
----------------------------------------------------------------------------------------------*/
STDMETHODIMP VwRsOdbcDa::Save(SqlDb & sdb)
{
	BEGIN_COM_METHOD

	const kcchErrMsgBuf = 1024;
	const kcbFmtBufMax = 1024;
	const kcchMaxColNameSize = 200;

	SQLINTEGER cbColVal;
	SDWORD cbClassName;
	long cbHvo;
	SDWORD cbFieldName;
	SDWORD cbFlid;
	int cbFmtBufSize = kcbFmtBufMax;
	int cbFmtSpaceTaken;
	SDWORD cbType;
	SQLUSMALLINT cParamsProcessed = 0;
	HRESULT hr;
	FieldMetaDataMap fmdm;		//  REVIEW PaulP:  Would be nice to have this kept globally.
	FieldMetaDataRec fmdr;
	int nColVal;
	int nFlid;
	ITsStringPtr qtssColVal;
	RETCODE rc;
	byte * rgbFmt = NewObj byte[kcbFmtBufMax]; //[kcbFmtBufMax];
	SmartBstr sbstr;
	SQLCHAR sqlchSqlState[5];
	SQLCHAR sqlchMsgTxt[kcchErrMsgBuf];
	SQLINTEGER sqlnNativeErrPtr;
	SQLSMALLINT sqlnTextLength;
	SQLRETURN sqlr;
	SqlStatement sstmt;
	StrUni suColumnName;
	StrUni suFieldMetaDataSql;
	StrUni suSql;
	StrUni suTableName;
	wchar wchClassName[kcchMaxColNameSize];
	wchar wchFieldName[kcchMaxColNameSize];


	Assert(sdb.IsOpen());


	/*------------------------------------------------------------------------------------------
		If a pointer to a HashMap of field$ metadata information was not passed in as a
		parameter, create the HashMap.  The metaData includes all field names, field types,
		class names, and destination class name from the field$ and class$ tables.
		This information is needed since only store the "flid" value is stored in the cache
		(as the "tag") so when it comes time to do SQL "insert" and "update" statements,
		one need's to know what table and column needs to be affected.

		REVIEW PaulP:  Should really cache this information globally so that it does not have
		to be reloaded each time the view cache is saved.  The only time this info would have
		to be reloaded is when custom fields are added.  Perhaps we could have a table with
		a single record which indicates the last date/time a change to the database was made.
		This could be compared with the currently loaded date each time the cache is saved to
		see if there is a need to reload the field$ meta information.  Of course, if we
		require that only one user is allowed to be connected for a custom field addition,
		this would not be necessary.

		TOxDO PaulP:  Cleanup on any error exit, including db rollback.
						CheckSqlRc(SQLEndTran(SQL_HANDLE_DBC, sdb.Hdbc(), SQL_ROLLBACK));
	------------------------------------------------------------------------------------------*/
	try
	{
		//  Set up SQL statment to obtain meta data.
		suFieldMetaDataSql.Format(
			L"select f.Id FLID, Type, f.Name FLD_NAME,"
			L" c.Name CLS_NAME"
			L" from Field$ f"
			L" join Class$ c on c.id = f.Class"
			L" order by f.id");
		sstmt.Init(sdb);
		CheckSqlRc(SQLExecDirectW(sstmt.Hstmt(), \
			const_cast<wchar *>(suFieldMetaDataSql.Chars()), SQL_NTS));

		//  Bind Columns.
		rc = SQLSetStmtAttr(sstmt.Hstmt(), SQL_ATTR_PARAMS_PROCESSED_PTR, &cParamsProcessed, 0);
		CheckSqlRc(SQLBindCol(sstmt.Hstmt(), 1, SQL_C_SLONG, &nFlid, isizeof(int),
			&cbFlid));
		CheckSqlRc(SQLBindCol(sstmt.Hstmt(), 2, SQL_C_SLONG, &fmdr.m_iType,
			isizeof(fmdr.m_iType), &cbType));
		CheckSqlRc(SQLBindCol(sstmt.Hstmt(), 3, SQL_C_WCHAR, &wchFieldName,
			kcchMaxColNameSize, &cbFieldName));
		CheckSqlRc(SQLBindCol(sstmt.Hstmt(), 4, SQL_C_WCHAR, &wchClassName,
			kcchMaxColNameSize, &cbClassName));

		//  Put info from the columns into a FieldMetaDataRec record and insert
		//  this in the FieldMetaData HashMap.
		for (;;)
		{
			rc = SQLFetch(sstmt.Hstmt());
			if (rc != SQL_SUCCESS)
				break;
			// TOxDO PaulP:  Change this so it just gets a null terminated string!!!
			fmdr.m_suFieldName.Assign(wchFieldName, kcchMaxColNameSize);
			fmdr.m_suClassName.Assign(wchClassName, kcchMaxColNameSize);
			fmdm.Insert(nFlid, fmdr);
		}
		if (rc != SQL_NO_DATA)
		{
			//  REVIEW PaulP (SteveMc): Handle possible error message?
			ThrowHr(WarnHr(E_UNEXPECTED));
		}
		sstmt.Clear();
	}
	catch (...)
	{
		sstmt.Clear();
		delete rgbFmt;
		return E_UNEXPECTED;
	}


	/*------------------------------------------------------------------------------------------
		For every key in the "m_soprMods" ObjPropSet set (ie. all the object properties
		that have been updated), look up that key in the appropriate HashMap and form an SQL
		"update" statement according to the field$ "Type".

		This begins a single database transaction.  All the data in the application view cache
		must either be inserted/updated to the database successfully or the action should fail.
		This necessitates that the database connection is in manual-commit mode.

		REVIEW PaulP:  It is probably faster to collect all the properties for a given object
		type and update the table in the database all with one SQL statement but this will
		do for now until the OLE DB stuff is done.
	------------------------------------------------------------------------------------------*/
	try
	{
		ObjPropSet::iterator itops;
		for (itops = m_soprMods.Begin(); itops != m_soprMods.End(); ++itops)
		{
			//  Get the oprKey from the "update object property" Set.
			ObjPropRec & oprKey = itops.GetValue();

			//  Get the field$ metadata information based on the tag of that oprKey.
			fmdm.Retrieve(oprKey.m_tag, &fmdr);

			//  Initialize and form the SQL statment based on the field "type".
			sstmt.Init(sdb);
			switch (fmdr.m_iType)
			{
				case kcptNil:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;

				case kcptBoolean:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;

				case kcptInteger:
					//  Prepare the SQL statement.  (Uses parameters).
					suSql.Format(L"update %s set %s=? where id=?", fmdr.m_suClassName.Chars(),
						fmdr.m_suFieldName.Chars());
					rc = SQLPrepareW(sstmt.Hstmt(), const_cast<wchar *>(suSql.Chars()),
						SQL_NTS);

					//  Get the integer value from the appropriate HashMap.
					if (m_hmoprn.Retrieve(oprKey, &nColVal))
					{
						//  Bind integer value as the first parameter.
						if (nColVal)
						{
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_SLONG, SQL_INTEGER, 0, 0, &nColVal, 0, &cbColVal);
						}
						else
						{
							// REVIEW JohnT:  How do we indicate in the HashMap that the user
							//		wants to set an integer to NULL?
							cbColVal = SQL_NULL_DATA;
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_SLONG, SQL_INTEGER, 0, 0, NULL, 0, &cbColVal);
						}

						//  Bind the HVO (Id) as the second parameter.
						rc = SQLBindParameter(sstmt.Hstmt(), 2, SQL_PARAM_INPUT,
							SQL_C_SLONG, SQL_INTEGER, 0, 0, &(oprKey.m_hvo), 0, &cbHvo);
					}
					else
					{
						ThrowHr(WarnHr(E_UNEXPECTED));
					}
					break;


				case kcptNumeric:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptFloat:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptTime:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptGuid:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptImage:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptGenDate:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptBinary:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;


				case kcptString:
				case kcptBigString:

					//  Prepare the SQL statement.  (Uses parameters.)
					//  REVIEW PaulP:  Should I be hard-coding "_Fmt" in like this?
					suSql.Format(L"update %s set %s=?, %s_Fmt=? where id=?",
						fmdr.m_suClassName.Chars(), fmdr.m_suFieldName.Chars(),
						fmdr.m_suFieldName.Chars());
					rc = SQLPrepareW(sstmt.Hstmt(), const_cast<wchar *>(suSql.Chars()),
						SQL_NTS);

					if (m_hmoprtss.Retrieve(oprKey, qtssColVal))
					{
						//  Obtain a SmartBstr from the COM smart pointer that points
						//  to the TsString.
						CheckHr(qtssColVal->get_Text(&sbstr));
						if (sbstr.Length())
						{
							//  Copy format information of the TsString to byte array rgbFmt.
							hr = qtssColVal->SerializeFmtRgb(rgbFmt, cbFmtBufSize,
								&cbFmtSpaceTaken);
							if (hr != S_OK)
							{
								if (hr == S_FALSE)
								{
									//  If the supplied buffer is too small, try it again with
									//  the value that cbFmtSpaceTaken was set to.  If this
									//   fails, throw error.
									delete rgbFmt;
									rgbFmt = NewObj byte[cbFmtSpaceTaken];
									cbFmtBufSize = cbFmtSpaceTaken;
									CheckHr(qtssColVal->SerializeFmtRgb(rgbFmt, cbFmtBufSize,
										&cbFmtSpaceTaken));
								}
								else
								{
									ThrowHr(WarnHr(E_UNEXPECTED));
								}
							}

							//  Bind the text and format parts of the string to the parameters.
							SQLINTEGER cbTextPart = sbstr.Length() * 2;
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_WCHAR, SQL_WVARCHAR, cbTextPart, 0,
								const_cast<wchar *>(sbstr.Chars()), cbTextPart, &cbTextPart);
							SQLINTEGER cbFmtPart = cbFmtSpaceTaken;
							rc = SQLBindParameter(sstmt.Hstmt(), 2, SQL_PARAM_INPUT,
								SQL_C_BINARY, SQL_VARBINARY, cbFmtPart, 0, rgbFmt, cbFmtPart,
								&cbFmtPart);
						}
						else
						{
							//  Since the string had no length, bind NULL to the parameters.
							SQLINTEGER cbTextPart = SQL_NULL_DATA;
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_WCHAR, SQL_WVARCHAR, 1, 0, NULL, 0, &cbTextPart);
							//  REVIEW PaulP:  Should we set the Fmt info to NULL for NULL
							//     strings or should we use the Fmt info returned from the
							//     TsString?
							SQLINTEGER cbFmtPart = SQL_NULL_DATA;
							rc = SQLBindParameter(sstmt.Hstmt(), 2, SQL_PARAM_INPUT,
								SQL_C_BINARY, SQL_VARBINARY, 1, 0, NULL, 0, &cbFmtPart);
						}
					}
					else
					{
						ThrowHr(WarnHr(E_UNEXPECTED));
					}

					//  Bind the HVO (ie. Id) value.
					rc = SQLBindParameter(sstmt.Hstmt(), 3, SQL_PARAM_INPUT, SQL_C_SLONG,
						SQL_INTEGER, 0, 0, &(oprKey.m_hvo), 0, &cbHvo);
					break;


				case kcptBigUnicode:
				case kcptUnicode:

					//  Prepare the SQL statement.  (Uses parameters.)
					suSql.Format(L"update %s set %s=? where id=?", fmdr.m_suClassName.Chars(),
						fmdr.m_suFieldName.Chars());
					rc = SQLPrepareW(sstmt.Hstmt(), const_cast<wchar *>(suSql.Chars()),
						SQL_NTS);

					if (m_hmoprtss.Retrieve(oprKey, qtssColVal))
					{
						//  Obtain a SmartBstr from the COM smart pointer that
						//  points to a TsString.
						CheckHr(qtssColVal->get_Text(&sbstr));
						if (sbstr.Length())
						{
							//  Bind the string parameter.
							SQLINTEGER cbTextPart = sbstr.Length() * 2;
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_WCHAR, SQL_WVARCHAR, cbTextPart, 0,
								const_cast<wchar *>(sbstr.Chars()), cbTextPart, &cbTextPart);
						}
						else
						{
							//  If the string had no length, bind NULL to the parameter.
							SQLINTEGER cbTextPart = SQL_NULL_DATA;
							rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
								SQL_C_WCHAR, SQL_WVARCHAR, 1, 0, NULL, 0, &cbTextPart);
						}
					}
					else
					{
						ThrowHr(WarnHr(E_UNEXPECTED));
					}

					//  Bind the HVO (ie. Id) value.
					rc = SQLBindParameter(sstmt.Hstmt(), 2, SQL_PARAM_INPUT, SQL_C_SLONG,
						SQL_INTEGER, 0, 0, &(oprKey.m_hvo), 0, &cbHvo);
					break;

				case kcptOwningAtom:
					//  Update owning field.
					//  Update Owner$ object of CmObject.
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptReferenceAtom:
					//  This is basically the same as the Integer case except we obtain the
					//  value from the m_hmoprobj HashMap rather than the m_hmoprn HashMap.
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptOwningCollection:
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptReferenceCollection:
					//  Affect the joiner table.
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptOwningSequence:
					//  Need to update.
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				case kcptReferenceSequence:
					//  Affect the joiner table.
					ThrowHr(WarnHr(E_NOTIMPL));
					break;
				default:
					ThrowHr(WarnHr(E_UNEXPECTED));
					break;
			}

			//  Execute the SQL update command.
			//rc = SQLSetStmtAttr(sstmt.Hstmt(), SQL_ATTR_PARAM_BIND_TYPE, SQL_PARAM_BIND_BY_COLUMN, 0);
			rc = SQLExecute(sstmt.Hstmt());
			if (rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO)
			{
				//  TOxDO PaulP:  Error information can be obtained from sqlchMsgTxt.
				sqlr = SQLGetDiagRec(SQL_HANDLE_STMT, sstmt.Hstmt(), 1, sqlchSqlState,
					&sqlnNativeErrPtr, sqlchMsgTxt, kcchErrMsgBuf, &sqlnTextLength);
				ThrowHr(WarnHr(E_UNEXPECTED));
			}
			sstmt.Clear();
		}


		/*--------------------------------------------------------------------------------------
			Go through the m_soperMods ObjPropSet set and update columns in the MultiX tables.
		--------------------------------------------------------------------------------------*/
		ObjPropEncSet::iterator itopes;
		for (itopes = m_soperMods.Begin(); itopes != m_soperMods.End(); ++itopes)
		{
			//  Get the operKey from the "update MSA" Set.
			ObjPropEncRec & operKey = itopes.GetValue();

			//  Get the field$ metadata information based on the tag of that operKey.
			fmdm.Retrieve(operKey.m_tag, &fmdr);

			//  Initialize and form the SQL statment.
			sstmt.Init(sdb);
			if (m_hmopertss.Retrieve(operKey, qtssColVal))
			{
				//  Obtain a SmartBstr from the COM smart pointer that points to the TsString.
				CheckHr(qtssColVal->get_Text(&sbstr));
				if (sbstr.Length())
				{
					//  Get the format of the TsString
					hr = qtssColVal->SerializeFmtRgb(rgbFmt, cbFmtBufSize, &cbFmtSpaceTaken);
					if (hr != S_OK)
					{
						if (hr == S_FALSE)
						{
							//  If the supplied buffer is too small, try it again with the value
							//  that cbFmtSpaceTaken was set to.  If this fails, signal error.
							delete rgbFmt;
							rgbFmt = NewObj byte[cbFmtSpaceTaken];
							cbFmtBufSize = cbFmtSpaceTaken;
							CheckHr(qtssColVal->SerializeFmtRgb(rgbFmt, cbFmtBufSize,
								&cbFmtSpaceTaken));
						}
						else
						{
							ThrowHr(WarnHr(E_UNEXPECTED));
						}
					}

					//  Execute stored procedure to set MSA value.
					//  REVIEW PaulP:  This technique isn't going to work for custom fields
					//		since there will likely not be any "Set" stored procedure.
					suSql.Format(L"exec Set_%s_%s %d, %d, ?, ?", fmdr.m_suClassName.Chars(),
						fmdr.m_suFieldName.Chars(), operKey.m_hvo, operKey.m_ws);
					rc = SQLPrepareW(sstmt.Hstmt(), const_cast<wchar *>(suSql.Chars()),
						SQL_NTS);

					//  Bind the text and format parts of the string to the parameters.
					SQLINTEGER cbTextPart = sbstr.Length() * 2;
					rc = SQLBindParameter(sstmt.Hstmt(), 1, SQL_PARAM_INPUT,
						SQL_C_WCHAR, SQL_WVARCHAR, cbTextPart, 0,
						const_cast<wchar *>(sbstr.Chars()), cbTextPart, &cbTextPart);

					SQLINTEGER cbFmtPart = cbFmtSpaceTaken;
					rc = SQLBindParameter(sstmt.Hstmt(), 2, SQL_PARAM_INPUT, SQL_C_BINARY,
					SQL_VARBINARY, cbFmtPart, 0, rgbFmt, cbFmtPart, &cbFmtPart);
				}
				else
				{
					//  REVIEW PaulP:  This technique isn't going to work for custom fields
					//		since there will likely not be any "Set" stored procedure.
					suSql.Format(L"exec Set_%s_%s %d, %d, NULL, NULL",
						fmdr.m_suClassName.Chars(), fmdr.m_suFieldName.Chars(), operKey.m_hvo,
						operKey.m_ws);
					rc = SQLPrepareW(sstmt.Hstmt(), const_cast<wchar *>(suSql.Chars()),
						SQL_NTS);
				}

				//  Execute the SQL update command.
				//rc = SQLSetStmtAttr(sstmt.Hstmt(), SQL_ATTR_PARAM_BIND_TYPE, SQL_PARAM_BIND_BY_COLUMN, 0);
				rc = SQLExecute(sstmt.Hstmt());
				if (rc == SQL_ERROR || rc == SQL_SUCCESS_WITH_INFO)
				{
					//  TOxDO PaulP:  Error information can be obtained from sqlchMsgTxt.
					sqlr = SQLGetDiagRec(SQL_HANDLE_STMT, sstmt.Hstmt(), 1, sqlchSqlState,
						&sqlnNativeErrPtr, sqlchMsgTxt, kcchErrMsgBuf, &sqlnTextLength);
					ThrowHr(WarnHr(E_UNEXPECTED));
				}
				sstmt.Clear();
			}
			else
			{
				ThrowHr(WarnHr(E_UNEXPECTED));
			}
		}


		/*--------------------------------------------------------------------------------------
			Commit the database transaction.
			REVIEW PaulP:  The DataSource MUST be in manual commit mode.
		--------------------------------------------------------------------------------------*/
		CheckSqlRc(SQLEndTran(SQL_HANDLE_DBC, sdb.Hdbc(), SQL_COMMIT));

	}
	catch (...)
	{
		sstmt.Clear();
		delete rgbFmt;
		CheckSqlRc(SQLEndTran(SQL_HANDLE_DBC, sdb.Hdbc(), SQL_ROLLBACK));
		return E_UNEXPECTED;
	}


	/*------------------------------------------------------------------------------------------
		Clear the two Sets containing records of modified properties and MBA's.
	------------------------------------------------------------------------------------------*/
	m_soprMods.Clear();
	m_soperMods.Clear();
	delete rgbFmt; // REVIEW: Shouldn't this be delete[]?

	return S_OK;

	END_COM_METHOD(g_fact, IID_IVwCacheDa);
}
コード例 #7
0
/*----------------------------------------------------------------------------------------------
	Set the values for the dialog controls based on the style styi.
	@param vwsProj Union of the current Vernacular and Analysis encodings for the project.
----------------------------------------------------------------------------------------------*/
void FmtGenDlg::SetDialogValues(StyleInfo & styi, Vector<int> & vwsProj)
{
	// During SetDialogValues we never need to handle loss of focus in the name control,
	// because if anything needed to be done about updating that, it was done during
	// GetDialogValues, which is always called before SetDialogValues. We need to suppress it
	// because during this call the current style index and the current value of the control
	// may not agree: the purpose of this method is to update the control from the new style.
	// The normal loss-of-focus code is trying to synchronize in the opposite direction, and
	// can cause problems, for example, when we are disabling the control. For example:
	//  - Disabling the window causes it to lose focus if it previously had focus.
	//  - There is a kill focus event that tries to make the contents of the box agree with
	//		the name of the current style.
	//	- when this method is called, the old style is still the current one, so if we
	//		already changed the text in the box, we wind up trying to rename the old style
	//		to the name of the 'provided' style and produce a name conflict error.

	try
	{
		m_vwsProj = vwsProj;

		StrApp strDesc;
		m_fSuppressLossOfFocus = true;
		StrApp strName = styi.m_stuName;
		StrApp strTemp; // Temporary string.
		bool fProtectedStyle = m_pafsd->IsStyleProtected(styi.m_stuName);

		// Name edit box.
		::SetDlgItemText(m_hwnd, kctidFgEdName, strName.Chars());
		// Diable the control for styles originally provided by FieldWorks.
		::EnableWindow(m_hwndName, !fProtectedStyle);

		// Style type ltext.
		switch (styi.m_st)
		{
		case kstParagraph:
			strTemp.Load(kstidParagraph);
			break;
		case kstCharacter:
			strTemp.Load(kstidCharacter);
			break;
		default:
			Assert(false); // Should not happen.
		}
		::SetWindowText(m_hwndType, strTemp.Chars());

		// Update the "next" and "basedOn" comboboxes
		LoadNextStyleCombobox(styi);
		SetNextStyleComboboxValue(styi);
		LoadBasedOnStyleCombobox(styi);
		SetBasedOnStyleComboboxValue(styi);

		// ENHANCE LarryW(JohnT): When shortcut is implemented initialize the value instead.
		::EnableWindow(m_hwndShortcut, false); // Disables it.

		// **************************************
		m_vesi.Clear();
		strDesc = m_pafsd->GetNameOfStyle(styi.m_hvoBasedOn);
		strDesc.Append(" + ");

		ITsTextProps * pttp = styi.m_qttp;
		if (pttp)
		{
			StrApp strT;
			StrAppBuf strb; // a temp, used for making strings with units

			// Add default font info
			bool fFirstPart = true;
			SmartBstr sbstr;
			CheckHr(pttp->GetStrPropValue(ktptFontFamily, &sbstr));
			StrUni stuFont(sbstr.Chars());
			AppendDescPart(strDesc, FwStyledText::FontStringMarkupToUi(false, stuFont), fFirstPart);
			int val, var;
			CheckHr(pttp->GetIntPropValues(ktptFontSize, &var, &val));
			if (var != -1)
			{
				AfUtil::MakeMsrStr (val , knpt, &strb);
				AppendDescPart(strDesc, strb, fFirstPart);
			}
			CheckHr(pttp->GetIntPropValues(ktptBold, &var, &val));
			if (val == kttvForceOn || val == kttvInvert)
				AppendDescPart(strDesc, kstidBold, fFirstPart);
			CheckHr(pttp->GetIntPropValues(ktptItalic, &var, &val));
			if (val == kttvForceOn || val == kttvInvert)
				AppendDescPart(strDesc, kstidItalic, fFirstPart);
			CheckHr(pttp->GetIntPropValues(ktptSuperscript, &var, &val));
			if (val == kssvSuper)
				AppendDescPart(strDesc, kstidFfdSuperscript, fFirstPart);
			else if (val == kssvSub)
				AppendDescPart(strDesc, kstidFfdSubscript, fFirstPart);

			AppendTextIs(strDesc, (COLORREF)ReadValOrNinch(pttp, ktptForeColor),
				(COLORREF)ReadValOrNinch(pttp, ktptBackColor), fFirstPart);

			AppendUnderlineInfo(strDesc, (COLORREF)ReadValOrNinch(pttp, ktptUnderColor),
				ReadValOrNinch(pttp, ktptUnderline), fFirstPart);

			AppendOffsetInfo(strDesc, ReadValOrNinch(pttp, ktptOffset), fFirstPart);

			// Add info about other tabs
			int nDir = ReadValOrNinch(pttp, ktptRightToLeft);
			AddIf(strDesc, nDir == 0, kstidLeftToRight, fFirstPart);
			AddIf(strDesc, nDir == 1, kstidRightToLeft, fFirstPart);

			static const Keyval rgkeyvals[] =
			{
				{ktalLeading, kstidFpAlignLead},
				{ktalLeft, kstidFpAlignLeft},
				{ktalCenter, kstidFpAlignCenter},
				{ktalRight, kstidFpAlignRight},
				{ktalTrailing, kstidFpAlignTrail},
				{ktalJustify, kstidFpAlignJustify}, //TODO: support when in use.
				{0, 0}
			};
			AddFromList(strDesc, ReadValOrNinch(pttp, ktptAlign), rgkeyvals, fFirstPart);

			int nLeadIndent = ReadValOrNinch(pttp, ktptLeadingIndent);
			int nTrailIndent = ReadValOrNinch(pttp, ktptTrailingIndent);
			int nFirstIndent = ReadValOrNinch(pttp, ktptFirstIndent);
			if (nLeadIndent != knNinch || nTrailIndent != knNinch || nFirstIndent != knNinch)
			{
				AppendDescPart(strDesc, kstidIndentColon, fFirstPart);
				AppendMeasurement(strDesc, nLeadIndent, m_nMsrSys, kstidLeadingFmt);
				if (nFirstIndent != knNinch)
				{
					if (nFirstIndent < 0)
						AppendMeasurement(strDesc, -nFirstIndent, m_nMsrSys, kstidHangingFmt);
					else
						AppendMeasurement(strDesc, nFirstIndent, m_nMsrSys, kstidFirstLineFmt);
				}
				AppendMeasurement(strDesc, nTrailIndent, m_nMsrSys, kstidTrailingFmt);
			}
			// line spacing
			CheckHr(pttp->GetIntPropValues(ktptLineHeight, &var, &val));
			StrApp strSpacing;
			StrApp strFmt;
			if (var == ktpvMilliPoint)
			{
				if (val < 0)
					strFmt.Load(kstidFpLsExactFmt);
				else
					strFmt.Load(kstidFpLsAtLeastFmt);
				StrAppBuf strb;
				AfUtil::MakeMsrStr (val , knpt, &strb);
				strSpacing.Format(strFmt.Chars(), strb.Chars());
			}
			else if (var == ktpvRelative)
			{
				if (val >= kdenTextPropRel * 2)
					strSpacing.Load(kstidFpLsDouble);
				else if (val >= kdenTextPropRel * 3 / 2)
					strSpacing.Load(kstidFpLs15Lines);
				else
					strSpacing.Load(kstidFpLsSingle);
			}
			if (strSpacing.Length() != 0)
			{
				strFmt.Load(kstidLineSpacingFmt);
				strT.Format(strFmt.Chars(), strSpacing.Chars());
				AppendDescPart(strDesc, strT, fFirstPart);
			}

			int mpBefore = ReadValOrNinch(pttp, ktptSpaceBefore);
			int mpAfter = ReadValOrNinch(pttp, ktptSpaceAfter);
			if (mpBefore != knNinch || mpAfter != knNinch)
			{
				AppendDescPart(strDesc, kstidSpace, fFirstPart);
				AppendMeasurement(strDesc, mpBefore, knpt, kstidBeforeFmt);
				AppendMeasurement(strDesc, mpAfter, knpt, kstidAfterFmt);
			}

			int bulnum = ReadValOrNinch(pttp, ktptBulNumScheme);
			AddIf(strDesc, bulnum >= kvbnBulletBase && bulnum < kvbnBulletMax,
				kstidBulleted, fFirstPart);
			AddIf(strDesc, bulnum >= kvbnNumberBase && bulnum < kvbnNumberMax,
				kstidNumbered, fFirstPart);

			int mpBTop = ReadValOrNinch(pttp, ktptBorderTop);
			int mpBB = ReadValOrNinch(pttp, ktptBorderBottom);
			int mpBL = ReadValOrNinch(pttp, ktptBorderLeading);
			int mpBTr = ReadValOrNinch(pttp, ktptBorderTrailing);

			if (mpBTop != knNinch || mpBB != knNinch || mpBL != knNinch || mpBTr != knNinch)
			{
				AppendDescPart(strDesc, kstidBorderColon, fFirstPart);
				int clrBorder = ReadValOrNinch(pttp, ktptBorderColor);
				bool fFirstBorder = true;
				if (clrBorder != knNinch)
				{
					StrApp strClr;
					strClr.Load(g_ct.GetColorRid(g_ct.GetIndexFromColor(clrBorder)));
					strDesc.Append(strClr.Chars());
					fFirstBorder = false;
				}
				AppendBorderInfo(strDesc, mpBTop, kstidTopBdrFmt, fFirstBorder);
				AppendBorderInfo(strDesc, mpBB, kstidBottomBdrFmt, fFirstBorder);
				AppendBorderInfo(strDesc, mpBL, kstidLeadingBdrFmt, fFirstBorder);
				AppendBorderInfo(strDesc, mpBTr, kstidTrailingBdrFmt, fFirstBorder);
			}


			// Add info about writing-system overrides of font info.
			Vector<int> vwsSoFar;


			// Get the appropropriate writing system factory.
			ILgWritingSystemFactoryPtr qwsf;
			AssertPtr(m_pafsd);
			m_pafsd->GetLgWritingSystemFactory(&qwsf);
			AssertPtr(qwsf);
		//-		IWritingSystemPtr qws;

			// Each iteration of this loop processes information about one writing system.
			SmartBstr sbstrCharStyles;
			CheckHr(pttp->GetStrPropValue(kspWsStyle, &sbstrCharStyles));
			if (sbstrCharStyles.Length())
			{
				FwStyledText::DecodeFontPropsString(sbstrCharStyles, m_vesi, vwsSoFar);

				SmartBstr sbstrWs;
				StrApp strWs;
				int wsUser;
				CheckHr(qwsf->get_UserWs(&wsUser));
				SmartBstr sbstrAbbr;
				for (int iesi = 0; iesi < m_vesi.Size(); iesi++)
				{
					WsStyleInfo & esi = m_vesi[iesi];
					if (vwsSoFar[iesi] == 0)
						continue;		// Ignore writing system set to 0.
					fFirstPart = true;
					StrApp strT;
					StrApp strT2;
					strT.Format(_T("\n"));
					// Use the abbreviation in the user ws if it exists.
					// else try for an abbreviation in each ws in m_vwsProj in turn,
					// else use the ICU locale name as a last resort.
					IWritingSystemPtr qws;
					CheckHr(qwsf->GetStrFromWs(vwsSoFar[iesi], &sbstrWs));
					CheckHr(qwsf->get_Engine(sbstrWs, &qws));
					CheckHr(qws->get_Abbr(wsUser, &sbstrAbbr));
					if (sbstrAbbr.Length() == 0)
					{
						for (int iws = 0; iws < m_vwsProj.Size(); ++iws)
						{
							CheckHr(qws->get_Abbr(m_vwsProj[iws], &sbstrAbbr));
							if (sbstrAbbr.Length() != 0)
								break;
						}
					}
					if (sbstrAbbr.Length() == 0)
						strWs.Assign(sbstrWs.Chars(), sbstrWs.Length());
					else
						strWs.Assign(sbstrAbbr.Chars(), sbstrAbbr.Length());
					strT2.Format(_T("%s: "), strWs.Chars());
					if (strT2 == _T("___: "))
						strT2.Load(kctidFgUnknown);
					strT.Append(strT2);
					strDesc.Append (strT);
					AppendDescPart(strDesc,
						FwStyledText::FontStringMarkupToUi(false, esi.m_stuFontFamily),
						fFirstPart);
					if (esi.m_mpSize != knNinch)
					{
						AfUtil::MakeMsrStr (esi.m_mpSize , knpt, &strb);
						AppendDescPart(strDesc, strb, fFirstPart);
					}
					if (esi.m_fBold == kttvForceOn || esi.m_fBold == kttvInvert)
						AppendDescPart(strDesc, kstidBold, fFirstPart);
					if (esi.m_fItalic == kttvForceOn || esi.m_fItalic == kttvInvert)
						AppendDescPart(strDesc, kstidItalic, fFirstPart);
					if (esi.m_ssv == kssvSuper)
						AppendDescPart(strDesc, kstidFfdSuperscript, fFirstPart);
					else if (esi.m_ssv == kssvSub)
						AppendDescPart(strDesc, kstidFfdSubscript, fFirstPart);
					AppendTextIs(strDesc, esi.m_clrFore, esi.m_clrBack, fFirstPart);

					AppendUnderlineInfo(strDesc, esi.m_clrUnder, esi.m_unt, fFirstPart);

					AppendOffsetInfo(strDesc, esi.m_mpOffset, fFirstPart);
				} // 'for' loop
			}
		}
		::SetDlgItemText(m_hwnd, kctidFgDescription, strDesc.Chars());
// **************************************
	}
	catch(...)
	{
		m_fSuppressLossOfFocus = false;
		throw;
	}
	m_fSuppressLossOfFocus = false;
} //:> FmtGenDlg::SetDialogValues.
コード例 #8
0
/*----------------------------------------------------------------------------------------------
	Write an integer-valued text property in XML format.

	@param pstrm Pointer to an IStream for output.
	@param tpt
	@param nVar
	@param nVal
----------------------------------------------------------------------------------------------*/
void FwXml::WriteIntTextProp(IStream * pstrm, ILgWritingSystemFactory * pwsf, int tpt, int nVar,
	int nVal)
{
	AssertPtr(pstrm);
	AssertPtr(pwsf);

	switch (tpt)
	{
	case ktptBackColor:
		FormatToStream(pstrm, " backcolor=\"%s\"", ColorName(nVal));
		break;
	case ktptBold:
		FormatToStream(pstrm, " bold=\"%s\"", ToggleValueName((byte)nVal));
		break;
	case ktptWs:
		if (nVal == 0)
		{
			Assert(nVar == 0);
		}
		else
		{
			SmartBstr sbstrWs;
			CheckHr(pwsf->GetStrFromWs(nVal, &sbstrWs));
			if (!sbstrWs.Length())
				ThrowInternalError(E_INVALIDARG, "Writing system invalid for <Run ws>");
			FormatToStream(pstrm, " ws=\"", nVal);
			WriteXmlUnicode(pstrm, sbstrWs.Chars(), sbstrWs.Length());
			FormatToStream(pstrm, "\"", nVal);
		}
		break;
	case ktptBaseWs:
		if (nVal == 0)
		{
			Assert(nVar == 0);
		}
		else
		{
			SmartBstr sbstrWs;
			CheckHr(pwsf->GetStrFromWs(nVal, &sbstrWs));
			if (!sbstrWs.Length())
				ThrowInternalError(E_INVALIDARG, "Writing system invalid for <Run wsBase>");
			FormatToStream(pstrm, " wsBase=\"", nVal);
			WriteXmlUnicode(pstrm, sbstrWs.Chars(), sbstrWs.Length());
			FormatToStream(pstrm, "\"", nVal);
		}
		break;
	case ktptFontSize:
		FormatToStream(pstrm, " fontsize=\"%d\"", nVal);
		if (nVar != ktpvDefault)
			FormatToStream(pstrm, " fontsizeUnit=\"%s\"", PropVarName(nVar));
		break;
	case ktptForeColor:
		FormatToStream(pstrm, " forecolor=\"%s\"", ColorName(nVal));
		break;
	case ktptItalic:
		FormatToStream(pstrm, " italic=\"%s\"", ToggleValueName((byte)nVal));
		break;
	case ktptOffset:
		FormatToStream(pstrm, " offset=\"%d\"", nVal);
		FormatToStream(pstrm, " offsetUnit=\"%s\"",	PropVarName(nVar));
		break;
	case ktptSuperscript:
		FormatToStream(pstrm, " superscript=\"%s\"", SuperscriptValName((byte)nVal));
		break;
	case ktptUnderColor:
		FormatToStream(pstrm, " undercolor=\"%s\"", ColorName(nVal));
		break;
	case ktptUnderline:
		FormatToStream(pstrm, " underline=\"%s\"", UnderlineTypeName((byte)nVal));
		break;
	case ktptSpellCheck:
		FormatToStream(pstrm, " spellcheck=\"%s\"", SpellingModeName((byte)nVal));
		break;

	//	Paragraph-level properties:

	case ktptAlign:
		FormatToStream(pstrm, " align=\"%s\"", AlignmentTypeName((byte)nVal));
		break;
	case ktptFirstIndent:
		FormatToStream(pstrm, " firstIndent=\"%d\"", nVal);
		break;
	case ktptLeadingIndent:
		FormatToStream(pstrm, " leadingIndent=\"%d\"", nVal);
		break;
	case ktptTrailingIndent:
		FormatToStream(pstrm, " trailingIndent=\"%d\"", nVal);
		break;
	case ktptSpaceBefore:
		FormatToStream(pstrm, " spaceBefore=\"%d\"", nVal);
		break;
	case ktptSpaceAfter:
		FormatToStream(pstrm, " spaceAfter=\"%d\"", nVal);
		break;
	case ktptTabDef:
		FormatToStream(pstrm, " tabDef=\"%d\"", nVal);
		break;
	case ktptLineHeight:
		FormatToStream(pstrm, " lineHeight=\"%d\"", abs(nVal));
		FormatToStream(pstrm, " lineHeightUnit=\"%s\"",	PropVarName(nVar));
		Assert(nVal >= 0 || nVar == ktpvMilliPoint);
		if (nVar == ktpvMilliPoint)
		{
			// negative means "exact" internally.  See FWC-20.
			FormatToStream(pstrm, " lineHeightType=\"%s\"", nVal < 0 ? "exact" : "atLeast");
		}
		break;
	case ktptParaColor:
		FormatToStream(pstrm, " paracolor=\"%s\"", ColorName(nVal));
		break;

	//	Properties from the views subsystem:

	case ktptRightToLeft:
		FormatToStream(pstrm, " rightToLeft=\"%d\"", nVal);
		break;
	case ktptPadLeading:
		FormatToStream(pstrm, " padLeading=\"%d\"", nVal);
		break;
	case ktptPadTrailing:
		FormatToStream(pstrm, " padTrailing=\"%d\"", nVal);
		break;
	// Not the other margins: they are duplicated by FirstIndent etc.
	case ktptMarginTop:
		FormatToStream(pstrm, " MarginTop=\"%d\"", nVal);
		break;
	case ktptPadTop:
		FormatToStream(pstrm, " padTop=\"%d\"", nVal);
		break;
	case ktptPadBottom:
		FormatToStream(pstrm, " padBottom=\"%d\"", nVal);
		break;

	case ktptBorderTop:
		FormatToStream(pstrm, " borderTop=\"%d\"", nVal);
		break;
	case ktptBorderBottom:
		FormatToStream(pstrm, " borderBottom=\"%d\"", nVal);
		break;
	case ktptBorderLeading:
		FormatToStream(pstrm, " borderLeading=\"%d\"", nVal);
		break;
	case ktptBorderTrailing:
		FormatToStream(pstrm, " borderTrailing=\"%d\"", nVal);
		break;
	case ktptBorderColor:
		FormatToStream(pstrm, " borderColor=\"%s\"", ColorName(nVal));
		break;

	case ktptBulNumScheme:
		FormatToStream(pstrm, " bulNumScheme=\"%d\"", nVal);
		break;
	case ktptBulNumStartAt:
		FormatToStream(pstrm, " bulNumStartAt=\"%d\"", nVal == INT_MIN ? 0 : nVal);
		break;

	case ktptDirectionDepth:
		FormatToStream(pstrm, " directionDepth=\"%d\"", nVal);
		break;
	case ktptKeepWithNext:
		FormatToStream(pstrm, " keepWithNext=\"%d\"", nVal);
		break;
	case ktptKeepTogether:
		FormatToStream(pstrm, " keepTogether=\"%d\"", nVal);
		break;
	case ktptHyphenate:
		FormatToStream(pstrm, " hyphenate=\"%d\"", nVal);
		break;
	case ktptWidowOrphanControl:
		FormatToStream(pstrm, " widowOrphan=\"%d\"", nVal);
		break;
	case ktptMaxLines:
		FormatToStream(pstrm, " maxLines=\"%d\"", nVal);
		break;
	case ktptCellBorderWidth:
		FormatToStream(pstrm, " cellBorderWidth=\"%d\"", nVal);
		break;
	case ktptCellSpacing:
		FormatToStream(pstrm, " cellSpacing=\"%d\"", nVal);
		break;
	case ktptCellPadding:
		FormatToStream(pstrm, " cellPadding=\"%d\"", nVal);
		break;
	case ktptEditable:
		FormatToStream(pstrm, " editable=\"%s\"", EditableName(nVal));
		break;
	case ktptSetRowDefaults:
		FormatToStream(pstrm, " setRowDefaults=\"%d\"", nVal);
		break;
	case ktptRelLineHeight:
		FormatToStream(pstrm, " relLineHeight=\"%d\"", nVal);
		break;
	case ktptTableRule:
		// Ignore this view-only property.
		break;
	default:
		break;
	}
}
コード例 #9
0
DEFINE_THIS_FILE

/*----------------------------------------------------------------------------------------------
	Write the given string, which encodes a group of writing-system styles, to WorldPad
	XML format.

	@param pstrm Pointer to an IStream for output.
	@param bstrWsStyles
	@param cchIndent Number of spaces to indent the XML output.

	This code must be kept in sync with FwStyledText::DecodeFontPropsString()!
----------------------------------------------------------------------------------------------*/
void FwXml::WriteWsStyles(IStream * pstrm, ILgWritingSystemFactory * pwsf, BSTR bstrWsStyles,
	int cchIndent)
{
	AssertPtr(pstrm);
	AssertPtr(pwsf);
	Assert(cchIndent >= 0);

	Vector<char> vchIndent;
	vchIndent.Resize(cchIndent + 1);	// new elements are zero initialized.
	memset(vchIndent.Begin(), ' ', cchIndent);
	Vector<WsStyleInfo> vesi;
	Vector<int> vws;
	FwStyledText::DecodeFontPropsString(bstrWsStyles, vesi, vws);
	if (vesi.Size())
	{
		FormatToStream(pstrm, "%s<WsStyles9999>%n", vchIndent.Begin());
		for (int iv = 0; iv < vesi.Size(); ++iv)
		{
			SmartBstr sbstrWs;
			CheckHr(pwsf->GetStrFromWs(vesi[iv].m_ws, &sbstrWs));
			if (!sbstrWs.Length())
			{
				// We don't want WorldPad writing invalid XML!
				// ThrowInternalError(E_INVALIDARG, "Writing system invalid for <WsProp ws>");
#if 99
				::MessageBoxA(NULL, "Writing system invalid for <WsProp ws>", "DEBUG!", MB_OK);
#endif
				::OutputDebugStringA("Writing system invalid for <WsProp ws>");
				continue;
			}
			FormatToStream(pstrm, "%s%s<WsProp ws=\"",
				vchIndent.Begin(), cchIndent ? "  " : "");
			WriteXmlUnicode(pstrm, sbstrWs.Chars(), sbstrWs.Length());
			FormatToStream(pstrm, "\"");
			if (vesi[iv].m_stuFontFamily.Length())
				FwXml::WriteStrTextProp(pstrm, ktptFontFamily, vesi[iv].m_stuFontFamily.Bstr());
			if (vesi[iv].m_stuFontVar.Length())
				FwXml::WriteStrTextProp(pstrm, ktptFontVariations,
					vesi[iv].m_stuFontVar.Bstr());
			if (vesi[iv].m_mpSize != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptFontSize, ktpvMilliPoint,
					vesi[iv].m_mpSize);
			if (vesi[iv].m_fBold != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptBold, ktpvEnum, vesi[iv].m_fBold);
			if (vesi[iv].m_fItalic != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptItalic, ktpvEnum, vesi[iv].m_fItalic);
			if (vesi[iv].m_ssv != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptSuperscript, ktpvEnum, vesi[iv].m_ssv);
			if (vesi[iv].m_clrFore != (COLORREF)knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptForeColor, ktpvDefault,
					vesi[iv].m_clrFore);
			if (vesi[iv].m_clrBack != (COLORREF)knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptBackColor, ktpvDefault,
					vesi[iv].m_clrBack);
			if (vesi[iv].m_clrUnder != (COLORREF)knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptUnderColor, ktpvDefault,
					vesi[iv].m_clrUnder);
			if (vesi[iv].m_unt != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptUnderline, ktpvEnum, vesi[iv].m_unt);
			if (vesi[iv].m_mpOffset != knNinch)
				FwXml::WriteIntTextProp(pstrm, pwsf, ktptOffset, ktpvMilliPoint,
					vesi[iv].m_mpOffset);
			FormatToStream(pstrm, " />%n");
		}
		FormatToStream(pstrm, "%s</WsStyles9999>%n", vchIndent.Begin());
	}
}