简体   繁体   中英

C++ load image from url using poco, convert to unsigned char*

I'm learning to use Poco to load an image from web. The code I found:

        std::string path(uri.getPathAndQuery());
        if (path.empty())
            path = "/";
        const Poco::Net::Context::Ptr context = new Poco::Net::Context(
                Poco::Net::Context::CLIENT_USE, "", "", "",
                Poco::Net::Context::VERIFY_NONE, 9, false,
                "ALL:!ADH:!LOW:!EXP:!MD5:@STRENGTH");
        Poco::Net::HTTPSClientSession session(uri.getHost(), uri.getPort(), context);
        Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_GET, path, Poco::Net::HTTPMessage::HTTP_1_1);
        Poco::Net::HTTPResponse response;

        bool isSuccess = false;
        session.sendRequest(request);
        std::istream &rs = session.receiveResponse(response);
        std::cout << response.getStatus() << " " << response.getReason() << std::endl;
        if (response.getStatus() != Poco::Net::HTTPResponse::HTTP_UNAUTHORIZED) {
            std::ofstream ofs("Poco_banner.png", std::fstream::binary);
            Poco::StreamCopier::copyStream(rs, ofs);
            isSuccess = true;
        } else {
            //it went wrong ?
            isSuccess = false;
        }

creates a local copy of the file. And I need this to have the same functionality as stbi_load:

unsigned char* localBuffer = stbi_load(path.c_str(), &width, &height, &bpp, 4);

ie do not download, but create an unsigned char* localBuffer with a known width and height from this online image. Thank you.

You can simply replace the std::ofstream with an std:stringstream or a Poco::MemoryOutputStream if you know the size ahead of time. Poco does not however have anything to deal with images. So you will need to use a different library to extract width and height. Or you can have a look at this answer https://stackoverflow.com/a/16725066/1366591 to manually extract width and height. Use Poco::ByteOrder to convert from big to little endian.

This solution worked:

Poco::URI uri(path);
std::string path(uri.getPathAndQuery());
if (path.empty())
    path = "/";
const Poco::Net::Context::Ptr context = new Poco::Net::Context(
                    Poco::Net::Context::CLIENT_USE, "", "", "",
                    Poco::Net::Context::VERIFY_NONE, 9, false,
                    "ALL:!ADH:!LOW:!EXP:!MD5:@STRENGTH");
Poco::Net::HTTPSClientSession session(uri.getHost(), uri.getPort(), context);
Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_GET, path, Poco::Net::HTTPMessage::HTTP_1_1);
Poco::Net::HTTPResponse response;

bool isSuccess = false;
session.sendRequest(request);
std::istream &rs = session.receiveResponse(response);
std::cerr << response.getStatus() << " " << response.getReason() << std::endl;
            
if (response.getStatus() != Poco::Net::HTTPResponse::HTTP_UNAUTHORIZED) {
     std:string ss;
     Poco::StreamCopier::copyToString64(rs, ss);
     std::cerr << "string length " << ss.size() << endl;
     std::vector<unsigned char> buffer(ss.begin(), ss.end());
                
     m_localBuffer = stbi_load_from_memory(buffer.data(), (int)buffer.size(), &m_width, &m_height, &m_type, 0);
     std::cerr << "width: " << m_width << ", height: " << m_height << ", type: " << m_type << "\n";
                
     isSuccess = true;
} 
else 
{
     //it went wrong ?
     isSuccess = false;
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM