Giter Club home page Giter Club logo

ptcollab's Introduction

pxtone collab

ptcollab
pxtone collab is a music editor where you can collaborate with friends!

Features

pxtone collab is based off pxtone collage, a music editor developed by Pixel, the creator of Cave Story and Kero Blaster. As such some features will be familiar:

  • Simple note and parameter input (pan, volume, portamento, fine-tuning, effects)
  • Hassle-free import of samples (ogg, wav) and custom instruments (ogg, wav, ptvoice, ptnoise)
  • Song parameter settings (tempo, time signature)

In addition, ptcollab supports:

  • Collaborative editing: host a server and have others connect and work with you!
  • Session recording: save a frame-by-frame recording of a session and play it back later!
  • MIDI input: Record notes either live while the song is playing, or using keyboard controls to step through time.

Information

Check out the landing page for more info about pxtone collab, including downloads, guides, further links, and thank yous.

Installation

The releases page has executables you can download and just run!

If you're building from source, it should work with a Qt5.15 install, but does require ogg/vorbis, rtmidi, and C++17.

On Mac, you may need to install a later version of clang (e.g., through brew install llvm).

If you have these dependencies , running qmake and then make should build an executable for you.

ptcollab's People

Contributors

blumia avatar ewancg avatar opna2608 avatar testpersonal avatar yuxshao avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

ptcollab's Issues

unit view

drum editing is finicky right now. maybe could be pinned voices instead?

Action to extend notes

Some way to extend an existing note without drawing the whole note again (suggested by damifortune).
Was originally thinking Ctrl+click in a pinned unit to 'merge' what you drew with what's put down already. But that selects the unit currently.

(Linux/macOS) Various installation suggestions

This applies to Linux in particular, but the other major OS' would benefit from it too: Please make the installation prefix user-defined, hard-coding them is never a good idea.

ptcollab/src/editor.pro

Lines 177 to 180 in cb670e6

# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target

The user / their build system manager might want to install them somewhere else, mine for example expects the project file to handle the quasi-standard PREFIX to designate what should be considered the root directory to place /bin, /lib, /share/[projectname] etc under. This path can be very different from /opt; in my case, PREFIX=/nix/store/ccbbas68vlr0d52h8wda9l30rma9gzn8-ptcollab-0.3.4 will be passed to the make invocation. A default should of course still be supplied, which can be /opt or /usr.

For an example how to handle this nicely, you can check out BambooTracker's project file.

https://github.com/rerrahkr/BambooTracker/blob/9fd422431e99f6bd76ad79db7fe1b0e67cf54430/BambooTracker/BambooTracker.pro#L25-L39

https://github.com/rerrahkr/BambooTracker/blob/9fd422431e99f6bd76ad79db7fe1b0e67cf54430/BambooTracker/BambooTracker.pro#L602-L627

Install phase on Windows should install licenses & samples

# These should really be handled by an install rule instead
cp -v -a ../res/sample_* ./
cp -v -a ../LICENSE ./LICENSE-ptcollab
cp -v -a ../src/pxtone/LICENSE ./LICENSE-pxtone
cp -v -a ../deps/lib/{COPYING,LICENSE}-* ./

These install rules

ptcollab/src/editor.pro

Lines 296 to 306 in b03ba18

distfiles.files = $$PWD/../res/sample_instruments $$PWD/../res/sample_songs
distfiles.path = $$PREFIX/share/ptcollab/
INSTALLS += distfiles
license.files = $$PWD/../LICENSE
license.path = $$PREFIX/share/doc/ptcollab
INSTALLS += license
pxtone_license.files = $$PWD/pxtone/LICENSE
pxtone_license.path = $$PREFIX/share/doc/pxtone
INSTALLS += pxtone_license

are currently gated behind a unix. I think it makes sense to install them no matter what platform we're on, albeit with a different path on Windows (where FHS is not a thing and having everything smushed into one place is preferred), similar to what's done here:

ptcollab/src/editor.pro

Lines 259 to 267 in b03ba18

# Rules for deployment.
isEmpty(PREFIX) {
win32:PREFIX = C:/$${TARGET}
else:PREFIX = /opt/$${TARGET}
}
win32:target.path = $$PREFIX
else:target.path = $$PREFIX/bin
INSTALLS += target


