content-editing-movie-player 0.38.0
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitmodules +3 -0
- data/.rvmrc +1 -0
- data/LICENSE.TXT +20 -0
- data/README.TXT +225 -0
- data/Rakefile +206 -0
- data/TODO +740 -0
- data/VERSION +1 -0
- data/_DO_NOT_RUN_IT_FROM_HERE_DOWNLOAD_THE_RELEASE_ZIP_FROM_SOURCEFORGE_INSTEAD +0 -0
- data/bin/sensible-cinema +60 -0
- data/bin/sensible-cinema-cli +161 -0
- data/business_ideas.txt +21 -0
- data/change_log_with_feature_list.txt +952 -0
- data/documentation/DOCUMENTATION_README.TXT +44 -0
- data/documentation/how_to_get_files_from_dvd.txt +30 -0
- data/documentation/is_it_legal_to_copy_dvds.txt +97 -0
- data/documentation/troubleshooting.txt +30 -0
- data/documentation/upconversion.txt +4 -0
- data/experimental_online_player_ocr_readme.txt +45 -0
- data/go +1 -0
- data/go.bat +2 -0
- data/go.sh +1 -0
- data/go_ocr_tracker.bat +1 -0
- data/goc +1 -0
- data/goc.bat +1 -0
- data/goc.sh +1 -0
- data/gpl-2.0.txt +339 -0
- data/gplv3.txt +219 -0
- data/history_and_related_works_list.txt +108 -0
- data/inventionzy_files/cone.png +0 -0
- data/inventionzy_files/md5s.txt +53 -0
- data/inventionzy_files/play_with_inserted_scene.bat +8 -0
- data/inventionzy_files/play_with_overlay.bat +24 -0
- data/inventionzy_files/transcript_mute_vlc.txt +117 -0
- data/legal_draft +23 -0
- data/lib/add_any_bundled_gems_to_load_path.rb +32 -0
- data/lib/auto_window_finder.rb +41 -0
- data/lib/blanker.rb +104 -0
- data/lib/check_installed_mac.rb +34 -0
- data/lib/convert_thirty_fps.rb +20 -0
- data/lib/edl_parser.rb +387 -0
- data/lib/eight_three.rb +28 -0
- data/lib/extract/dumpstream.bat +1 -0
- data/lib/extract/get_init.bat +3 -0
- data/lib/extract/pause_early.rb +13 -0
- data/lib/fake_blanker.rb +35 -0
- data/lib/frame_accurate.rb +3 -0
- data/lib/gui/base.rb +748 -0
- data/lib/gui/create-file.rb +24 -0
- data/lib/gui/create.rb +581 -0
- data/lib/gui/dependencies.rb +219 -0
- data/lib/gui/normal.rb +123 -0
- data/lib/gui/upconvert.rb +284 -0
- data/lib/keyboard_input.rb +60 -0
- data/lib/media_info_parser.rb +27 -0
- data/lib/mouse_forever.rb +19 -0
- data/lib/movie_hasher.rb +27 -0
- data/lib/mplayer_edl.rb +42 -0
- data/lib/muter.rb +87 -0
- data/lib/ocr.rb +125 -0
- data/lib/ocr_seed/netflix_b9.bmp +0 -0
- data/lib/overlayer.rb +373 -0
- data/lib/screen_tracker.rb +269 -0
- data/lib/subtitle_profanity_finder.rb +294 -0
- data/lib/vlc_programmer.rb +112 -0
- data/lib/zoom_player_max_edl.rb +50 -0
- data/never_do +40 -0
- data/notes_for_potential_developers.txt +46 -0
- data/preamble +17 -0
- data/roadmap_possibilities +12 -0
- data/spec/arse.srt +41 -0
- data/spec/auto_window_finder.spec.rb +65 -0
- data/spec/bad_beginning.srt +3778 -0
- data/spec/blanker.spec.rb +60 -0
- data/spec/common.rb +81 -0
- data/spec/convert_image.rb +25 -0
- data/spec/deity_end.srt +11 -0
- data/spec/dragon.srt +34 -0
- data/spec/edl_parser.spec.rb +270 -0
- data/spec/frame_accurate.spec.rb +71 -0
- data/spec/keyboard_input.spec.rb +73 -0
- data/spec/media_info_parser.spec.rb +29 -0
- data/spec/mplayer_edl.spec.rb +100 -0
- data/spec/muter.spec.rb +50 -0
- data/spec/notes +4996 -0
- data/spec/ocr.spec.rb +119 -0
- data/spec/overlayer.spec.rb +440 -0
- data/spec/screen_tracker.spec.rb +318 -0
- data/spec/sensible_cinema_gui.spec.rb +452 -0
- data/spec/subtitle_profanity_finder.spec.rb +224 -0
- data/spec/test_yaml.yml +4 -0
- data/spec/tsmuxer.output +33 -0
- data/spec/vlc_programmer.spec.rb +124 -0
- data/spec/youtube_edl.spec.rb +28 -0
- data/spec/zoom_player_max_edl.spec.rb +29 -0
- data/template_bats/README_DISTRO.TXT +8 -0
- data/template_bats/RUN SENSIBLE CINEMA CLICK HERE WINDOWS.bat +25 -0
- data/template_bats/_DO_NOT_RUN_IT_FROM_HERE_DOWNLOAD_THE_RELEASE_ZIP_FROM_SOURCEFORGE_INSTEAD +0 -0
- data/template_bats/mac/RUN SENSIBLE CINEMA CLICK HERE.command +5 -0
- data/template_bats/mac/advanced--create or edit sensible cinema edit list files.command +3 -0
- data/template_bats/mac/advanced--run-upconverting-video-player.command +3 -0
- data/template_bats/pc/advanced--create or edit sensible cinema edit list files.bat +2 -0
- data/template_bats/pc/advanced--run-upconverting-video-player.bat +2 -0
- data/todo.build_library.txt +11 -0
- data/todo.inventionzy.txt +162 -0
- data/todo.open_edl_list_org.txt +169 -0
- data/todo.propaganda +107 -0
- data/todo.subtitle +17 -0
- data/todo.upconvert +53 -0
- data/upconvert.bat +1 -0
- data/upconvert_from_screen/go_upscaling.bat +12 -0
- data/upconvert_from_screen/go_upscaling_works +0 -0
- data/upconvert_from_screen/old/latest2/combine_video.avs +23 -0
- data/upconvert_from_screen/old/latest2/go_no_upscaling.bat +1 -0
- data/upconvert_from_screen/old/latest2/go_upscaling.bat +12 -0
- data/upconvert_from_screen/old/latest2/push2.GRF +0 -0
- data/upconvert_from_screen/old/latest2/push3.grf +0 -0
- data/upconvert_from_screen/old/latest2/setup_capture_coords.rb +27 -0
- data/upconvert_from_screen/old/latest2/setup_directshow_filter_params.rb +29 -0
- data/upconvert_from_screen/old/latest2/upconvert_from_screen_me2.avs +19 -0
- data/upconvert_from_screen/old/latest_now_possibly_oudated/push2.GRF +0 -0
- data/upconvert_from_screen/old/latest_now_possibly_oudated/upconvert_from_screen_me2.avs +18 -0
- data/upconvert_from_screen/old/position_window.png +0 -0
- data/upconvert_from_screen/old/push_source_desktop.GRF +0 -0
- data/upconvert_from_screen/old/record_screen/record.bat +2 -0
- data/upconvert_from_screen/old/upconvert_from_screen.avs +21 -0
- data/upconvert_from_screen/old/upconvert_from_screen_me.avs +21 -0
- data/upconvert_from_screen/old/upconvert_from_screen_me2.avs +3 -0
- data/upconvert_from_screen/old/upconvert_from_screen_me_push_source.avs +3 -0
- data/upconvert_from_screen/old/uscreen.GRF +0 -0
- data/upconvert_from_screen/old/uscreen_me.GRF +0 -0
- data/upconvert_from_screen/push3.grf +0 -0
- data/upconvert_from_screen/upconvert_from_screen_me2.avs +19 -0
- data/vendor/movie-content-editor-read-only/.metadata/.lock +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.mylyn/.tasks.xml.zip +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.mylyn/repositories.xml.zip +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.mylyn/tasks.xml.zip +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.resources/.root/.indexes/history.version +1 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.resources/.root/.indexes/properties.index +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.resources/.root/.indexes/properties.version +1 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.resources/.root/2.tree +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.resources/.safetable/org.eclipse.core.resources +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.runtime/.settings/org.eclipse.core.resources.prefs +3 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.runtime/.settings/org.eclipse.jdt.ui.prefs +14 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.runtime/.settings/org.eclipse.mylyn.context.core.prefs +3 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.runtime/.settings/org.eclipse.ui.ide.prefs +5 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.core.runtime/.settings/org.eclipse.ui.prefs +3 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.jdt.core/nonChainingJarsCache +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.jdt.core/variablesAndContainers.dat +0 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.jdt.ui/OpenTypeHistory.xml +2 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.jdt.ui/QualifiedTypeNameHistory.xml +2 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.jdt.ui/dialog_settings.xml +10 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.ui.ide/dialog_settings.xml +11 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.ui.intro/dialog_settings.xml +4 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.ui.workbench/dialog_settings.xml +10 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.ui.workbench/workbench.xml +232 -0
- data/vendor/movie-content-editor-read-only/.metadata/.plugins/org.eclipse.ui.workbench/workingsets.xml +4 -0
- data/vendor/movie-content-editor-read-only/.metadata/version.ini +1 -0
- data/vendor/movie-content-editor-read-only/.project +17 -0
- data/vendor/movie-content-editor-read-only/.pydevproject +11 -0
- data/vendor/movie-content-editor-read-only/.settings/org.eclipse.core.resources.prefs +6 -0
- data/vendor/movie-content-editor-read-only/SubIt.py +171 -0
- data/vendor/movie-content-editor-read-only/VLCMacVideo.py +257 -0
- data/vendor/movie-content-editor-read-only/VideoMac.ui +102 -0
- data/vendor/movie-content-editor-read-only/badwords.txt +4 -0
- data/vendor/movie-content-editor-read-only/blank.srt +4 -0
- data/vendor/movie-content-editor-read-only/edit.py +197 -0
- data/vendor/movie-content-editor-read-only/mergeCommands.py +73 -0
- data/vendor/movie-content-editor-read-only/mute.txt +5 -0
- data/vendor/movie-content-editor-read-only/panda.srt +4235 -0
- data/vendor/movie-content-editor-read-only/panda_custom.txt +3 -0
- data/vendor/movie-content-editor-read-only/panda_edit.srt +4235 -0
- data/vendor/movie-content-editor-read-only/subtitle.py +90 -0
- data/vendor/movie-content-editor-read-only/vlc.py +5579 -0
- data/vendor/movie-content-editor-read-only/vlcwidget.py +154 -0
- data/vendor/mplayer_patches/how_to_doze.bat +6 -0
- data/vendor/mplayer_patches/port_dir/PortIndex.quick +2 -0
- data/vendor/mplayer_patches/port_dir/how_to +20 -0
- data/vendor/mplayer_patches/port_dir/multimedia/mplayer-edl/Portfile +285 -0
- data/vendor/mplayer_patches/port_dir/multimedia/mplayer-edl/files/configure.x11.patch +20 -0
- data/vendor/mplayer_patches/port_dir/multimedia/mplayer-edl/files/llvm-gcc-workaround.patch +11 -0
- data/vendor/mplayer_patches/port_dir/multimedia/rdp-projects/Portfile +43 -0
- data/vendor/mplayer_patches/port_dir_is_for_mac +0 -0
- data/www/content_editor.html +92 -0
- data/www/index.html +47 -0
- data/www/upconverting_movie_player.html +62 -0
- data/www/video reel.jpg +0 -0
- data/www/youtube_edl/.htaccess +44 -0
- data/www/youtube_edl/control_youtube.rhtml +141 -0
- data/www/youtube_edl/dispatch.fcgi +25 -0
- data/www/youtube_edl/render_edited.rb +25 -0
- data/www/youtube_edl/server_this_dir.rb +6 -0
- data/www/youtube_edl/todo +23 -0
- data/www/zoomplayer_max.png +0 -0
- data/zamples/edit_decision_lists/dvds/Harry Potter 2 chamber of secrets.txt +22 -0
- data/zamples/edit_decision_lists/dvds/aa_example_delete_list_that_has_no_cuts_in_it.txt +10 -0
- data/zamples/edit_decision_lists/dvds/aladdin.txt +30 -0
- data/zamples/edit_decision_lists/dvds/bambi.txt +17 -0
- data/zamples/edit_decision_lists/dvds/big_buck_bunny_dvd.txt +23 -0
- data/zamples/edit_decision_lists/dvds/bob the builder pets in a pickle.txt +10 -0
- data/zamples/edit_decision_lists/dvds/bobs_big_plan.txt +10 -0
- data/zamples/edit_decision_lists/dvds/cars_2.txt +26 -0
- data/zamples/edit_decision_lists/dvds/cars_disney.txt +40 -0
- data/zamples/edit_decision_lists/dvds/condor_man_widescreen.txt +22 -0
- data/zamples/edit_decision_lists/dvds/cool runnings.txt +53 -0
- data/zamples/edit_decision_lists/dvds/court_jester.txt +24 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/amazing_grace.txt +49 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/father_goose.txt +41 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/harry_potter_and_the_goblet_of_fire.txt +45 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/hugo.txt +31 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/making_marriage_work.txt +15 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/national_treasure.txt +26 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/percy_jackson_lightening_thief.txt +40 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/percy_jackson_lightening_thief_mute_scary.txt +23 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/prince_of_egypt.txt +28 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/puss_in_boots.txt +33 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/ratatouille.txt +35 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/rio.txt +24 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/test_delete_list_for_experimenting_with.txt +10 -0
- data/zamples/edit_decision_lists/dvds/edls_being_edited/the_explorers.txt +49 -0
- data/zamples/edit_decision_lists/dvds/finding_neverland.txt +32 -0
- data/zamples/edit_decision_lists/dvds/flight_of_the_navigator.txt +40 -0
- data/zamples/edit_decision_lists/dvds/happiest baby on the block.txt +9 -0
- data/zamples/edit_decision_lists/dvds/harry_potter_3_prisoner_of_azkaban.txt +37 -0
- data/zamples/edit_decision_lists/dvds/hitchhiker's_guide_to_the_galaxy.txt +32 -0
- data/zamples/edit_decision_lists/dvds/how_to_train_your_dragon.txt +25 -0
- data/zamples/edit_decision_lists/dvds/if_a_man_answers.txt +43 -0
- data/zamples/edit_decision_lists/dvds/innerspace.txt +77 -0
- data/zamples/edit_decision_lists/dvds/iq.txt +32 -0
- data/zamples/edit_decision_lists/dvds/king_of_kings.txt +28 -0
- data/zamples/edit_decision_lists/dvds/kung_fu_panda_1.txt +17 -0
- data/zamples/edit_decision_lists/dvds/legend_of_the_guardians_the_owls_of_gahoole.txt +18 -0
- data/zamples/edit_decision_lists/dvds/monsters_vs_aliens.txt +41 -0
- data/zamples/edit_decision_lists/dvds/muppet_treasure_island.txt +21 -0
- data/zamples/edit_decision_lists/dvds/nanny_mcphee.txt +31 -0
- data/zamples/edit_decision_lists/dvds/narnia_voyage_of_the_dawn_treader.txt +16 -0
- data/zamples/edit_decision_lists/dvds/pack_jackson_wedding_2007-03-03.txt +31 -0
- data/zamples/edit_decision_lists/dvds/peter_pan.txt +29 -0
- data/zamples/edit_decision_lists/dvds/remember_the_titans.txt +35 -0
- data/zamples/edit_decision_lists/dvds/sintel_open_source_blender_ntsc_dvd.txt +22 -0
- data/zamples/edit_decision_lists/dvds/snow_white_and_the_7_dwarfs_1937.txt +19 -0
- data/zamples/edit_decision_lists/dvds/speed_racer.txt +47 -0
- data/zamples/edit_decision_lists/dvds/tangled.txt +21 -0
- data/zamples/edit_decision_lists/dvds/tron_legacy.txt +29 -0
- data/zamples/edit_decision_lists/dvds/turn_around_alma_younger.txt +17 -0
- data/zamples/edit_decision_lists/files/conference_music_video.txt +10 -0
- data/zamples/edit_decision_lists/netflix_instant/avatar-last-air-bender-movie.txt +13 -0
- data/zamples/edit_decision_lists/netflix_instant/avatar-last-airbender-series.txt +1 -0
- data/zamples/edit_decision_lists/netflix_instant/greatest_story_ever_told_netflix.txt +10 -0
- data/zamples/edit_decision_lists/netflix_instant/wrinkle-in-time.txt +23 -0
- data/zamples/edit_decision_lists/notes_on_movies_without_edls_yet/tron.txt +10 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/White Christmas.txt +15 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/all_dogs_go_to_heaven.txt +9 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/cars_disney.txt +24 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/happy_feet.txt +12 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/labyrinth.txt +17 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/dvds/star_trek_generations_hulu.txt +8 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/example_edit_decision_list.txt +14 -0
- data/zamples/edit_decision_lists/old_not_yet_updated/youtube/gummy_bear_song_youtube.txt +9 -0
- data/zamples/edit_decision_lists/youtube/demo_mutes.txt +12 -0
- data/zamples/edit_decision_lists/youtube/nuki_song_youtube.txt +14 -0
- data/zamples/edit_decision_lists/youtube/nuki_song_youtube_pointer.txt +3 -0
- data/zamples/players/how_to_create_more_players.txt +24 -0
- data/zamples/players/hulu/total_length_over_an_hour.txt +25 -0
- data/zamples/players/netflix/netflix_firefox_non_maximized.txt +25 -0
- data/zamples/players/vlc/full_screened_total_length_over_an_hour.txt +27 -0
- data/zamples/players/vlc/windowed_total_length_over_an_hour.txt +26 -0
- data/zamples/players/vlc/windowed_total_length_under_an_hour.txt +22 -0
- data/zamples/players/youtube/full_screened_1024x768.txt +20 -0
- data/zamples/players/youtube/full_screened_1152x864.txt +20 -0
- data/zamples/players/youtube/full_screened_1680x1050.txt +20 -0
- data/zamples/players/youtube/normal_in_youtube.com.chrome.txt +23 -0
- data/zamples/players/youtube/note_these_assume_less_than_10_minutes_length.txt +2 -0
- metadata +483 -0
@@ -0,0 +1,269 @@
|
|
1
|
+
=begin
|
2
|
+
Copyright 2010, Roger Pack
|
3
|
+
This file is part of Sensible Cinema.
|
4
|
+
|
5
|
+
Sensible Cinema is free software: you can redistribute it and/or modify
|
6
|
+
it under the terms of the GNU General Public License as published by
|
7
|
+
the Free Software Foundation, either version 3 of the License, or
|
8
|
+
(at your option) any later version.
|
9
|
+
|
10
|
+
Sensible Cinema is distributed in the hope that it will be useful,
|
11
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
GNU General Public License for more details.
|
14
|
+
|
15
|
+
You should have received a copy of the GNU General Public License
|
16
|
+
along with Sensible Cinema. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
=end
|
18
|
+
require 'win32/screenshot'
|
19
|
+
require 'sane'
|
20
|
+
require 'yaml'
|
21
|
+
require File.dirname(__FILE__)+ '/ocr'
|
22
|
+
require 'ffi'
|
23
|
+
|
24
|
+
class ScreenTracker
|
25
|
+
|
26
|
+
extend FFI::Library
|
27
|
+
ffi_lib 'user32'
|
28
|
+
# second parameter, pointer, LPRECT is FFI::MemoryPointer.new(:long, 4)
|
29
|
+
# read it like rect.read_array_of_long(4)
|
30
|
+
attach_function :GetWindowRect, [:long, :pointer], :int # returns a BOOL
|
31
|
+
|
32
|
+
def self.new_from_yaml yaml, callback # callback can be nil, is used for timestamp changed stuff
|
33
|
+
settings = YAML.load yaml
|
34
|
+
return new(settings["name"], settings["x"], settings["y"], settings["width"],
|
35
|
+
settings["height"], settings["use_class_name"], settings["digits"], callback)
|
36
|
+
end
|
37
|
+
|
38
|
+
attr_accessor :hwnd
|
39
|
+
|
40
|
+
# digits are like {:hours => [100,5], :minute_tens, :minute_ones, :second_tens, :second_ones}
|
41
|
+
# digits share the height start point, have their own x and width...
|
42
|
+
def initialize name_or_regex, x, y, width, height, use_class_name=nil, digits=nil, callback=nil
|
43
|
+
# cache to save us 0.00445136 per time LOL
|
44
|
+
@name_or_regex = name_or_regex
|
45
|
+
@use_class_name = use_class_name
|
46
|
+
pps 'height', height, 'width', width if $VERBOSE
|
47
|
+
raise 'poor dimentia' if width <= 0 || height <= 0
|
48
|
+
get_hwnd_loop_forever
|
49
|
+
max_x, max_y = Win32::Screenshot::Util.dimensions_for(@hwnd)
|
50
|
+
if(x < 0 || y < 0)
|
51
|
+
if x < 0
|
52
|
+
x = max_x + x
|
53
|
+
end
|
54
|
+
if y < 0
|
55
|
+
y = max_y + y
|
56
|
+
end
|
57
|
+
end
|
58
|
+
@x = x; @y = y; @x2 = x+width; @y2 = y+height; @callback = callback
|
59
|
+
@max_x = max_x
|
60
|
+
raise "poor width or wrong window #{@x2} #{max_x} #{x}" if @x2 > max_x || @x2 == x
|
61
|
+
if @y2 > max_y || @y2 == y || @y2 <= 0
|
62
|
+
raise "poor height or wrong window selected #{@y2} > #{max_y} || #{@y2} == #{y} || #{@y2} <= 0"
|
63
|
+
end
|
64
|
+
if max_x == 0 || max_y == 0
|
65
|
+
# I don't think we can ever get here, because of the checks above
|
66
|
+
raise 'window invisible?'
|
67
|
+
end
|
68
|
+
@digits = digits
|
69
|
+
@previously_displayed_warning = false
|
70
|
+
@dump_digit_count = 1
|
71
|
+
pps 'using x',@x, 'from x', x, 'y', @y, 'from y', y,'x2',@x2,'y2',@y2,'digits', @digits.inspect if $VERBOSE
|
72
|
+
end
|
73
|
+
|
74
|
+
def get_hwnd_loop_forever
|
75
|
+
if @name_or_regex.to_s.downcase == 'desktop'
|
76
|
+
# full screen option
|
77
|
+
assert !@use_class_name # not an option
|
78
|
+
@hwnd = hwnd = Win32::Screenshot::BitmapMaker.desktop_window
|
79
|
+
return
|
80
|
+
else
|
81
|
+
raise if OS.mac?
|
82
|
+
@hwnd = Win32::Screenshot::BitmapMaker.hwnd(@name_or_regex, @use_class_name)
|
83
|
+
end
|
84
|
+
|
85
|
+
# display the 'found it message' only if it was previously lost...
|
86
|
+
unless @hwnd
|
87
|
+
until @hwnd
|
88
|
+
print 'unable to find the player window currently [%s] (maybe need to start program or move mouse over it)' % @name_or_regex.inspect
|
89
|
+
sleep 1
|
90
|
+
STDOUT.flush
|
91
|
+
|
92
|
+
hwnd = Win32::Screenshot::BitmapMaker.hwnd(@name_or_regex, @use_class_name)
|
93
|
+
width, height = Win32::Screenshot::Util.dimensions_for(hwnd)
|
94
|
+
p width, height
|
95
|
+
@hwnd = hwnd
|
96
|
+
end
|
97
|
+
puts 're-established contact with window'
|
98
|
+
end
|
99
|
+
true
|
100
|
+
end
|
101
|
+
|
102
|
+
# gets the snapshot of "all the digits together"
|
103
|
+
def get_bmp
|
104
|
+
# Note: we no longer bring the window to the front tho...which it needs to be in both XP and Vista to work...sigh.
|
105
|
+
Win32::Screenshot::BitmapMaker.capture_area(@hwnd,@x,@y,@x2,@y2) {|h,w,bmp| return bmp}
|
106
|
+
end
|
107
|
+
|
108
|
+
# gets snapshot of the full window
|
109
|
+
def get_full_bmp
|
110
|
+
Win32::Screenshot::BitmapMaker.capture_all(@hwnd) {|h,w,bmp| return bmp}
|
111
|
+
end
|
112
|
+
|
113
|
+
# writes out all screen tracking info to various files in the current pwd
|
114
|
+
def dump_bmps filename = 'dump.bmp'
|
115
|
+
File.binwrite filename, get_bmp
|
116
|
+
File.binwrite 'all.' + filename, get_full_bmp
|
117
|
+
dump_digits(get_digits_as_bitmaps, 'dump_bmp') if @digits
|
118
|
+
end
|
119
|
+
|
120
|
+
def dump_digits digits, message
|
121
|
+
p "#{message} dumping digits to dump no: #{@dump_digit_count} #{Time.now.to_f}"
|
122
|
+
for type, bitmap in digits
|
123
|
+
File.binwrite type.to_s + '.' + @dump_digit_count.to_s + '.bmp', bitmap
|
124
|
+
end
|
125
|
+
File.binwrite @dump_digit_count.to_s + '.mrsh', Marshal.dump(digits)
|
126
|
+
@dump_digit_count += 1
|
127
|
+
end
|
128
|
+
|
129
|
+
DIGIT_TYPES = [:hours, :minute_tens, :minute_ones, :second_tens, :second_ones]
|
130
|
+
|
131
|
+
# returns like {:hours => nil, :minutes_tens => raw_bmp, ...
|
132
|
+
def get_digits_as_bitmaps
|
133
|
+
# @digits are like {:hours => [100,5], :minute_tens => [x, width], :minute_ones, :second_tens, :second_ones}
|
134
|
+
out = {}
|
135
|
+
for type in DIGIT_TYPES
|
136
|
+
assert @digits.key?(type)
|
137
|
+
if @digits[type]
|
138
|
+
x,w = @digits[type]
|
139
|
+
if(x < 0)
|
140
|
+
x = @max_x + x
|
141
|
+
end
|
142
|
+
x2 = x + w
|
143
|
+
raise 'a digit width can never be negative #{w}' if w <= 0
|
144
|
+
y2 = @y2
|
145
|
+
width = x2 - x
|
146
|
+
height = y2 - @y
|
147
|
+
# lodo calculate these only once...
|
148
|
+
out[type] = Win32::Screenshot::BitmapMaker.capture_area(@hwnd, x, @y, x2, y2) {|h,w,bmp| bmp}
|
149
|
+
end
|
150
|
+
end
|
151
|
+
out
|
152
|
+
end
|
153
|
+
|
154
|
+
def get_relative_coords_of_timestamp_window
|
155
|
+
[@x,@y,@x2,@y2]
|
156
|
+
end
|
157
|
+
|
158
|
+
def get_coords_of_window_on_display # yea
|
159
|
+
out = FFI::MemoryPointer.new(:long, 4)
|
160
|
+
ScreenTracker.GetWindowRect @hwnd, out
|
161
|
+
out.read_array_of_long(4)
|
162
|
+
end
|
163
|
+
|
164
|
+
def identify_digit bitmap
|
165
|
+
OCR.identify_digit(bitmap, @digits)
|
166
|
+
end
|
167
|
+
|
168
|
+
# we have to wait until the next change, because when we start, it might be half-way through
|
169
|
+
# the current second...
|
170
|
+
def wait_till_next_change
|
171
|
+
original = get_bmp
|
172
|
+
time_since_last_screen_change = Time.now
|
173
|
+
loop {
|
174
|
+
# save away the current time to try and be most accurate...
|
175
|
+
time_before_current_scan = Time.now
|
176
|
+
current = get_bmp
|
177
|
+
if current != original
|
178
|
+
if @digits
|
179
|
+
got = attempt_to_get_time_from_screen time_before_current_scan
|
180
|
+
if @previously_displayed_warning && got
|
181
|
+
# reassure user :)
|
182
|
+
p 'tracking it successfully again'
|
183
|
+
@previously_displayed_warning = false
|
184
|
+
end
|
185
|
+
return got
|
186
|
+
else
|
187
|
+
puts 'screen time change only detected... [unexpected]' # unit tests do this still <sigh>
|
188
|
+
return
|
189
|
+
end
|
190
|
+
else
|
191
|
+
if(Time.now - time_since_last_screen_change > 2.0)
|
192
|
+
got_implies_able_to_still_ocr = attempt_to_get_time_from_screen time_before_current_scan
|
193
|
+
if got_implies_able_to_still_ocr
|
194
|
+
return got_implies_able_to_still_ocr
|
195
|
+
else
|
196
|
+
p 'warning--unable to track screen time for some reason [perhaps screen obscured or it\'s not playing yet?] ' + @hwnd.to_s
|
197
|
+
@previously_displayed_warning = true
|
198
|
+
# also reget window hwnd, just in case that's the problem...(can be with VLC moving from title to title)
|
199
|
+
get_hwnd_loop_forever
|
200
|
+
# LODO loop through all available player descriptions to find the right one, or a changed different new one, et al
|
201
|
+
end
|
202
|
+
time_since_last_screen_change = Time.now
|
203
|
+
end
|
204
|
+
end
|
205
|
+
sleep 0.02
|
206
|
+
}
|
207
|
+
end
|
208
|
+
|
209
|
+
def attempt_to_get_time_from_screen start_time
|
210
|
+
out = {}
|
211
|
+
# force it to have two matching snapshots in a row, to avoid race conditions grabbing the digits...
|
212
|
+
# allow youtube to update (sigh) lodo just for utube
|
213
|
+
previous = nil
|
214
|
+
sleep 0.05
|
215
|
+
current = get_digits_as_bitmaps
|
216
|
+
while previous != current
|
217
|
+
previous = current
|
218
|
+
sleep 0.05
|
219
|
+
current = get_digits_as_bitmaps
|
220
|
+
# lodo it should probably poll *before* calling this, not here...maybe?
|
221
|
+
end
|
222
|
+
assert previous == current
|
223
|
+
digits = current = previous
|
224
|
+
DIGIT_TYPES.each{|type|
|
225
|
+
if digits[type]
|
226
|
+
digit = identify_digit(digits[type])
|
227
|
+
unless digit
|
228
|
+
bitmap = digits[type]
|
229
|
+
# unable to identify a digit?
|
230
|
+
if $DEBUG || $VERBOSE && (type != :hours)
|
231
|
+
@a ||= 1
|
232
|
+
@a += 1
|
233
|
+
@already_wrote ||= {}
|
234
|
+
unless @already_wrote[bitmap]
|
235
|
+
p 'unable to identify capture!' + type.to_s + @a.to_s + ' dump:' + @dump_digit_count.to_s
|
236
|
+
File.binwrite("bad_digit#{@a}#{type}.bmp", bitmap)
|
237
|
+
@already_wrote[bitmap] = true
|
238
|
+
end
|
239
|
+
end
|
240
|
+
if type == :hours
|
241
|
+
digit = 0 # this one can fail and that's ok in VLC bottom right
|
242
|
+
else
|
243
|
+
# early (failure) return
|
244
|
+
return nil
|
245
|
+
end
|
246
|
+
else
|
247
|
+
p " got digit #{type} OCR as #{digit} which was captured to dump #{@dump_digit_count - 1} #{Time.now_f}" if $DEBUG
|
248
|
+
end
|
249
|
+
out[type] = digit
|
250
|
+
else
|
251
|
+
# there isn't one specified as being on screen, so assume it is always zero (like youtube hour)...
|
252
|
+
out[type] = 0
|
253
|
+
end
|
254
|
+
}
|
255
|
+
out = "%d:%d%d:%d%d" % DIGIT_TYPES.map{ |type| out[type] }
|
256
|
+
puts '', 'got new screen time ' + out + " (+ tracking delta:" + (Time.now - start_time).to_s + ")" if $VERBOSE
|
257
|
+
return out, Time.now-start_time
|
258
|
+
end
|
259
|
+
|
260
|
+
def process_forever_in_thread
|
261
|
+
Thread.new {
|
262
|
+
loop {
|
263
|
+
out_time, delta = wait_till_next_change
|
264
|
+
@callback.timestamp_changed out_time, delta
|
265
|
+
}
|
266
|
+
}
|
267
|
+
end
|
268
|
+
|
269
|
+
end
|
@@ -0,0 +1,294 @@
|
|
1
|
+
#
|
2
|
+
# warning: somewhat scary/explicit down there!
|
3
|
+
# see also todo.subtitle file, though what's here is mostly pretty well functional/complete
|
4
|
+
#
|
5
|
+
begin
|
6
|
+
require 'sane'
|
7
|
+
rescue LoadError
|
8
|
+
require 'rubygems'
|
9
|
+
require 'sane'
|
10
|
+
end
|
11
|
+
require_relative 'edl_parser'
|
12
|
+
require 'ostruct'
|
13
|
+
|
14
|
+
module SubtitleProfanityFinder
|
15
|
+
|
16
|
+
# splits into timestamps -> timestamps\ncontent blocks
|
17
|
+
def self.split_to_entries subtitles_raw_text
|
18
|
+
all = subtitles_raw_text.gsub("\r\n", "\n").scan(/^\d+\n\d\d:\d\d:\d\d.*?^$/m) # line endings so that it parses right when linux reads a windows file <huh?>
|
19
|
+
all.map!{|glop|
|
20
|
+
lines = glop.lines.to_a
|
21
|
+
index_line = lines[0]
|
22
|
+
timing_line = lines[1].strip
|
23
|
+
text = lines.to_a[2..-1].join("") # they still have separating "\n"'s
|
24
|
+
# create english-ified version
|
25
|
+
text.gsub!(/<(.|)(\/|)i>/i, '') # kill <i> type things
|
26
|
+
text.gsub!(/[^a-zA-Z0-9\-!,.\?'\n\(\)]/, ' ') # kill weird stuff like ellipseses, also quotes would hurt so kill them too
|
27
|
+
text.gsub!(/ +/, ' ') # remove duplicate " " 's now since we may have inserted many
|
28
|
+
# extract timing info
|
29
|
+
# "00:03:00.0" , "00:04:00.0", "violence", "of some sort",
|
30
|
+
timing_line =~ /((\d\d:\d\d:\d\d),(\d\d\d) --> (\d\d:\d\d:\d\d),(\d\d\d))/
|
31
|
+
ts_begin = "#{$2}.#{$3}"
|
32
|
+
ts_end = "#{$4}.#{$5}"
|
33
|
+
out = OpenStruct.new
|
34
|
+
out.index_number = index_line.strip.to_i
|
35
|
+
out.beginning_time = EdlParser.translate_string_to_seconds ts_begin
|
36
|
+
out.ending_time = EdlParser.translate_string_to_seconds ts_end
|
37
|
+
out.text = text.strip # harmless right?
|
38
|
+
add_single_line_minimized_text_from_multiline out
|
39
|
+
out
|
40
|
+
}
|
41
|
+
if all.size < 10
|
42
|
+
raise "unable to parse subtitle file?"
|
43
|
+
end
|
44
|
+
|
45
|
+
# strip out auto inserted trailers/headers
|
46
|
+
reg = / by|download| eng|www|http|sub/i
|
47
|
+
while all[0].text =~ reg
|
48
|
+
all.shift
|
49
|
+
end
|
50
|
+
while all[-1] =~ reg
|
51
|
+
all.pop
|
52
|
+
end
|
53
|
+
all
|
54
|
+
end
|
55
|
+
|
56
|
+
def self.add_single_line_minimized_text_from_multiline entry
|
57
|
+
entry.single_line_text = entry.text.strip.gsub(/^[- ,_\.]+/, '').gsub(/[- ,_]+$/, '').gsub(/[\r\n]/, ' ')
|
58
|
+
end
|
59
|
+
|
60
|
+
# convert string to regexp, also accomodating for "full word" type profanities
|
61
|
+
def self.convert_to_regexps profanity_hash
|
62
|
+
all_profanity_combinations = []
|
63
|
+
profanity_hash.to_a.sort.reverse.each{|profanity, sanitized|
|
64
|
+
as_regexp = Regexp.new(profanity, Regexp::IGNORECASE)
|
65
|
+
if sanitized.is_a? Array
|
66
|
+
# like 'bad word' => ['vain use', :partial_word, 'deity']
|
67
|
+
raise unless sanitized.length.in? [2, 3]
|
68
|
+
raise unless sanitized[1].in? [:full_word, :partial_word]
|
69
|
+
is_single_word_profanity = true if sanitized[1] == :full_word
|
70
|
+
if sanitized.length == 3
|
71
|
+
category = sanitized[2]
|
72
|
+
end
|
73
|
+
sanitized = sanitized[0]
|
74
|
+
end
|
75
|
+
|
76
|
+
permutations = [profanity]
|
77
|
+
if profanity =~ /l/
|
78
|
+
permutations << profanity.gsub(/l/i, 'i')
|
79
|
+
end
|
80
|
+
if profanity =~ /i/
|
81
|
+
permutations << profanity.gsub(/i/i, 'l')
|
82
|
+
end
|
83
|
+
|
84
|
+
replace_with = '[' + sanitized + ']'
|
85
|
+
category ||= sanitized
|
86
|
+
|
87
|
+
for permutation in permutations
|
88
|
+
if is_single_word_profanity
|
89
|
+
# \s is whitespace
|
90
|
+
as_regexp = Regexp.new("(?:\s|^|[^a-zA-Z])" + permutation + "(?:\s|$|[^a-zA-Z])", Regexp::IGNORECASE)
|
91
|
+
all_profanity_combinations << [as_regexp, category, ' ' + replace_with + ' '] # might introduce an extra space in there, but that's prolly ok since they're full-word already, and we collapse them
|
92
|
+
else
|
93
|
+
all_profanity_combinations << [as_regexp, category, replace_with]
|
94
|
+
end
|
95
|
+
end
|
96
|
+
}
|
97
|
+
all_profanity_combinations
|
98
|
+
end
|
99
|
+
|
100
|
+
def self.edl_output incoming_filename, extra_profanity_hash = {}, subtract_from_each_beginning_ts = 0, add_to_end_each_ts = 0, beginning_srt = 0.0, beginning_actual_movie = 0.0, ending_srt = 7200.0, ending_actual = 7200.0
|
101
|
+
edl_output_from_string(File.read(incoming_filename), extra_profanity_hash, subtract_from_each_beginning_ts, add_to_end_each_ts, beginning_srt, beginning_actual_movie, ending_srt, ending_actual)[0]
|
102
|
+
end
|
103
|
+
|
104
|
+
# **_time means "a float"
|
105
|
+
|
106
|
+
def self.edl_output_from_string subtitles, extra_profanity_hash, subtract_from_each_beginning_ts, add_to_end_each_ts, starting_time_given_srt, starting_time_actual, ending_srt_time, ending_actual_time, include_minor_profanities=true # lodo may not need include_minor_profs :P
|
107
|
+
raise if subtract_from_each_beginning_ts < 0 # these have to be positive...in my twisted paradigm
|
108
|
+
raise if add_to_end_each_ts < 0
|
109
|
+
|
110
|
+
# accomodate for both styles of rewrite, except it messes up the math...delete this soon...
|
111
|
+
# difference = starting_timestamp_given_srt - starting_timestamp_actual
|
112
|
+
# subtract_from_each_beginning_ts += difference
|
113
|
+
# add_to_end_each_ts -= difference
|
114
|
+
|
115
|
+
# you minus the initial srt time... (given)
|
116
|
+
# ratio = (end actual - init actual/ end given - init given)*(how far you are past the initial srt) plus initial actual
|
117
|
+
multiply_by_this_factor = (ending_actual_time - starting_time_actual)/(ending_srt_time - starting_time_given_srt)
|
118
|
+
|
119
|
+
multiply_proc = proc {|you|
|
120
|
+
((you - starting_time_given_srt) * multiply_by_this_factor) + starting_time_actual
|
121
|
+
}
|
122
|
+
|
123
|
+
|
124
|
+
|
125
|
+
|
126
|
+
|
127
|
+
|
128
|
+
|
129
|
+
|
130
|
+
|
131
|
+
|
132
|
+
|
133
|
+
|
134
|
+
|
135
|
+
|
136
|
+
|
137
|
+
|
138
|
+
|
139
|
+
|
140
|
+
|
141
|
+
|
142
|
+
|
143
|
+
|
144
|
+
|
145
|
+
|
146
|
+
|
147
|
+
|
148
|
+
|
149
|
+
|
150
|
+
|
151
|
+
bad_profanities = {'hell' => ['h...', :full_word],
|
152
|
+
'g' +
|
153
|
+
111.chr +
|
154
|
+
100.chr => ['vain use', :partial_word, 'deity'], 'g' +
|
155
|
+
111.chr +
|
156
|
+
100.chr +
|
157
|
+
's' => 'deitys',
|
158
|
+
'meu deus' => 'l...',
|
159
|
+
'lo' +
|
160
|
+
'rd' => 'l...', 'da' +
|
161
|
+
'mn' => 'd...',
|
162
|
+
'f' +
|
163
|
+
117.chr +
|
164
|
+
99.chr +
|
165
|
+
107.chr =>
|
166
|
+
'f...',
|
167
|
+
'allah' => 'all..',
|
168
|
+
'bi' +
|
169
|
+
'tc' + 104.chr => 'b....',
|
170
|
+
'bas' +
|
171
|
+
'ta' +
|
172
|
+
'r' + 100.chr => 'ba.....',
|
173
|
+
((arse = 'a' +
|
174
|
+
's'*2)) => ['a..', :full_word],
|
175
|
+
arse + 'h' +
|
176
|
+
'ole' => 'a..h...',
|
177
|
+
'dieu' => ['deity', :full_word],
|
178
|
+
arse + 'w' +
|
179
|
+
'ipe' => 'a..w...',
|
180
|
+
'jes' +
|
181
|
+
'u' + 's' => ['vain use', :partial_word, 'deity'],
|
182
|
+
'chri' +
|
183
|
+
'st'=> ['vain use', :full_word, 'deity'], # allow for christian[ity]
|
184
|
+
'sh' +
|
185
|
+
'i' + 't' => 'sh..',
|
186
|
+
'cu' +
|
187
|
+
'nt' => 'c...',
|
188
|
+
'cock' +
|
189
|
+
'su' +
|
190
|
+
'cker' => 'cock......',
|
191
|
+
}
|
192
|
+
|
193
|
+
|
194
|
+
semi_bad_profanities = {}
|
195
|
+
['moron', 'breast', 'idiot',
|
196
|
+
'sex', 'genital',
|
197
|
+
'boob',
|
198
|
+
'tits',
|
199
|
+
'make love', 'pen' +
|
200
|
+
'is',
|
201
|
+
'pu' +
|
202
|
+
'ssy',
|
203
|
+
'fart',
|
204
|
+
'whore',
|
205
|
+
'debauch',
|
206
|
+
'making' +
|
207
|
+
' love', 'love mak',
|
208
|
+
'dumb', 'suck', 'piss', 'c' +
|
209
|
+
'u' + 'nt',
|
210
|
+
'd' + 'ick', 'vag' +
|
211
|
+
'i' + 'na',
|
212
|
+
].each{|name|
|
213
|
+
semi_bad_profanities[name] = name
|
214
|
+
}
|
215
|
+
semi_bad_profanities['bloody'] = 'bloo..'
|
216
|
+
semi_bad_profanities['crap'] = ['crap', :full_word]
|
217
|
+
semi_bad_profanities['butt'] = ['butt', :full_word]
|
218
|
+
# butter?
|
219
|
+
|
220
|
+
semi_bad_profanities.merge! extra_profanity_hash
|
221
|
+
|
222
|
+
all_profanity_combinationss = [convert_to_regexps(bad_profanities)]
|
223
|
+
if include_minor_profanities
|
224
|
+
all_profanity_combinationss += [convert_to_regexps(semi_bad_profanities)]
|
225
|
+
end
|
226
|
+
|
227
|
+
output = ''
|
228
|
+
entries = split_to_entries(subtitles)
|
229
|
+
for all_profanity_combinations in all_profanity_combinationss
|
230
|
+
output += "\n"
|
231
|
+
for entry in entries
|
232
|
+
text = entry.text
|
233
|
+
ts_begin = entry.beginning_time
|
234
|
+
ts_begin -= subtract_from_each_beginning_ts
|
235
|
+
ts_begin = multiply_proc.call(ts_begin)
|
236
|
+
|
237
|
+
ts_end = entry.ending_time
|
238
|
+
ts_end += add_to_end_each_ts
|
239
|
+
ts_end = multiply_proc.call(ts_end)
|
240
|
+
found_category = nil
|
241
|
+
for (profanity, category, sanitized) in all_profanity_combinations
|
242
|
+
if text =~ profanity
|
243
|
+
found_category = category
|
244
|
+
break
|
245
|
+
end
|
246
|
+
end
|
247
|
+
|
248
|
+
if found_category
|
249
|
+
# sanitize/euphemize the subtitle text for all profanities...
|
250
|
+
for all_profanity_combinations2 in all_profanity_combinationss
|
251
|
+
for (profanity, category, sanitized) in all_profanity_combinations2
|
252
|
+
text.gsub!(profanity, sanitized)
|
253
|
+
end
|
254
|
+
end
|
255
|
+
|
256
|
+
# because we now have duplicate's for the letter l/i, refactor [[[word]]] to just [word]
|
257
|
+
text.gsub!(/\[+/, '[')
|
258
|
+
text.gsub!(/\]+/, ']')
|
259
|
+
entry.text = text
|
260
|
+
add_single_line_minimized_text_from_multiline entry
|
261
|
+
text = text.gsub(/[\r\n]|\n/, ' ') # flatten up to 3 lines of text to just 1
|
262
|
+
ts_begin_human = EdlParser.translate_time_to_human_readable ts_begin, true
|
263
|
+
ts_end_human = EdlParser.translate_time_to_human_readable ts_end, true
|
264
|
+
unless output.contain? ts_begin_human # some previous profanity already found this line :P
|
265
|
+
output += %! "#{ts_begin_human}" , "#{ts_end_human}", "profanity", "#{found_category}", "#{text}",\n!
|
266
|
+
end
|
267
|
+
end
|
268
|
+
end
|
269
|
+
end
|
270
|
+
# update timestamps to be synchro'ed
|
271
|
+
for entry in entries
|
272
|
+
entry.beginning_time = multiply_proc.call(entry.beginning_time)
|
273
|
+
entry.ending_time = multiply_proc.call(entry.ending_time)
|
274
|
+
end
|
275
|
+
[output, entries]
|
276
|
+
end
|
277
|
+
end
|
278
|
+
|
279
|
+
if $0 == __FILE__
|
280
|
+
if ARGV.empty?
|
281
|
+
p 'syntax: [filename.srt | [--create-edl|--create-edl-including-minor-profanities] input_name.srt output_name.edl]'
|
282
|
+
exit
|
283
|
+
elsif ARGV[0].in? ['--create-edl', '--create-edl-including-minor-profanities']
|
284
|
+
require_relative 'mplayer_edl'
|
285
|
+
incoming_filename = ARGV[1]
|
286
|
+
include_minors = true if ARGV[0] == '--create-edl-including-minor-profanities'
|
287
|
+
mutes = SubtitleProfanityFinder.edl_output_from_string File.read(incoming_filename), {}, 0, 0, "00:00", "00:00", "10:00:00", "10:00:00", include_minors
|
288
|
+
specs = EdlParser.parse_string %!"mutes" => [#{mutes}]!
|
289
|
+
File.write(ARGV[2], MplayerEdl.convert_to_edl(specs))
|
290
|
+
puts "wrote to #{ARGV[2]}"
|
291
|
+
else
|
292
|
+
print SubtitleProfanityFinder.edl_output ARGV.first
|
293
|
+
end
|
294
|
+
end
|