Search in sources :

Example 1 with VideoStream

use of org.opencastproject.mediapackage.VideoStream in project opencast by opencast.

the class EventIndexUtils method updateEvent.

/**
 * Update the given {@link Event} with the given {@link MediaPackage}.
 *
 * @param event
 *          the event to update
 * @param mp
 *          the mediapackage containing the metadata for the update
 * @return the updated event
 */
public static Event updateEvent(Event event, MediaPackage mp) {
    // Tracks
    List<String> trackMimeTypes = new ArrayList<String>();
    List<String> trackStreamResolutions = new ArrayList<String>();
    List<String> trackFlavors = new ArrayList<String>();
    for (Track t : mp.getTracks()) {
        if (t.getMimeType() != null)
            trackMimeTypes.add(t.getMimeType().toString());
        if (t.getFlavor() != null)
            trackFlavors.add(t.getFlavor().toString());
        VideoStream[] streams = TrackSupport.byType(t.getStreams(), VideoStream.class);
        for (VideoStream s : streams) {
            trackStreamResolutions.add(s.getFrameWidth() + "x" + s.getFrameHeight());
        }
    }
    event.setTrackMimetypes(trackMimeTypes);
    event.setTrackStreamResolutions(trackStreamResolutions);
    event.setTrackFlavors(trackFlavors);
    // Metadata
    List<String> metadataFlavors = new ArrayList<String>();
    List<String> metadataMimetypes = new ArrayList<String>();
    for (Catalog c : mp.getCatalogs()) {
        if (c.getFlavor() != null)
            metadataFlavors.add(c.getFlavor().toString());
        if (c.getMimeType() != null)
            metadataMimetypes.add(c.getMimeType().toString());
    }
    event.setMetadataFlavors(metadataFlavors);
    event.setMetadataMimetypes(metadataMimetypes);
    // Attachments
    List<String> attachmentFlavors = new ArrayList<String>();
    for (Attachment a : mp.getAttachments()) {
        if (a.getFlavor() != null)
            attachmentFlavors.add(a.getFlavor().toString());
    }
    event.setAttachmentFlavors(attachmentFlavors);
    // Publications
    List<Publication> publications = new ArrayList<Publication>();
    for (Publication p : mp.getPublications()) {
        publications.add(p);
    }
    event.setPublications(publications);
    event.setSeriesName(mp.getSeriesTitle());
    return event;
}
Also used : ArrayList(java.util.ArrayList) VideoStream(org.opencastproject.mediapackage.VideoStream) Publication(org.opencastproject.mediapackage.Publication) Attachment(org.opencastproject.mediapackage.Attachment) Track(org.opencastproject.mediapackage.Track) Catalog(org.opencastproject.mediapackage.Catalog)

Example 2 with VideoStream

use of org.opencastproject.mediapackage.VideoStream in project opencast by opencast.

the class PartialImportWorkflowOperationHandler method getLargestTrack.

/**
 * Returns the track with the largest resolution from the list of tracks
 *
 * @param tracks
 *          the list of tracks
 * @return a {@link Tuple} with the largest track and it's dimension
 */
private Tuple<Track, Dimension> getLargestTrack(List<Track> tracks) {
    Track track = null;
    Dimension dimension = null;
    for (Track t : tracks) {
        if (!t.hasVideo())
            continue;
        VideoStream[] videoStreams = TrackSupport.byType(t.getStreams(), VideoStream.class);
        int frameWidth = videoStreams[0].getFrameWidth();
        int frameHeight = videoStreams[0].getFrameHeight();
        if (dimension == null || (frameWidth * frameHeight) > (dimension.getWidth() * dimension.getHeight())) {
            dimension = Dimension.dimension(frameWidth, frameHeight);
            track = t;
        }
    }
    if (track == null || dimension == null)
        return null;
    return Tuple.tuple(track, dimension);
}
Also used : VideoStream(org.opencastproject.mediapackage.VideoStream) Dimension(org.opencastproject.composer.layout.Dimension) Track(org.opencastproject.mediapackage.Track)

Example 3 with VideoStream

use of org.opencastproject.mediapackage.VideoStream in project opencast by opencast.

the class CompositeWorkflowOperationHandler method handleMultipleTracks.