For inspiration from BambooTracker:
https://github.com/BambooTracker/BambooTracker/blob/ad82460c598390ded7ea64d119b5f98c4be15027/data/data.pro
https://github.com/BambooTracker/BambooTracker/blob/ad82460c598390ded7ea64d119b5f98c4be15027/qmake/variables.pri#L1-L19

configurable audio settings

e.g. audio sample rate. 44100 is sometimes not the sound card native but instead 48000. it might be more performance if user could set it to their sound card native.

also options for changing the audio device

escape takes you to repeat measure

If your last seek head is after the repeat measure, and your playhead position is after that, escape should take you first to the seek head, then to the repeat measure, then the beginning of the song.

Segfault on shutdown

OPNA2608 reports:

Thread 1 ".ptcollab-wrapp" received signal SIGSEGV, Segmentation fault.
0x00000000004b5a70 in pxtnMaster::get_beat_clock() const ()
(gdb) bt
#0  0x00000000004b5a70 in pxtnMaster::get_beat_clock() const ()
#1  0x00000000004b626e in MasterExtended::last_clock(pxtnMaster const*) ()
#2  0x00000000004851c4 in MooClock::tick() ()
#3  0x00007ffff6d02487 in ?? () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#4  0x00007ffff6ac0ba2 in QVariantAnimation::valueChanged(QVariant const&) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#5  0x00007ffff6ac0ecb in ?? () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#6  0x00007ffff6abe347 in QAbstractAnimation::setCurrentTime(int) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#7  0x00007ffff6abe4d7 in ?? () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#8  0x00007ffff6abce73 in QUnifiedTimer::updateAnimationTimers(long long) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#9  0x00007ffff6abeb1d in QAnimationDriver::advanceAnimation(long long) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#10 0x00007ffff6cf812f in QObject::event(QEvent*) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#11 0x00007ffff7a4576f in QApplicationPrivate::notify_helper(QObject*, QEvent*) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Widgets.so.5
#12 0x00007ffff6ccb48a in QCoreApplication::notifyInternal2(QObject*, QEvent*) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#13 0x00007ffff6d2281b in QTimerInfoList::activateTimers() () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#14 0x00007ffff6d230a4 in ?? () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#15 0x00007ffff6189b0b in g_main_context_dispatch () from /nix/store/400jv7hm1qdi4hzn9yrx1wk7319mrzgm-glib-2.70.2/lib/libglib-2.0.so.0
#16 0x00007ffff6189db8 in g_main_context_iterate.constprop () from /nix/store/400jv7hm1qdi4hzn9yrx1wk7319mrzgm-glib-2.70.2/lib/libglib-2.0.so.0
#17 0x00007ffff6189e6f in g_main_context_iteration () from /nix/store/400jv7hm1qdi4hzn9yrx1wk7319mrzgm-glib-2.70.2/lib/libglib-2.0.so.0
#18 0x00007ffff6d234e1 in QEventDispatcherGlib::processEvents(QFlags<QEventLoop::ProcessEventsFlag>) () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#19 0x00007fffe896a728 in ?? () from /nix/store/id4dw4ligz34ss360ihagk8zkkkqajsk-qtmultimedia-5.15.3-bin/lib/qt-5.15.3/plugins/audio/libqtmedia_pulse.so
#20 0x00007fffe896a7f9 in ?? () from /nix/store/id4dw4ligz34ss360ihagk8zkkkqajsk-qtmultimedia-5.15.3-bin/lib/qt-5.15.3/plugins/audio/libqtmedia_pulse.so
#21 0x00007ffff782f831 in QAudioOutput::~QAudioOutput() () from /nix/store/b09dq4wn9w6x8dcbmj72bmx7zbn5alsb-qtmultimedia-5.15.3/lib/libQt5Multimedia.so.5
#22 0x00007ffff782f849 in QAudioOutput::~QAudioOutput() () from /nix/store/b09dq4wn9w6x8dcbmj72bmx7zbn5alsb-qtmultimedia-5.15.3/lib/libQt5Multimedia.so.5
#23 0x00007ffff6cf58d8 in QObjectPrivate::deleteChildren() () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#24 0x00007ffff6d00694 in QObject::~QObject() () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#25 0x00000000004cde3c in PxtoneClient::~PxtoneClient() ()
#26 0x00007ffff6cf58d8 in QObjectPrivate::deleteChildren() () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Core.so.5
#27 0x00007ffff7a830d8 in QWidget::~QWidget() () from /nix/store/l9lbmr8mmambd5lbyg99lmmk6j66zd1j-qtbase-5.15.3/lib/libQt5Widgets.so.5
#28 0x0000000000431ced in main ()

