Помогите создать экшн / кастом экшн / скрипт

  • Автор темы Автор темы @Michael
  • Дата начала Дата начала
Было б круто если бы тут мне помогли)
http://rmmedia.ru/threads/110165/page-8#post-1907917 - Я для себя вот такой наваял.
Правда,открывает только явно указанный в скрипте сенд (его плагин).Можно сделать копии скрипта для 1-2-3-сенда и назначить на разные "кнопки".
Ну и открывается плагин,который расположен в первом инсерте назначенного трека (тоже редактируется в скрипте,если нужно.)
 
  • Like
Реакции: naash_g
В миди-едиторе видел где-то скрипт "Restrict Polyphony", отлично работает lua(если не ошибаюсь).
Вопрос:
Можно ли подобный скрипт намутить для аудио-айтемов?
P.S. В кубе ещё была такая функция:)
 
@Furqat, нужно брать точки старта и конца соответсвенно предыдущего и следуещего айтема,сравнивать и изменять,если не совпадают(еще диапазон несоответствий).
 
  • Like
Реакции: Furqat
Не нашел экшены:
1. выделение региона, на котором в данный момент находится курсор (select region under edit cursor)
2. снять выделение с айтема под курсором мыши, сохранив (оставив) текущее выделение (unselect items keeping current selection)
3. перемещение к первому/последнему/следующему/предыдущему солируемому/мьютированному треку, а также к родительскому треку (думаю, смог бы реализовать в CAE, если бы там while'ы)

ну и наверно несбыточные мечты в Media Explorer'е:
- переход к следующему/предыдущему транзиенту (тогда не нужно будет щелкать мышью чтобы пропустить пустоту в файле)
- остановка воспроизведения с fade-out'ом в браузере (тогда не будет неприятных щелчков)
- сохранение в браузере текущего выделения файла (либо текущей позиции при удалении), чтобы, к примеру при удалении файла в браузере не надо было пролистывать с начала
 
Парни, можно так: по скрипту покромсало аудиоайтем на участки с информацией и тишиной, тишину повырезало(тишина -действительно тишина, вообще ноль, то есть пороги настраивать не надо), айтемы проклеило и нормализовало по уровню каждый по отдельности?
Заранее спасибо.
 
Последнее редактирование:
  • Like
Реакции: Alexander Yakuba
Вообще будет выглядеть примерно так, но это очень грубо построенный скрипт. Может у кого-то намного проще получится сделать.

PHP:
   threshold = -60 -- db
   release = 0.03 -- seconds


   count_items = reaper.CountSelectedMediaItems(0)
   if count_items ~= nil then
     items_t = {}
     for i =1, count_items do
       item = reaper.GetSelectedMediaItem(0, i-1)
       if item ~= nil then     
         item_guid = reaper.BR_GetMediaItemGUID (item)
         item_pos = reaper.GetMediaItemInfo_Value(item,"D_POSITION")
         item_len = reaper.GetMediaItemInfo_Value(item,"D_LENGTH")
         track = reaper.GetMediaItem_Track(item)
         itemdata = {item_guid, item_pos, item_len}
         table.insert(items_t, itemdata)
         take = reaper.GetActiveTake(item)
         if take ~= nil then     
           is_midi = reaper.TakeIsMIDI(take)   
           if is_midi == false then
             takerate = reaper.GetMediaItemTakeInfo_Value(take, 'D_PLAYRATE')
             src = reaper.GetMediaItemTake_Source(take)
             src_num_ch = 1
             --src_num_ch = reaper.GetMediaSourceNumChannels(src)
             src_rate = reaper.GetMediaSourceSampleRate(src)
             audio_accessor = reaper.CreateTakeAudioAccessor(take)
             window_samples = math.floor(src_rate * item_len)         
          
             audio_accessor_buffer = reaper.new_array(window_samples)
             reaper.GetAudioAccessorSamples(audio_accessor, src_rate, src_num_ch, 0, window_samples, audio_accessor_buffer)
             audio_accessor_buffer_t = audio_accessor_buffer.table(1, window_samples)
          
             -- insert peaks into table
             peaks_db_t = {}
             for j =1, #audio_accessor_buffer_t do
               sample_db_val = math.log(audio_accessor_buffer_t[j]) * 20           
               table.insert(peaks_db_t, sample_db_val)
             end
          
             -- detect gates start / lenght
             release_smpls = src_rate*release
             gates_t = {}
             prev_gate_pos = 0
             current_gate_len=0
             for k = 1, #peaks_db_t do
               peaks_db_item = peaks_db_t[k]           
               if peaks_db_item < threshold then
                 current_gate_pos = k
                 if current_gate_pos == prev_gate_pos + 1 then
                   current_gate_len = current_gate_len+1
                   gate_t_size = #gates_t
                   if gate_t_size == 0 then  gate_t_size = 1 end
                   table.insert(gates_t, gate_t_size, {current_gate_pos, current_gate_len})
                  else
                   current_gate_len = 1
                   table.insert(gates_t, #gates_t + 1, {current_gate_pos, current_gate_len})
                 end
                 prev_gate_pos = current_gate_pos
               end
             end
          
             -- form table from gate lengths matching release time
             gates_t2 = {}
             for m = 1, #gates_t do
               gates_subt = gates_t[m]
               if gates_subt[2] > release_smpls then
                 table.insert(gates_t2, {gates_subt[1],gates_subt[2]})
               end
             end
          
             -- form start point table
             start_point_t = {}
             for n = 1, #gates_t2 do
               gates_subt2 = gates_t2[n]
               start_point = gates_subt2[1]- gates_subt2[2]
               table.insert(start_point_t, start_point)
             end         
          
             -- delete same values from start points table
             start_point_t_delete_ids_t = {}
             for p = 1, #start_point_t do
               start_point_item = start_point_t[p]
               if start_point_item == prev_point_item then
                 table.insert(start_point_t_delete_ids_t, p)
               end
               prev_point_item = start_point_item
             end         
             table.sort(start_point_t_delete_ids_t, function(a,b) return a > b end)
             for r =1, #start_point_t_delete_ids_t do
               table.remove(start_point_t, start_point_t_delete_ids_t[r])
             end
          
             -- search for maximum length refer to start points
             end_point_t = {}
             for t = 1, #start_point_t do
               start_point = start_point_t[t]
               max_len = 0
               for u = 1, #gates_t2 do
                 gates_t2_subt = gates_t2[u]
                 if gates_t2_subt[1] - gates_t2_subt[2] == start_point then
                   max_len = math.max(max_len, gates_t2_subt[2])
                 end
               end 
               table.insert(end_point_t, start_point+max_len)       
             end
                      
             --[[ split test
             for s = 1, #start_point_t do
               split_pos_item = start_point_t[s]
               reaper.SetTakeStretchMarker(take, -1, (split_pos_item/src_rate)*takerate) 
             end
          
             for s = 1, #end_point_t do
               split_pos_item = end_point_t[s]
               reaper.SetTakeStretchMarker(take, -1, (split_pos_item/src_rate)*takerate) 
             end]]
          
             -- form items
             item_edges_t = {}
             for w = 1, #start_point_t-1  do
               if w == 1 then
                 i_start = 0 i_end = start_point_t[1]
                else
                 i_start = end_point_t[w-1]
                 i_end = start_point_t[w]
               end           
               item_edges = {i_start, i_end}
               table.insert(item_edges_t,item_edges )
             end
          
            
             -- split trick:
            
             --duplicate item for splitting trick
             reaper.ApplyNudge(0, 0, 5, 0, 0, false, #start_point_t-1)
             --get matched items guids
             items_t2 = {}
             count_items2 = reaper.CountMediaItems(0)
             if count_items2 ~= nil then
               for i =1, count_items2 do
                 item2 = reaper.GetMediaItem(0, i-1)               
                 item_pos2 = reaper.GetMediaItemInfo_Value(item2,"D_POSITION")
                 item_len2 = reaper.GetMediaItemInfo_Value(item2,"D_LENGTH")
                 if item_pos2 == item_pos and item_len2 == item_len then
                   item_guid2 = reaper.BR_GetMediaItemGUID(item2)
                   table.insert(items_t2, item_guid2)
                 end
               end
             end
            
             -- split items
             for v =1,  #items_t2  do
               item_guid2ret = items_t2[v]
               item2 = reaper.BR_GetMediaItemByGUID(0,  item_guid2ret)
               item_edges_subt = {}
               item_edges_subt = item_edges_t[v]
               if item2 ~= nil then
                 reaper.SetMediaItemInfo_Value(item2,"D_POSITION", (item_edges_subt[1]/src_rate)*takerate)
                 reaper.SetMediaItemInfo_Value(item2,"D_LENGTH", (item_edges_subt[2]/src_rate)*takerate)
               end
             end
                      
             reaper.DestroyAudioAccessor(audio_accessor)
           end -- if isnt midi
         end -- if take ~=  nil
       end -- if item ~= nil
     end -- loop items
   end -- if count ~+ nil

   reaper.UpdateArrange()

Тут сразу куча проблем всплывает - как делать сплит айтема и определять как новые айтемы новые куски, какие из каналов юзать для детектирования и т.д.
 
Последнее редактирование:
какие из каналов юзать для детектирования
Не совсем понял. Если имеется ввиду левый-правый, то хотя бы моно айтем почикать.

Вообще будет выглядеть примерно так
А пробовать его уже можно, или обождать? Надежда вообще есть на благополучный исход? Но в любом случае спасибо .
 
Скорее нет, чем да. Ну это считай динамический процессор с нуля написать, да ещё это ещё с айтемами как-то разрулить. Вообщем, если кто захочет, пусть доработает. Я сам может допишу как-нибудь, если настроение будет.
 
не нашел экшен, перемещающий курсор к ближайшему делению сетки (есть отдельно к левому и отдельно к правому - move cursor left/right to grid division, 40646 и 40647)
 
@@Michael, возможно Вы знаете,в чем проблема если сталкивались с этим.
Есть SNM_GetIntConfigVar и SNM_SetIntConfigVar.
Позволяют читать и изменяет глобальные настройки программы(в REAPER.ini).
Но с настройками,например,секции [audioconfig] в .ini не работает.
Может как-то прописывается название секции,потому что нормально работает только с секцией [reaper].
Хочу скриптом менять аудиодрайвер.Или,может быть,есть другие варианты.
П.С.Откопал еще BR_Win32_GetPrivateProfileString и BR_Win32_WritePrivateProfileString
Похоже,есть шанс,пытаюсь разобраться.
=====
Короче,файл REAPER.ini переписывается,что уже неплохо,но изменения вступают в силу только после перезагрузки.Есть какие-то идеи,как еще можно поступить?
Пока нужно просто переключать драйвер с Асио на Васапи и наоборот одним щелчком,не залазя в настройки.
 
Последнее редактирование:
Очень хотелось бы иметь возможность скрывать/показывать (toggle) автоматизацию трека-папки вместе с автоматизацией его дочерних дорожек.
 
Скорее нет, чем да. Ну это считай динамический процессор с нуля написать, да ещё это ещё с айтемами как-то разрулить. Вообщем, если кто захочет, пусть доработает. Я сам может допишу как-нибудь, если настроение будет.
Есть более простой вариант-использовать встроенный "auto trim/split" Рипера.
Тогда появляется и возможность тонкой подстройки и скрипт идет просто как оболочка,собирающая все в кучу.
PHP:
///==Remove_Silence>Normalize Each Item>Glue (!!!-Only For First Selected Item)==///

function Remove_Silence() ////Remove_Silence
(Undo_BeginBlock();
SelectAllMediaItems(0,0);//Unselect All Items in Project
SetMediaItemSelected(First_Sel_Item_id,1);//Select Only FIRST item by id

Main_OnCommand(40315, 0);//MAIN section action "Remove Silence"
Main_OnCommand(40108, 0);//MAIN section action "Normalize"
Main_OnCommand(40362, 0);//MAIN section action "Glue ignoring TimeSel"
Undo_EndBlock("~Remove Silence~", 0); //Undo End
UpdateArrange();
);


First_Sel_Item_id = GetSelectedMediaItem(0,0);//Get first sel item id
First_Sel_Item_id ? Remove_Silence();
 
Последнее редактирование:
EUGEN27771, спасибо, избавил от такой работы. Я, честно говоря, не использую такое, привык руками деликатные вещи делать, поэтому про этот экшн забыл))
Скриптом к этому к окну не подберёшся вроде только.
 
Хочу добавить любимые плагины в тулбар, подскажите команды-после которых vst появится в инсерте?
 
Хочу добавить любимые плагины в тулбар, подскажите команды-после которых vst появится в инсерте?
Это уже миллион раз обсуждалось, поэтому проще поискать по форуму.

Михаил, можно ли сделать а-ля FL STUDIO style удаление итемов при зажатой правой кнопке мыши?
 
как можно инвертировать выделение айтемов внутри тайм-селекшена?
[DOUBLEPOST=1443549879,1443549622][/DOUBLEPOST]
можно ли сделать а-ля FL STUDIO style удаление итемов при зажатой правой кнопке мыши?

нельзя, это ограничение Mouse Modifiers, уже хорошо, что хотя бы ноты можно удалять как в FL
 
Можно с зажатым хоткеем, смотри мой гитхаб в разделе item, delete item under mouse cursor. Про мышь уже тыщу раз писал кокосам в API реквесты, не дают (с другой стороны правильно делают). Но тогда б могли всё же по свободнее сделать модифаеры.

Если дадут привязать скрипт к правом клику мыши, то можно будет идентично FL сделать.
 
Последнее редактирование:
Реально ли создать скрипт snap items to items? эта опция есть в snap settings, но надо лезть в окошко с этими настройками, а так бы одной кнопкой - ляпота:)
 
Парни, вот здесь описан весьма полезный скрипт, но он - на Питоне...
Соорудите плиз такое на Lua, если не сложно. Буду очень благодарен.
[DOUBLEPOST=1444224593,1444224074][/DOUBLEPOST]И ещё один реквест.
Очень нужен скрипт, с помощью которого можно было бы управлять параметром opacity докера. Мне бы хватило двух скриптов - например, "Set docker opacity to 75%" и "Set docker opacity to 100%".
 
  • Like
Реакции: lil-burn
Можно ли сделать, чтоб при нажатии на кнопку первый раз срабатывал один экшн, а второй раз другой? Можно ли повесить экшн на нажатие двух кнопок одновременно?
 
Можно ли сделать, чтоб при нажатии на кнопку первый раз срабатывал один экшн, а второй раз другой?
Можно, через Cycle Action.

Можно ли повесить экшн на нажатие двух кнопок одновременно?
Если одна из этих кнопок Ctrl, Shift, Alt или Win - запросто. Если же вы хотите повесить экшн на комбинацию двух обычных кнопок (например, H+J), то это можно сделать через костыль типа Autohotkey. Непосредственно в Рипере этого сделать нельзя.
 
@@Michael, вопрос,немного не по теме предложений-как Вы реализовали
потенциальные маркеры из разных частей спектра
Есть мысль сделать скрипт преобразующий аудио-барабаны в миди дорожку,хотя бы на основе 3-элементов,различных по спектру(Kick,Snare,Hat)Ме могу понять,как с FFT работать.
 

Сейчас просматривают