private WorkflowOperationResult handleMultipleTracks(MediaPackage mediaPackage, WorkflowOperationInstance operation, CompositeSettings compositeSettings, Option<Attachment> watermarkAttachment) throws EncoderException, IOException, NotFoundException, MediaPackageException, WorkflowOperationException {
    if (compositeSettings.getMultiSourceLayouts() == null || compositeSettings.getMultiSourceLayouts().size() == 0) {
        throw new WorkflowOperationException("Multi video layout must be set! Please verify that you have a " + LAYOUT_MULTIPLE + " or " + LAYOUT + " property in your composite operation in your workflow definition to be able to handle multiple videos");
    }
    try {
        Track upperTrack = compositeSettings.getUpperTrack();
        Track lowerTrack = compositeSettings.getLowerTrack();
        List<HorizontalCoverageLayoutSpec> layouts = compositeSettings.getMultiSourceLayouts();
        VideoStream[] upperVideoStreams = TrackSupport.byType(upperTrack.getStreams(), VideoStream.class);
        if (upperVideoStreams.length == 0) {
            logger.warn("No video stream available in the upper track! {}", upperTrack);
            return createResult(mediaPackage, Action.SKIP);
        }
        VideoStream[] lowerVideoStreams = TrackSupport.byType(lowerTrack.getStreams(), VideoStream.class);
        if (lowerVideoStreams.length == 0) {
            logger.warn("No video stream available in the lower track! {}", lowerTrack);
            return createResult(mediaPackage, Action.SKIP);
        }
        // Read the video dimensions from the mediapackage stream information
        Dimension upperDimensions = Dimension.dimension(upperVideoStreams[0].getFrameWidth(), upperVideoStreams[0].getFrameHeight());
        Dimension lowerDimensions = Dimension.dimension(lowerVideoStreams[0].getFrameWidth(), lowerVideoStreams[0].getFrameHeight());
        // Determine dimension of output
        Dimension outputDimension = null;
        String outputResolutionSource = compositeSettings.getOutputResolutionSource();
        if (outputResolutionSource.equals(CompositeSettings.OUTPUT_RESOLUTION_FIXED)) {
            outputDimension = compositeSettings.getOutputDimension();
        } else if (outputResolutionSource.equals(CompositeSettings.OUTPUT_RESOLUTION_LOWER)) {
            outputDimension = lowerDimensions;
        } else if (outputResolutionSource.equals(CompositeSettings.OUTPUT_RESOLUTION_UPPER)) {
            outputDimension = upperDimensions;
        }
        // Create the video layout definitions
        List<Tuple<Dimension, HorizontalCoverageLayoutSpec>> shapes = new ArrayList<Tuple<Dimension, HorizontalCoverageLayoutSpec>>();
        shapes.add(0, Tuple.tuple(lowerDimensions, layouts.get(0)));
        shapes.add(1, Tuple.tuple(upperDimensions, layouts.get(1)));
        // Calculate the layout
        MultiShapeLayout multiShapeLayout = LayoutManager.multiShapeLayout(outputDimension, shapes);
        // Create the laid out element for the videos
        LaidOutElement<Track> lowerLaidOutElement = new LaidOutElement<Track>(lowerTrack, multiShapeLayout.getShapes().get(0));
        LaidOutElement<Track> upperLaidOutElement = new LaidOutElement<Track>(upperTrack, multiShapeLayout.getShapes().get(1));
        // Create the optionally laid out element for the watermark
        Option<LaidOutElement<Attachment>> watermarkOption = createWatermarkLaidOutElement(compositeSettings, outputDimension, watermarkAttachment);
        Job compositeJob = composerService.composite(outputDimension, Option.option(upperLaidOutElement), lowerLaidOutElement, watermarkOption, compositeSettings.getProfile().getIdentifier(), compositeSettings.getOutputBackground());
        // Wait for the jobs to return
        if (!waitForStatus(compositeJob).isSuccess())
            throw new WorkflowOperationException("The composite job did not complete successfully");
        if (compositeJob.getPayload().length() > 0) {
            Track compoundTrack = (Track) MediaPackageElementParser.getFromXml(compositeJob.getPayload());
            compoundTrack.setURI(workspace.moveTo(compoundTrack.getURI(), mediaPackage.getIdentifier().toString(), compoundTrack.getIdentifier(), "composite." + FilenameUtils.getExtension(compoundTrack.getURI().toString())));
            // Adjust the target tags
            for (String tag : compositeSettings.getTargetTags()) {
                logger.trace("Tagging compound track with '{}'", tag);
                compoundTrack.addTag(tag);
            }
            // Adjust the target flavor.
            compoundTrack.setFlavor(compositeSettings.getTargetFlavor());
            logger.debug("Compound track has flavor '{}'", compoundTrack.getFlavor());
            // store new tracks to mediaPackage
            mediaPackage.add(compoundTrack);
            WorkflowOperationResult result = createResult(mediaPackage, Action.CONTINUE, compositeJob.getQueueTime());
            logger.debug("Composite operation completed");
            return result;
        } else {
            logger.info("Composite operation unsuccessful, no payload returned: {}", compositeJob);
            return createResult(mediaPackage, Action.SKIP);
        }
    } finally {
        if (compositeSettings.getSourceUrlWatermark() != null)
            workspace.deleteFromCollection(COLLECTION, compositeSettings.getWatermarkIdentifier() + "." + FilenameUtils.getExtension(compositeSettings.getSourceUrlWatermark()));
    }
}
Also used : MultiShapeLayout(org.opencastproject.composer.layout.MultiShapeLayout) VideoStream(org.opencastproject.mediapackage.VideoStream) ArrayList(java.util.ArrayList) Dimension(org.opencastproject.composer.layout.Dimension) WorkflowOperationResult(org.opencastproject.workflow.api.WorkflowOperationResult) WorkflowOperationException(org.opencastproject.workflow.api.WorkflowOperationException) LaidOutElement(org.opencastproject.composer.api.LaidOutElement) HorizontalCoverageLayoutSpec(org.opencastproject.composer.layout.HorizontalCoverageLayoutSpec) Job(org.opencastproject.job.api.Job) Track(org.opencastproject.mediapackage.Track) Tuple(org.opencastproject.util.data.Tuple)

