├── .buildpacks ├── .gitignore ├── .ruby-gemset ├── .ruby-version ├── Dockerfile ├── Gemfile ├── Gemfile.lock ├── LICENSE.md ├── README.md ├── Rakefile ├── app ├── assets │ ├── .js.coffee.cjsx │ ├── fonts │ │ └── .keep │ ├── images │ │ ├── .keep │ │ ├── black-pixel-screen.png │ │ ├── bullet.svg │ │ ├── neh_logo.png │ │ ├── nypllabs_logo.png │ │ ├── scribe-logo-inv.png │ │ ├── searchtool.svg │ │ └── zooniverse_logo.png │ ├── javascripts │ │ ├── __tests__ │ │ │ ├── action-button-test.cjsx │ │ │ ├── generic-tests.cjsx │ │ │ ├── pick-one-test.cjsx │ │ │ ├── preprocessor.js │ │ │ └── text-tool-test.cjsx │ │ ├── admin │ │ │ ├── all.js.coffee │ │ │ └── stats.js.coffee │ │ ├── application.js.coffee │ │ ├── components.js.coffee │ │ ├── components │ │ │ ├── action-button.cjsx │ │ │ ├── app-router.cjsx │ │ │ ├── app.cjsx │ │ │ ├── appnew.cjsx │ │ │ ├── appnewer.cjsx │ │ │ ├── browser-warning.cjsx │ │ │ ├── button │ │ │ │ └── index.cjsx │ │ │ ├── buttons │ │ │ │ ├── bad-subject-button.cjsx │ │ │ │ ├── delete-mark.cjsx │ │ │ │ ├── done-button.cjsx │ │ │ │ ├── generic-button.cjsx │ │ │ │ ├── help-button.cjsx │ │ │ │ ├── hide-other-marks-button.cjsx │ │ │ │ ├── illegible-subject-button.cjsx │ │ │ │ ├── labeled-radio-button.cjsx │ │ │ │ ├── next-button.cjsx │ │ │ │ └── small-button.cjsx │ │ │ ├── core-tools │ │ │ │ ├── generic.cjsx │ │ │ │ ├── index.cjsx │ │ │ │ ├── pick-many.cjsx │ │ │ │ ├── pick-one-dropdown.cjsx │ │ │ │ ├── pick-one-mark-one.cjsx │ │ │ │ ├── pick-one.cjsx │ │ │ │ └── transcribe.cjsx │ │ │ ├── draggable-modal.cjsx │ │ │ ├── favourite_button.cjsx │ │ │ ├── forum-connectors │ │ │ │ ├── discourse-connector.cjsx │ │ │ │ ├── index.cjsx │ │ │ │ └── talk-connector.cjsx │ │ │ ├── forum-subject-widget.cjsx │ │ │ ├── group-browser.cjsx │ │ │ ├── group-page.cjsx │ │ │ ├── help-modal.cjsx │ │ │ ├── home-page.cjsx │ │ │ ├── light-box.cjsx │ │ │ ├── loading-indicator.cjsx │ │ │ ├── login.cjsx │ │ │ ├── mark-button.cjsx │ │ │ ├── mark │ │ │ │ ├── index.cjsx │ │ │ │ └── tools │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── point-tool │ │ │ │ │ ├── delete-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ └── root.cjsx │ │ │ │ │ ├── rectangle-tool │ │ │ │ │ ├── delete-button.cjsx │ │ │ │ │ ├── drag-handle.cjsx │ │ │ │ │ └── index.cjsx │ │ │ │ │ └── text-row-tool │ │ │ │ │ ├── delete-button.cjsx │ │ │ │ │ ├── drag-handle.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ └── root.cjsx │ │ │ ├── name-search.cjsx │ │ │ ├── row-focus-tool.cjsx │ │ │ ├── subject-metadata.cjsx │ │ │ ├── subject-set-toolbar.cjsx │ │ │ ├── subject-set-viewer.cjsx │ │ │ ├── subject-viewer.cjsx │ │ │ ├── subject-zoom-pan.cjsx │ │ │ ├── svg-image.cjsx │ │ │ ├── transcribe │ │ │ │ ├── index.cjsx │ │ │ │ ├── input-components │ │ │ │ │ ├── date-field.cjsx │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── test-component.cjsx │ │ │ │ │ ├── text-area-field.cjsx │ │ │ │ │ └── text-field.cjsx │ │ │ │ └── tools │ │ │ │ │ ├── composite-tool │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── next-button.cjsx │ │ │ │ │ └── prev-button.cjsx │ │ │ │ │ ├── date-tool │ │ │ │ │ └── index.cjsx │ │ │ │ │ ├── generic.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── number-tool │ │ │ │ │ └── index.cjsx │ │ │ │ │ ├── single-tool │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── next-button.cjsx │ │ │ │ │ ├── prev-button.cjsx │ │ │ │ │ └── transcribe-input.cjsx │ │ │ │ │ ├── text-area-tool │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── index_old.cjsx │ │ │ │ │ ├── next-button.cjsx │ │ │ │ │ ├── prev-button.cjsx │ │ │ │ │ └── transcribe-input.cjsx │ │ │ │ │ ├── text-tool │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── next-button.cjsx │ │ │ │ │ ├── prev-button.cjsx │ │ │ │ │ └── transcribe-input.cjsx │ │ │ │ │ └── transcribe-row-tool │ │ │ │ │ ├── done-button.cjsx │ │ │ │ │ ├── index.cjsx │ │ │ │ │ ├── next-button.cjsx │ │ │ │ │ ├── prev-button.cjsx │ │ │ │ │ └── transcribe-input.cjsx │ │ │ ├── tutorial.cjsx │ │ │ └── verify │ │ │ │ ├── index.cjsx │ │ │ │ └── tools │ │ │ │ ├── index.cjsx │ │ │ │ └── verify-tool │ │ │ │ ├── done-button.cjsx │ │ │ │ ├── index.cjsx │ │ │ │ ├── next-button.cjsx │ │ │ │ ├── prev-button.cjsx │ │ │ │ └── transcribe-input.cjsx │ │ ├── lib │ │ │ ├── api.cjsx │ │ │ ├── d3.min.js │ │ │ ├── draggable.cjsx │ │ │ ├── example_subject.json │ │ │ ├── fetch-subject-sets-mixin.cjsx │ │ │ ├── fetch-subjects-mixin.cjsx │ │ │ ├── getUrlParamByName.cjsx │ │ │ ├── jquery-ui.min.js │ │ │ ├── jquery.extensions.coffee │ │ │ ├── jquery.mousewheel.min.js │ │ │ ├── mark-button-mixin.cjsx │ │ │ ├── mark-drawing-mixin.cjsx │ │ │ ├── marked.min.js │ │ │ ├── modernizr-custom.js │ │ │ ├── moment.min.js │ │ │ ├── mouse-handler.cjsx │ │ │ ├── proto.coffee │ │ │ ├── workflow-methods-mixin.cjsx │ │ │ └── zoom-pan-listener-methods.cjsx │ │ ├── models │ │ │ ├── classification.coffee │ │ │ └── project.coffee │ │ └── partials │ │ │ ├── footer.cjsx │ │ │ ├── main-header.cjsx │ │ │ └── zooniverse-logo.cjsx │ └── stylesheets │ │ ├── about.styl │ │ ├── accordian.styl │ │ ├── admin │ │ ├── all.styl │ │ ├── browse.styl │ │ └── dashboard.styl │ │ ├── application.styl │ │ ├── buttons.styl │ │ ├── classify.styl │ │ ├── common.styl │ │ ├── components │ │ ├── mark │ │ │ ├── point-tool.styl │ │ │ ├── rectangle-tool.styl │ │ │ └── text-row-tool.styl │ │ └── transcribe │ │ │ └── transcribe-tool.styl │ │ ├── flexbox.styl │ │ ├── forum-subject-widget.styl │ │ ├── group-browser.styl │ │ ├── groups.styl │ │ ├── home-page.styl │ │ ├── jquery-ui.min.css │ │ ├── light-box.styl │ │ ├── loading-indicator.styl │ │ ├── main-header.styl │ │ ├── mixins │ │ └── gradients.styl │ │ ├── name-search.styl │ │ ├── panoptes-common.styl │ │ ├── subject-metadata.styl │ │ ├── subject-set-toolbar.styl │ │ ├── subject-set-viewer.styl │ │ ├── subject-viewer.styl │ │ ├── subject-zoom-pan.styl │ │ ├── tutorial.styl │ │ └── verify-tool.styl ├── controllers │ ├── admin │ │ ├── admin_base_controller.rb │ │ ├── auth_controller.rb │ │ ├── classifications_controller.rb │ │ ├── dashboard_controller.rb │ │ ├── data_controller.rb │ │ ├── subject_sets_controller.rb │ │ ├── subjects_controller.rb │ │ └── users_controller.rb │ ├── application_controller.rb │ ├── classifications_controller.rb │ ├── concerns │ │ └── .keep │ ├── favourites_controller.rb │ ├── groups_controller.rb │ ├── home_controller.rb │ ├── omniauth_callbacks_controller.rb │ ├── projects_controller.rb │ ├── registrations_controller.rb │ ├── sessions_controller.rb │ ├── subject_sets_controller.rb │ ├── subjects_controller.rb │ ├── users_controller.rb │ └── workflow_controller.rb ├── helpers │ ├── admin_helper.rb │ ├── application_helper.rb │ └── home_helper.rb ├── mailers │ └── .keep ├── models │ ├── .keep │ ├── classification.rb │ ├── concerns │ │ ├── .keep │ │ ├── cached_stats.rb │ │ └── randomizer.rb │ ├── favourite.rb │ ├── group.rb │ ├── project.rb │ ├── subject.rb │ ├── subject_generation_method.rb │ ├── subject_generation_methods │ │ ├── collect_unique.rb │ │ ├── most_popular.rb │ │ └── one_per_classification.rb │ ├── subject_set.rb │ ├── term.rb │ ├── user.rb │ ├── workflow.rb │ └── workflow_task.rb ├── serializers │ ├── auth_state_serializer.rb │ ├── classification_serializer.rb │ ├── complete_subject_serializer.rb │ ├── complete_subjects_serializer.rb │ ├── favourite_serializer.rb │ ├── final_classification_serializer.rb │ ├── final_data_serializer.rb │ ├── final_data_subject_serializer.rb │ ├── final_data_subject_set_serializer.rb │ ├── group_result_serializer.rb │ ├── group_serializer.rb │ ├── project_serializer.rb │ ├── subject_result_serializer.rb │ ├── subject_serializer.rb │ ├── subject_set_result_serializer.rb │ ├── subject_set_serializer.rb │ ├── user_serializer.rb │ ├── workflow_serializer.rb │ └── workflow_task_serializer.rb └── views │ ├── admin │ ├── auth │ │ └── signin.html.erb │ ├── classifications │ │ ├── index.html.erb │ │ └── show.html.erb │ ├── dashboard │ │ ├── ancestory.html.erb │ │ └── index.html.erb │ ├── data │ │ └── index.html.erb │ ├── partials │ │ └── _head.html.erb │ ├── subject_sets │ │ ├── index.html.erb │ │ └── show.html.erb │ ├── subjects │ │ ├── index.html.erb │ │ └── show.html.erb │ └── users │ │ ├── index.html.erb │ │ └── show.html.erb │ ├── devise │ ├── registrations │ │ ├── edit.html.erb │ │ └── new.html.erb │ └── shared │ │ └── _links.html.erb │ ├── home │ └── index.html.erb │ ├── layouts │ ├── _navigation_links.html.erb │ ├── admin.html.erb │ └── application.html.erb │ ├── partials │ ├── _breadcrumb.html.erb │ ├── _classification_breadcrumb.html.erb │ ├── _data_hash.html.erb │ ├── _subject_breadcrumb.html.erb │ └── _subject_hierarchy.html.erb │ └── users │ ├── index.html.erb │ └── show.html.erb ├── bin ├── bundle ├── rails └── rake ├── config.ru ├── config ├── application.rb ├── boot.rb ├── cucumber.yml ├── environment.rb ├── environments │ ├── development.rb │ ├── production.rb │ └── test.rb ├── initializers │ ├── backtrace_silencers.rb │ ├── devise.rb │ ├── filter_parameter_logging.rb │ ├── fix_ssl.rb │ ├── inflections.rb │ ├── mime_types.rb │ ├── mongoid_serializer.rb │ ├── register_auth_options.rb │ ├── register_project_static_routes.rb │ ├── secret_token.rb │ ├── serializers.rb │ ├── session_store.rb │ ├── streaming_proxy.rb │ └── wrap_parameters.rb ├── locales │ ├── devise.en.yml │ └── en.yml ├── login_providers.yml.erb ├── mongoid.yml ├── mongoid_old.yml └── routes.rb ├── db └── seeds.rb ├── docker-compose.yml ├── features ├── step_definitions │ ├── email_steps.rb │ └── user_steps.rb ├── support │ ├── email_spec.rb │ ├── env.rb │ └── paths.rb └── users │ ├── sign_in.feature │ ├── sign_out.feature │ ├── sign_up.feature │ ├── user_edit.feature │ └── user_show.feature ├── lib ├── assets │ └── .keep ├── ca-bundle.crt └── tasks │ ├── .keep │ ├── cucumber.rake │ ├── project.rake │ └── subjects.rake ├── package.json ├── procfile ├── project ├── anzac │ ├── assets │ │ ├── css │ │ │ └── styles.css │ │ ├── images │ │ │ ├── 1_part_att_q.gif │ │ │ ├── att_chest_mesurement.gif │ │ │ ├── att_hearing.gif │ │ │ ├── att_height.gif │ │ │ ├── att_sight.gif │ │ │ ├── background.png │ │ │ ├── hs_example_marking.gif │ │ │ ├── hs_mark_help.gif │ │ │ ├── hs_transfer_ex.gif │ │ │ ├── hs_transfer_row.gif │ │ │ ├── logo.png │ │ │ ├── logo.svg │ │ │ └── sa_att_ex.jpeg │ │ └── js │ │ │ └── custom.js │ ├── content │ │ ├── about.html.erb │ │ ├── field_guide.html.erb │ │ ├── help │ │ │ ├── att_hearing.md │ │ │ ├── att_q_help.md │ │ │ ├── att_sight.md │ │ │ ├── autocomplete_q_help.md │ │ │ ├── basic_transcribe_help.md │ │ │ ├── explore.md │ │ │ ├── help_mark_other.md │ │ │ ├── help_sticky_note.md │ │ │ ├── hs_help_last_fields.md │ │ │ ├── hs_mark_help.md │ │ │ ├── hs_transfer_help │ │ │ ├── hs_transfer_help.md │ │ │ ├── learn_marking.md │ │ │ ├── learn_transcribing.md │ │ │ ├── mark_att_two_part.md │ │ │ ├── mark_or_transcribe.md │ │ │ ├── one_slide_tutorial.md │ │ │ ├── pick_page_type.md │ │ │ ├── transcribe_while_mark.md │ │ │ └── welcome.md │ │ └── home.html.erb │ ├── images │ │ ├── 1_part_att_q.gif │ │ ├── att_chest_mesurement.gif │ │ ├── att_hearing.gif │ │ ├── att_height.gif │ │ ├── att_sight.gif │ │ ├── background.png │ │ ├── hs_mark_help.gif │ │ ├── hs_transfer_row.gif │ │ ├── logo.png │ │ ├── logo.svg │ │ └── sa_att_ex.jpeg │ ├── project.json │ ├── subjects │ │ ├── group_individual_files.csv │ │ └── groups.csv │ ├── tutorial │ │ └── tutorial.json │ └── workflows │ │ ├── mark.json │ │ └── transcribe.json ├── emigrant │ ├── assets │ │ ├── background.jpg │ │ ├── css │ │ │ └── styles.css │ │ ├── fonts │ │ │ ├── KievitWeb-Book.eot │ │ │ ├── KievitWeb-Book.woff │ │ │ ├── KievitWeb-Medi.eot │ │ │ └── KievitWeb-Medi.woff │ │ ├── hero.jpg │ │ ├── images │ │ │ ├── background.jpg │ │ │ ├── favicon.ico │ │ │ ├── hero.jpg │ │ │ ├── logo.png │ │ │ ├── logo.svg │ │ │ ├── m_address_1.png │ │ │ ├── m_address_2.png │ │ │ ├── m_address_3.png │ │ │ ├── m_address_4.png │ │ │ ├── m_date_1.png │ │ │ ├── m_date_2.png │ │ │ ├── m_date_3.png │ │ │ ├── m_date_4.png │ │ │ ├── m_loan_1.png │ │ │ ├── m_loan_2.png │ │ │ ├── m_loan_3.png │ │ │ ├── m_loan_4.png │ │ │ ├── m_mortgager_1.png │ │ │ ├── m_mortgager_2.png │ │ │ ├── m_mortgager_3.png │ │ │ ├── m_mortgager_4.png │ │ │ ├── m_number_1.png │ │ │ ├── m_number_2.png │ │ │ ├── m_survey_1.png │ │ │ ├── m_survey_2.png │ │ │ ├── m_survey_3.png │ │ │ ├── m_survey_4.png │ │ │ ├── m_value_1.png │ │ │ ├── m_value_2.png │ │ │ ├── m_value_3.png │ │ │ ├── m_value_4.png │ │ │ ├── mark_task.mp4 │ │ │ ├── mark_task2.mp4 │ │ │ ├── nypl-logo.svg │ │ │ ├── t_address_1.png │ │ │ ├── t_address_2.png │ │ │ ├── t_address_3.png │ │ │ ├── t_address_4.png │ │ │ ├── t_date_1.png │ │ │ ├── t_date_2.png │ │ │ ├── t_date_3.png │ │ │ ├── t_date_4.png │ │ │ ├── t_loan_1.png │ │ │ ├── t_loan_2.png │ │ │ ├── t_loan_3.png │ │ │ ├── t_loan_4.png │ │ │ ├── t_mortgager_1.png │ │ │ ├── t_mortgager_2.png │ │ │ ├── t_mortgager_3.png │ │ │ ├── t_mortgager_4.png │ │ │ ├── t_number_1.png │ │ │ ├── t_number_2.png │ │ │ ├── t_survey_1.png │ │ │ ├── t_survey_2.png │ │ │ ├── t_survey_3.png │ │ │ ├── t_survey_4.png │ │ │ ├── t_value_1.png │ │ │ ├── t_value_2.png │ │ │ ├── t_value_3.png │ │ │ ├── t_value_4.png │ │ │ ├── transcribe_task.mp4 │ │ │ └── verify_task.mp4 │ │ └── js │ │ │ └── custom.js │ ├── content │ │ ├── about.html.erb │ │ ├── data.html.erb │ │ ├── help │ │ │ ├── learn_marking.md │ │ │ ├── learn_transcribing.md │ │ │ ├── learn_verifying.md │ │ │ ├── m_record_amount_loaned.md │ │ │ ├── m_record_date.md │ │ │ ├── m_record_material.md │ │ │ ├── m_record_mortgager.md │ │ │ ├── m_record_number.md │ │ │ ├── m_record_stories.md │ │ │ ├── m_record_street_address.md │ │ │ ├── m_record_survey.md │ │ │ ├── m_record_valuation.md │ │ │ ├── m_record_valuation_date.md │ │ │ ├── mark_primary.md │ │ │ ├── t_record_additional_info.md │ │ │ ├── t_record_amount_loaned.md │ │ │ ├── t_record_date.md │ │ │ ├── t_record_mortgager.md │ │ │ ├── t_record_number.md │ │ │ ├── t_record_street_address.md │ │ │ ├── t_record_survey_stories_materials.md │ │ │ ├── t_record_valuation.md │ │ │ ├── t_survey.md │ │ │ ├── tutorial_mark_1.md │ │ │ ├── tutorial_mark_2.md │ │ │ ├── tutorial_mark_3.md │ │ │ ├── tutorial_mark_4.md │ │ │ ├── tutorial_mark_5.md │ │ │ ├── tutorial_transcribe_1.md │ │ │ ├── tutorial_verify_1.md │ │ │ ├── v_currency.md │ │ │ ├── v_date.md │ │ │ └── v_text.md │ │ ├── home.html.erb │ │ ├── intro.html.erb │ │ └── partials │ │ │ └── footer.html.erb │ ├── project.json │ ├── scripts │ │ ├── query_subjects.rb │ │ ├── split_subjects_four_ways.rb │ │ └── split_subjects_vertically.rb │ ├── subjects │ │ ├── group_only_one_group.csv │ │ ├── group_some_multi_page_subjects.csv │ │ ├── groups.csv │ │ └── subjects_from_api.csv │ ├── tutorial │ │ └── tutorial.json │ └── workflows │ │ ├── mark.json │ │ ├── transcribe.json │ │ └── verify.json └── whale_tales │ ├── assets │ ├── css │ │ └── styles.css │ ├── images │ │ ├── Clive_Wilkinson.jpg │ │ ├── Gil_Compo.jpg │ │ ├── Gordon_Smith.jpg │ │ ├── Kevin_Wood.jpg │ │ ├── Mark_Mollan.jpg │ │ ├── Mark_Procknik.jpg │ │ ├── Michael_Lapides.jpg │ │ ├── Philip_Brohan.jpg │ │ ├── Rob_Allan.JPG │ │ ├── alfred_gibbs.jpg │ │ ├── background.jpg │ │ ├── background_cropped.jpg │ │ ├── background_old.jpg │ │ ├── california.jpg │ │ ├── compass.jpg │ │ ├── logo.svg │ │ ├── phillipe.jpg │ │ ├── placeholder_ship.jpg │ │ └── whaling_logo.png │ └── js │ │ └── custom.js │ ├── content │ ├── about.html.erb │ ├── help │ │ ├── marking.md │ │ ├── sea_ice_concentration.md │ │ ├── sea_ice_special.md │ │ ├── sea_ice_thickness.md │ │ ├── start_exploring.md │ │ ├── transcribing.md │ │ ├── weather.md │ │ └── welcome.md │ ├── home.html.erb │ └── team.html.erb │ ├── project.json │ ├── subjects │ ├── group_beluga.csv │ ├── group_betsey_williams.csv │ ├── group_congress.csv │ ├── group_congress_short.csv │ ├── group_eliza_adams.csv │ ├── group_grampus_1.csv │ ├── group_grampus_2.csv │ ├── group_helen_snow.csv │ ├── group_herman_1.csv │ ├── group_herman_2.csv │ ├── group_horatio.csv │ ├── group_john_wells.csv │ ├── group_mary_hume.csv │ ├── group_milo.csv │ ├── group_newport.csv │ ├── group_progress.csv │ ├── group_rosario.csv │ ├── group_saratoga.csv │ ├── group_seneca.csv │ ├── group_trident.csv │ ├── group_william_baylies_1.csv │ ├── group_william_baylies_2.csv │ ├── group_william_baylies_3.csv │ ├── groups.csv │ ├── groups1.csv │ ├── groups2.csv │ └── groups_short.csv │ ├── tutorial │ └── tutorial.json │ └── workflows │ ├── mark.json │ └── transcribe.json ├── public ├── 404.html ├── 422.html ├── 500.html ├── black-pixel-screen.png ├── fake-transcription-subject-sets.json ├── fake-transcription-subjects.json ├── favicon.ico ├── humans.txt ├── offline │ ├── example_subjects │ │ ├── logbookofalfredg1851unse_0083.jpg │ │ ├── marking_subjects.json │ │ └── transcription_subjects.json │ └── subjects.json ├── oldweather │ ├── alfred_gibbs.jpg │ ├── california.jpg │ └── phillipe.jpg └── robots.txt ├── script └── cucumber ├── spec ├── controllers │ ├── home_controller_spec.rb │ └── users_controller_spec.rb ├── factories │ └── users.rb ├── models │ ├── classification_spec.rb │ ├── favourite_spec.rb │ ├── subject_set_spec.rb │ ├── subject_spec.rb │ ├── user_spec.rb │ └── workflow_spec.rb ├── spec_helper.rb └── support │ ├── devise.rb │ └── mongoid.rb ├── start.sh └── vendor └── assets ├── javascripts └── .keep └── stylesheets └── .keep /.buildpacks: -------------------------------------------------------------------------------- 1 | https://github.com/heroku/heroku-buildpack-nodejs.git 2 | https://github.com/heroku/heroku-buildpack-ruby.git 3 | -------------------------------------------------------------------------------- /.ruby-gemset: -------------------------------------------------------------------------------- 1 | scribe 2 | -------------------------------------------------------------------------------- /.ruby-version: -------------------------------------------------------------------------------- 1 | ruby-2.1.5 2 | -------------------------------------------------------------------------------- /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM zooniverse/ruby:2.1.5 2 | 3 | ENV DEBIAN_FRONTEND noninteractive 4 | 5 | RUN apt-get update && apt-get upgrade -y && \ 6 | apt-get install -y git nodejs npm coffeescript && \ 7 | ln -s /usr/bin/nodejs /usr/local/bin/node 8 | 9 | ADD . /src/ 10 | 11 | WORKDIR /src/ 12 | 13 | RUN bundle install 14 | 15 | RUN npm install 16 | 17 | EXPOSE 80 18 | 19 | ENTRYPOINT ["/src/start.sh"] 20 | -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Zooniverse and New York Public Library 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /Rakefile: -------------------------------------------------------------------------------- 1 | # Add your own tasks in files placed in lib/tasks ending in .rake, 2 | # for example lib/tasks/capistrano.rake, and they will automatically be available to Rake. 3 | 4 | require File.expand_path('../config/application', __FILE__) 5 | 6 | API::Application.load_tasks 7 | -------------------------------------------------------------------------------- /app/assets/.js.coffee.cjsx: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/.js.coffee.cjsx -------------------------------------------------------------------------------- /app/assets/fonts/.keep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/fonts/.keep -------------------------------------------------------------------------------- /app/assets/images/.keep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/.keep -------------------------------------------------------------------------------- /app/assets/images/black-pixel-screen.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/black-pixel-screen.png -------------------------------------------------------------------------------- /app/assets/images/bullet.svg: -------------------------------------------------------------------------------- 1 | 4 | -------------------------------------------------------------------------------- /app/assets/images/neh_logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/neh_logo.png -------------------------------------------------------------------------------- /app/assets/images/nypllabs_logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/nypllabs_logo.png -------------------------------------------------------------------------------- /app/assets/images/scribe-logo-inv.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/scribe-logo-inv.png -------------------------------------------------------------------------------- /app/assets/images/searchtool.svg: -------------------------------------------------------------------------------- 1 | 4 | -------------------------------------------------------------------------------- /app/assets/images/zooniverse_logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zooniverse/scribeAPI/33590c080ae82d2e8e97bc0ae9e76a0a5558c9f7/app/assets/images/zooniverse_logo.png -------------------------------------------------------------------------------- /app/assets/javascripts/__tests__/action-button-test.cjsx: -------------------------------------------------------------------------------- 1 | jest 2 | .dontMock '../components/action-button' 3 | 4 | describe 'ActionButton', -> 5 | React = require 'react/addons' 6 | {renderIntoDocument, Simulate} = React.addons.TestUtils 7 | 8 | ActionButton = require '../components/action-button' 9 | 10 | it 'should grab the action-button code', -> 11 | expect(ActionButton).toBeTruthy() 12 | 13 | actionButton = renderIntoDocument() 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /app/assets/javascripts/__tests__/generic-tests.cjsx: -------------------------------------------------------------------------------- 1 | jest 2 | .dontMock '../components/core-tools/generic' 3 | 4 | describe "GenericTask", -> 5 | React = require 'react/addons' 6 | {renderIntoDocument, Simulate} = React.addons.TestUtils 7 | 8 | GenericTask = require '../components/core-tools/generic' 9 | it 'should grab the GenericTask code', -> 10 | expect(GenericTask).toBeTruthy() 11 | # this isn't working becuase the props.answers is an array of react elements from the parent core-tool 12 | # genericTask = renderIntoDocument() -------------------------------------------------------------------------------- /app/assets/javascripts/__tests__/preprocessor.js: -------------------------------------------------------------------------------- 1 | var coffee = require('coffee-script'); 2 | var transform = require('coffee-react-transform'); 3 | 4 | module.exports = { 5 | process: function(src, path) { 6 | if (path.match(/\.cjsx/) || (coffee.helpers.isCoffee(path))) { 7 | return coffee.compile(transform(src), {'bare': true}); 8 | } 9 | return src; 10 | } 11 | }; -------------------------------------------------------------------------------- /app/assets/javascripts/admin/all.js.coffee: -------------------------------------------------------------------------------- 1 | #= require jquery 2 | #= require jquery_ujs 3 | #= require lib/d3.min 4 | #= require admin/stats 5 | -------------------------------------------------------------------------------- /app/assets/javascripts/application.js.coffee: -------------------------------------------------------------------------------- 1 | #= require jquery 2 | #= require 'lib/jquery-ui.min' 3 | #= require 'lib/jquery.extensions' 4 | #= require 'lib/marked.min' 5 | #= require 'lib/moment.min' 6 | #= require 'lib/proto' 7 | #= require 'lib/modernizr-custom.js' 8 | #= require 'components' 9 | -------------------------------------------------------------------------------- /app/assets/javascripts/components.js.coffee: -------------------------------------------------------------------------------- 1 | AppRouter = require 'components/app-router' 2 | 3 | $(document).ready -> 4 | new AppRouter() 5 | 6 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/appnewer.cjsx: -------------------------------------------------------------------------------- 1 | React = require("react") 2 | Router = require 'react-router' 3 | {Handler, Root, RouteHandler, Route, DefaultRoute, Navigation, Link} = Router 4 | 5 | BrowserHistory = require 'react-router/lib/BrowserHistory' 6 | 7 | Foo1 = React.createClass 8 | displayName: 'Foo1' 9 | render: -> 10 |
Foo 1 page
11 | 12 | Foo2 = React.createClass 13 | displayName: 'Foo2' 14 | render: -> 15 |
Foo 2 page
16 | 17 | NoMatch = React.createClass 18 | displayName: 'NoMatch' 19 | render: -> 20 |
No match
21 | 22 | 23 | App = React.createClass 24 | displayName: 'App' 25 | render: -> 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | module.exports = App 34 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/button/index.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | 3 | ResizeButton = require './resize-button' 4 | 5 | React = require 'react' 6 | 7 | module.export = React.createClass 8 | displayName: 'ButtonLink' 9 | 10 | propTypes: 11 | name: React.PropTypes.string 12 | type: React.PropTypes.string 13 | url: React.PropTypes.string 14 | 15 | handleClick: (event) -> 16 | event.preventDefault() 17 | $.ajax 18 | url: this.props.url 19 | dataType: 'json' 20 | type: this.props.type 21 | success: (data) -> 22 | #further thought needed 23 | #if a delete button it will depend on parent component? 24 | error: (jqXHR, textStatus, errorThrown) -> 25 | console.log "Error in button action:", xhr, textStatus, errorThrown 26 | 27 | render: -> 28 | if @props.type == "delete" 29 | 30 | else @props.type == "resize" 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/bad-subject-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | SmallButton = require './small-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'BadSubjectButton' 6 | 7 | render: -> 8 | label = @props.label ? ( if @props.active then 'Bad Subject' else 'Bad Subject?' ) 9 | 10 | additional_classes = [] 11 | additional_classes.push 'toggled' if @props.active 12 | additional_classes.push @props.className if @props.className? 13 | 14 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/delete-mark.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | RADIUS = 8 4 | STROKE_COLOR = '#000' 5 | FILL_COLOR = '#f00' 6 | STROKE_WIDTH = 1.5 7 | 8 | CROSS_PATH = " 9 | M #{-1 * RADIUS * 0.7 } 0 10 | L #{RADIUS * 0.7 } 0 11 | M 0 #{-1 * RADIUS * 0.7 } 12 | L 0 #{RADIUS * 0.7 } 13 | " 14 | 15 | module.exports = React.createClass 16 | displayName: 'DeleteButton' 17 | 18 | getDefaultProps: -> 19 | x: 0 20 | y: 0 21 | rotate: 0 22 | 23 | render: -> 24 | 25 | transform = " 26 | translate(#{@props.x}, #{@props.y}) 27 | rotate(#{@props.rotate}) 28 | scale(#{1 / @props.scale}, #{1 / @props.scale}) 29 | " 30 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/done-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | GenericButton = require './generic-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'DoneButton' 6 | 7 | getDefaultProps: -> 8 | label: 'Done' 9 | 10 | render: -> 11 | 12 | 13 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/generic-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | module.exports = React.createClass 4 | displayName: 'GenericButton' 5 | 6 | getDefaultProps: -> 7 | label: 'Okay' 8 | disabled: false 9 | className: '' 10 | major: false 11 | onClick: null 12 | href: null 13 | 14 | render: -> 15 | classes = @props.className.split /\s+/ 16 | classes.push (if @props.major then "major-button" else "minor-button") 17 | classes.push "disabled" if @props.disabled 18 | 19 | onClick = @props.onClick 20 | 21 | if @props.href 22 | c = @props.onClick 23 | onClick = () => 24 | c?() 25 | window.location.href = @props.href 26 | 27 | key = @props.href ? @props.onClick 28 | 29 | 32 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/help-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | SmallButton = require './small-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'HelpButton' 6 | 7 | getDefaultProps: -> 8 | label: 'Need some help?' 9 | key: 'help-button' 10 | 11 | render: -> 12 | classes = ['help-button','ghost'] 13 | classes.push @props.className if @props.className? 14 | 15 | 16 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/hide-other-marks-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | SmallButton = require './small-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'HideOtherMarksButton' 6 | 7 | render: -> 8 | label = if @props.active then 'Show Other Marks' else 'Hide Other Marks' 9 | 10 | 11 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/illegible-subject-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | SmallButton = require './small-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'IllegibleSubjectButton' 6 | 7 | render: -> 8 | label = if @props.active then 'Illegible' else 'Illegible?' 9 | 10 | 11 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/labeled-radio-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | module.exports = React.createClass 4 | displayName: 'LabeledRadioButton' 5 | 6 | getDefaultProps: -> 7 | classes: '' 8 | key: Math.random() 9 | name: 'input0' 10 | value: '' 11 | checked: false 12 | onChange: () => true 13 | label: "" 14 | disabled: false 15 | 16 | render: -> 17 | classes = @props.classes + (if @props.disabled then ' disabled' else '') 18 | 22 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/next-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | GenericButton = require './generic-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'NextButton' 6 | 7 | getDefaultProps: -> 8 | label: 'Next >' 9 | 10 | render: -> 11 | 12 | 13 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/buttons/small-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | GenericButton = require './generic-button' 3 | 4 | module.exports = React.createClass 5 | displayName: 'SmallButton' 6 | 7 | getDefaultProps: -> 8 | label: 'Next >' 9 | 10 | render: -> 11 | classes = ['small-button'] 12 | classes.push @props.className if @props.className? 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/core-tools/generic.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | cloneWithProps = require 'react/lib/cloneWithProps' 3 | HelpModal = require '../help-modal' 4 | HelpButton = require 'components/buttons/help-button' 5 | BadSubjectButton = require 'components/buttons/bad-subject-button' 6 | 7 | module.exports = React.createClass 8 | displayName: 'GenericTask' 9 | 10 | getDefaultProps: -> 11 | question: '' 12 | help: '' 13 | answers: '' 14 | 15 | render: -> 16 |
17 | 18 |
19 | { React.Children.map @props.answers, (answer) => 20 | cloneWithProps answer, classes: answer.props.classes + ' answer', disabled: @props.badSubject 21 | } 22 |
23 | 24 |
25 | 26 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/core-tools/index.cjsx: -------------------------------------------------------------------------------- 1 | # HASH OF CORE TOOLS 2 | module.exports = 3 | pickOne: require './pick-one' 4 | pickOneDropdown: require './pick-one-dropdown' 5 | pickMany: require './pick-many' 6 | pickOneMarkOne: require './pick-one-mark-one' 7 | transcribe: require './transcribe' # ???? 8 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/favourite_button.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | 3 | React = require 'react' 4 | 5 | 6 | # IMPORTANT! 7 | window.React = React 8 | 9 | FavouriteButton = React.createClass 10 | displayname: 'FavouriteButton' 11 | 12 | getInitialState:=> 13 | favourite: this.props.subject.user_favourite 14 | loading: false 15 | 16 | add_favourite:(e)-> 17 | e.preventDefault() 18 | 19 | @setState 20 | loading: true 21 | 22 | $.post "/subjects/#{this.props.subject.id}/favourite", => 23 | @setState 24 | loading:false 25 | favourite: true 26 | 27 | 28 | remove_favourite: (e)-> 29 | e.preventDefault() 30 | $.post "/subjects/#{this.props.subject.id}/unfavourite", => 31 | @setState 32 | loading:false 33 | favourite: false 34 | 35 | render: -> 36 | if this.state.loading 37 | Loading 38 | else if this.state.favourite 39 | Unfavourite 40 | else 41 | Favourite 42 | 43 | 44 | module.exports = FavouriteButton 45 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/forum-connectors/index.cjsx: -------------------------------------------------------------------------------- 1 | # HASH OF FORUM CONNECTORS 2 | module.exports = 3 | discourse: require './discourse-connector' 4 | talk: require './talk-connector' 5 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/help-modal.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | DraggableModal = require 'components/draggable-modal' 3 | 4 | module.exports = React.createClass 5 | displayName: 'HelpModal' 6 | 7 | componentDidMount: -> 8 | el = $(React.findDOMNode(this)).find("#accordion-help-modal") 9 | el.accordion 10 | collapsible: true 11 | active: false 12 | heightStyle: "content" 13 | 14 | render: -> 15 | return null unless @props.help? 16 | 17 |
18 | 19 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/loading-indicator.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | 3 | React = require 'react' 4 | 5 | LoadingIndicator = React.createClass 6 | displayName: 'LoadingIndicator' 7 | 8 | render: -> 9 | 10 | Loading 11 | 12 | 13 | 14 | 15 | 16 | module.exports = LoadingIndicator -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/index.cjsx: -------------------------------------------------------------------------------- 1 | module.exports = 2 | pointTool: require './point-tool' 3 | textRowTool: require './text-row-tool' 4 | rectangleTool: require './rectangle-tool' 5 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/point-tool/delete-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | RADIUS = 8 4 | STROKE_COLOR = '#000' 5 | FILL_COLOR = '#f00' 6 | STROKE_WIDTH = 1.5 7 | 8 | CROSS_PATH = " 9 | M #{-1 * RADIUS * 0.7 } 0 10 | L #{RADIUS * 0.7 } 0 11 | M 0 #{-1 * RADIUS * 0.7 } 12 | L 0 #{RADIUS * 0.7 } 13 | " 14 | 15 | DESTROY_TRANSITION_DURATION = 0 16 | 17 | module.exports = React.createClass 18 | displayName: 'DeleteButton' 19 | 20 | getDefaultProps: -> 21 | x: 0 22 | y: 0 23 | rotate: 0 24 | 25 | render: -> 26 | transform = " 27 | translate(#{@props.x+40}, #{@props.y-40}) 28 | rotate(#{@props.rotate}) 29 | scale(#{1 / @props.tool.props.xScale}, #{1 / @props.tool.props.yScale}) 30 | " 31 | 32 | 33 | 34 | 35 | 36 | destroyTool: -> 37 | @props.tool.setState destroying: true, => 38 | setTimeout @props.tool.props.onDestroy, DESTROY_TRANSITION_DURATION 39 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/rectangle-tool/delete-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | RADIUS = 8 4 | STROKE_COLOR = '#000' 5 | FILL_COLOR = '#f00' 6 | STROKE_WIDTH = 1.5 7 | 8 | CROSS_PATH = " 9 | M #{-1 * RADIUS * 0.7 } 0 10 | L #{RADIUS * 0.7 } 0 11 | M 0 #{-1 * RADIUS * 0.7 } 12 | L 0 #{RADIUS * 0.7 } 13 | " 14 | 15 | DESTROY_TRANSITION_DURATION = 0 16 | 17 | module.exports = React.createClass 18 | displayName: 'DeleteButton' 19 | 20 | getDefaultProps: -> 21 | x: 0 22 | y: 0 23 | rotate: 0 24 | 25 | render: -> 26 | transform = " 27 | translate(#{@props.x+40}, #{@props.y-40}) 28 | rotate(#{@props.rotate}) 29 | scale(#{1 / @props.tool.props.xScale}, #{1 / @props.tool.props.yScale}) 30 | " 31 | 32 | 33 | 34 | 35 | 36 | destroyTool: -> 37 | @props.tool.setState destroying: true, => 38 | setTimeout @props.tool.props.onDestroy, DESTROY_TRANSITION_DURATION 39 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/rectangle-tool/drag-handle.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | Draggable = require 'lib/draggable' 3 | 4 | RADIUS = 4 5 | STROKE_COLOR = '#fff' 6 | FILL_COLOR = '#000' 7 | STROKE_WIDTH = 1.5 8 | 9 | OVERSHOOT = 4 10 | 11 | module.exports = React.createClass 12 | displayName: 'DragHandle' 13 | 14 | render: -> 15 | scale = (@props.tool.props.xScale + @props.tool.props.yScale) / 2 16 | 17 | 18 | 23 | 29 | 30 | 31 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/text-row-tool/delete-button.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | 3 | RADIUS = 8 4 | STROKE_COLOR = '#000' 5 | FILL_COLOR = '#f00' 6 | STROKE_WIDTH = 1.5 7 | 8 | CROSS_PATH = " 9 | M #{-1 * RADIUS * 0.7 } 0 10 | L #{RADIUS * 0.7 } 0 11 | M 0 #{-1 * RADIUS * 0.7 } 12 | L 0 #{RADIUS * 0.7 } 13 | " 14 | 15 | DESTROY_TRANSITION_DURATION = 0 16 | 17 | module.exports = React.createClass 18 | displayName: 'DeleteButton' 19 | 20 | getDefaultProps: -> 21 | x: 0 22 | y: 0 23 | rotate: 0 24 | 25 | render: -> 26 | transform = " 27 | translate(#{@props.position.x}, #{@props.position.y}) 28 | rotate(#{@props.rotate}) 29 | scale(#{1 / @props.tool.props.xScale}, #{1 / @props.tool.props.yScale}) 30 | " 31 | 32 | 33 | 34 | 35 | 36 | 37 | destroyTool: -> 38 | @props.tool.setState destroying: true, => 39 | setTimeout @props.tool.props.onDestroy, DESTROY_TRANSITION_DURATION 40 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/mark/tools/text-row-tool/drag-handle.cjsx: -------------------------------------------------------------------------------- 1 | React = require 'react' 2 | Draggable = require 'lib/draggable' 3 | 4 | RADIUS = 8 5 | STROKE_COLOR = 'white' 6 | FILL_COLOR = 'black' 7 | STROKE_WIDTH = 1.5 8 | 9 | DESTROY_TRANSITION_DURATION = 0 10 | 11 | module.exports = React.createClass 12 | displayName: 'DragHandle' 13 | 14 | getDefaultProps: -> 15 | x: 0 16 | y: 0 17 | rotate: 0 18 | 19 | render: -> 20 | transform = " 21 | translate(#{@props.position.x}, #{@props.position.y}) 22 | rotate(#{@props.rotate}) 23 | scale(#{1 / @props.tool.props.xScale}, #{1 / @props.tool.props.yScale}) 24 | " 25 | 26 | 27 | 33 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/subject-metadata.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | 3 | React = require 'react' 4 | 5 | SubjectMetadata = React.createClass 6 | displayName: "Metadata" 7 | 8 | render: -> 9 |
10 |