Seems to do with 67723d1 but I'm not sure why there'd be a use-after-free here; the signal and slot that caused the segfault are both children of PxtoneClient, so I would've thought they'd be cleaned up before the rest of PxtoneClient is destroyed.

Detect RtMidi via pkg-config

ptcollab/src/editor.pro

Lines 8 to 10 in 7783fce

# Including /usr/include/rtmidi since in some dists RtMidi.h is in root dir and
# others it's in a subdir
INCLUDEPATH += . /usr/include/rtmidi

ptcollab/src/editor.pro

Lines 184 to 185 in 7783fce

!win32:LIBS += -logg -lvorbisfile -lrtmidi
win32:LIBS += -L"$$PWD/../deps/lib" -L"$$PWD/deps/lib" -llibogg_static -llibvorbisfile -lrtmidi -lwinmm

You can use pkg-config (added compile-time dependency) via Qmake to add the include paths, library paths and linker arguments for RtMidi instead. This doesn't rely on a hardcoded path like /usr/include/rtmidi and library name like -lrtmidi.

CONFIG += link_pkgconfig
PKGCONFIG += rtmidi

improve polyphonic mode with step input

backspace only deletes main unit, should delete note ons from all selected units
additionally, if someone presses a chord during step input, it'd be good if they all went to the same timestep even with auto-advance on. maybe have a bit of delay before auto-advancing?

switch to not qmultimedia for audio

rtaudio or miniaudio could probably work.
will need to throw all operations in big lock, or do yet more message passing between parallel data structures between audio thread and ui thread

Using Keyboard shortcuts to adjust the selection box

When working with small note values it may be beneficial to be able to use keyboard shortcuts to adjust the selection box

For example the keyboard shortcuts could be as follows:
Shift + Left Arrow Key: Moves the left bound one snap unit left
Ctrl + Shift + Right Arrow Key: Moves the left bound one snap unit right
Shift + Right Arrow Key: Moves the right bound one snap unit right
Ctrl + Shift + Left Arrow Key: Moves the right bound one snap unit left

quick external editor open for instruments

Would be nice to configure some external programs to open when you want to edit a voice, and have it so when the program closes / saves, the voice is automatically updated in the project. At first this would hook into ptvoice / ptnoise / maybe audacity?

Add an easier way to toggle "preview with all voices"

I'm not sure how useful this would be to anyone else, but I would find it nice to have a way to toggle the "preview with all voices" in an easier to reach spot due to the fact that when working on a song there are may times that you only want to hear the melody you're writing and many other times where you want to hear the full harmonies. Just the option isolated in the options dropdown menu would probably be fine or a checkmark box somewhere on the main panel, Either implementation would be convenient enough.

I don't know how complicated a feature like "preview with unmuted/selected units" would be to implement, but I could see me using a feature like that a lot as well.

more menu actions

things like moving between units, etc.
just as a way to make shortcuts more discoverable

Audio output resets with new project

If I change the audio output to a particular device, then open a new ptcop, the audio output resets to the previous device the program opened with, which is annoying.

Smooth follow playhead

have an option to follow the playhead exactly vs. jumping to it when it leaves the window

polyphonic input

  • midi input when you have multiple units selected should alternate input on the selected units
  • maybe could do the same for mouse input too? might want to specify voices for poly input separately from the selection

MIDI output?

Can pxtone collab output MIDI files? I've got a bunch of old ptcop projects that I'd like to extract the MIDI from and drop into Ableton