Example 4 with VideoStream

use of org.opencastproject.mediapackage.VideoStream in project opencast by opencast.

the class ConcatWorkflowOperationHandlerTest method testFrameRatePartValue.

@Test
public void testFrameRatePartValue() throws Exception {
    Track part1 = (Track) mp.getElementsByFlavor(MediaPackageElementFlavor.parseFlavor("presenter/source"))[0];
    VideoStream[] videoStreams = TrackSupport.byType(part1.getStreams(), VideoStream.class);
    createTestFrameRateWithValue("part-1", videoStreams[0].getFrameRate());
}
Also used : VideoStream(org.opencastproject.mediapackage.VideoStream) Track(org.opencastproject.mediapackage.Track) Test(org.junit.Test)

Example 5 with VideoStream

use of org.opencastproject.mediapackage.VideoStream in project opencast by opencast.

the class ConcatWorkflowOperationHandler method concat.

private WorkflowOperationResult concat(MediaPackage src, WorkflowOperationInstance operation) throws EncoderException, IOException, NotFoundException, MediaPackageException, WorkflowOperationException {
    MediaPackage mediaPackage = (MediaPackage) src.clone();
    Map<Integer, Tuple<TrackSelector, Boolean>> trackSelectors = getTrackSelectors(operation);
    String outputResolution = StringUtils.trimToNull(operation.getConfiguration(OUTPUT_RESOLUTION));
    String outputFrameRate = StringUtils.trimToNull(operation.getConfiguration(OUTPUT_FRAMERATE));
    String encodingProfile = StringUtils.trimToNull(operation.getConfiguration(ENCODING_PROFILE));
    // Skip the worklow if no source-flavors or tags has been configured
    if (trackSelectors.isEmpty()) {
        logger.warn("No source-tags or source-flavors has been set.");
        return createResult(mediaPackage, Action.SKIP);
    }
    String targetTagsOption = StringUtils.trimToNull(operation.getConfiguration(TARGET_TAGS));
    String targetFlavorOption = StringUtils.trimToNull(operation.getConfiguration(TARGET_FLAVOR));
    // Target tags
    List<String> targetTags = asList(targetTagsOption);
    // Target flavor
    if (targetFlavorOption == null)
        throw new WorkflowOperationException("Target flavor must be set!");
    // Find the encoding profile
    if (encodingProfile == null)
        throw new WorkflowOperationException("Encoding profile must be set!");
    EncodingProfile profile = composerService.getProfile(encodingProfile);
    if (profile == null)
        throw new WorkflowOperationException("Encoding profile '" + encodingProfile + "' was not found");
    // Output resolution
    if (outputResolution == null)
        throw new WorkflowOperationException("Output resolution must be set!");
    Dimension outputDimension = null;
    if (outputResolution.startsWith(OUTPUT_PART_PREFIX)) {
        if (!trackSelectors.keySet().contains(Integer.parseInt(outputResolution.substring(OUTPUT_PART_PREFIX.length()))))
            throw new WorkflowOperationException("Output resolution part not set!");
    } else {
        try {
            String[] outputResolutionArray = StringUtils.split(outputResolution, "x");
            if (outputResolutionArray.length != 2) {
                throw new WorkflowOperationException("Invalid format of output resolution!");
            }
            outputDimension = Dimension.dimension(Integer.parseInt(outputResolutionArray[0]), Integer.parseInt(outputResolutionArray[1]));
        } catch (WorkflowOperationException e) {
            throw e;
        } catch (Exception e) {
            throw new WorkflowOperationException("Unable to parse output resolution!", e);
        }
    }
    float fps = -1.0f;
    if (StringUtils.isNotEmpty(outputFrameRate)) {
        if (StringUtils.startsWith(outputFrameRate, OUTPUT_PART_PREFIX)) {
            if (!NumberUtils.isNumber(outputFrameRate.substring(OUTPUT_PART_PREFIX.length())) || !trackSelectors.keySet().contains(Integer.parseInt(outputFrameRate.substring(OUTPUT_PART_PREFIX.length())))) {
                throw new WorkflowOperationException("Output frame rate part not set or invalid!");
            }
        } else if (NumberUtils.isNumber(outputFrameRate)) {
            fps = NumberUtils.toFloat(outputFrameRate);
        } else {
            throw new WorkflowOperationException("Unable to parse output frame rate!");
        }
    }
    MediaPackageElementFlavor targetFlavor = null;
    try {
        targetFlavor = MediaPackageElementFlavor.parseFlavor(targetFlavorOption);
        if ("*".equals(targetFlavor.getType()) || "*".equals(targetFlavor.getSubtype()))
            throw new WorkflowOperationException("Target flavor must have a type and a subtype, '*' are not allowed!");
    } catch (IllegalArgumentException e) {
        throw new WorkflowOperationException("Target flavor '" + targetFlavorOption + "' is malformed");
    }
    List<Track> tracks = new ArrayList<Track>();
    for (Entry<Integer, Tuple<TrackSelector, Boolean>> trackSelector : trackSelectors.entrySet()) {
        Collection<Track> tracksForSelector = trackSelector.getValue().getA().select(mediaPackage, false);
        String currentFlavor = StringUtils.join(trackSelector.getValue().getA().getFlavors());
        String currentTag = StringUtils.join(trackSelector.getValue().getA().getTags());
        if (tracksForSelector.size() > 1) {
            logger.warn("More than one track has been found with flavor '{}' and/or tag '{}' for concat operation, skipping concatenation!", currentFlavor, currentTag);
            return createResult(mediaPackage, Action.SKIP);
        } else if (tracksForSelector.size() == 0 && trackSelector.getValue().getB()) {
            logger.warn("No track has been found with flavor '{}' and/or tag '{}' for concat operation, skipping concatenation!", currentFlavor, currentTag);
            return createResult(mediaPackage, Action.SKIP);
        } else if (tracksForSelector.size() == 0 && !trackSelector.getValue().getB()) {
            logger.info("No track has been found with flavor '{}' and/or tag '{}' for concat operation, skipping track!", currentFlavor, currentTag);
            continue;
        }
        for (Track t : tracksForSelector) {
            tracks.add(t);
            VideoStream[] videoStreams = TrackSupport.byType(t.getStreams(), VideoStream.class);
            if (videoStreams.length == 0) {
                logger.info("No video stream available in the track with flavor {}! {}", currentFlavor, t);
                return createResult(mediaPackage, Action.SKIP);
            }
            if (StringUtils.startsWith(outputResolution, OUTPUT_PART_PREFIX) && NumberUtils.isNumber(outputResolution.substring(OUTPUT_PART_PREFIX.length())) && trackSelector.getKey() == Integer.parseInt(outputResolution.substring(OUTPUT_PART_PREFIX.length()))) {
                outputDimension = new Dimension(videoStreams[0].getFrameWidth(), videoStreams[0].getFrameHeight());
                if (!trackSelector.getValue().getB()) {
                    logger.warn("Output resolution track {} must be mandatory, skipping concatenation!", outputResolution);
                    return createResult(mediaPackage, Action.SKIP);
                }
            }
            if (fps <= 0 && StringUtils.startsWith(outputFrameRate, OUTPUT_PART_PREFIX) && NumberUtils.isNumber(outputFrameRate.substring(OUTPUT_PART_PREFIX.length())) && trackSelector.getKey() == Integer.parseInt(outputFrameRate.substring(OUTPUT_PART_PREFIX.length()))) {
                fps = videoStreams[0].getFrameRate();
            }
        }
    }
    if (tracks.size() == 0) {
        logger.warn("No tracks found for concating operation, skipping concatenation!");
        return createResult(mediaPackage, Action.SKIP);
    } else if (tracks.size() == 1) {
        Track track = (Track) tracks.get(0).clone();
        track.setIdentifier(null);
        addNewTrack(mediaPackage, track, targetTags, targetFlavor);
        logger.info("At least two tracks are needed for the concating operation, skipping concatenation!");
        return createResult(mediaPackage, Action.SKIP);
    }
    Job concatJob;
    if (fps > 0) {
        concatJob = composerService.concat(profile.getIdentifier(), outputDimension, fps, tracks.toArray(new Track[tracks.size()]));
    } else {
        concatJob = composerService.concat(profile.getIdentifier(), outputDimension, tracks.toArray(new Track[tracks.size()]));
    }
    // Wait for the jobs to return
    if (!waitForStatus(concatJob).isSuccess())
        throw new WorkflowOperationException("The concat job did not complete successfully");
    if (concatJob.getPayload().length() > 0) {
        Track concatTrack = (Track) MediaPackageElementParser.getFromXml(concatJob.getPayload());
        concatTrack.setURI(workspace.moveTo(concatTrack.getURI(), mediaPackage.getIdentifier().toString(), concatTrack.getIdentifier(), "concat." + FilenameUtils.getExtension(concatTrack.getURI().toString())));
        addNewTrack(mediaPackage, concatTrack, targetTags, targetFlavor);
        WorkflowOperationResult result = createResult(mediaPackage, Action.CONTINUE, concatJob.getQueueTime());
        logger.debug("Concat operation completed");
        return result;
    } else {
        logger.info("concat operation unsuccessful, no payload returned: {}", concatJob);
        return createResult(mediaPackage, Action.SKIP);
    }
}
Also used : ArrayList(java.util.ArrayList) VideoStream(org.opencastproject.mediapackage.VideoStream) EncodingProfile(org.opencastproject.composer.api.EncodingProfile) Dimension(org.opencastproject.composer.layout.Dimension) MediaPackageElementFlavor(org.opencastproject.mediapackage.MediaPackageElementFlavor) WorkflowOperationException(org.opencastproject.workflow.api.WorkflowOperationException) NotFoundException(org.opencastproject.util.NotFoundException) IOException(java.io.IOException) MediaPackageException(org.opencastproject.mediapackage.MediaPackageException) EncoderException(org.opencastproject.composer.api.EncoderException) WorkflowOperationResult(org.opencastproject.workflow.api.WorkflowOperationResult) MediaPackage(org.opencastproject.mediapackage.MediaPackage) WorkflowOperationException(org.opencastproject.workflow.api.WorkflowOperationException) Job(org.opencastproject.job.api.Job) Tuple(org.opencastproject.util.data.Tuple) Track(org.opencastproject.mediapackage.Track)

