एक वीडियो को क्रॉप और आकार बदलकर एक निश्चित स्क्रीन आकार में बदलें


22

मैंने खुद यह पता लगाने की कोशिश की है, लेकिन विकल्पों का असंख्य मुझे चकित करता है।

मैं आदर्श रूप में या तो उपयोग करना चाहते हैं ffmpegया mencoder(या कुछ और, लेकिन उन दो मैं मैं काम कर रहा है पता है) एक निश्चित स्क्रीन आकार के लिए किसी भी आने वाली वीडियो कन्वर्ट करने के लिए।

यदि वीडियो इसके लिए व्यापक या बहुत छोटा है, तो वीडियो को केंद्र में रखें। यदि यह सही आकार नहीं है, तो इसे ठीक स्क्रीन आकार बनाने के लिए ऊपर या नीचे आकार बदलें।

एक MP3 ऑडियो ट्रैक के साथ XVID AVI में सटीक अंतिम चीज़ जिसकी मुझे आवश्यकता है 720x480 है।

मैंने बहुत सारे पृष्ठ दिखाए हैं कि कैसे अधिकतम रिज़ॉल्यूशन का आकार बदलना है, लेकिन मुझे उस रिज़ॉल्यूशन के लिए वीडियो की आवश्यकता है (अतिरिक्त भागों के साथ, कोई काली पट्टियाँ नहीं)।

किसी ने मुझे चलाने के लिए कमांड लाइन बता सकते हैं - या कम से कम मुझे वहाँ कुछ / सबसे अधिक तरीका है? यदि इसे कई कमांड लाइन (रन एक्स को रिज़ॉल्यूशन प्राप्त करने के लिए, इस गणना को करने के लिए और फिर उस गणना के आउटपुट के साथ वाई को चलाने की आवश्यकता है) तो मैं इसे स्क्रिप्ट कर सकता हूं।


जाहिरा तौर पर वीडियो डिवाइस Mpeg4 के साथ-साथ XVid AVI के साथ काम करता है, अगर यह आसान / बेहतर है।
एंडी जेफ्रीज

जवाबों:


19

मैं कोई ffmpeg गुरु नहीं हूँ, लेकिन इस चाल को करना चाहिए।

सबसे पहले, आप इनपुट वीडियो का आकार इस तरह प्राप्त कर सकते हैं:

ffprobe -v error -of flat=s=_ -select_streams v:0 -show_entries stream=height,width in.mp4

यथोचित हाल के ffmpeg के साथ, आप इन विकल्पों के साथ अपने वीडियो का आकार बदल सकते हैं:

ffmpeg -i in.mp4 -vf scale=720:480 out.mp4

आप करने के लिए चौड़ाई या ऊंचाई सेट कर सकते हैं -1क्रम में जाने के लिए ffmpegवीडियो पहलू अनुपात रखने का आकार बदलें। वास्तव में, -2एक बेहतर विकल्प है क्योंकि गणना मूल्य भी होना चाहिए। तो आप टाइप कर सकते हैं:

ffmpeg -i in.mp4 -vf scale=720:-2 out.mp4

एक बार जब आप वीडियो प्राप्त करते हैं, तो यह उम्मीद 720x480से बड़ा हो सकता है क्योंकि आप ffmpegऊंचाई की गणना करते हैं, इसलिए आपको इसे फसल करना होगा। इसे इस तरह किया जा सकता है:

ffmpeg -i in.mp4 -filter:v "crop=in_w:480" out.mp4

अंत में, आप इस तरह से एक स्क्रिप्ट लिख सकते हैं (आसानी से अनुकूलित किया जा सकता है, लेकिन मैंने इसे सुगमता के लिए रखा है):

#!/bin/bash

FILE="/tmp/test.mp4"
TMP="/tmp/tmp.mp4"
OUT="/tmp/out.mp4"

OUT_WIDTH=720
OUT_HEIGHT=480