I know that @yuxshao yuxshao has a ptmidi program (https://github.com/yuxshao/ptmidi) but wondering if this functionality got bundled into pxtone collab?

tool palette

some sort of dock on the side that shows different modes the cursor can be in - pen tool, hand tool, seek tool, select tool, jump to unit tool, etc.

maybe can make it permanently switchable too vs a quasimode just so that the dock serves more than just a visual purpose

Unreasonably slow view painting at HiDPI

Makes the app very slow on a high DPI screen (4k at fullscreen should be doable). Smooth playback requires the use of a very high buffer and framerates range from 5-35 depending on the project loaded (for me, at least; Win11 on i5 9400f and 1070 TI) . The painting APIs used are unable to effectively leverage the GPU for the things that would help in this case, since the slog is mainly logic-based and doesn't lie in the actual painting operations. Of all the QOL things being added to ptcollab recently this one seems like it should be a pretty obvious priority considering I find myself changing my desktop resolution just to use ptcollab & have it fill up my whole screen

Recording mode, like many trackers have

Some interface control that lets the user determine whether or not to record MIDI events in the song. Notes will still make noise if not in recording mode. Playhead could be red/pink (by default) when in recording mode

Editor "userstate" for collaborative sessions

When following a user and then returning back to non-follow mode, settings like playhead follow mode, h/v zoom, selected unit, and more are not set back to what they were initially & are instead kept from the user being watched. Potentially make it so this isn't the case

Allow exporting a project in multiple tracks

This is a feature request which would allow a user to then put the exported tracks in a DAW for further post-processing, for example. Only downside is that the overdrive effect would not work through this and would prolly have to be disabled.

This could potentially be integrated in the export dialog as an export mode: "Export full track" as the default .wav export and "Export as stems", which could export to a folder with the same name as the project and having the individual tracks named after units.

What do you think, though?

add labels for fine tune

show multiplier next to fine tuning events, or cent offset, since ptcollage does things by inputting a number

cannot bind non-const lvalue reference of type ‘QChar&’ to an rvalue of type ‘QChar’

Screenshot from 2020-11-20 16-09-27
Full output of error:

//Desktop/Projects/ptcollabProject/ptcollab/src/protocol/RemoteAction.h:392: error: cannot bind non-const lvalue reference of type ‘QChar&’ to an rvalue of type ‘QChar’
In file included from /home/prinzeono/Qt/5.9.9/gcc_64/include/QtCore/qstring.h:48,
from /home/prinzeono/Qt/5.9.9/gcc_64/include/QtCore/qcoreapplication.h:44,
from /home/prinzeono/Qt/5.9.9/gcc_64/include/QtWidgets/qapplication.h:44,
from /home/prinzeono/Qt/5.9.9/gcc_64/include/QtWidgets/QApplication:1,
from ../../ptcollab/src/main.cpp:1:
/home/prinzeono/Qt/5.9.9/gcc_64/include/QtCore/qchar.h:599:28: note: candidate: ‘QDataStream& operator>>(QDataStream&, QChar&)’
599 | Q_CORE_EXPORT QDataStream &operator>>(QDataStream &, QChar &);
| ^~~~~~~~
/home/prinzeono/Qt/5.9.9/gcc_64/include/QtCore/qchar.h:599:28: note: conversion of argument 2 would be ill-formed:
In file included from ../../ptcollab/src/network/ServerSession.h:9,
from ../../ptcollab/src/network/BroadcastServer.h:10,
from ../../ptcollab/src/editor/EditorWindow.h:18,
from ../../ptcollab/src/main.cpp:7:
../../ptcollab/src/protocol/RemoteAction.h:392:11: error: cannot bind non-const lvalue reference of type ‘QChar&’ to an rvalue of type ‘QChar’
392 | in >> a.flag >> a.set;
| ~~^~~~

macOS build changes

Creating this as a placeholder for a PR I'm working on.

  • Statically link libvorbis/libogg
  • Statically link QT

button to delete backup dir

add a third button in the backup dir dialog for deleting the dir. add a confirmation prompt behind it too

midi sustain, pitch, mod wheel support

mod wheel will probably add note event vibrato similar to ctrl+click. the current porta length can control the speed, and the wheel value can control the depth of the zigzag (prob according to the current snap y?)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.