wip
This commit is contained in:
parent
702a39ef3c
commit
10543665ee
|
|
@ -391,4 +391,5 @@ limit_counter_reminders.sql
|
||||||
amazon_v2.sql
|
amazon_v2.sql
|
||||||
store_backend_details_rate_session.sql
|
store_backend_details_rate_session.sql
|
||||||
invited_user_receiver.sql
|
invited_user_receiver.sql
|
||||||
live_streams.sql
|
live_streams.sql
|
||||||
|
find_sessions_2020.sql
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
ALTER TABLE rsvp_requests ADD COLUMN music_session_id VARCHAR(64) REFERENCES music_sessions(id);
|
||||||
|
ALTER TABLE rsvp_requests ADD COLUMN chosen boolean DEFAULT FALSE NOT NULL;
|
||||||
|
CREATE INDEX rsvp_request_music_session_id ON rsvp_requests USING btree (music_session_id);
|
||||||
|
|
@ -243,6 +243,99 @@ module JamRuby
|
||||||
return query
|
return query
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
|
# all sessions that are private and active, yet I can see
|
||||||
|
def self.friend_active_index(user, options)
|
||||||
|
|
||||||
|
session_id = options[:session_id]
|
||||||
|
genre = options[:genre]
|
||||||
|
lang = options[:lang]
|
||||||
|
keyword = options[:keyword]
|
||||||
|
offset = options[:offset]
|
||||||
|
limit = options[:limit]
|
||||||
|
|
||||||
|
query = MusicSession.select('music_sessions.*')
|
||||||
|
|
||||||
|
query = query.joins("INNER JOIN active_music_sessions ON music_sessions.id = active_music_sessions.id")
|
||||||
|
|
||||||
|
# one flaw in the join below is that we only consider if the creator of the session has asked you to be your friend, but you have not accepted. While this means you may always see a session by someone you haven't friended, the goal is to match up new users more quickly
|
||||||
|
query = query.joins(
|
||||||
|
%Q{
|
||||||
|
|
||||||
|
LEFT OUTER JOIN
|
||||||
|
rsvp_requests
|
||||||
|
ON rsvp_requests.music_session_id = music_sessions.id and rsvp_requests.user_id = '#{user.id}' AND rsvp_requests.chosen = true
|
||||||
|
|
||||||
|
LEFT OUTER JOIN
|
||||||
|
invitations
|
||||||
|
ON
|
||||||
|
active_music_sessions.id = invitations.music_session_id AND invitations.receiver_id = '#{user.id}'
|
||||||
|
LEFT OUTER JOIN
|
||||||
|
friendships
|
||||||
|
ON
|
||||||
|
active_music_sessions.user_id = friendships.user_id AND friendships.friend_id = '#{user.id}'
|
||||||
|
LEFT OUTER JOIN
|
||||||
|
friendships as friendships_2
|
||||||
|
ON
|
||||||
|
active_music_sessions.user_id = friendships_2.friend_id AND friendships_2.user_id = '#{user.id}'
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
# keep only rsvp/invitation/friend results. Nice tailored active list now!
|
||||||
|
query = query.where("rsvp_requests.id IS NOT NULL OR invitations.id IS NOT NULL or active_music_sessions.user_id = '#{user.id}' OR (friendships.id IS NOT NULL AND friendships_2.id IS NOT NULL)")
|
||||||
|
|
||||||
|
# if not specified, default offset to 0
|
||||||
|
offset ||= 0
|
||||||
|
offset = offset.to_i
|
||||||
|
# if not specified, default limit to 20
|
||||||
|
limit ||= 20
|
||||||
|
limit = limit.to_i
|
||||||
|
|
||||||
|
query = query.offset(offset)
|
||||||
|
query = query.limit(limit)
|
||||||
|
query = query.where("music_sessions.genre_id = ?", genre) unless genre.blank?
|
||||||
|
query = query.where('music_sessions.language = ?', lang) unless lang.blank?
|
||||||
|
query = query.where('music_sessions.id = ?', session_id) unless session_id.blank?
|
||||||
|
query = query.where("(description_tsv @@ to_tsquery('jamenglish', ?))", ActiveRecord::Base.connection.quote(keyword) + ':*') unless keyword.blank?
|
||||||
|
query = query.group("music_sessions.id")
|
||||||
|
query
|
||||||
|
end
|
||||||
|
|
||||||
|
# all sessions that are private and active, yet I can see
|
||||||
|
def self.public_index(user, options)
|
||||||
|
|
||||||
|
session_id = options[:session_id]
|
||||||
|
genre = options[:genre]
|
||||||
|
lang = options[:lang]
|
||||||
|
keyword = options[:keyword]
|
||||||
|
offset = options[:offset]
|
||||||
|
limit = options[:limit]
|
||||||
|
|
||||||
|
query = MusicSession.select('music_sessions.*')
|
||||||
|
|
||||||
|
query = query.joins("INNER JOIN active_music_sessions ON music_sessions.id = active_music_sessions.id")
|
||||||
|
|
||||||
|
query = query.where("musician_access = TRUE")
|
||||||
|
|
||||||
|
|
||||||
|
# if not specified, default offset to 0
|
||||||
|
offset ||= 0
|
||||||
|
offset = offset.to_i
|
||||||
|
# if not specified, default limit to 20
|
||||||
|
limit ||= 20
|
||||||
|
limit = limit.to_i
|
||||||
|
|
||||||
|
query = query.offset(offset)
|
||||||
|
query = query.limit(limit)
|
||||||
|
query = query.where("music_sessions.genre_id = ?", genre) unless genre.blank?
|
||||||
|
query = query.where('music_sessions.language = ?', lang) unless lang.blank?
|
||||||
|
query = query.where('music_sessions.id = ?', session_id) unless session_id.blank?
|
||||||
|
query = query.where("(description_tsv @@ to_tsquery('jamenglish', ?))", ActiveRecord::Base.connection.quote(keyword) + ':*') unless keyword.blank?
|
||||||
|
query = query.group("music_sessions.id")
|
||||||
|
query
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
# This is a little confusing. You can specify *BOTH* friends_only and my_bands_only to be true
|
# This is a little confusing. You can specify *BOTH* friends_only and my_bands_only to be true
|
||||||
# If so, then it's an OR condition. If both are false, you can get sessions with anyone.
|
# If so, then it's an OR condition. If both are false, you can get sessions with anyone.
|
||||||
# note, this is mostly the same as above but includes paging through the result and and scores.
|
# note, this is mostly the same as above but includes paging through the result and and scores.
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
module JamRuby
|
module JamRuby
|
||||||
class InvitedUser < ActiveRecord::Base
|
class InvitedUser < ActiveRecord::Base
|
||||||
include HtmlSanitize
|
include HtmlSanitize
|
||||||
html_sanitize strict: [:note]
|
html_sanitize strict: [:note]
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -52,6 +52,7 @@ module JamRuby
|
||||||
has_many :fan_invitations, :foreign_key => "music_session_id", :inverse_of => :music_session, :class_name => "JamRuby::FanInvitation"
|
has_many :fan_invitations, :foreign_key => "music_session_id", :inverse_of => :music_session, :class_name => "JamRuby::FanInvitation"
|
||||||
has_many :invited_fans, :through => :fan_invitations, :class_name => "JamRuby::User", :foreign_key => "receiver_id", :source => :receiver
|
has_many :invited_fans, :through => :fan_invitations, :class_name => "JamRuby::User", :foreign_key => "receiver_id", :source => :receiver
|
||||||
has_many :rsvp_slots, :class_name => "JamRuby::RsvpSlot", :foreign_key => "music_session_id", :dependent => :destroy
|
has_many :rsvp_slots, :class_name => "JamRuby::RsvpSlot", :foreign_key => "music_session_id", :dependent => :destroy
|
||||||
|
has_many :rsvp_requests, :class_name => "JamRuby::RsvpRequest", :foreign_key => "music_session_id", :dependent => :destroy
|
||||||
has_many :music_notations, :class_name => "JamRuby::MusicNotation", :foreign_key => "music_session_id"
|
has_many :music_notations, :class_name => "JamRuby::MusicNotation", :foreign_key => "music_session_id"
|
||||||
has_many :jam_track_session, :class_name => "JamRuby::JamTrackSession"
|
has_many :jam_track_session, :class_name => "JamRuby::JamTrackSession"
|
||||||
has_many :broadcasts, :class_name => "JamRuby::Broadcast"
|
has_many :broadcasts, :class_name => "JamRuby::Broadcast"
|
||||||
|
|
@ -359,6 +360,7 @@ module JamRuby
|
||||||
rsvp = RsvpRequest.find_by_id(rsvp_request_slot.rsvp_request_id)
|
rsvp = RsvpRequest.find_by_id(rsvp_request_slot.rsvp_request_id)
|
||||||
new_rsvp = RsvpRequest.new
|
new_rsvp = RsvpRequest.new
|
||||||
new_rsvp.user_id = rsvp.user_id
|
new_rsvp.user_id = rsvp.user_id
|
||||||
|
new_rsvp.music_session_id = rsvp.music_session_id
|
||||||
|
|
||||||
new_rsvp_req_slot = RsvpRequestRsvpSlot.new
|
new_rsvp_req_slot = RsvpRequestRsvpSlot.new
|
||||||
new_rsvp_req_slot.rsvp_request = new_rsvp
|
new_rsvp_req_slot.rsvp_request = new_rsvp
|
||||||
|
|
@ -379,6 +381,7 @@ module JamRuby
|
||||||
if rsvp.canceled && !rsvp.cancel_all
|
if rsvp.canceled && !rsvp.cancel_all
|
||||||
new_rsvp = RsvpRequest.new
|
new_rsvp = RsvpRequest.new
|
||||||
new_rsvp.user_id = rsvp.user_id
|
new_rsvp.user_id = rsvp.user_id
|
||||||
|
new_rsvp.music_session_id = rsvp.music_session_id
|
||||||
|
|
||||||
new_rsvp_req_slot = RsvpRequestRsvpSlot.new
|
new_rsvp_req_slot = RsvpRequestRsvpSlot.new
|
||||||
new_rsvp_req_slot.rsvp_request = new_rsvp
|
new_rsvp_req_slot.rsvp_request = new_rsvp
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@ module JamRuby
|
||||||
class RsvpRequest < ActiveRecord::Base
|
class RsvpRequest < ActiveRecord::Base
|
||||||
|
|
||||||
belongs_to :user, :class_name => "JamRuby::User"
|
belongs_to :user, :class_name => "JamRuby::User"
|
||||||
|
belongs_to :music_session, :class_name => "JamRuby::MusicSession"
|
||||||
has_many :rsvp_requests_rsvp_slots, :class_name => "JamRuby::RsvpRequestRsvpSlot", :foreign_key => "rsvp_request_id"
|
has_many :rsvp_requests_rsvp_slots, :class_name => "JamRuby::RsvpRequestRsvpSlot", :foreign_key => "rsvp_request_id"
|
||||||
has_many :rsvp_slots, :class_name => "JamRuby::RsvpSlot", :through => :rsvp_requests_rsvp_slots
|
has_many :rsvp_slots, :class_name => "JamRuby::RsvpSlot", :through => :rsvp_requests_rsvp_slots
|
||||||
|
|
||||||
|
|
@ -69,6 +70,8 @@ module JamRuby
|
||||||
RsvpRequest.transaction do
|
RsvpRequest.transaction do
|
||||||
@rsvp = RsvpRequest.new
|
@rsvp = RsvpRequest.new
|
||||||
@rsvp.user = user
|
@rsvp.user = user
|
||||||
|
@rsvp.music_session = music_session
|
||||||
|
@rsvp.chosen = true if params[:autoapprove] == true
|
||||||
|
|
||||||
slot_ids = params[:rsvp_slots]
|
slot_ids = params[:rsvp_slots]
|
||||||
|
|
||||||
|
|
@ -165,6 +168,8 @@ module JamRuby
|
||||||
end
|
end
|
||||||
|
|
||||||
RsvpRequest.transaction do
|
RsvpRequest.transaction do
|
||||||
|
|
||||||
|
rsvp_request.chosen = true
|
||||||
rsvp_responses = params[:rsvp_responses]
|
rsvp_responses = params[:rsvp_responses]
|
||||||
if !rsvp_responses.blank?
|
if !rsvp_responses.blank?
|
||||||
instruments = []
|
instruments = []
|
||||||
|
|
@ -234,6 +239,8 @@ module JamRuby
|
||||||
else
|
else
|
||||||
raise StateError, "Invalid request."
|
raise StateError, "Invalid request."
|
||||||
end
|
end
|
||||||
|
|
||||||
|
rsvp_request.save
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -657,7 +657,8 @@ module JamRuby
|
||||||
end
|
end
|
||||||
|
|
||||||
def recording_count
|
def recording_count
|
||||||
self.recordings.size
|
#self.recordings.size
|
||||||
|
0
|
||||||
end
|
end
|
||||||
|
|
||||||
def age
|
def age
|
||||||
|
|
@ -666,7 +667,8 @@ module JamRuby
|
||||||
end
|
end
|
||||||
|
|
||||||
def session_count
|
def session_count
|
||||||
MusicSession.where("user_id = ? AND started_at IS NOT NULL", self.id).size
|
0
|
||||||
|
#MusicSession.where("user_id = ? AND started_at IS NOT NULL", self.id).size
|
||||||
end
|
end
|
||||||
|
|
||||||
# count up any session you are RSVP'ed to
|
# count up any session you are RSVP'ed to
|
||||||
|
|
|
||||||
|
|
@ -389,7 +389,174 @@ describe ActiveMusicSession do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "ams_index", no_transaction: true do
|
|
||||||
|
describe "public index", no_transaction: false do
|
||||||
|
it "public_index" do
|
||||||
|
|
||||||
|
creator = FactoryGirl.create(:user)
|
||||||
|
creator2 = FactoryGirl.create(:user)
|
||||||
|
earlier_session = FactoryGirl.create(:active_music_session, :creator => creator, :description => "Earlier Session")
|
||||||
|
later_session = FactoryGirl.create(:active_music_session, :creator => creator2, :description => "Later Session")
|
||||||
|
user = FactoryGirl.create(:user)
|
||||||
|
earlier_session.music_session.musician_access = true
|
||||||
|
earlier_session.music_session.save!
|
||||||
|
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.public_index(creator, {}).take(100)
|
||||||
|
music_sessions.should_not be_nil
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
describe "friend_active_index", no_transaction: false do
|
||||||
|
it "does not crash" do
|
||||||
|
|
||||||
|
creator = FactoryGirl.create(:user)
|
||||||
|
creator2 = FactoryGirl.create(:user)
|
||||||
|
earlier_session = FactoryGirl.create(:active_music_session, :creator => creator, :description => "Earlier Session")
|
||||||
|
later_session = FactoryGirl.create(:active_music_session, :creator => creator2, :description => "Later Session")
|
||||||
|
user = FactoryGirl.create(:user)
|
||||||
|
earlier_session.music_session.musician_access = false
|
||||||
|
earlier_session.music_session.save!
|
||||||
|
|
||||||
|
Friendship.save_using_models(creator, creator2)
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(creator, {}).take(100)
|
||||||
|
music_sessions.should_not be_nil
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
end
|
||||||
|
|
||||||
|
describe "parameters" do
|
||||||
|
let(:creator_1) { FactoryGirl.create(:user, last_jam_locidispid: 4, last_jam_audio_latency: 8) }
|
||||||
|
let(:creator_conn_1) { FactoryGirl.create(:connection, user: creator_1, ip_address: '4.4.4.4', locidispid: 4, addr:4) }
|
||||||
|
let(:creator_2) { FactoryGirl.create(:user, last_jam_locidispid: 1, last_jam_audio_latency: 10) }
|
||||||
|
let(:creator_conn_2) { FactoryGirl.create(:connection, user: creator_2, ip_address: '4.4.4.4', locidispid: 1, addr:1) }
|
||||||
|
let(:creator_3) { FactoryGirl.create(:user, last_jam_locidispid: 2, last_jam_audio_latency: 12) }
|
||||||
|
let(:creator_conn_3) { FactoryGirl.create(:connection, user: creator_3, ip_address: '5.5.5.5', locidispid: 2, addr:2) }
|
||||||
|
let(:searcher_1) { FactoryGirl.create(:user, last_jam_locidispid: 5, last_jam_audio_latency: 6) }
|
||||||
|
let(:searcher_conn_1) { FactoryGirl.create(:connection, user: searcher_1, ip_address: '8.8.8.8', locidispid: 5, addr:5) }
|
||||||
|
let(:searcher_2) { FactoryGirl.create(:user, last_jam_locidispid: 3, last_jam_audio_latency: 14) }
|
||||||
|
let(:searcher_conn_2) { FactoryGirl.create(:connection, user: searcher_2, ip_address: '9.9.9.9', locidispid: 3, addr:3) }
|
||||||
|
|
||||||
|
|
||||||
|
let!(:music_session_1) { FactoryGirl.create(:active_music_session, :creator => creator_1, genre: Genre.find('african'), language: 'eng', description: "Bunny Jumps" ) }
|
||||||
|
let!(:music_session_2) { FactoryGirl.create(:active_music_session, :creator => creator_2, genre: Genre.find('ambient'), language: 'spa', description: "Play with us as we jam to beatles and bunnies") }
|
||||||
|
|
||||||
|
let(:tracks) { [{'sound' => 'mono', 'client_track_id' => 'abc', 'instrument_id' => 'piano'}] }
|
||||||
|
|
||||||
|
it "as invited" do
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 0
|
||||||
|
|
||||||
|
Friendship.save_using_models(searcher_1, creator_1)
|
||||||
|
FactoryGirl.create(:invitation, music_session: music_session_1.music_session, sender: creator_1, receiver: searcher_1)
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].should == music_session_1.music_session
|
||||||
|
end
|
||||||
|
|
||||||
|
it "as rsvp" do
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 0
|
||||||
|
|
||||||
|
rsvp_slot = FactoryGirl.create(:rsvp_slot, music_session: music_session_1.music_session, instrument: Instrument.find('piano'))
|
||||||
|
rsvp_request = FactoryGirl.create(:rsvp_request, user: searcher_1, chosen:true, music_session: music_session_1.music_session)
|
||||||
|
rsvp_request_rsvp_slot = FactoryGirl.create(:rsvp_request_rsvp_slot, chosen:true, rsvp_request: rsvp_request, rsvp_slot:rsvp_slot)
|
||||||
|
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].should == music_session_1.music_session
|
||||||
|
end
|
||||||
|
|
||||||
|
describe "as friends" do
|
||||||
|
|
||||||
|
before(:each) {
|
||||||
|
Friendship.save_using_models(searcher_1, creator_1)
|
||||||
|
Friendship.save_using_models(searcher_1, creator_2)
|
||||||
|
}
|
||||||
|
|
||||||
|
it "offset/limit" do
|
||||||
|
# put creators in the session
|
||||||
|
creator_conn_1.join_the_session(music_session_1.music_session, true, tracks, creator_1, 10)
|
||||||
|
creator_conn_1.errors.any?.should be_false
|
||||||
|
creator_conn_2.join_the_session(music_session_2.music_session, true, tracks, creator_2, 10)
|
||||||
|
creator_conn_2.errors.any?.should be_false
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
music_sessions[0].should == music_session_1.music_session
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, offset:0, limit:1)
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].should == music_session_1.music_session
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, offset:1, limit:2)
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].should == music_session_2.music_session
|
||||||
|
end
|
||||||
|
|
||||||
|
it "genre" do
|
||||||
|
# verify we can get all 2 sessions
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
|
||||||
|
# get only african
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, genre: 'african')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].genre.should == Genre.find('african')
|
||||||
|
|
||||||
|
# get only ambient
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, genre: 'ambient')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].genre.should == Genre.find('ambient')
|
||||||
|
end
|
||||||
|
|
||||||
|
it "language" do
|
||||||
|
# verify we can get all 2 sessions
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, {})
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
|
||||||
|
# get only english
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, lang: 'eng')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].language.should == 'eng'
|
||||||
|
|
||||||
|
# get only ambient
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, lang: 'spa')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
music_sessions[0].language.should == 'spa'
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
it "keyword" do
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, keyword: 'Jump')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
|
||||||
|
music_sessions[0].should == music_session_1.music_session
|
||||||
|
music_sessions = ams(searcher_1, keyword: 'Bunny')
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, keyword: 'play')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, keyword: 'bun')
|
||||||
|
music_sessions.length.should == 2
|
||||||
|
|
||||||
|
|
||||||
|
music_sessions = ActiveMusicSession.friend_active_index(searcher_1, keyword: 'bunny play')
|
||||||
|
music_sessions.length.should == 1
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
describe "ams_index", no_transaction: true do
|
||||||
it "does not crash" do
|
it "does not crash" do
|
||||||
|
|
||||||
creator = FactoryGirl.create(:user, last_jam_locidispid: 1, last_jam_audio_latency: 5)
|
creator = FactoryGirl.create(:user, last_jam_locidispid: 1, last_jam_audio_latency: 5)
|
||||||
|
|
|
||||||
|
|
@ -145,6 +145,20 @@
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function findFriendSessions(query) {
|
||||||
|
return $.ajax({
|
||||||
|
type: "GET",
|
||||||
|
url: "/api/sessions/friends?" + $.param(query)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function findPublicSessions(query) {
|
||||||
|
return $.ajax({
|
||||||
|
type: "GET",
|
||||||
|
url: "/api/sessions/public?" + $.param(query)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
function findActiveSessions(query) {
|
function findActiveSessions(query) {
|
||||||
return $.ajax({
|
return $.ajax({
|
||||||
type: "GET",
|
type: "GET",
|
||||||
|
|
@ -3097,6 +3111,8 @@
|
||||||
this.listOnboardings = listOnboardings;
|
this.listOnboardings = listOnboardings;
|
||||||
this.getOnboarding = getOnboarding;
|
this.getOnboarding = getOnboarding;
|
||||||
this.updateOnboarding = updateOnboarding;
|
this.updateOnboarding = updateOnboarding;
|
||||||
|
this.findFriendSessions = findFriendSessions;
|
||||||
|
this.findPublicSessions = findPublicSessions;
|
||||||
return this;
|
return this;
|
||||||
};
|
};
|
||||||
})(window, jQuery);
|
})(window, jQuery);
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,133 @@
|
||||||
|
context = window
|
||||||
|
|
||||||
|
@FindSessionFriends = React.createClass({
|
||||||
|
|
||||||
|
mixins: [Reflux.listenTo(@AppStore, "onAppInit")]
|
||||||
|
|
||||||
|
getInitialState: () ->
|
||||||
|
{sessions: [], currentPage: 0, next: null, searching: false, count: 0}
|
||||||
|
|
||||||
|
|
||||||
|
search: () ->
|
||||||
|
return if @state.searching
|
||||||
|
|
||||||
|
$root = $(@getDOMNode())
|
||||||
|
# disable scroll watching now that we've started a new search
|
||||||
|
$root.find('.content-body-scroller').off('scroll')
|
||||||
|
$root.find('.end-of-sessions-list').hide()
|
||||||
|
|
||||||
|
|
||||||
|
# we have to make sure the query starts from page 1, and no 'next' from previous causes a 'since' to show up
|
||||||
|
query = @defaultQuery({page: 0})
|
||||||
|
delete query.since
|
||||||
|
@rest.findFriendSessions(query)
|
||||||
|
.done((response) =>
|
||||||
|
@setState({sessions: response.sessions, searching: false, first_search: false, currentPage: 1})
|
||||||
|
)
|
||||||
|
.fail((jqXHR) =>
|
||||||
|
@app.notifyServerError jqXHR, 'Search Unavailable'
|
||||||
|
@setState({searching: false, first_search: false})
|
||||||
|
)
|
||||||
|
|
||||||
|
@setState({currentPage: 0, sessions:[], searching: true})
|
||||||
|
|
||||||
|
sessionResults: () ->
|
||||||
|
results = []
|
||||||
|
for session in @state.sessions
|
||||||
|
results.push(`<FindSessionRow session={session} />`)
|
||||||
|
results
|
||||||
|
|
||||||
|
render: () ->
|
||||||
|
results = @sessionResults()
|
||||||
|
|
||||||
|
className = "sessions-for-me"
|
||||||
|
|
||||||
|
if(@props.active)
|
||||||
|
className = className + " active"
|
||||||
|
|
||||||
|
`<div className={className}>
|
||||||
|
<div className="content-body-scroller">
|
||||||
|
<div className="content-wrapper">
|
||||||
|
<div id="sessions-active" className="session-container">
|
||||||
|
<h2>sessions for me</h2>
|
||||||
|
<br/>
|
||||||
|
|
||||||
|
<div className="findsession-container">
|
||||||
|
<table id="sessions-active" className="findsession-table" cellspacing="0"
|
||||||
|
cellpadding="0" border="0">
|
||||||
|
<tr>
|
||||||
|
<th align="left" width="30%">SESSION</th>
|
||||||
|
<th align="left" width="35%">MUSICIANS</th>
|
||||||
|
<th align="left" width="30%" style={{textAlign:'center'}}>ACTIONS</th>
|
||||||
|
</tr>
|
||||||
|
{results}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>`
|
||||||
|
|
||||||
|
|
||||||
|
defaultQuery: (extra) ->
|
||||||
|
query =
|
||||||
|
limit: @LIMIT
|
||||||
|
offset: @state.currentPage * @LIMIT
|
||||||
|
|
||||||
|
$.extend(query, extra)
|
||||||
|
|
||||||
|
componentDidMount: () ->
|
||||||
|
@EVENTS = context.JK.EVENTS
|
||||||
|
@rest = context.JK.Rest()
|
||||||
|
@logger = context.JK.logger
|
||||||
|
|
||||||
|
@search()
|
||||||
|
|
||||||
|
componentDidUpdate: () ->
|
||||||
|
$root = $(this.getDOMNode())
|
||||||
|
$scroller = $root.find('.content-body-scroller')
|
||||||
|
|
||||||
|
if @state.next == null
|
||||||
|
$scroller = $root.find('.content-body-scroller')
|
||||||
|
# if we less results than asked for, end searching
|
||||||
|
#$scroller.infinitescroll 'pause'
|
||||||
|
$scroller.off('scroll')
|
||||||
|
if @state.currentPage == 1 and @state.sessions.length == 0
|
||||||
|
$root.find('.end-of-sessions-list').text('No friend sessions found').show()
|
||||||
|
@logger.debug("FindSessions: empty search")
|
||||||
|
else if @state.currentPage > 0
|
||||||
|
$noMoreSessions = $root.find('.end-of-sessions-list').text('No more sessions').show()
|
||||||
|
# there are bugs with infinitescroll not removing the 'loading'.
|
||||||
|
# it's most noticeable at the end of the list, so whack all such entries
|
||||||
|
else
|
||||||
|
@registerInfiniteScroll($scroller)
|
||||||
|
|
||||||
|
registerInfiniteScroll: ($scroller) ->
|
||||||
|
$scroller.off('scroll')
|
||||||
|
$scroller.on('scroll', () =>
|
||||||
|
|
||||||
|
# be sure to not fire off many refreshes when user hits the bottom
|
||||||
|
return if @refreshing
|
||||||
|
|
||||||
|
if $scroller.scrollTop() + $scroller.innerHeight() + 100 >= $scroller[0].scrollHeight
|
||||||
|
$scroller.append('<div class="infinite-scroll-loader-2">... Loading more Sessions ...</div>')
|
||||||
|
@refreshing = true
|
||||||
|
@logger.debug("refreshing more sessions for infinite scroll")
|
||||||
|
@setState({searching: true})
|
||||||
|
@rest.findFriendSessions(@defaultQuery())
|
||||||
|
.done((json) =>
|
||||||
|
@setState({
|
||||||
|
sessions: @state.sessions.concat(json.sessions),
|
||||||
|
currentPage: @state.currentPage + 1
|
||||||
|
})
|
||||||
|
)
|
||||||
|
.always(() =>
|
||||||
|
$scroller.find('.infinite-scroll-loader-2').remove()
|
||||||
|
@refreshing = false
|
||||||
|
@setState({searching: false})
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
|
onAppInit: (@app) ->
|
||||||
|
return
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,272 @@
|
||||||
|
context = window
|
||||||
|
rest = window.JK.Rest()
|
||||||
|
logger = context.JK.logger
|
||||||
|
|
||||||
|
@FindSessionRow = React.createClass({
|
||||||
|
|
||||||
|
createInstrument: (participant) ->
|
||||||
|
|
||||||
|
instruments = []
|
||||||
|
existingTracks = []
|
||||||
|
for j in [0 .. participant.tracks.length]
|
||||||
|
|
||||||
|
track = participant.tracks[j]
|
||||||
|
|
||||||
|
if existingTracks.indexOf(track.instrument_id) < 0
|
||||||
|
existingTracks.push(track.instrument_id)
|
||||||
|
logger.debug("Find:Finding instruments. Participant tracks:", participant.tracks)
|
||||||
|
inst = context.JK.getInstrumentIcon24(track.instrument_id)
|
||||||
|
instruments.push(`<img title={context.JK.getInstrumentId(track.instrument_id)} hoveraction="instrument" data-instrument-id={track.instrument_id} src={inst} width="24" height="24" />`)
|
||||||
|
|
||||||
|
instruments
|
||||||
|
|
||||||
|
|
||||||
|
createInSessionUser: (participant) ->
|
||||||
|
|
||||||
|
instruments = @createInstrument(participant)
|
||||||
|
id = participant.user.id;
|
||||||
|
name = participant.user.name;
|
||||||
|
userId = id
|
||||||
|
avatar_url = context.JK.resolveAvatarUrl(participant.user.photo_url)
|
||||||
|
profile_url = "/client#/profile/" + id
|
||||||
|
musician_name = name
|
||||||
|
more_link = ''
|
||||||
|
|
||||||
|
`<tr>
|
||||||
|
<td width="24">
|
||||||
|
<a user-id={userId} hoveraction="musician" href={profile_url} className="avatar-tiny">
|
||||||
|
<img src={avatar_url} />
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a user-id={userId} hoveraction="musician" href={profile_url}>{musician_name}</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div className="instruments nowrap">{instruments}</div>
|
||||||
|
</td>
|
||||||
|
<td>{more_link} </td>
|
||||||
|
</tr>`
|
||||||
|
|
||||||
|
|
||||||
|
createOpenSlot:(slot) ->
|
||||||
|
|
||||||
|
|
||||||
|
` <tr>
|
||||||
|
<td width="24">
|
||||||
|
<img src="{instrument_url}" />
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div className="instruments nowrap">{instrument} ({proficiency})</div>
|
||||||
|
</td>
|
||||||
|
<td>{more_link} </td>
|
||||||
|
</tr>`
|
||||||
|
|
||||||
|
createRsvpUser: (user, session, isLast) ->
|
||||||
|
instrumentLogoHtml = []
|
||||||
|
|
||||||
|
if user.instrument_list
|
||||||
|
for j in [0 .. user.instrument_list.length]
|
||||||
|
instrument = user.instrument_list[j];
|
||||||
|
inst = context.JK.getInstrumentIcon24(instrument.id);
|
||||||
|
instrumentLogoHtml.push(`<img title={context.JK.getInstrumentId(instrument.id)} hoveraction="instrument" data-instrument-id={instrument.id} src={inst} width="24" height="24" />`)
|
||||||
|
|
||||||
|
moreLinkHtml = '';
|
||||||
|
if isLast
|
||||||
|
moreLinkHtml = `<span><a class="rsvps more">more</a><a className="details-arrow arrow-down-orange"></a></span>`
|
||||||
|
|
||||||
|
instruments = @createInstrument(user)
|
||||||
|
id = participant.user.id;
|
||||||
|
name = participant.user.name;
|
||||||
|
userId = id
|
||||||
|
avatar_url = context.JK.resolveAvatarUrl(participant.user.photo_url)
|
||||||
|
profile_url = "/client#/profile/" + id
|
||||||
|
musician_name = name
|
||||||
|
more_link = ''
|
||||||
|
|
||||||
|
`<tr>
|
||||||
|
<td width="24">
|
||||||
|
<a user-id={userId} hoveraction="musician" href={profile_url} className="avatar-tiny">
|
||||||
|
<img src={avatar_url} />
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a user-id={userId} hoveraction="musician" href={profile_url}>{musician_name}</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div className="instruments nowrap">{instruments}</div>
|
||||||
|
</td>
|
||||||
|
<td>{more_link} </td>
|
||||||
|
</tr>`
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
inSessionUsersHtml: (session) ->
|
||||||
|
inSessionUsers = []
|
||||||
|
|
||||||
|
result = []
|
||||||
|
if session.active_music_session && "participants" in session.active_music_session && session.active_music_session.participants.length > 0
|
||||||
|
for i in [0 .. session.active_music_session.participants.length]
|
||||||
|
participant = session.active_music_session.participants[i]
|
||||||
|
inSessionUsers.push(participant.user.id);
|
||||||
|
result.push(@createInSessionUser(participant))
|
||||||
|
|
||||||
|
return [result, inSessionUsers]
|
||||||
|
|
||||||
|
|
||||||
|
createRsvpUsers:( ) ->
|
||||||
|
|
||||||
|
session = @props.session
|
||||||
|
|
||||||
|
firstResults = []
|
||||||
|
lastResults = []
|
||||||
|
|
||||||
|
approvedRsvpCount = session.approved_rsvps.length
|
||||||
|
|
||||||
|
if session.approved_rsvps
|
||||||
|
first = session.approved_rsvps.slice(0, 3)
|
||||||
|
last = session.approved_rsvps.slice(3)
|
||||||
|
|
||||||
|
for i in [0..first]
|
||||||
|
user = first[i]
|
||||||
|
firstResults.push(@createRsvpUser(user, session, approvedRsvpCount > 3 && i == 2))
|
||||||
|
for i in [0..last]
|
||||||
|
user = last[i]
|
||||||
|
lastResults.push(@createRsvpUser(user, session, false))
|
||||||
|
|
||||||
|
[firstResults, lastResults]
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
createOpenSlots: () ->
|
||||||
|
session = @prop.session
|
||||||
|
|
||||||
|
firstResults = []
|
||||||
|
remainingResults = []
|
||||||
|
|
||||||
|
if session['is_unstructured_rsvp?']
|
||||||
|
firstResults.push(@createOpenSlot({description: 'Any Instrument'}))
|
||||||
|
|
||||||
|
if session.open_slots
|
||||||
|
openSlotCount = session.open_slots.length
|
||||||
|
for i in [0 .. openSlotCount]
|
||||||
|
openSlot = session.open_slots[i]
|
||||||
|
if i < 3
|
||||||
|
firstResults.push(@createOpenSlot(session.open_slots[i], openSlotCount > 3 && i == 2))
|
||||||
|
else
|
||||||
|
remainingResults.push(@createOpenSlot(session.open_slots[i], false))
|
||||||
|
|
||||||
|
return [firstResults, remainingResults]
|
||||||
|
|
||||||
|
showJoinLinks: (inSessionUsers) ->
|
||||||
|
session = @prop.session
|
||||||
|
showJoinLink = session.musician_access
|
||||||
|
if session.approved_rsvps
|
||||||
|
approvedRsvpCount = session.approved_rsvps.length
|
||||||
|
for i in [0 .. approvedRsvpCount]
|
||||||
|
# do not show the user in this section if he is already in the session
|
||||||
|
if $.inArray(session.approved_rsvps[i].id, inSessionUsers) == -1
|
||||||
|
if session.approved_rsvps[i].id == context.JK.currentUserId
|
||||||
|
showJoinLink = true
|
||||||
|
else
|
||||||
|
showJoinLink = true
|
||||||
|
|
||||||
|
showJoinLink
|
||||||
|
|
||||||
|
|
||||||
|
render: () ->
|
||||||
|
|
||||||
|
session = @props.session
|
||||||
|
|
||||||
|
id = session.id
|
||||||
|
name = session.name
|
||||||
|
description = session.description || "(No description)"
|
||||||
|
genres = '(' + session.genres.join (', ') + ')'
|
||||||
|
[in_session_musicians, inSessionUsers] = @inSessionUsersHtml()
|
||||||
|
[rsvp_musicians_first_3, rsvp_musicians_remaining] = @createRsvpUsers()
|
||||||
|
[open_slots_first_3, open_slots_remaining] = @createOpenSlots()
|
||||||
|
showJoinLink = @showJoinLink(inSessionUsers)
|
||||||
|
showListenLink = session.fan_access && session.active_music_session && session.active_music_session.mount
|
||||||
|
join_link_display_style = {display: "none"}
|
||||||
|
listen_link_display_style = {display: "none"}
|
||||||
|
if showJoinLink
|
||||||
|
join_link_display_style = {display: "block"}
|
||||||
|
if showListenLink
|
||||||
|
listen_link_display_style = {display: "inline-block"}
|
||||||
|
listen_link_text = ''
|
||||||
|
|
||||||
|
if !session.fan_access
|
||||||
|
listen_link_text = ''
|
||||||
|
else if session.active_music_session && session.active_music_session.mount
|
||||||
|
listen_link_text = 'Listen'
|
||||||
|
else
|
||||||
|
listen_link_text = '';
|
||||||
|
|
||||||
|
|
||||||
|
`<tr data-session-id={id} className="found-session">
|
||||||
|
<td width="30%">
|
||||||
|
<table className="musician-groups" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
<tr>
|
||||||
|
<td className="bold"><a href={"/sessions/" + id} rel="external">{name}</a></td>
|
||||||
|
<td align="right" width="75">{genres}</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="2">{description}</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="35%">
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
<tr>
|
||||||
|
<td>In Session:</td>
|
||||||
|
<td>
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{in_session_musicians}
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>RSVPs:</td>
|
||||||
|
<td>
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none;">
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>Still Needed:</td>
|
||||||
|
<td>
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none">
|
||||||
|
<table className="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="30%" className="latency">
|
||||||
|
<div className="center">
|
||||||
|
<a className="listen-link" style="display:{listen_link_display_style};">
|
||||||
|
<img className="listen-icon" />
|
||||||
|
</a>
|
||||||
|
<br/>
|
||||||
|
<span className="listen-link-details"><span className="listen-link-text">{listen_link_text}</span><a href="#" className="listen-detail-hover">?</a></span>
|
||||||
|
</div>
|
||||||
|
<div className="center">
|
||||||
|
<a className="join-link" style="display:{join_link_display_style};">
|
||||||
|
<img className="join-icon" />
|
||||||
|
</a>
|
||||||
|
<span className="join-link-text">Join</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</td>
|
||||||
|
</tr>`
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,108 @@
|
||||||
|
context = window
|
||||||
|
MIX_MODES = context.JK.MIX_MODES
|
||||||
|
|
||||||
|
|
||||||
|
@FindSessionScreen = React.createClass({
|
||||||
|
|
||||||
|
mixins: [Reflux.listenTo(@AppStore, "onAppInit"), Reflux.listenTo(@UserStore, "onUserChanged")]
|
||||||
|
|
||||||
|
LIMIT: 20
|
||||||
|
instrument_logo_map: context.JK.getInstrumentIconMap24()
|
||||||
|
|
||||||
|
getInitialState: () ->
|
||||||
|
{activeTab: 'friends', search: '', type: 'user-input'}
|
||||||
|
|
||||||
|
|
||||||
|
generateProperties: (tab) ->
|
||||||
|
properties = {}
|
||||||
|
properties['active'] = @state.activeTab == tab
|
||||||
|
properties
|
||||||
|
|
||||||
|
generateTabClasses: (tab) ->
|
||||||
|
classes = {}
|
||||||
|
classes['button-orange'] = true
|
||||||
|
classes['find-tab'] = true
|
||||||
|
classes[tab] = true
|
||||||
|
|
||||||
|
if @state.activeTab == tab
|
||||||
|
classes['active'] = true
|
||||||
|
|
||||||
|
classNames(classes)
|
||||||
|
|
||||||
|
render: () ->
|
||||||
|
|
||||||
|
friendTabClasses = @generateTabClasses('friends')
|
||||||
|
publicTabClasses = @generateTabClasses('public')
|
||||||
|
scheduledTabClasses = @generateTabClasses('scheduled')
|
||||||
|
|
||||||
|
friendProperties = @generateProperties('friends')
|
||||||
|
publicProperties = @generateProperties('public')
|
||||||
|
scheduledProperties = @generateProperties('scheduled')
|
||||||
|
|
||||||
|
search = ''
|
||||||
|
|
||||||
|
`<div className="">
|
||||||
|
<div className="">
|
||||||
|
<form id="find-session-form">
|
||||||
|
<div className="session-filter">
|
||||||
|
<div style={{minWidth:'770px'}}>
|
||||||
|
<div className="tabs">
|
||||||
|
<a className={friendTabClasses}>
|
||||||
|
Friends
|
||||||
|
</a>
|
||||||
|
|
||||||
|
<a className={publicTabClasses}>
|
||||||
|
Public
|
||||||
|
</a>
|
||||||
|
|
||||||
|
<a className={scheduledTabClasses}>
|
||||||
|
Scheduled
|
||||||
|
</a>
|
||||||
|
|
||||||
|
|
||||||
|
<div className="search-box">
|
||||||
|
<input className="session-keyword-srch" type="text" name="search"
|
||||||
|
placeholder="Search by Keyword"/>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="right mr10">
|
||||||
|
<a href="/client#/findSession" style={{textDecoration:'none'}}
|
||||||
|
className="button-grey btn-refresh">REFRESH<span class="extra"></span></a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<FindSessionFriends active={friendProperties.active} />
|
||||||
|
</div>
|
||||||
|
</div>`
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
componentDidMount: () ->
|
||||||
|
return
|
||||||
|
|
||||||
|
componentDidUpdate: () ->
|
||||||
|
return
|
||||||
|
|
||||||
|
beforeShow: () ->
|
||||||
|
return
|
||||||
|
|
||||||
|
afterShow: () ->
|
||||||
|
return
|
||||||
|
|
||||||
|
onAppInit: (@app) ->
|
||||||
|
@EVENTS = context.JK.EVENTS
|
||||||
|
@rest = context.JK.Rest()
|
||||||
|
@logger = context.JK.logger
|
||||||
|
|
||||||
|
screenBindings =
|
||||||
|
'beforeShow': @beforeShow
|
||||||
|
'afterShow': @afterShow
|
||||||
|
|
||||||
|
@app.bindScreen('findSession', screenBindings)
|
||||||
|
|
||||||
|
onUserChanged: (userState) ->
|
||||||
|
@user = userState?.user
|
||||||
|
})
|
||||||
|
|
@ -2,6 +2,49 @@
|
||||||
|
|
||||||
#findSession {
|
#findSession {
|
||||||
|
|
||||||
|
.btn-refresh {
|
||||||
|
position: absolute;
|
||||||
|
right: 2%;
|
||||||
|
top: 13px;
|
||||||
|
margin-right: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.session-keyword-srch {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
.tabs {
|
||||||
|
padding-left: 25px;
|
||||||
|
}
|
||||||
|
.find-tab {
|
||||||
|
|
||||||
|
float: left;
|
||||||
|
margin: 0 10px;
|
||||||
|
|
||||||
|
&.active {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.sessions-for-me {
|
||||||
|
display:none;
|
||||||
|
&.active {
|
||||||
|
display:block;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.join-icon {
|
||||||
|
background: url('/assets/content/join-icon.jpg') no-repeat;
|
||||||
|
height: 37px;
|
||||||
|
width: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.listen-icon {
|
||||||
|
background: url('/assets/content/listen-icon.jpg') no-repeat;
|
||||||
|
height: 40px;
|
||||||
|
width: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
.paginate-wait {
|
.paginate-wait {
|
||||||
margin:auto;
|
margin:auto;
|
||||||
text-align:center;
|
text-align:center;
|
||||||
|
|
@ -45,6 +88,7 @@
|
||||||
min-height:20px;
|
min-height:20px;
|
||||||
overflow-x:visible;
|
overflow-x:visible;
|
||||||
vertical-align:middle;
|
vertical-align:middle;
|
||||||
|
position:relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
.session-filter select {
|
.session-filter select {
|
||||||
|
|
|
||||||
|
|
@ -62,6 +62,14 @@ class ApiMusicSessionsController < ApiController
|
||||||
limit: params[:limit])
|
limit: params[:limit])
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def friend_active_index
|
||||||
|
@music_sessions = ActiveMusicSession.friend_active_index(current_user, params)
|
||||||
|
end
|
||||||
|
|
||||||
|
def public_index
|
||||||
|
@music_sessions = ActiveMusicSession.public_index(current_user, params)
|
||||||
|
end
|
||||||
|
|
||||||
def ams_index
|
def ams_index
|
||||||
# returns a relation which will produce a list of music_sessions which are active and augmented with attributes
|
# returns a relation which will produce a list of music_sessions which are active and augmented with attributes
|
||||||
# tag and latency, then sorted by tag, latency, and finally music_sessions.id (for stability). the list is
|
# tag and latency, then sorted by tag, latency, and finally music_sessions.id (for stability). the list is
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
child @music_sessions => :sessions do
|
||||||
|
extends "api_music_sessions/show_history"
|
||||||
|
end
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
child @music_sessions => :sessions do
|
||||||
|
extends "api_music_sessions/show_history"
|
||||||
|
end
|
||||||
|
|
@ -10,294 +10,10 @@
|
||||||
|
|
||||||
<%= render "screen_navigation" %>
|
<%= render "screen_navigation" %>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="content-body">
|
<div class="content-body">
|
||||||
<div class="content-body-scroller">
|
<%= react_component 'FindSessionScreen', {} %>
|
||||||
<form id="find-session-form">
|
|
||||||
<div class="session-filter">
|
|
||||||
<div style="min-width:770px;">
|
|
||||||
<div class="left ml35" style="padding-top:3px;">Filter Session List:</div>
|
|
||||||
|
|
||||||
<!-- genre filter -->
|
|
||||||
<div id="find-session-genre" class="left ml10">
|
|
||||||
<%= render "genreSelector" %>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- date filter -->
|
|
||||||
<div class="search-box">
|
|
||||||
<input type="text" id="session-date-filter" placeholder="Any Date" />
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- language filter -->
|
|
||||||
<div class="language">
|
|
||||||
<select id="session-language-filter">
|
|
||||||
<option value="">All Languages</option>
|
|
||||||
<% music_session_languages.each do |language| %>
|
|
||||||
<option value="<%= language[:id] %>"><%= language[:label] %></option>
|
|
||||||
<% end %>
|
|
||||||
</select>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<!-- keyword filter -->
|
|
||||||
<div class="search-box">
|
|
||||||
<input id="session-keyword-srch" type="text" name="search" placeholder="Search by Keyword" />
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="right mr10">
|
|
||||||
<a id="btn-refresh" href="/client#/findSession" style="text-decoration:none;" class="button-grey">REFRESH<span class="extra"></span></a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<div class="content-wrapper">
|
|
||||||
<div id="sessions-active" class="session-container">
|
|
||||||
<%= render :partial => "sessionList", :locals => {:title => "current, active sessions", :category => "sessions-active"} %>
|
|
||||||
<br />
|
|
||||||
<div class="paginate-wait">Fetching results...<div class="spinner-small"></div></div>
|
|
||||||
<div id="no-active-sessions" class="end-of-list">
|
|
||||||
End of list.
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<br />
|
|
||||||
<div id="sessions-scheduled" class="session-container">
|
|
||||||
<%= render :partial => "sessionList", :locals => {:title => "future, scheduled sessions", :category => "sessions-scheduled"} %>
|
|
||||||
<br />
|
|
||||||
<div class="paginate-wait">Fetching results...<div class="spinner-small"></div></div>
|
|
||||||
<div id="no-scheduled-sessions" class="end-of-list">
|
|
||||||
End of list.
|
|
||||||
</div>
|
|
||||||
<span class="btn-next-wrapper"><a href="/api/sessions/inactive?page=1" class="btn-next">Next</a></span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</form>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- active session template -->
|
|
||||||
<script type="text/template" id="template-active-session-row">
|
|
||||||
<tr data-session-id="{id}" class="found-session">
|
|
||||||
<td width="30%">
|
|
||||||
<table class="musician-groups" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
<tr>
|
|
||||||
<td class="bold"><a href="/sessions/{id}" rel="external">{name}</a></td>
|
|
||||||
<td align="right" width="75">({genres})</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td colspan="2">{description}</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>Notation Files:</td>
|
|
||||||
<td>{notation_files}</td>
|
|
||||||
</tr>
|
|
||||||
<tr class="action-links">
|
|
||||||
<td>
|
|
||||||
<a class="listen-link" style="display:{listen_link_display_style};">
|
|
||||||
<%= image_tag "content/listen-icon.jpg", :size => "40x40" %>
|
|
||||||
</a>
|
|
||||||
<br/>
|
|
||||||
<span class="listen-link-details"><span class="listen-link-text">{listen_link_text}</span><a href="#" class="listen-detail-hover">?</a></span>
|
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
<a class="join-link" style="display:{join_link_display_style};">
|
|
||||||
<%= image_tag "content/join-icon.jpg", :size => "37x40" %>
|
|
||||||
</a>
|
|
||||||
<span class="join-link-text">Join</span>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
<td width="35%">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
<tr>
|
|
||||||
<td>In Session:</td>
|
|
||||||
<td>
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
{in_session_musicians}
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>RSVPs:</td>
|
|
||||||
<td>
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
{rsvp_musicians_first_3}
|
|
||||||
</table>
|
|
||||||
<div style="display:none;">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
{rsvp_musicians_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>Still Needed:</td>
|
|
||||||
<td>
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{open_slots_first_3}
|
|
||||||
</table>
|
|
||||||
<div style="display:none">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{open_slots_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
<td width="10%" class="latency">
|
|
||||||
<div class="center">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{latency_in_session}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
<div class="center">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{latency_first_3}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
<div id="latency-extra-{id}" class="center" style="display:none;">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{latency_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
<td width="20%">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
<tr><td><span class="bold">Chat Language:</span><br/>{language}</td></tr>
|
|
||||||
<tr><td><span class="bold">Musician Access:</span><br/>{musician_access}</td></tr>
|
|
||||||
<tr><td><span class="bold">Fan Access:</span><br/>{fan_access}</td></tr>
|
|
||||||
<tr><td><span class="bold">Legal Policy:</span><br/>{legal_policy}</td></tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<!-- inactive session template -->
|
|
||||||
<script type="text/template" id="template-inactive-session-row">
|
|
||||||
<tr data-session-id="{id}" class="found-session">
|
|
||||||
<td width="30%">
|
|
||||||
<table class="musician-groups" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
<tr>
|
|
||||||
<td class="bold"><a href="/sessions/{id}/details" rel="external">{name}</a></td></td>
|
|
||||||
<td align="right" width="75">({genres})</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td colspan="2">{description}</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>Notation Files:</td>
|
|
||||||
<td>{notation_files}</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td colspan="2">{scheduled_start}</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>
|
|
||||||
</td>
|
|
||||||
<td class="nowrap">
|
|
||||||
<span class="rsvp-msg" style="display:none;">You cannot RSVP to this session.</span>
|
|
||||||
<a class="rsvp-link">
|
|
||||||
<%= image_tag "content/rsvp-icon.jpg", :size => "40x40" %>
|
|
||||||
</a>
|
|
||||||
<br/>
|
|
||||||
<span class="rsvp-link-text">RSVP</span>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
<td width="35%">
|
|
||||||
<table class="musician-groups" cellpadding="0" cellspacing="0">
|
|
||||||
<tr>
|
|
||||||
<td>RSVPs:</td>
|
|
||||||
<td>
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
{rsvp_musicians_first_3}
|
|
||||||
</table>
|
|
||||||
<div style="display:none">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
|
||||||
{rsvp_musicians_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td>Still Needed:</td>
|
|
||||||
<td>
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{open_slots_first_3}
|
|
||||||
</table>
|
|
||||||
<div style="display:none;">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{open_slots_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
<td width="10%" class="latency pt10">
|
|
||||||
<div class="center">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{latency_first_3}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
<div id="latency-extra-{id}" class="center" style="display:none;">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
{latency_remaining}
|
|
||||||
</table>
|
|
||||||
</div>
|
|
||||||
</td>
|
|
||||||
<td width="20%">
|
|
||||||
<table class="musicians" cellpadding="0" cellspacing="0">
|
|
||||||
<tr><td><span class="bold">Chat Language:</span><br/>{language}</td></tr>
|
|
||||||
<tr><td><span class="bold">Musician Access:</span><br/>{musician_access}</td></tr>
|
|
||||||
<tr><td><span class="bold">Fan Access:</span><br/>{fan_access}</td></tr>
|
|
||||||
<tr><td><span class="bold">Legal Policy:</span><br/>{legal_policy}</td></tr>
|
|
||||||
</table>
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<script type="text/template" id="template-notation-files">
|
|
||||||
<a class="{link_class}" data-notation-id="{notation_id}" href="{file_url}" rel="external">{file_name}</a><br />
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<script type="text/template" id="template-musician-info">
|
|
||||||
<tr>
|
|
||||||
<td width="24">
|
|
||||||
<a user-id="{userId}" hoveraction="musician" href="{profile_url}" class="avatar-tiny">
|
|
||||||
<img src="{avatar_url}" />
|
|
||||||
</a>
|
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
<a user-id="{userId}" hoveraction="musician" href="{profile_url}">{musician_name}</a>
|
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
<div class="instruments" class="nowrap">{instruments}</div>
|
|
||||||
</td>
|
|
||||||
<td>{more_link} </td>
|
|
||||||
</tr>
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<script type="text/template" id="template-open-slots">
|
|
||||||
<tr>
|
|
||||||
<td width="24">
|
|
||||||
<img src="{instrument_url}" />
|
|
||||||
</td>
|
|
||||||
<td>
|
|
||||||
<div class="instruments" class="nowrap">{instrument} ({proficiency})</div>
|
|
||||||
</td>
|
|
||||||
<td>{more_link} </td>
|
|
||||||
</tr>
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<script type="text/template" id="template-latency">
|
|
||||||
<tr class="mb15">
|
|
||||||
<td class="{{data.latency_style}} latency-value" data-user-id="{{data.id}}" data-audio-latency="{{data.audio_latency || ''}}" data-full-score="{{data.full_score || ''}}" data-internet-score="{{data.internet_score || ''}}">
|
|
||||||
{{data.latency_text}}
|
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr><td><div style='height:5px;'> </div></td></tr>
|
|
||||||
</script>
|
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,287 @@
|
||||||
|
<!-- Find Session Screen -->
|
||||||
|
<div layout="screen" layout-id="findSession" id="findSession" class="screen secondary">
|
||||||
|
<div class="content">
|
||||||
|
<div class="content-head">
|
||||||
|
<div class="content-icon">
|
||||||
|
<%= image_tag "content/icon_search.png", :size => "19x19" %>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<h1>find a session</h1>
|
||||||
|
|
||||||
|
<%= render "screen_navigation" %>
|
||||||
|
</div>
|
||||||
|
<div class="content-body">
|
||||||
|
<div class="content-body-scroller">
|
||||||
|
<form id="find-session-form">
|
||||||
|
<div class="session-filter">
|
||||||
|
<div style="min-width:770px;">
|
||||||
|
<div class="left ml35" style="padding-top:3px;">Filter Session List:</div>
|
||||||
|
|
||||||
|
|
||||||
|
<!-- keyword filter -->
|
||||||
|
<div class="search-box">
|
||||||
|
<input id="session-keyword-srch" type="text" name="search" placeholder="Search by Keyword" />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="right mr10">
|
||||||
|
<a id="btn-refresh" href="/client#/findSession" style="text-decoration:none;" class="button-grey">REFRESH<span class="extra"></span></a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="content-wrapper">
|
||||||
|
<div id="sessions-active" class="session-container">
|
||||||
|
<%= render :partial => "sessionList", :locals => {:title => "current, active sessions", :category => "sessions-active"} %>
|
||||||
|
<br />
|
||||||
|
<div class="paginate-wait">Fetching results...<div class="spinner-small"></div></div>
|
||||||
|
<div id="no-active-sessions" class="end-of-list">
|
||||||
|
End of list.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<br />
|
||||||
|
<div id="sessions-scheduled" class="session-container">
|
||||||
|
<%= render :partial => "sessionList", :locals => {:title => "future, scheduled sessions", :category => "sessions-scheduled"} %>
|
||||||
|
<br />
|
||||||
|
<div class="paginate-wait">Fetching results...<div class="spinner-small"></div></div>
|
||||||
|
<div id="no-scheduled-sessions" class="end-of-list">
|
||||||
|
End of list.
|
||||||
|
</div>
|
||||||
|
<span class="btn-next-wrapper"><a href="/api/sessions/inactive?page=1" class="btn-next">Next</a></span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- active session template -->
|
||||||
|
<script type="text/template" id="template-active-session-row">
|
||||||
|
<tr data-session-id="{id}" class="found-session">
|
||||||
|
<td width="30%">
|
||||||
|
<table class="musician-groups" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
<tr>
|
||||||
|
<td class="bold"><a href="/sessions/{id}" rel="external">{name}</a></td>
|
||||||
|
<td align="right" width="75">({genres})</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="2">{description}</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>Notation Files:</td>
|
||||||
|
<td>{notation_files}</td>
|
||||||
|
</tr>
|
||||||
|
<tr class="action-links">
|
||||||
|
<td>
|
||||||
|
<a class="listen-link" style="display:{listen_link_display_style};">
|
||||||
|
<%= image_tag "content/listen-icon.jpg", :size => "40x40" %>
|
||||||
|
</a>
|
||||||
|
<br/>
|
||||||
|
<span class="listen-link-details"><span class="listen-link-text">{listen_link_text}</span><a href="#" class="listen-detail-hover">?</a></span>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a class="join-link" style="display:{join_link_display_style};">
|
||||||
|
<%= image_tag "content/join-icon.jpg", :size => "37x40" %>
|
||||||
|
</a>
|
||||||
|
<span class="join-link-text">Join</span>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="35%">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
<tr>
|
||||||
|
<td>In Session:</td>
|
||||||
|
<td>
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{in_session_musicians}
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>RSVPs:</td>
|
||||||
|
<td>
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none;">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>Still Needed:</td>
|
||||||
|
<td>
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="10%" class="latency">
|
||||||
|
<div class="center">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{latency_in_session}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div class="center">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{latency_first_3}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div id="latency-extra-{id}" class="center" style="display:none;">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{latency_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
<td width="20%">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
<tr><td><span class="bold">Chat Language:</span><br/>{language}</td></tr>
|
||||||
|
<tr><td><span class="bold">Musician Access:</span><br/>{musician_access}</td></tr>
|
||||||
|
<tr><td><span class="bold">Fan Access:</span><br/>{fan_access}</td></tr>
|
||||||
|
<tr><td><span class="bold">Legal Policy:</span><br/>{legal_policy}</td></tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<!-- inactive session template -->
|
||||||
|
<script type="text/template" id="template-inactive-session-row">
|
||||||
|
<tr data-session-id="{id}" class="found-session">
|
||||||
|
<td width="30%">
|
||||||
|
<table class="musician-groups" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
<tr>
|
||||||
|
<td class="bold"><a href="/sessions/{id}/details" rel="external">{name}</a></td></td>
|
||||||
|
<td align="right" width="75">({genres})</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="2">{description}</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>Notation Files:</td>
|
||||||
|
<td>{notation_files}</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td colspan="2">{scheduled_start}</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>
|
||||||
|
</td>
|
||||||
|
<td class="nowrap">
|
||||||
|
<span class="rsvp-msg" style="display:none;">You cannot RSVP to this session.</span>
|
||||||
|
<a class="rsvp-link">
|
||||||
|
<%= image_tag "content/rsvp-icon.jpg", :size => "40x40" %>
|
||||||
|
</a>
|
||||||
|
<br/>
|
||||||
|
<span class="rsvp-link-text">RSVP</span>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="35%">
|
||||||
|
<table class="musician-groups" cellpadding="0" cellspacing="0">
|
||||||
|
<tr>
|
||||||
|
<td>RSVPs:</td>
|
||||||
|
<td>
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0" width="100%">
|
||||||
|
{rsvp_musicians_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td>Still Needed:</td>
|
||||||
|
<td>
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_first_3}
|
||||||
|
</table>
|
||||||
|
<div style="display:none;">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{open_slots_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
<td width="10%" class="latency pt10">
|
||||||
|
<div class="center">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{latency_first_3}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
<div id="latency-extra-{id}" class="center" style="display:none;">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
{latency_remaining}
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</td>
|
||||||
|
<td width="20%">
|
||||||
|
<table class="musicians" cellpadding="0" cellspacing="0">
|
||||||
|
<tr><td><span class="bold">Chat Language:</span><br/>{language}</td></tr>
|
||||||
|
<tr><td><span class="bold">Musician Access:</span><br/>{musician_access}</td></tr>
|
||||||
|
<tr><td><span class="bold">Fan Access:</span><br/>{fan_access}</td></tr>
|
||||||
|
<tr><td><span class="bold">Legal Policy:</span><br/>{legal_policy}</td></tr>
|
||||||
|
</table>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script type="text/template" id="template-notation-files">
|
||||||
|
<a class="{link_class}" data-notation-id="{notation_id}" href="{file_url}" rel="external">{file_name}</a><br />
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script type="text/template" id="template-musician-info">
|
||||||
|
<tr>
|
||||||
|
<td width="24">
|
||||||
|
<a user-id="{userId}" hoveraction="musician" href="{profile_url}" class="avatar-tiny">
|
||||||
|
<img src="{avatar_url}" />
|
||||||
|
</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<a user-id="{userId}" hoveraction="musician" href="{profile_url}">{musician_name}</a>
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div class="instruments" class="nowrap">{instruments}</div>
|
||||||
|
</td>
|
||||||
|
<td>{more_link} </td>
|
||||||
|
</tr>
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script type="text/template" id="template-open-slots">
|
||||||
|
<tr>
|
||||||
|
<td width="24">
|
||||||
|
<img src="{instrument_url}" />
|
||||||
|
</td>
|
||||||
|
<td>
|
||||||
|
<div class="instruments" class="nowrap">{instrument} ({proficiency})</div>
|
||||||
|
</td>
|
||||||
|
<td>{more_link} </td>
|
||||||
|
</tr>
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script type="text/template" id="template-latency">
|
||||||
|
<tr class="mb15">
|
||||||
|
<td class="{{data.latency_style}} latency-value" data-user-id="{{data.id}}" data-audio-latency="{{data.audio_latency || ''}}" data-full-score="{{data.full_score || ''}}" data-internet-score="{{data.internet_score || ''}}">
|
||||||
|
{{data.latency_text}}
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<tr><td><div style='height:5px;'> </div></td></tr>
|
||||||
|
</script>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -9,7 +9,7 @@ script type="text/template" id="client-download-blurb-contents"
|
||||||
h5 SYSTEM REQUIREMENTS:
|
h5 SYSTEM REQUIREMENTS:
|
||||||
| {% if(data.platform == "Win32") { %}
|
| {% if(data.platform == "Win32") { %}
|
||||||
ul.windows-requirements
|
ul.windows-requirements
|
||||||
li Windows 7 or 8, 64-bit (32-bit not supported)
|
li Windows 7, 8, or 10 - 64-bit (32-bit not supported)
|
||||||
li Dual core processor or higher
|
li Dual core processor or higher
|
||||||
li 75MB hard disk space for app
|
li 75MB hard disk space for app
|
||||||
li External audio interface recommended (but you can start with built-in mic and & headphone jack)
|
li External audio interface recommended (but you can start with built-in mic and & headphone jack)
|
||||||
|
|
@ -18,7 +18,7 @@ script type="text/template" id="client-download-blurb-contents"
|
||||||
li Broadband Internet service with 1Mbps uplink bandwidth for real-time online sessions
|
li Broadband Internet service with 1Mbps uplink bandwidth for real-time online sessions
|
||||||
| {% } else if(data.platform == "MacOSX") { %}
|
| {% } else if(data.platform == "MacOSX") { %}
|
||||||
ul.mac-requirements
|
ul.mac-requirements
|
||||||
li Mac OS X 10.7 or higher, 64-bit
|
li Mac OS X 10.8 or higher, 64-bit
|
||||||
li Dual-core processor or higher
|
li Dual-core processor or higher
|
||||||
li 75MB hard disk space for app
|
li 75MB hard disk space for app
|
||||||
li External audio interface recommended (but you can start with built-in mic and & headphone jack)
|
li External audio interface recommended (but you can start with built-in mic and & headphone jack)
|
||||||
|
|
@ -45,4 +45,4 @@ script type="text/template" id="client-download-select-others"
|
||||||
br
|
br
|
||||||
| Click here for to get JamKazam
|
| Click here for to get JamKazam
|
||||||
br
|
br
|
||||||
| for {{data.platformDisplay1}}
|
| for {{data.platformDisplay1}} ' ''
|
||||||
|
|
@ -244,6 +244,8 @@ Rails.application.routes.draw do
|
||||||
match '/sessions/scheduled' => 'api_music_sessions#scheduled', :via => :get
|
match '/sessions/scheduled' => 'api_music_sessions#scheduled', :via => :get
|
||||||
match '/sessions/scheduled_rsvp' => 'api_music_sessions#scheduled_rsvp', :via => :get
|
match '/sessions/scheduled_rsvp' => 'api_music_sessions#scheduled_rsvp', :via => :get
|
||||||
match '/sessions/legacy' => 'api_music_sessions#create_legacy', :via => :post
|
match '/sessions/legacy' => 'api_music_sessions#create_legacy', :via => :post
|
||||||
|
match '/sessions/friends' => 'api_music_sessions#friend_active_index', :via => :get
|
||||||
|
match '/sessions/public' => 'api_music_sessions#public_index', :via => :get
|
||||||
match '/sessions/active' => 'api_music_sessions#ams_index', :via => :get
|
match '/sessions/active' => 'api_music_sessions#ams_index', :via => :get
|
||||||
match '/sessions/inactive' => 'api_music_sessions#sms_index', :via => :get
|
match '/sessions/inactive' => 'api_music_sessions#sms_index', :via => :get
|
||||||
match '/sessions/:id' => 'api_music_sessions#show', :via => :get, :as => 'api_session_detail'
|
match '/sessions/:id' => 'api_music_sessions#show', :via => :get, :as => 'api_session_detail'
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue