Source code for reapy.core.reaper.reaper

import reapy
import reapy.reascript_api as RPR
import contextlib
from .defer import ReaperConsole

import collections
import io
import os
import sys


_ORIGINAL_PRINT = print


[docs]def add_project_tab(make_current_project=True): """Open new project tab and return it. Parameters ---------- make_current_project : bool Whether to select new project as current project (default=`True`). Returns ------- project : Project New project. """ if not make_current_project: current_project = reapy.Project() project = add_project_tab(make_current_project=True) current_project.make_current_project() return project perform_action(40859) return reapy.Project()
[docs]def add_reascript(path, section_id=0, commit=True): """ Add a ReaScript and return the new action ID. Parameters ---------- path : str Path to script. section_id : int, optional (default=0, corresponds to main section). Action section ID to which the script must be added. commit : bool, optional Whether to commit change. Use it when adding a single script. You can optimize bulk adding `n` scripts by setting `commit=False` for the first `n-1` calls and `commit=True` for the last call. Returns ------- action_id : int New ReaScript action ID. """ if not os.path.isfile(path): raise FileNotFoundError(path) path = os.path.abspath(path) action_id = RPR.AddRemoveReaScript( True, section_id, path, commit ) if action_id == 0: message = "Script at {} wasn't successfully added.".format(path) raise ValueError(message) return action_id
[docs]def arm_command(command_id, section=""): """ Arm or disarm command. Parameters ---------- command_id : int Command ID. If 0, disarm command. section : str, optional Command section. Empty string for main section. Default="". """ RPR.ArmCommand(command_id, section)
[docs]def browse_for_file(window_title="", extension=""): """ Ask the user to select a file. Parameters ---------- window_title : str, optional Window title (default="") extension : str, optional Extension for file (e.g. "mp3", "txt"...) (default=all types). Returns ------- path : str or NoneType Path to file, or None if user cancelled. """ success, path, *_ = RPR.GetUserFileNameForRead("", window_title, extension) if success: return path
[docs]def clear_console(): """ Clear Reaper console. See also -------- ReaProject.show_console_message """ RPR.ClearConsole()
[docs]def clear_peak_cache(): """ Reset global peak cache. """ RPR.ClearPeakCache()
[docs]def dB_to_slider(db): """ Convert decibel value to slider. Parameters ---------- db : float Decibel value. Returns ------- slider : float Slider value. See also -------- slider_to_dB """ slider = RPR.DB2SLIDER(db) return slider
[docs]def delete_ext_state(section, key, persist=False): """ Delete extended state value for a given section and key. Parameters ---------- section : str Extended state section. key : str Extended state key. persist : bool Whether extended state should remain deleted next time REAPER is opened. """ RPR.DeleteExtState(section, key, persist)
[docs]def disarm_command(): """ Disarm command. """ arm_command(0)
[docs]def get_armed_command(): command_id, section, _ = RPR.GetArmedCommand("", 2048) if command_id == 0: return return command_id, section
[docs]def get_command_id(command_name): """ Return ID of command with a given name. Parameters ---------- command_name : str Command name. Returns ------- command_id : int or None Command ID, or None if name can't be found. """ command_id = RPR.NamedCommandLookup(command_name) command_id = command_id if command_id else None return command_id
[docs]def get_command_name(command_id): """ Return name of command with a given ID. Parameters ---------- command_id : int Command ID. Returns ------- command_name : str, None Command name, or None for a native command. """ command_name = RPR.ReverseNamedCommandLookup(command_id) if command_name is not None: command_name = "_" + command_name return command_name
[docs]def get_exe_dir(): """ Return REAPER.exe directory (e.g. "C:\\Program Files\\REAPER"). Returns ------- path : str Path to REAPER.exe directory. """ path = RPR.GetExePath() return path
[docs]def get_ext_state(section, key): """ Get the extended state value for a specific section and key. Parameters ---------- section : str Extended state section. key : str Extended state key for section `section`. Returns ------- value : str Extended state value. See also -------- delete_ext_state set_ext_state """ value = RPR.GetExtState(section, key) return value
[docs]def get_global_automation_mode(): """ Return global automation override mode. Returns ------- override_mode : str One of the following values: "bypass" "latch" "none" "read" "touch" "trim/read" "write" """ modes = { -1: "none", 0: "trim/read", 1: "read", 2: "touch", 3: "write", 4: "latch", 5: "bypass" } override_mode = modes[RPR.GetGlobalAutomationOverride()] return override_mode
[docs]def get_ini_file(): """ Return path to REAPER.ini file. Returns ------- path : str Path to REAPER.ini file. """ path = RPR.get_ini_file() return path
[docs]def get_last_touched_track(): """ Return last touched track, or None if no track has been touched. Returns ------- track : Track or None if no track has been touched. """ track = reapy.Track(RPR.GetLastTouchedTrack()) if not track._is_defined: track = None return track
[docs]def get_main_window(): """ Return main window. Returns ------- window : Window Main window. """ window = reapy.Window(RPR.GetMainHwnd()) return window
[docs]@reapy.inside_reaper() def get_projects(): """ Return list of all opened projects. Returns ------- projects : list of Project List of all projects. """ i, projects = 0, [reapy.Project(index=0)] while projects[-1]._is_defined: i += 1 projects.append(reapy.Project(index=i)) projects.pop() return projects
[docs]def get_reaper_version(): version = RPR.GetAppVersion() return version
[docs]def get_resource_path(): """ Return path to directory where .ini files are stored. Returns ------- path : str Path to directory where .ini files are stored. """ path = RPR.GetResourcePath() return path
[docs]def get_user_inputs(title, captions, retvals_size=1024): """Show text inputs to user and get values from them. Parameters ---------- title : str Popup title. captions : List[str] Names of input fields. retvals_size : int, optional Maximum number of characters that will be retrieved for each field. User may enter more, but only the first `retvals_size` will be returned. (default=1024) Returns ------- Dict[str,str] Dictionary of pairs {caption: response}. Raises ------ RuntimeError When user clicked the Cancel button. """ success, _, _, _, retvals_csv, _ = RPR.GetUserInputs( title, len(captions), ",".join(captions), "", retvals_size ) if success: return dict(zip(captions, retvals_csv.split(","))) else: raise RuntimeError('User clicked Cancel.')
[docs]def has_ext_state(section, key): """ Return whether extended state exists for given section and key. Parameters ---------- section : str Extended state section. key : str Extended state key. Returns ------- has_ext_state : bool """ has_ext_state = bool(RPR.HasExtState(section, key)) return has_ext_state
[docs]@reapy.inside_reaper() def open_project(filepath, in_new_tab=False, make_current_project=True): """ Open project and return it. Parameters ---------- filepath : str in_new_tab : bool, optional Whether to open project in new tab (default=`False`). make_current_project : bool, optional Whether to make opened project current project (has no effect if `in_new_tab` is `False`). Returns ------- project : Project Opened project. """ if not make_current_project: current_project = reapy.Project() if in_new_tab: add_project_tab(make_current_project=True) RPR.Main_openProject(filepath) project = reapy.Project() if not make_current_project: current_project.make_current_project() return project
[docs]def perform_action(action_id): """ Perform action with ID `action_id` in the main Actions section. Parameters ---------- action_id : int Action ID in the main Actions section. """ RPR.Main_OnCommand(action_id, 0)
[docs]class prevent_ui_refresh(contextlib.ContextDecorator): """Class to prevent UI refresh on certain pieces of code. Its instance can be used both as decorator and as context manager: >>> with reapy.prevent_ui_refresh(): ... reapy.Project.add_track() >>> @prevent_ui_refresh() >>> def some_function(*args, **kwargs): ... reapy.Project.add_track() """ def __enter__(self): RPR.PreventUIRefresh(1) def __exit__(self, exc_type, exc_val, exc_tb): RPR.PreventUIRefresh(-1)
[docs]def print(*args, **kwargs): """ Alias to ReaProject.show_console_message. """ show_console_message(*args, **kwargs)
[docs]class reaprint(contextlib.ContextDecorator): """Class to send all prints to ReaperConsole. Its instance can be used both as decorator and context manager: >>> with reapy.reaprint(): ... print('This will go to the console!') ... print('All these contexted will go to the console!') >>> @reapy.reaprint() >>> def some_function(*args, **kwargs): ... print('This will go to the console!') ... print('All these decorated prints will go to the console!') """ _original_stdouts = collections.deque() def __enter__(self): self._original_stdouts.append(sys.stdout) sys.stdout = ReaperConsole() def __exit__(self, exc_type, exc_val, exc_tb): sys.stdout = self._original_stdouts.pop()
[docs]def remove_reascript(path, section_id=0, commit=True): """ Remove a ReaScript. Parameters ---------- path : str Path to script. section_id : int, optional (default=0, corresponds to main section). Action section ID to which the script must be added. commit : bool, optional Whether to commit change. Use it when removing a single script. You can optimize bulk removing `n` scripts by setting `commit=False` for the first `n-1` calls and `commit=True` for the last call. """ path = os.path.abspath(path) success = RPR.AddRemoveReaScript( False, section_id, path, commit ) if not success: message = "Script at {} wasn't successfully added.".format(path) raise ValueError(message)
[docs]def rgb_from_native(native_color): """ Extract RGB values from a native (OS-dependent) color. Parameters ---------- native_color : int Native color. Returns ------- r, g, b : (int, int, int) RGB values between 0 and 255. """ _, r, g, b = RPR.ColorFromNative(native_color, 0, 0, 0) return r, g, b
[docs]def rgb_to_native(rgb): """ Make a native (OS-dependent) color from RGB values. Parameters ---------- rgb : (int, int, int) RGB triplet of integers between 0 and 255. Returns ------- native_color : int Native color. """ native_color = RPR.ColorToNative(*rgb) return native_color
[docs]def set_ext_state(section, key, value, persist=False): """ Set the extended state value for a specific section and key. Parameters ---------- section : str Extended state section. key : str Extended state key for section `section`. value : str Extended state value for section `section` and key `key`. persist : bool Whether the value should be stored and reloaded the next time REAPER is opened. See also -------- delete_ext_state get_ext_state """ RPR.SetExtState(section, key, value, persist)
[docs]def set_global_automation_mode(mode): """ Set global automation mode. Parameters ---------- mode : str One of the following values: "bypass" "latch" "none" "read" "touch" "trim/read" "write" """ modes = { "none": -1, "trim/read": 0, "read": 1, "touch": 2, "write": 3, "latch": 4, "bypass": 5 } RPR.SetGlobalAutomationOverride(modes[mode])
[docs]def show_console_message(*args, sep=" ", end="\n"): """ Print a message to the Reaper console. Parameters ---------- args : tuple Values to print. sep : str, optional String inserted between values (default=" "). end : str, optional String appended after the last value (default="\n"). """ file = io.StringIO() _ORIGINAL_PRINT(*args, sep=sep, end=end, file=file) file.seek(0) txt = file.read() RPR.ShowConsoleMsg(txt)
[docs]def show_message_box(text="", title="", type="ok"): """ Show message box. Parameters ---------- text : str Box message title : str Box title type : str One of the following values. "ok" "ok-cancel" "abort-retry-ignore" "yes-no-cancel" "yes-no" "retry-cancel" Returns ------- status : str One of the following values. "ok" "cancel" "abort" "retry" "ignore" "yes" "no" """ all_types = { "ok": 0, "ok-cancel": 1, "abort-retry-ignore": 2, "yes-no-cancel": 3, "yes-no": 4, "retry-cancel": 5 } all_status = { 1: "ok", 2: "cancel", 3: "abort", 4: "retry", 5: "ignore", 6: "yes", 7: "no" } status = RPR.ShowMessageBox(text, title, all_types[type]) status = all_status[status] return status
[docs]def slider_to_dB(slider): """ Convert slider value to decibel. Parameters ---------- slider : float Slider value. Returns ------- db : float Decibel value. See also -------- dB_to_slider """ db = RPR.SLIDER2DB(slider) return db
[docs]def test_api(): """Display a message window if the API can successfully be called.""" RPR.APITest()
[docs]class undo_block(contextlib.ContextDecorator): """Class to register undo block. Its instance can be used both as decorator and context manager: >>> with reapy.undo_block('add track'): ... reapy.Project.add_track() >>> @reapy.undo_block('add track') >>> def some_function(*args, **kwargs): ... reapy.Project.add_track() :param undo_name: Str to register undo name (shown later in Undo menu) :param flags: Int to pass to Undo_EndBlock (leave default if you don't know what it is) """ def __init__(self, undo_name, flags=0): self.undo_name = undo_name self.flags = flags def __enter__(self): RPR.Undo_BeginBlock() def __exit__(self, exc_type, exc_val, exc_tb): RPR.Undo_EndBlock(self.undo_name, self.flags)
[docs]def update_arrange(): """ Redraw the arrange view. """ RPR.UpdateArrange()
[docs]def update_timeline(): """ Redraw the arrange view and ruler. """ RPR.UpdateTimeline()
[docs]def view_prefs(): """ Open Preferences. """ RPR.ViewPrefs(0, "")