Details

    • Type: New Feature New Feature
    • Status: Closed Closed
    • Priority: Minor Minor
    • Resolution: Fixed
    • Affects Version/s: None
    • Fix Version/s: None
    • Component/s: None
    • Labels:
      None

      Description

      We should implement handling of CUE points in the standard library, either by calling some external programs or by hacking into liq. This feature has been requested many times, see for example below.

      From the ML:

      I use liquidsoap 0.9.x and I need to manually apply so-called cue
      points (the place where fade out or fade in begins). This data will be
      set manually by users of my system and will be pushed to liquidsoap
      via metadata in the annotate interface.

      In other words: I just want to mix my songs in previously manually
      specified points.

      I know how to write transition function, but how can I "strip"
      specified amount of seconds from the beginning or the end of my song?
      Is there any way to do that?

      Answer from David:

      Liquidsoap has no such facility. However, some people have solved that
      problem before by writing a script that cuts a file as wanted, using
      corresponding tools for mp3 and ogg formats. Then they could hook up
      that script using protocols. I don't remember who it was but we met
      them in Berlin. I thought that they gave the script to Romain, but I
      might be wrong since he didn't mention it.

      It wouldn't be a good solution to have a cut operator because that
      would be done after decoding the file. Hence it would be very
      inefficient. Unless you cut a very small portion at the beginning of
      the file. Regarding the end of file, precision would be an issue
      unless we buffer in advance.

      Now that I think of it, small cue-in points may be implemented using a
      transition that sets the volume to 0 on the new track for a while...
      If it sounds like it could be enough for your particular need, and if
      you feel like hacking in liquidsoap, it could be something to try.
      1. cut-file
        2 kB
        Romain Beauxis
      2. out.log
        54 kB
        Martin Konecny

        Activity

        Hide
        Romain Beauxis
        added a comment -
        This issue should be fixed for local files only in the next stable release. I am submitting another more general feature request for the general case.
        Show
        Romain Beauxis
        added a comment - This issue should be fixed for local files only in the next stable release. I am submitting another more general feature request for the general case.
        Hide
        Samuel Mimram
        added a comment -
        Thanks for taking care of this. However, thinking of it I think that implementing a cut operator would be a good idea to implement a cut operator directly in Liquidsoap. Usually, CUE points are located very close to the beginning and the end (these are just cosmetic adjustments) so decoding the file is not really an issue here. Moreover, an operator would work with any format supported by liq, with local and non-local files, without requiring any runtime dependency. The only real issue here is how we could deal with the end of the file. What do you think of this?
        Show
        Samuel Mimram
        added a comment - Thanks for taking care of this. However, thinking of it I think that implementing a cut operator would be a good idea to implement a cut operator directly in Liquidsoap. Usually, CUE points are located very close to the beginning and the end (these are just cosmetic adjustments) so decoding the file is not really an issue here. Moreover, an operator would work with any format supported by liq, with local and non-local files, without requiring any runtime dependency. The only real issue here is how we could deal with the end of the file. What do you think of this?
        Hide
        Samuel Mimram
        added a comment -
        Actually dealing with the end of files is not even a problem if the CUE out points are indicated as time from the beginning of the file... So, it's just a simple matter of dropping data at the beginning and at the end of the file.
        Show
        Samuel Mimram
        added a comment - Actually dealing with the end of files is not even a problem if the CUE out points are indicated as time from the beginning of the file... So, it's just a simple matter of dropping data at the beginning and at the end of the file.
        Hide
        Romain Beauxis
        added a comment -
        Hi,

        I agree that a solution internal to liquidsoap would be great. Indeed, if the start point is closed to the beginning, the decoding load should not be too bad. This would require some testing, though.

        I am still worried, however, that some user will want to use that to broadcast a part of a long live archive starting right in the middle..

        Finally, how are you planning to implement this? At the decoder level? Then how would you pass the information to the decoder infrastructure?
        Show
        Romain Beauxis
        added a comment - Hi, I agree that a solution internal to liquidsoap would be great. Indeed, if the start point is closed to the beginning, the decoding load should not be too bad. This would require some testing, though. I am still worried, however, that some user will want to use that to broadcast a part of a long live archive starting right in the middle.. Finally, how are you planning to implement this? At the decoder level? Then how would you pass the information to the decoder infrastructure?
        Hide
        Samuel Mimram
        added a comment -
        I think that the most simple way would be to implement a cue_cut operator which would listen to metadata to know the CUE points for each track.
        Show
        Samuel Mimram
        added a comment - I think that the most simple way would be to implement a cue_cut operator which would listen to metadata to know the CUE points for each track.
        Hide
        David Baelde
        added a comment -
        A cut operator is doable, but it'll have to manage the clock by itself, and require exclusivity just like crossfaders. But I agree with Romain that adding this operator will probably result in people trying to use it for playing sections of live shows far from the beginning of the file, resulting in poor performances -- this use case was actually explicitly mentionned on the ML.
        Show
        David Baelde
        added a comment - A cut operator is doable, but it'll have to manage the clock by itself, and require exclusivity just like crossfaders. But I agree with Romain that adding this operator will probably result in people trying to use it for playing sections of live shows far from the beginning of the file, resulting in poor performances -- this use case was actually explicitly mentionned on the ML.
        Hide
        Samuel Mimram
        added a comment -
        I think that we had both use cases on the ML. We could issue a warning if the cue in is after 10 sec (for example).
        Show
        Samuel Mimram
        added a comment - I think that we had both use cases on the ML. We could issue a warning if the cue in is after 10 sec (for example).
        Hide
        Samuel Mimram
        added a comment -
        I made a preliminary implementation in 3fd9b0598765 (in branch LS-469). Feel free to review and test it :)
        Show
        Samuel Mimram
        added a comment - I made a preliminary implementation in 3fd9b0598765 (in branch LS-469 ). Feel free to review and test it :)
        Hide
        Samuel Mimram
        added a comment -
        Tested. It seems to work as expected. Shall we merge?
        Show
        Samuel Mimram
        added a comment - Tested. It seems to work as expected. Shall we merge?
        Hide
        David Baelde
        added a comment -
        Are you sure about how you handled clocks? I don't have time right now but I'll take a look in the next few days.
        Show
        David Baelde
        added a comment - Are you sure about how you handled clocks? I don't have time right now but I'll take a look in the next few days.
        Hide
        Romain Beauxis
        added a comment -
        Thanks for the work!
        Before mergin I'd suggests testing and polishing the operator, in particular concerning the warning if cue_start is too early.
        Also, we need to check its behaviour when used with crossfade/smart_crossfade.

        I'll test that very soon..

        Finally, David should have a pass and check for clocks management. I do not understand these issues well enough but if we don't pay attention to that this is gonna be a recipe for new bugs :-)
        Show
        Romain Beauxis
        added a comment - Thanks for the work! Before mergin I'd suggests testing and polishing the operator, in particular concerning the warning if cue_start is too early. Also, we need to check its behaviour when used with crossfade/smart_crossfade. I'll test that very soon.. Finally, David should have a pass and check for clocks management. I do not understand these issues well enough but if we don't pay attention to that this is gonna be a recipe for new bugs :-)
        Hide
        Samuel Mimram
        added a comment -
        What do you mean by "cue_in too early"? I have tested with smart-cross without any problem so far...

        I agree concerning the clocks though.
        Show
        Samuel Mimram
        added a comment - What do you mean by "cue_in too early"? I have tested with smart-cross without any problem so far... I agree concerning the clocks though.
        Hide
        Romain Beauxis
        added a comment -
        Sorry, I meant starting point is too late therefore the operator will consume too much CPU..

        BTW, I was just thinking that the operator could also have a mode where it does not consume all data at the beginning at once but waits for the start point to come at the real rate.. This way it could be used with streams such as input.http and input.harbor. I am not sure if this would really be interesting though :)
        Show
        Romain Beauxis
        added a comment - Sorry, I meant starting point is too late therefore the operator will consume too much CPU.. BTW, I was just thinking that the operator could also have a mode where it does not consume all data at the beginning at once but waits for the start point to come at the real rate.. This way it could be used with streams such as input.http and input.harbor. I am not sure if this would really be interesting though :)
        Hide
        Samuel Mimram
        added a comment -
        I don't really know how we should limit cue_in time... any idea?

        Feel free to add an option for you behavior (although I don't really see any application for now...)
        Show
        Samuel Mimram
        added a comment - I don't really know how we should limit cue_in time... any idea? Feel free to add an option for you behavior (although I don't really see any application for now...)
        Hide
        David Baelde
        added a comment -
        I'm reviewing the cue operator's code. I made some mostly cosmetic changes, here are a few extra remarks:
         * The operator doesn't respect the source's clock (several source#get in the same tick) so it should have its own internal clock, force it on the source, and animate it when streaming -- cf cross(). If you need some concrete test: you should not be able to write output(add([s,cue_cut(s)])).
         * The default metadata fields are cue_in/out, where we use liq_fade_in/out in other operators: would it be a good idea to use the liq_ prefix everywhere/nowhere? The idea of the prefix is to make sure that the metadata is not passed by accident -- a fade_in metadata might not be intended for liquidsoap, not in the same unit for example.
         * The sub-frame precision seems important to me, right now it's a bit sloppy (remaining TODO #1 and #2).
         * Regarding TODO #3, cue_split is a good idea but unfortunately not trivial to implement (it might take some clock wizardry to delay something a source has produced).
        Show
        David Baelde
        added a comment - I'm reviewing the cue operator's code. I made some mostly cosmetic changes, here are a few extra remarks:  * The operator doesn't respect the source's clock (several source#get in the same tick) so it should have its own internal clock, force it on the source, and animate it when streaming -- cf cross(). If you need some concrete test: you should not be able to write output(add([s,cue_cut(s)])).  * The default metadata fields are cue_in/out, where we use liq_fade_in/out in other operators: would it be a good idea to use the liq_ prefix everywhere/nowhere? The idea of the prefix is to make sure that the metadata is not passed by accident -- a fade_in metadata might not be intended for liquidsoap, not in the same unit for example.  * The sub-frame precision seems important to me, right now it's a bit sloppy (remaining TODO #1 and #2).  * Regarding TODO #3, cue_split is a good idea but unfortunately not trivial to implement (it might take some clock wizardry to delay something a source has produced).
        Hide
        Samuel Mimram
        added a comment -
        Thanks for your review!

        * Clocks: I agree but I really don't know enough about them to properly do the job by myself...
        * The liq_ prefix: ok for me, you can commit the change if you want
        * Subframe precision: I find it difficult to do. How would you implement this? Using a Generator?
        * cue_split would provide a clean solution to LS-468 using a metadata source. It does not seem so complicated to me. What is frightening you exactly?
        Show
        Samuel Mimram
        added a comment - Thanks for your review! * Clocks: I agree but I really don't know enough about them to properly do the job by myself... * The liq_ prefix: ok for me, you can commit the change if you want * Subframe precision: I find it difficult to do. How would you implement this? Using a Generator? * cue_split would provide a clean solution to LS-468 using a metadata source. It does not seem so complicated to me. What is frightening you exactly?
        Hide
        Martin Konecny
        added a comment -
        Hi Samuel, Thanks for the work so far. I've switched to the LS-469 branch, but when compiling I get an error. Ill attach the make log here.
        Show
        Martin Konecny
        added a comment - Hi Samuel, Thanks for the work so far. I've switched to the LS-469 branch, but when compiling I get an error. Ill attach the make log here.
        Hide
        Martin Konecny
        added a comment -
        make error log
        Show
        Martin Konecny
        added a comment - make error log
        Hide
        Samuel Mimram
        added a comment -
        Looks like a problem with the configure soundtouch library.... I will have a look at it. Did you boostrap before configure?

        Since you are likely not to need this library, an easy workaround is to remove ocaml-soundtouch from the PACKAGES file, configure and make.
        Show
        Samuel Mimram
        added a comment - Looks like a problem with the configure soundtouch library.... I will have a look at it. Did you boostrap before configure? Since you are likely not to need this library, an easy workaround is to remove ocaml-soundtouch from the PACKAGES file, configure and make.
        Hide
        Martin Konecny
        added a comment -
        Looks like it's a problem with Ubuntu 11.04 packages. I went back to my 10.10 machine and everything compiled fine. Will start testing soon!
        Show
        Martin Konecny
        added a comment - Looks like it's a problem with Ubuntu 11.04 packages. I went back to my 10.10 machine and everything compiled fine. Will start testing soon!
        Hide
        Romain Beauxis
        added a comment -
        Not a blocker anymore with the new seek functionalities..
        Show
        Romain Beauxis
        added a comment - Not a blocker anymore with the new seek functionalities..
        Hide
        Romain Beauxis
        added a comment -
        Sorry I misinterpreted the title.. We can close now in fact :-)
        Show
        Romain Beauxis
        added a comment - Sorry I misinterpreted the title.. We can close now in fact :-)
        Hide
        David Baelde
        added a comment -
        Everybody agreed.
        Show
        David Baelde
        added a comment - Everybody agreed.

          People

          • Assignee:
            Romain Beauxis
            Reporter:
            Samuel Mimram
          • Votes:
            0 Vote for this issue
            Watchers:
            1 Start watching this issue

            Dates

            • Created:
              Updated:
              Resolved: