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