# Get the size of input video:
eval $(ffprobe -v error -of flat=s=_ -select_streams v:0 -show_entries stream=height,width ${FILE})
IN_WIDTH=${streams_stream_0_width}
IN_HEIGHT=${streams_stream_0_height}

# Get the difference between actual and desired size
W_DIFF=$[ ${OUT_WIDTH} - ${IN_WIDTH} ]
H_DIFF=$[ ${OUT_HEIGHT} - ${IN_HEIGHT} ]

# Let's take the shorter side, so the video will be at least as big
# as the desired size:
CROP_SIDE="n"
if [ ${W_DIFF} -lt ${H_DIFF} ] ; then
  SCALE="-2:${OUT_HEIGHT}"
  CROP_SIDE="w"
else
  SCALE="${OUT_WIDTH}:-2"
  CROP_SIDE="h"
fi

# Then perform a first resizing
ffmpeg -i ${FILE} -vf scale=${SCALE} ${TMP}

# Now get the temporary video size
eval $(ffprobe -v error -of flat=s=_ -select_streams v:0 -show_entries stream=height,width ${TMP})
IN_WIDTH=${streams_stream_0_width}
IN_HEIGHT=${streams_stream_0_height}

# Calculate how much we should crop
if [ "z${CROP_SIDE}" = "zh" ] ; then
  DIFF=$[ ${IN_HEIGHT} - ${OUT_HEIGHT} ]
  CROP="in_w:in_h-${DIFF}"
elif [ "z${CROP_SIDE}" = "zw" ] ; then
  DIFF=$[ ${IN_WIDTH} - ${OUT_WIDTH} ]
  CROP="in_w-${DIFF}:in_h"
fi

# Then crop...
ffmpeg -i ${TMP} -filter:v "crop=${CROP}" ${OUT}

मुझे यह अजीब लग रहा था कि यह एक परिदृश्य को याद करेगा, लेकिन मैंने इसे वीडियो फ़ाइलों के भार के साथ आज़माया है और यह सही ढंग से फसल को लगता है और वीडियो को पूर्ण सही आकार में बदल देता है - अच्छी तरह से किया!
एंडी जेफ्रीज

ऐसा लगता है कि CROP_SIDE निर्णय में कुछ गड़बड़ है।
सूत्र