Aggregations

VideoStream (org.opencastproject.mediapackage.VideoStream)14 Track (org.opencastproject.mediapackage.Track)11 ArrayList (java.util.ArrayList)5 TrackImpl (org.opencastproject.mediapackage.track.TrackImpl)5 WorkflowOperationException (org.opencastproject.workflow.api.WorkflowOperationException)5 Dimension (org.opencastproject.composer.layout.Dimension)4 Job (org.opencastproject.job.api.Job)4 AudioStream (org.opencastproject.mediapackage.AudioStream)4 HashMap (java.util.HashMap)3 Test (org.junit.Test)3 MediaPackage (org.opencastproject.mediapackage.MediaPackage)3 MediaPackageElementFlavor (org.opencastproject.mediapackage.MediaPackageElementFlavor)3 Tuple (org.opencastproject.util.data.Tuple)3 WorkflowOperationResult (org.opencastproject.workflow.api.WorkflowOperationResult)3 Fraction (org.apache.commons.lang3.math.Fraction)2 LaidOutElement (org.opencastproject.composer.api.LaidOutElement)2 HorizontalCoverageLayoutSpec (org.opencastproject.composer.layout.HorizontalCoverageLayoutSpec)2 MultiShapeLayout (org.opencastproject.composer.layout.MultiShapeLayout)2 Attachment (org.opencastproject.mediapackage.Attachment)2 MediaPackageElement (org.opencastproject.mediapackage.MediaPackageElement)2