Metadata

11 |
12 | 13 | module.exports = SubjectMetadata -------------------------------------------------------------------------------- /app/assets/javascripts/components/svg-image.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | 3 | React = require 'react' 4 | 5 | # React.DOM doesn't include an SVG tag 6 | # (because of its namespaced `xlink:href` attribute, I think), 7 | # so this fakes one by wrapping it in a . 8 | 9 | module.exports = React.createClass 10 | displayName: 'SVGImage' 11 | 12 | getInitialState: -> 13 | key: 0 14 | 15 | getDefaultProps: -> 16 | src: '' 17 | width: 0 18 | height: 0 19 | 20 | render: -> 21 | imageHTML = "" 22 | 23 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/transcribe/input-components/date-field.cjsx: -------------------------------------------------------------------------------- 1 | DoneButton = require './done-button' 2 | 3 | DateField = React.createClass 4 | displayName: 'DateField' 5 | 6 | render: -> 7 | 8 |
9 |
10 | 11 | 18 |
19 |
20 |
21 | 22 |
23 |
24 | 25 | module.exports = DateField 26 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/transcribe/input-components/done-button.cjsx: -------------------------------------------------------------------------------- 1 | # @cjsx React.DOM 2 | React = require 'react' 3 | 4 | DoneButton = React.createClass 5 | displayName: 'DoneButton' 6 | 7 | render: -> 8 | classes = 'button done' 9 | title = 'Next' 10 | 11 | 14 | 15 | module.exports = DoneButton 16 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/transcribe/input-components/index.cjsx: -------------------------------------------------------------------------------- 1 | module.exports = 2 | textField: require './text-field' 3 | dateField: require './date-field' 4 | textAreaField: require './text-area-field' 5 | testComponent: require './test-component' 6 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/transcribe/input-components/test-component.cjsx: -------------------------------------------------------------------------------- 1 | DoneButton = require './done-button' 2 | 3 | TestComponent = React.createClass 4 | displayName: 'TestComponent' 5 | 6 | render: -> 7 | 8 |
9 |
10 |
11 | Location 12 | 13 | 14 |
15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 |
26 |
27 |
28 |
29 | 30 |
31 |
32 | 33 | module.exports = TestComponent 34 | -------------------------------------------------------------------------------- /app/assets/javascripts/components/transcribe/input-components/text-area-field.cjsx: -------------------------------------------------------------------------------- 1 | DoneButton = require './done-button' 2 | 3 | TextAreaField = React.createClass 4 | displayName: 'TextAreaField' 5 | 6 | render: -> 7 | 8 |
9 |
10 | 11 |