`# वास्तविक और वांछित आकार के बीच की दर प्राप्त करें w_rate = echo "scale=3; ${in_width}/${out_width}*1000"| bc | awk '{printf "%d", $0}' h_rate = echo "scale=3; ${in_height}/${out_height}*1000"| bc | awk '{printf "%d", $0}' # चलो छोटी साइड लेते हैं, इसलिए वीडियो कम से कम बड़ा # वांछित आकार का होगा, और लंबे पक्ष को क्रॉप करेगा: फसल_साइड = 'एन' यदि [$] {w_rate} -gt $ {h_rate}]; फिर स्केल = "- 2: $ {out_height}" फसल_साइड = 'w' और पैमाना = "$ {out_width}: - 2" फसल_साइड = 'एच' फाई '
सूत्र

23
ffmpeg -i input.file -vf "scale=(iw*sar)*max(720/(iw*sar)\,480/ih):ih*max(720/(iw*sar)\,480/ih), crop=720:480" -c:v mpeg4 -vtag XVID -q:v 4 -c:a libmp3lame -q:a 4 output.avi

अपनी इनपुट फ़ाइल के नाम के साथ "input.file" बदलें।


यह शीर्ष उत्तर होना चाहिए क्योंकि इसे ffprobe पर कॉल की आवश्यकता नहीं है। कमांड में बैकस्लैश कॉमा दृश्यों पर ध्यान दें। यदि आप C / JavaScript / PHP स्ट्रिंग में कमांड डाल रहे हैं तो आपको बैकस्लैश से बचना होगा।
क्लींज

अच्छा, ब्रायन। वीडियो-फ़िल्टर वाला भाग ठीक वैसा ही है जैसा मुझे चाहिए था। (पुराने 4: 3 वीडियो को 16: 9 में बदलने के लिए)!
डेव

1
प्रतिभा! सब एक में किया।
सोली

2
बहुत सफाई है कि ऊपर की स्क्रिप्ट। यदि आप XVID / MP3 नहीं चाहते हैं तो नोट करें कि आप दूसरे उद्धरण चिह्न के बाद टैग को कुछ इस तरह बदल सकते हैं-c:a copy scaled_result.mp4
Nick

7

यदि आप एक बार में फसल लेना चाहते हैं और पैमाने पर हैं, तो आप एक फसल-जैसे-स्केल फ़िल्टरचेन बना सकते हैं:

ffmpeg -i SomeInput.mp4 -vf "crop=in_h*9/16:in_h,scale=-2:400" -t 4 SomeOutput.mp4

उपरोक्त पहली वीडियो 16: 9 पोर्ट्रेट की वीडियो है, फिर 400px हाई x उपयुक्त (सम संख्या) चौड़ाई के लिए स्केल करता है।


1

मैं ffmpeg के लिए नया हूं, लेकिन अब VB.NET में एक अच्छा सा कनवर्टर जा रहा है जो छोटे उपकरणों में उपयोग के लिए विभिन्न आउटपुट प्रारूपों की कच्ची फिल्में बनाता है जिनके पास एसडी कार्ड एक्सेस है लेकिन जटिल वीडियो को डिकोड करने के लिए पर्याप्त शक्ति नहीं है।

जिस तरह से यह काम करता है क्योंकि आकार और क्रॉपिंग के दौरान मुझे इसे मैन्युअल रूप से कोड करना और मापदंडों का निर्माण करना था। मूल रूप से मुझे परिणामी चौड़ाई और ऊंचाई जानने की आवश्यकता है।

मेरे पास विकल्पों के लिए 2 चेक बॉक्स हैं: -

पहलू अनुपात को संरक्षित करें (X) सभी पिक्सेल भरें (X)

इनपुट (1) मूल वीडियो चौड़ाई, (२) मूल वीडियो ऊंचाई, (३) डिवाइस चौड़ाई, (४) डिवाइस ऊंचाई के रूप में केवल ४ चर की आवश्यकता होती है।

हालांकि VB.NET के लिए किसी भी भाषा के लिए काफी आसान अनुकूलित किया जा सकता है।

    Dim crop As String = "" ' will build this in ffmpeg format for -s or scale and crop

    If cbAspectRatio.Checked = False Then
        m_dest_output_w = sz._w
        m_dest_output_h = sz._h

        ' scale to w * h - simple
        crop = " -s " & m_dest_output_w & ":" & m_dest_output_h
    Else
        Dim ratio As Double = CDbl(m_video_width) / CDbl(m_video_height) ' this is aspect ratio of original unsized video

        If cbFillPixels.Checked = False Then ' shrink to fit
            If sz._w * ratio <= m_video_height Then
                m_dest_output_w = sz._w
                m_dest_output_h = sz._w / ratio
            Else
                m_dest_output_h = sz._h
                m_dest_output_w = sz._h / ratio
            End If

            ' no cropping just resizing to a non-filled area that fits

            crop = " -s " & m_dest_output_w & ":" & m_dest_output_h ' no cropping needed as letterboxed

        Else ' expand / fill --- cropping needed
            If sz._w * ratio >= m_video_height Then
                m_dest_output_w = sz._w
                m_dest_output_h = sz._w * ratio

                crop = ",crop=" & sz._w & ":" & sz._h & ":0:" & Math.Abs((m_dest_output_h - sz._h)) \ 2
            Else
                m_dest_output_h = sz._h
                m_dest_output_w = sz._h * ratio

                crop = ",crop=" & sz._w & ":" & sz._h & ":" & Math.Abs((m_dest_output_w - sz._w)) \ 2 & ":0"
            End If

            crop = " -vf scale=" & m_dest_output_w & ":" & m_dest_output_h & crop

            m_dest_output_w = sz._w
            m_dest_output_h = sz._h
        End If
    End If
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.