1 // SetProperties.cpp 2 3 #include "StdAfx.h" 4 5 #include "../../../Common/MyCom.h" 6 #include "../../../Common/MyString.h" 7 #include "../../../Common/StringToInt.h" 8 9 #include "../../../Windows/PropVariant.h" 10 11 #include "../../Archive/IArchive.h" 12 13 #include "SetProperties.h" 14 15 using namespace NWindows; 16 using namespace NCOM; 17 18 static void ParseNumberString(const UString &s, NCOM::CPropVariant &prop) 19 { 20 const wchar_t *end; 21 UInt64 result = ConvertStringToUInt64(s, &end); 22 if (*end != 0 || s.IsEmpty()) 23 prop = s; 24 else if (result <= (UInt32)0xFFFFFFFF) 25 prop = (UInt32)result; 26 else 27 prop = result; 28 } 29 30 HRESULT SetProperties(IUnknown *unknown, const CObjectVector<CProperty> &properties) 31 { 32 if (properties.IsEmpty()) 33 return S_OK; 34 CMyComPtr<ISetProperties> setProperties; 35 unknown->QueryInterface(IID_ISetProperties, (void **)&setProperties); 36 if (!setProperties) 37 return S_OK; 38 39 UStringVector realNames; 40 CPropVariant *values = new CPropVariant[properties.Size()]; 41 try 42 { 43 unsigned i; 44 for (i = 0; i < properties.Size(); i++) 45 { 46 const CProperty &property = properties[i]; 47 NCOM::CPropVariant propVariant; 48 UString name = property.Name; 49 if (property.Value.IsEmpty()) 50 { 51 if (!name.IsEmpty()) 52 { 53 wchar_t c = name.Back(); 54 if (c == L'-') 55 propVariant = false; 56 else if (c == L'+') 57 propVariant = true; 58 if (propVariant.vt != VT_EMPTY) 59 name.DeleteBack(); 60 } 61 } 62 else 63 ParseNumberString(property.Value, propVariant); 64 realNames.Add(name); 65 values[i] = propVariant; 66 } 67 CRecordVector<const wchar_t *> names; 68 for (i = 0; i < realNames.Size(); i++) 69 names.Add((const wchar_t *)realNames[i]); 70 71 RINOK(setProperties->SetProperties(&names.Front(), values, names.Size())); 72 } 73 catch(...) 74 { 75 delete []values; 76 throw; 77 } 78 delete []values; 79 return S_OK; 80 } 81