| 204 | } |
| 205 | |
| 206 | std::string MovieDecoder::createScaleString(const std::string& sizeString, bool maintainAspectRatio) |
| 207 | { |
| 208 | int width = -1; |
| 209 | int height = -1; |
| 210 | bool pureNumericSize = true; |
| 211 | |
| 212 | if (sizeString.empty()) { |
| 213 | return "w=0:h=0"; |
| 214 | } |
| 215 | |
| 216 | try { |
| 217 | std::regex sizeRegex(R"r(([w|h])=(-?\d+)(?::([w|h])=(-?\d+))?)r"); |
| 218 | std::smatch baseMatch; |
| 219 | if (std::regex_match(sizeString, baseMatch, sizeRegex)) { |
| 220 | if (baseMatch.size() != 3 && baseMatch.size() != 5) { |
| 221 | throw std::runtime_error("Failed to parse size string"); |
| 222 | } |
| 223 | |
| 224 | auto parseMatch = [&width, &height](std::smatch& match, size_t index) { |
| 225 | auto specifier = match[index].str(); |
| 226 | if (specifier == "w") { |
| 227 | width = std::stoi(match[index + 1].str()); |
| 228 | if (width <= 0) { |
| 229 | width = -1; |
| 230 | } |
| 231 | } else if (specifier == "h") { |
| 232 | height = std::stoi(match[index + 1].str()); |
| 233 | if (height <= 0) { |
| 234 | height = -1; |
| 235 | } |
| 236 | } |
| 237 | }; |
| 238 | |
| 239 | pureNumericSize = false; |
| 240 | if (baseMatch.size() >= 3) { |
| 241 | parseMatch(baseMatch, 1); |
| 242 | } |
| 243 | |
| 244 | if (baseMatch.size() == 5) { |
| 245 | parseMatch(baseMatch, 3); |
| 246 | } |
| 247 | } else { |
| 248 | width = std::stoi(sizeString); |
| 249 | } |
| 250 | } catch (const std::regex_error&) { |
| 251 | throw std::runtime_error("Failed to parse size string"); |
| 252 | } |
| 253 | |
| 254 | std::stringstream scale; |
| 255 | |
| 256 | if (width != -1 && height != -1) { |
| 257 | scale << "w=" << width << ":h=" << height; |
| 258 | if (maintainAspectRatio) { |
| 259 | scale << ":force_original_aspect_ratio=decrease"; |
| 260 | } |
| 261 | } else if (!maintainAspectRatio) { |
| 262 | if (width == -1) { |
| 263 | scale << "w=" << height << ":h=" << height; |