zip/unzip z wykorzystaniem win32 api

0

Witam!
W systemach Win XP, 2000, Vista można pakować i rozpakowywać pliki.
Czy system wykorzystuje do tego gotową bibliotekę?
Czy można to robić z wykorzystaniem API np. ładując właściwą bibliotekę i wykorzystując jej funkcje?
Jeśli tak, to jak ta biblioteka sie nazywa(chodzi mi o załadowanie jej) i jakich funkcji, struktur używa?
Chciałbym uniknąć wykorzystanie zew. programów (WinRar'a, ZIP-7).
Pozdrawiam

0

Biblioteka to zipfldr.dll, nie wiem czy cokolwiek eksportuje, ale możesz poszukać info. Możesz też po prostu sam zaimplementować obsługę zipa zaczynając od NULL.

0

proponuje jednak uzywac bibliotek innych dostawcow niz ta wbudowana w windoze.. szczerze, wolniejszego zippera/unzipera jeszcze nie widzialem

0

zipfldr.dll eksportuje interfejsy shellowe, takie jak IShellFolder, więc wszelakie operacje na archiwach są na tyle możliwe, na ile znasz programowanie winshell'a.

Sposób na wylistowanie plików i folderów z pierwszego poziomu znajdziesz w 10-tym poście na stronie http://forum.sources.ru/index.php?showtopic=201707.
Poniżej wstawiłem demo wypakowujące pliki z roota zipa do %temp%\zipdemo
// możliwe małe braki kompatybilości z c++

void ExtractRootFiles()
{
    IShellFolder *psfZip;
    IShellFolder *psfParent;
    ITEMIDLIST *pidl = ILCreateFromPath("D:\\download\\myzip.zip");

    if (pidl)
    {
        ITEMIDLIST *pidlChild;
        if (!SHBindToParent(pidl, IID_IShellFolder, (void**)&psfParent, &pidlChild))
        {
            psfParent->BindToObject(pidlChild, NULL, IID_IShellFolder, (void**)&psfZip);

            char szDisplayName[MAX_PATH];
            char szSavePath[MAX_PATH];

            GetTempPath(MAX_PATH, szSavePath);
            strcat(szSavePath, "zipdemo");
            CreateDirectory(szSavePath, NULL);
            strcat(szSavePath, "\\");
            char *pFileName = &szSavePath[strlen(szSavePath)];

            IEnumIDList *penum;
            psfZip->EnumObjects(NULL, SHCONTF_NONFOLDERS, &penum);

            ULONG celtFetched;
            ITEMIDLIST *pidlItems;
            while (!penum->Next(1, &pidlItems, &celtFetched) && celtFetched)
            {
                STRRET strDispName;
                psfZip->GetDisplayNameOf(pidlItems, SHGDN_INFOLDER, &strDispName);
                StrRetToBuf(&strDispName, pidlItems, szDisplayName, MAX_PATH);
                printf(" - %s\n", szDisplayName);

                IDataObject *dataobj;
                if (!psfZip->GetUIObjectOf(0, 1, &pidlItems, IID_IDataObject, 0, (void**)&dataobj))
                {
                    int FormatBits = 0;
                    FORMATETC fmt;
                    FORMATETC fmtDescriptor;
                    FORMATETC fmtContents;
                    STGMEDIUM mediumContents;
                    STGMEDIUM mediumDescriptor;

                    UINT CF_FILEDESCRIPTORA = RegisterClipboardFormat(CFSTR_FILEDESCRIPTORA);
                    UINT CF_FILEDESCRIPTORW = RegisterClipboardFormat(CFSTR_FILEDESCRIPTORW);
                    UINT CF_FILECONTENTS = RegisterClipboardFormat(CFSTR_FILECONTENTS);

                    IEnumFORMATETC *formats;
                    dataobj->EnumFormatEtc(DATADIR_GET, &formats);

                    while (!formats->Next(1, &fmt, &celtFetched) && celtFetched)
                    {
                        if ((!(FormatBits & 1)) && ((fmt.cfFormat == CF_FILEDESCRIPTORA) || (fmt.cfFormat == CF_FILEDESCRIPTORW)))
                        {
                            FormatBits |= 1;
                            MoveMemory(&fmtDescriptor, &fmt, sizeof(FORMATETC));
                        }
                        else if ((!(FormatBits & 2)) && (fmt.cfFormat == CF_FILECONTENTS))
                        {
                            FormatBits |= 2;
                            MoveMemory(&fmtContents, &fmt, sizeof(FORMATETC));
                        }
                    }

                    formats->Release();
                    fmtContents.lindex = 0;
                    // FormatBits musi być równe 3

                    hr = dataobj->GetData(&fmtDescriptor, &mediumDescriptor);

                    if (!hr)
                    {
                        FILEGROUPDESCRIPTOR *pdsc = GlobalLock(mediumDescriptor.hGlobal);
                        LARGE_INTEGER liSize;
                        liSize.LowPart = pdsc->fgd[0].nFileSizeLow;
                        liSize.HighPart = pdsc->fgd[0].nFileSizeHigh;

                        GlobalUnlock(mediumDescriptor.hGlobal);
                        ReleaseStgMedium(&mediumDescriptor);

                        hr = dataobj->GetData(&fmtContents, &mediumContents);

                        if (!hr)
                        {
                            // zapisz plik w \temp\zipdemo\szDisplayName
                            strcpy(pFileName, szDisplayName);

                            IStream *file;
                            hr = SHCreateStreamOnFile(szSavePath, STGM_READ | STGM_WRITE | STGM_CREATE, &file);

                            mediumContents.pstm->CopyTo(file, liSize, NULL, NULL);
                            file->Release();

                            GlobalUnlock(mediumDescriptor.hGlobal);
                            ReleaseStgMedium(&mediumContents);
                        }
                    }
                    dataobj->Release();
                }
                CoTaskMemFree(pidlItems);
            }
            psfParent->Release();
            CoTaskMemFree(pidlChild);
        }
        CoTaskMemFree(pidl);
    }
}

//q:pousuwalem troche whitespaceow zeby lepiej sie miescilo

0

Witam,
Po poprawieniu dosyć sporej ilości błędów, lista plików w zipie wyświetla mi się w konsoli. Ale kombinuję i kombinuję i nie mogę wykombinować jak go teraz wypakować... Otóż wszystkie funkcje zwracają S_OK, a nawet pusty plik nie zostaje stworzony... Doszedłem już, że wina leży gdzieś przy odczytu z 'mediumContents.pstm'. Help...

0

wystarczy podpiąć dll-kę,
np 7-zip.dll ma własny dialogbox wraz z progress-em

0

Chyba się nie zrozumieliśmy...
Skopiowałem powyższy kod do VSC++ 2008 Express, zacząłem poprawiać błędy - na początku kompilatora, potem poszczególne funkcje... (Bo Od razu pierwszy if był pomijany -> funkcja zwracała błąd).
Eh, oto mój, poprawiony, kod:

// stdafx.h : include file for standard system include files,
// or project specific include files that are used frequently, but
// are changed infrequently
//

#pragma once

//#include <vcl.h>
#pragma hdrstop

//#pragma argsused
//#pragma   link   "shell32.lib"
//#pragma   link   "shlwapi.lib"


#include <shlobj.h>
#include <shlwapi.h>
#include <iostream>
#include <Objbase.h>

// TODO: reference additional headers your program requires here
// unzip.cpp : main project file.

#include "stdafx.h"
#define NO_WIN32_LEAN_AND_MEAN

using namespace System;
using namespace std;

void ExtractRootFiles()
{
	printf(" Let's start\n");
    IShellFolder *psfZip = NULL;
    IShellFolder *psfParent = NULL;
    LPITEMIDLIST pidl = ILCreateFromPathA(LPCSTR("C:\\test.zip"));

	printf(" 1.if\n");

    if (pidl) {
		printf(" 2.ini...\n");
        LPITEMIDLIST pidlChild;
		LPCITEMIDLIST pidlChild2 = NULL;

        if (!SHBindToParent(pidl, IID_IShellFolder, (void**)&psfParent, &pidlChild2)) {
			if (pidlChild2 == NULL) {printf("  Blad!!\n"); return;}

			printf(" 3.szukanie?...\n");
			pidlChild = (LPITEMIDLIST) pidlChild2;
			//CoTaskMemFree(pidlChild2);

            psfParent->BindToObject(pidlChild, NULL, IID_IShellFolder, (void**)&psfZip);
			if (psfZip == NULL) {printf("  Blad!!\n"); return;}

            char szDisplayName[MAX_PATH];
            /*char szSavePath[MAX_PATH];
			szSavePath[0]= 'C';
			szSavePath[1]= ':';
			szSavePath[2]= '\\';
            strcat_s(szSavePath, "test");*/
			string szSavePath ("C:\\test2\\");
			//LPSECURITY_ATTRIBUTES attr = NULL;
			//if (CreateDirectory(LPCTSTR("C:\\test2"), attr)) {printf("   true\n");}
			//else printf("   false\n");
            //szSavePath.append("\\");
			
			printf("   Sciezka: %s\n", szSavePath.c_str());
            //char *pFileName = &szSavePath[strlen(szSavePath.c_str())];
			//if (*pFileName == NULL) {printf("Blad!\n");}
			//printf(" 4.do katalogu\n");

            IEnumIDList *penum = NULL;
			//IShellFolder *penum2 = NULL;

			/*psfZip->BindToObject(pidlChild, NULL, IID_IShellFolder, (void**)&penum);
			if (penum == NULL) {printf("  Blad!!\n"); return;}*/

            psfZip->EnumObjects(NULL, SHCONTF_NONFOLDERS, &penum);
			if (penum == NULL) {printf("  Blad!!\n"); return;}

			/*penum2->EnumObjects(NULL, SHCONTF_NONFOLDERS, &penum);
			if (penum == NULL) {printf("  Blad!!\n"); return;}*/

            ULONG celtFetched;
            ITEMIDLIST *pidlItems = NULL;

			printf(" 4.pliki:\n");
			HRESULT hr;
			//hr = penum->Next((ULONG)i, &pidlItems, &celtFetched);
			//if (hr == S_FALSE) {printf("  ==S_FALSE\n");}
            
			while (!penum->Next(1, &pidlItems, &celtFetched) && celtFetched+1) {
				printf("\n");
				//printf("   while:\n");
				//getchar();
                STRRET strDispName;
				//psfZip->BindToObject`
                psfZip->GetDisplayNameOf(LPCITEMIDLIST(pidlItems), SHGDN_INFOLDER, &strDispName);
                StrRetToBuf(&strDispName, pidlItems, LPWSTR(szDisplayName), MAX_PATH);
				printf(" - ");
				int i= 0;
				while (szDisplayName[2*i] != 0) {
					printf("%c", szDisplayName[2*i]); 
					szDisplayName[i]= szDisplayName[2*i];
					i++;
				}
				szDisplayName[i]= '\0';
                printf("\n");

                IDataObject *dataobj;
				
				hr = psfZip->GetUIObjectOf(0, 1, (LPCITEMIDLIST*)(&pidlItems), IID_IDataObject, 0, IID_PPV_ARGS_Helper(&dataobj));
				if (hr != S_OK) {printf("   blad!\n");}
                if (!psfZip->GetUIObjectOf(0, 1, (LPCITEMIDLIST*)(&pidlItems), IID_IDataObject, 0, IID_PPV_ARGS_Helper(&dataobj))) {
                    printf("    if:\n");
					int FormatBits = 0;
                    FORMATETC fmt;
                    FORMATETC fmtDescriptor;
                    FORMATETC fmtContents;
                    STGMEDIUM mediumContents;
                    STGMEDIUM mediumDescriptor;

                    UINT CF_FILEDESCRIPTORA = RegisterClipboardFormat(CFSTR_FILEDESCRIPTORA);
                    UINT CF_FILEDESCRIPTORW = RegisterClipboardFormat(CFSTR_FILEDESCRIPTORW);
                    UINT CF_FILECONTENTS = RegisterClipboardFormat(CFSTR_FILECONTENTS);

                    IEnumFORMATETC *formats;
                    hr = dataobj->EnumFormatEtc(DATADIR_GET, &formats);
					if (hr != S_OK) {printf("   blad!\n");}

                    while (!formats->Next(1, &fmt, &celtFetched) && celtFetched) {
						//printf("     wh:\n");
                        if ((!(FormatBits & 1)) && ((fmt.cfFormat == CF_FILEDESCRIPTORA) || (fmt.cfFormat == CF_FILEDESCRIPTORW))) {
                            //printf("      if:\n");
							FormatBits |= 1;
                            MoveMemory(&fmtDescriptor, &fmt, sizeof(FORMATETC));
							//printf("       %d\n", FormatBits);
                        }
                        else if ((!(FormatBits & 2)) && (fmt.cfFormat == CF_FILECONTENTS)) {
							//printf("      if:\n");
                            FormatBits |= 2;
                            MoveMemory(&fmtContents, &fmt, sizeof(FORMATETC));
							//printf("       %d\n", FormatBits);
                        }
						//printf("         %d\n", fmtContents.lindex);
                    }
					if (FormatBits == 3) printf("       FormatBits... OK\n");
                    formats->Release();
                    fmtContents.lindex = 0;
                    // FormatBits musi być równe 3

                    hr = dataobj->GetData(&fmtDescriptor, &mediumDescriptor);
					//printf(": %s.\n", (char*) mediumDescriptor.lpszFileName);

                    if (!hr) {
						printf("     jadziem:\n");
                        FILEGROUPDESCRIPTOR *pdsc = (FILEGROUPDESCRIPTOR*) GlobalLock(mediumDescriptor.hGlobal);
                        ULARGE_INTEGER liSize;
                        liSize.LowPart = pdsc->fgd[0].nFileSizeLow;
                        liSize.HighPart = pdsc->fgd[0].nFileSizeHigh;

                        if (!GlobalUnlock(mediumDescriptor.hGlobal)) printf("    blad!\n");
                        ReleaseStgMedium(&mediumDescriptor);

                        hr = dataobj->GetData(&fmtContents, &mediumContents);
						//printf(": %s.\n", (char*) mediumContents.lpszFileName);
						if (hr) printf("     blad!\n");
                        if (!hr) {
                            szSavePath.append(szDisplayName);
							printf("      plik: %s.\n", szDisplayName);

                            IStream *file;
							//           
							char c[256] = "C:\\test2\\";
							strcat(c, szDisplayName);
							printf("      zapisuje plik: %s.\n", c);
                            hr = SHCreateStreamOnFile(LPCWSTR(c), STGM_READ | STGM_WRITE | STGM_CREATE, &file);
							if (hr != S_OK) printf("       Nie utworzono pliku!\n");      

							
                            if (mediumContents.pstm->CopyTo(file, liSize, NULL, NULL) == S_OK) printf("      skopiowano.\n");
							char* p;
							char** pp= &p;
							mediumContents.pstm->Read(pp, 10, NULL);
							//file->Read(p ,8, NULL);
							printf("          plik: %s...\n", &pp);

							//getchar();
							if (file->Release() == S_OK) printf("      zamknieto.\n");

                            GlobalUnlock(mediumDescriptor.hGlobal);
                            ReleaseStgMedium(&mediumContents);
                        }
                    }
                    dataobj->Release();
                }
                //CoTaskMemFree(pidlItems);
            }
            psfParent->Release();
            //CoTaskMemFree(pidlChild);
        }
        CoTaskMemFree(pidl);
    }
}

int main()
{
	//printf("start?\n");
	//getchar();
	ExtractRootFiles();

	printf("\n\n\ndone!!");
	getchar();
    return 0;
}

Każdy 'printf' z informacją sukcesu wyświetla się. Ale nawet pusty plik nie zostaje stworzony...

Gdy 'C:\test.zip' zawierał 2 pliki, to nazwy tych plików zostały wyświetlane. Gdy był spakowany folder i w nim pliki, wyświetlona została tylko nazwa tego katalogu. Potrzebuje jednak rozpakować zipa, w którym siedzą 4 katalogi, a w nich po kilkadziesiąt plików (<300KB). Z tego co się 'douczyłem' (z kodami powłoki mam pierwszy raz styczność) wystarczy jeszcze dodać jeden obiekt, ale moje intuicyjne próby nie powiodły się.
Krytykujcie...

0

Napiszmy to inaczej, używajac IShellFolder tylko chwilowo:

// extractzip.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include <shlobj.h>
#include <shlwapi.h>

#define ZIP_PATH  _T("D:\\download\\myzip.zip")
#define UNPACK_TO _T("D:\\download\\myzip")

void EnumZipFiles(IStorage *storage, TCHAR *pszTargetDir)
{
   IMalloc *memory;
   if (CoGetMalloc(1, &memory)) return;

   CreateDirectory(pszTargetDir, NULL); // sprawdź błąd

   IEnumSTATSTG *enumerator;
   if (!storage->EnumElements(0,0,0,&enumerator))
   {
      ULONG celtFetched;
      STATSTG stat;
      while (!enumerator->Next(1, &stat, &celtFetched) && celtFetched)
      {
         if (stat.pwcsName)
         {
            TCHAR *pszPath = new TCHAR[lstrlen(pszTargetDir)+wcslen(stat.pwcsName)+2];
            if (pszPath)
            {
#ifdef UNICODE
               wsprintf(pszPath, L"%s\\%s", pszTargetDir, stat.pwcsName);
#else
               wsprintf(pszPath, "%s\\%S", pszTargetDir, stat.pwcsName);
#endif
               if (stat.type == STGTY_STORAGE) // katalog
               {
                  IStorage *subfolder;
                  if (!storage->OpenStorage(stat.pwcsName, 0, STGM_READ, 0, 0, &subfolder))
                  {
                     EnumZipFiles(subfolder, pszPath);
                     subfolder->Release();
                  }
               }
               else if (stat.type == STGTY_STREAM) // plik
               {
                  _tprintf(_T("processing %s "), pszPath);

                  if (stat.cbSize.QuadPart < 1024ul)
                     _tprintf(_T("(%d bytes)\n"), stat.cbSize.LowPart);
                  else if (stat.cbSize.QuadPart < 1048576ul)
                     _tprintf(_T("(%.2f KB)\n"), (double)(stat.cbSize.LowPart/1024.0));
                  else
                     _tprintf(_T("(%.2f MB)\n"), (double)(stat.cbSize.QuadPart/1048576.0));

                  IStream *stream;
                  if (!storage->OpenStream(stat.pwcsName, 0, STGM_READ, 0, &stream))
                  {
                     IStream *file;
                     if (!SHCreateStreamOnFile(pszPath, STGM_WRITE | STGM_CREATE, &file))
                     {
                        stream->CopyTo(file, stat.cbSize, NULL, NULL);
                        file->Release();
                     }
                     stream->Release();
                  }
               }
               delete pszPath;
            }
            memory->Free(stat.pwcsName);
         }
      }
      enumerator->Release();
   }
   memory->Release();
}


void ExtractZip(TCHAR *pszZip, TCHAR *pszTargetDir)
{
   ITEMIDLIST *pidl = ILCreateFromPath(pszZip);

   if (pidl)
   {
      IShellFolder *psfParent;
      ITEMIDLIST   *pidlChild;
      if (!SHBindToParent(pidl, IID_IShellFolder, (void**)&psfParent, (LPCITEMIDLIST*)&pidlChild))
      {
         IStorage *storage;
         if (!psfParent->BindToObject(pidlChild, NULL, IID_IStorage, (void**)&storage))
         {
            EnumZipFiles(storage, pszTargetDir);
            storage->Release();
         }
         psfParent->Release();
      }
      ILFree(pidl);
   }
}


int _tmain(int argc, _TCHAR* argv[])
{
   CoInitialize(0);
   ExtractZip(ZIP_PATH, UNPACK_TO);
   CoUninitialize();
   return 0;
}
0

WIELKIE DZIĘKI!!!
Działa:

// unzip2.cpp : main project file.

// extractzip.cpp : Defines the entry point for the console application.
//

#include "stdafx.h" //pusty
#include <stdio.h>
#include <shlobj.h>
#include <shlwapi.h>
#include <windows.h>

#define ZIP_PATH  ("C:\\test.zip")
#define UNPACK_TO ("C:\\test3")

void EnumZipFiles(IStorage *storage, LPCWSTR pszTargetDir)
{
   IMalloc *memory;
   if (CoGetMalloc(1, &memory)) return;

   if (CreateDirectoryA((LPCSTR)pszTargetDir, NULL)) printf(" Folder %s utworzono.\n", pszTargetDir);     //(1.)
   else if (GetLastError() == ERROR_ALREADY_EXISTS) printf(" Folder %s juz istnial.\n", pszTargetDir);
   else printf(" Nie udalo sie utworzyc folderu %s\n", pszTargetDir);

   IEnumSTATSTG *enumerator;
   if (!storage->EnumElements(0,0,0,&enumerator))
   {
      ULONG celtFetched;
      STATSTG stat;
      while (!enumerator->Next(1, &stat, &celtFetched) && celtFetched)
      {
         if (stat.pwcsName)
         {
            TCHAR *pszPath = new TCHAR[lstrlen(pszTargetDir)+wcslen(stat.pwcsName)+2];
            if (pszPath)
            {
#ifdef UNICODE
               wsprintf(pszPath, L"%s", pszTargetDir);
#else
               wsprintf(pszPath, "%s", pszTargetDir);
#endif //tak działają powyższe funkcje... :/
				char name[256];
				name[0]= '\\';
				//strcat(name, (char*) stat.pwcsName); //nie dziala
				//{
				int i= 0;
				while (stat.pwcsName[i] != '\0') {
					name[i+1]= (char)stat.pwcsName[i];
					i++;
				}
				name[i+1]= '\0';
				// } najpewniej ;p         (2.)
				strcat((char*) pszPath, name);

               if (stat.type == STGTY_STORAGE) // katalog
               {
                  IStorage *subfolder;
                  if (!storage->OpenStorage(stat.pwcsName, 0, STGM_READ, 0, 0, &subfolder))
                  {
                     EnumZipFiles(subfolder, pszPath);
                     subfolder->Release();
                  }
               }
               else if (stat.type == STGTY_STREAM) // plik
               {
                  printf(("  processing %s  "), pszPath);

                  if (stat.cbSize.QuadPart < 1024ul)
                     printf(("(%d bytes)\n"), stat.cbSize.LowPart);
                  else if (stat.cbSize.QuadPart < 1048576ul)
                     printf(("(%.2f KB)\n"), (double)(stat.cbSize.LowPart/1024.0));
                  else
                     printf(("(%.2f MB)\n"), (double)(stat.cbSize.QuadPart/1048576.0));

                  IStream *stream;
                  if (!storage->OpenStream(stat.pwcsName, 0, STGM_READ, 0, &stream))
                  {
                     IStream *file;
                     if (!SHCreateStreamOnFileA((LPCSTR)pszPath, STGM_WRITE | STGM_CREATE, &file))
                     {
                        stream->CopyTo(file, stat.cbSize, NULL, NULL);
                        file->Release();
                     }
                     stream->Release();
                  }
               }
               delete pszPath;
            }
            memory->Free(stat.pwcsName);
         }
      }
      enumerator->Release();
   }
   memory->Release();
}


void ExtractZip(LPCWSTR pszZip, LPCWSTR pszTargetDir) {
	//printf("Let's start\n");
	printf("adres zipa:%s, adres docelowy:%s.\n\n", pszZip, pszTargetDir);
   ITEMIDLIST *pidl = ILCreateFromPathA((LPCSTR)pszZip);                     //(3.)

   if (pidl) {
      IShellFolder *psfParent;
      ITEMIDLIST   *pidlChild;
      if (!SHBindToParent(pidl, IID_IShellFolder, (void**)&psfParent, (LPCITEMIDLIST*)&pidlChild))
      {
         IStorage *storage;
         if (!psfParent->BindToObject(pidlChild, NULL, IID_IStorage, (void**)&storage))
         {
            EnumZipFiles(storage, pszTargetDir);
            storage->Release();
         }
         psfParent->Release();
      }
      ILFree(pidl);
   }
}


int main() {
   CoInitialize(0);
   ExtractZip((LPCWSTR)ZIP_PATH, (LPCWSTR)UNPACK_TO);
   CoUninitialize();

   printf("--end.\n");
   getchar();
   return 0;
}

Ale jestem głodny wiedzy: (odnośniki z kodu)
(1.) CreateDirectory: Nie działało. Na wszelkie sposoby. Dopiero CreateDirectoryA zadziałało...
(2.) #ifdef UNICODE...: też nie działało w pełni: kopiowana była tylko pierwsza zmienna, ani '\' ani druga zmienna nie była dodawana... Dopiero 'na piechotę'... ;)
(3.) ILCreateFromPath: Też nie działało. Też dopiero ILCreateFromPathA...

O co tu chodzi?? Mam wrażenie, jakby te UNICODE było włączone, a nie działało.... (bądź odwrotnie....)

0

Kod jest ok, niepotrzebnie go pozmieniałeś, wszystko przez to, że stdafx wyczyściłeś i ci TCHAR'a nie znał, po co [glowa] . Jak ci stdafx przeszkadza, to możesz <tchar.h> zaincluduować i kod sapero będzie w porząsiu. Dziwne, że ci to w ogóle zadziałało po tym rzutowaniu LPWSTR na LPSTR...

0

mi VSC++ 2008 Express Edition w 'stdafx.h' nic nie dodaje. A wyczyściłem, dokładniej przekopiowałem całość z stdafx.h do *.cpp dla jasności kodu - żeby już tego nie rozbijać. Nie wiedziałem o '<tchar.h>' więc zrobiłem tak...

Wracając do mojego pytania. Czy da się jakoś wyłączyć te UNICODE??

1 użytkowników online, w tym zalogowanych: 0, gości: 1